Database design for weekly time tracking - ms-access

I am planning on creating a database to track user's time in/time out M-F. Every week should begin on monday and run through sunday.
I have a table filled with my entire user population, so I know which users I need to create entries for and where they belong to. I have proposed so far, a table consisting of the following fields to track the entries (along with example data to fill the fields):
Field Name in table (Example of possible data)
---------------------
Employee (John Smith) 'String
Unit (Quality Assurance) 'String
WeekOf (9/9/13) 'date
InMonday (6:30) 'string, validate either a time in/out or N/A if holiday/vacation
OutMonday (3:15) '^^
HoursWorkedMonday (8.00) 'total hours worked
VacationMonday (0.00) 'if N/A for time, should have hours here
OvertimeMonday (0.00) 'any additional work hours should go here
For this instance, I would have to create In/Out for each day of the week (and perhaps track the date that each day is for). Is this extraneous or is there a seemingly better organization to tracking weekly time measurements? Should I use one table with a unit indicator or multiple tables for each unit?

Usually it's one table with a Date field, an In field and an Out field. That's pretty much standard timesheet data. Take a look at how this guy has it set up.
Make sure you're using an Employee ID in the timesheet, and then you would have a corresponding Employee table with all relevant info (ID, Name, Address, whatever else you store on him/her).

While this project is technically feasible, I have to question the value of making it yourself in Access.
The main issue is with security:
As a desktop program, this can be very easy to hack without precautions. Keep in mind that with Access, the user interface and the designer interface are by default the same thing.
If this is going to be a simple, straightforward db, a motivated user just needs to open the navigation panel and they can add/edit/delete all the timesheets.
If you hide the navigation panel, the user can just do a quick google search and learn to hit F11 (or find it by accident, either way)
You can try regularly (daily? hourly?) transferring the data from the publicly accessible back-end to an archive db that is not accessible to the general users. This can work, but still gives them a window to edit records. And if you don't do the transfer right, they can still add old records.
As a webform on a SharePoint, this can be fairly secure. I'd recommend this if you have Sharepoint.
You should also consider your development time. This is a very common business task across many industries, from restaurants to factories to schools. As such, there's a huge number of cheap web-based options already out there that you can start using today. I'll even assume some of these include summary reviews breaking out numbers by departments as well.
I've never researched these myself, but a quick google search found this interesting page: http://en.wikipedia.org/wiki/Comparison_of_time_tracking_software

Related

Create multiple records from one form (MS Access 2010)

I'm creating a database that will be used to keep track of maintenance performed on equipment in a nursing home. I'm using MS Access 2010, and I'd say my skills are somewhere between novice and intermediate, almost entirely self-taught for this project.
The database structure is as follows:
tblAssetTypes:
TypeID (PK),
MaintenanceSchedule,
EquipmentType,
EquipmentSubgroup,
MaintenanceTime,
TasksRequired
tblUniqueAssets:
UniqueID (PK),
StorageLocation,
TypeID (FK)
tblPrevMaintRecord:
ID (PK),
UniqueID (FK),
DatePerformed,
TimePerformed,
MaintenanceComments
I currently have a form that can be used to record when preventative maintenance is performed on an individual asset. The user enters the UniqueID for that asset, and details about the maintenance (date, time, comments), and then this information is saved to tblPrevMaintRecord. That works fine, but when I presented it to my supervisor he pointed out that in many instances, maintenance people would gather all equipment of a certain type and complete the preventative maintenance in one batch. Needing to enter that data in multiple times would be very tedious and so he asked if it would be possible to record the maintenance performed on multiple items at once. I've spent all day trying to research how to do this but can't seem to find anything that explains how this would be possible.
For each kind of asset, there is one TypeID. However, some values for EquipmentType, such as "Trolley" have subgroups recorded in EquipmentSubgroup (in the example of trolleys, "Medication", "Laundry", "Dressing", "Food", etc.). If there is no subgroup for an EquipmentType, such as "Bed", the EquipmentSubgroup is recorded as a dash "-".
I think ideally, the user should be able to selected any EquipmentType or EquipmentSubgroup category, be shown a list of assets in those categories and the corresponding UniqueIDs, and then select the UniqueIDs that they wish to act on. Then they complete the details of the maintenance (date, time, comments) and records are added for each UniqueID reflecting the maintenance performed on each item. I worry this might be too complicated, and I'm open to compromise solutions.
This is my first time posting here after being a long-term reader, so I hope I've given all the information and detail required for people to be able to help! This database has not been rolled out yet either, so if anyone has other suggestions that they think might be helpful I'm happy to hear them!

Database model for a 24/7 Staff roster at a casino

We presently use a pen/paper based roster to manage table games staff at the casino. Each row is an employee, each column is a 20 minute block of time and each cell represents what table the employee is assigned to, or alternatively they've been assigned to a break. The start and end time of shifts for employees vary as do the games/skills they can deal. We need to keep a copy of the rosters for 7 years, with paper this is fairly easy, I'm wanting to develop a digital application and am having difficulty how to store the data in a database for archiving.
I'm fairly new to working with databases, I think I understand how to model the data for a graph database like neo4j, but I had difficulty when it came to working with time. I've tried to learn about RDBMS databases like MySQL, below is how I think the data should be modelled. Please point out if I'm going in the wrong direction or if a different database type would be more appropriate, it would be greatly appreciated!
Basic Data
Here is some basic data to work with before we factor in scheduling/time.
Employee
- ID Number
- Name
- Skills (Blackjack, Baccarat, Roulette, etc)
Table
- ID Number
- Skill/Type (Can only be one skill)
It may be better to store the roster data as a file like JSON instead? Time sensitive data wouldn't be so much of a problem then. The benefit of going digital with a database would be queries, these could help assist time consuming tasks where human error is common.
Possible Queries
Note: Staff that are on shift are either on a break or on the floor (assigned to a table), Skills have a major or minor type based on difficulty to learn.
What staff have been on the floor for 80 minutes or more? (They are due for a break)
What open tables can I assign this employee to based on their skillset?
I need an employee that has Baccarat skill but is not already been assigned to a Baccarat table.
What employee(s) was on this table during this period of time?
Where was this employee at this point in time?
Who is on shift right now?
How many staff on shift can deal Blackjack?
How many staff have 3 major skills?
What staff have had the Baccarat skill for at least 3 months?
These queries could also be sorted by alphabetical order or time, skill etc.
I'm pretty sure I know how to perform these queries with cypher for neo4j provided I model the data right. I'm not as knowledgeable with SQL queries, I've read it can get a bit complicated depending on the query and structure.
----------------------------------------------------------------------------------------
MYSQL Specific
An employee table could contain properties such as their ID number and Name, but am I right that for their skills and shifts these would be separate tables that reference the employee by a unique integer(I think this is called a foreign key?).
Another table could store the gaming Tables, these would have their own ID and reference a skill/gametype with a foreign key.
To record data like the pen/paper roster, each day could have a table with columns starting from 0000 increasing by 20 in value going all the way to 2340? Prior to the time columns I could have one for staff where each employee is represented with their foreign key, the time columns would then have foreign keys to the assigned gaming Tables, the row data is bound to have many cells that aren't populated since the employee shift won't be 24/7. If I'm using foreign keys to reference gaming Tables I now have a problem when the employee is on break? Unless I treat say the first gaming Table entry as a break?
I may need to further complicate things though, management will over time try different gaming Table layouts, some of the gaming Tables can be converted from say Blackjack to Baccarat. this is bound to happen quite a bit over 7 years, would I want to be creating new gaming Table entries or add a column to use a foreign key and refer to a new table that stores the history of game types during periods of time? Employees will also learn to deal new games during their career, very rarely they may also have the skill removed.
----------------------------------------------------------------------------------------
Neo4j Specific
With this data would I have an Employee and a Table node that have "isA" relationship edges mapping to actual employees or tables?
I imagine with the skills for the two types I would be best with a Skill node and establish relationships like so?: Blackjack->isA->Skill, Employee->hasSkill->Blackjack, Table->typeIs->Blackjack?
TIME
I find difficulty when I want this database to now work with a timeline. I've come across the following suggestions for connecting nodes with time:
Unix Epoch seems to be a common recommendation?
Connecting nodes to a year/month/day graph?
Lucene timeline? (I don't know much about this or how to work with it, have seen some mention it)
And some cases with how time and data relate:
Staff have varied days and start/end times from week to week, this could be shift node with properties {shiftStart,shiftEnd,actualStart,actualEnd}, staff may arrive late or get sick during shift. Would this be the right way to link each shift to an employee? Employee(node)->Shifts(groupNode)->Shift(node)
Tables and Staff may have skill data modified, with archived data this could be an issue, I think the solution is to have time property on the relationship to the skill?
We open and close tables throughout the day, each table has open/close times for each day, this could change in a month depending on what management wants, in addition the times are not strict, for various reasons a manager may open or close tables during the shift. The open/closed status of a table node may only be relevant for queries during the shift, which confuses me as I'd want this for queries but for archiving with time it might not make sense?
It's with queries that I have trouble deciding when to use a node or add a property to a node. For an Employee they have a name and ID number, if I wanted to find an employee by their ID number would it be better to have that as a node of it's own? It would be more direct right, instead of going through all employees for that unique ID number.
I've also come across labels just recently, I can understand that those would be useful for typing employee and table nodes rather than grouping them under a node. With the shifts for an employee I think should continue to be grouped with a shifts node, If I were to do cypher queries for employees working shifts through a time period a label might be appropriate, however should it be applied to individual shift nodes or the shifts group node that links back to the employee? I might need to add a property to individual shift nodes or the relationship to the shifts group node? I'm not sure if there should be a shifts group node, I'm assuming that reducing the edges connecting to the employee node would be optimal for queries.
----------------------------------------------------------------------------------------
If there are any great resources I can learn about database development that'd be great, there is so much information and options out there it's difficult to know what to begin with. Thanks for your time :)
Thanks for spending the time to put a quality question together. Your requirements are great and your specifications of your system are very detailed. I was able to translate your specs into a graph data model for Neo4j. See below.
Above you'll see a fairly explanatory graph data model. In case you are unfamiliar with this, I suggest reading Graph Databases: http://graphdatabases.com/ -- This website you can get a free digital PDF copy of the book but in case you want to buy a hard copy you can find it on Amazon.
Let's break down the graph model in the image. At the top you'll see a time indexing structure that is (Year)->(Month)->(Day)->(Hour), which I have abbreviated as Y M D H. The ellipses indicate that the graph is continuing, but for the sake of space on the screen I've only showed a sub-graph.
This time index gives you a way to generate time series or ask certain questions on your data model that are time specific. Very useful.
The bottom portion of the image contains your enterprise data model for your casino. The nodes represent your business objects:
Game
Table
Employee
Skill
What's great about graph databases is that you can look at this image and semantically understand the language of your question by jumping from one node to another by their relationships.
Here is a Cypher query you can use to ask your questions about the data model. You can just tweak it slightly to match your questions.
MATCH (employee:Employee)-[:HAS_SKILL]->(skill:Skill),
(employee)<-[:DEALS]-(game:Game)-[:LOCATION]->(table:Table),
(game)-[:BEGINS]->(hour:H)<-[*]-(day:D)<-[*]-(month:M)<-[*]-(year:Y)
WHERE skill.type = "Blackjack" AND
day.day = 17 AND
month.month = 1 AND
year.year = 2014
RETURN employee, skill, game, table
The above query finds the sub-graph for all employees who have the skill Blackjack and their table and location on a specific date (1/17/14).
To do this in SQL would be very difficult. The next thing you need to think about is importing your data into a Neo4j database. If you're curious on how to do that please look at other questions here on SO and if you need more help, feel free to post another question or reach out to me on Twitter #kennybastani.
Cheers,
Kenny

alternative solution to asking user to create a new table

I use access to store concert registration information at the non-profit I currently work at. I have it set up so that I dump all of the patron contact information into one table, and all of the concert registration information into another. when we change our concert season, I simply copy/paste the "2012-13 concert registration table" and rename it the "2013-14" concert registration table".
the concert registration table serves as my "hub" for all my other information. I have about a half-dozen summary queries that show information for specific concerts, who I still need to collect payment for etc. as well as many Word mail merges associated with each document. This setup works great, except that every season I need to go in and re-link all of the queries and word docs to the new registration table
I will be leaving my job at the end of next month, and I would like to make the database more user-friendly, especially since I am fairly certain that my replacement will have zero familiarity with access. my questions are:
1) Is there a more elegant, easy way to transition from season to season other than to create a new registration table and subsequent queries from year-to-year?
2) How can I idiot-proof this database for the new person when I'm gone? I'm scared that if I create an extensive "how-to" guide, it simply won't be read and the person will be forced to reinvent the wheel. I'm toying with creating a switchboard, but I'm scared that this will make the database seem more unapproachable.
Thank you for your insight, happy to clarify if there are any questions!
Just make 1 table. Call it "registration table" and add a new field called Season. Your queries will be include a filter for that field. Then you won't need to relink your queries, copy tables, etc.
For an example, say you have a query to pull all the information from that table for a particular season. It might look something like:
Select * from RegistrationTable where Season=[What Season];
When run, the query will prompt the user for the season and pull only that data.
Also, I do recommend the "how-to" guide. There's probably a lot of manual manipulation of the database that you do and don't even think about. And if nothing else, you can always say you gave them documentation and thus provided for your successor.

MS Access tracking effective dates of employees

I currently have an MS Access application that stores information about the employees who have responsibility for a certain task.
My form goes like this. You enter the task in a textbox. You pick the employee from a combo box which is bound to the staff table. And finally we save this information to the Task table. As simple as that I thought...
But here is the problem. No employee works forever in a company. A new/another employee maybe assigned the task which was previously carried out by an employee who is no longer working there. In the form once I update the new employee the old employee information is replaced and we wouldn't even know that that employee existed.
I came across the concept of adding effective dates to the employee which may be used to track the history of employees.
Now I would like to know how I would be able to preserve the data of the previous employee when I update the Task form with the information of the new employee.
What should I do?
Thank you for your assistance.
BR,
Paul
I have uploaded links to three forms that I am working on.
In the outside company officer form we don't have the date fields mentioned.
In our companies proposal form we might need to add additional officers but don't want to repeat the proposal information just the officer, division, alternate officer & division.
In the outside company detail form we might need to apply the same concept to the director of the company without applying to other institute information.
I was also researching on this topic where I found a document which explains the concept of effective dates. I need to know how to apply this and also without making a lot of changes to the application.
www.gsa.gov/graphics/staffoffices/DatedInformationandDateTracking.pdf
I hope this helps you understand my problem.
It would seem you are keeping very simple information, you want to know who is currently assigned to any given task. Add a "assignedDate" field to your table. Then you can change any reports or forms where you need to display the current assignee to a query whereby you group by "task" and select only the latest record.
Do not include the assignee as a field in the task table. You would need an additional table, say "TaskAssignees" comprised of TaskID, ContactID, entry date, assigned date, unassigned date. Now in reporting you can pull the correct assignee given any date or list a history of the assignees from start to finish.
I would say that you are making the issue too complicated.
Surely there's an administrative policy on what happens to tasks when an employee leaves -- their replacement takes them over or they are assigned to the departing employee's supervisor or a co-worker.
Thus, your application should encode that business practice. The form where you edit the employees should be set up so that when an employee leaves, their tasks are moved to the appropriate employee. This means you don't have to store effective dates and then write the complex SQL to filter by those dates. Instead, you'll use the same structure as you already have.
Now, of course, I'm not stupid -- I know that many companies SHOULD have such policies, but very often, these things fall through the cracks. When I'm in this position (as an outside contractor) I tell them their two options and price the two options. Implementing a policy for what happens with the assigned tasks when the employee leaves is cheap. Implementing an effective date is EXPENSIVE. So, if they want to save money, they'll come up with a policy that can be implemented in the database application.
If the solutions already suggested don't work for you then you could look at creating an audit table which effectively logs every change that is made to a record (This would have the advantage of allowing you to track ALL changes, even in areas of your system you have not yet developed).
Here are a couple of links that show how you could go about doing this:
a simple solution for tracking changes to access data
Allen Browne - creating an audit log.

Mysql database design

currently Im working on a project that, at first glance, will require many tables in a database. Most of the tables are fairly straightforward however I do have an issue. One of the tables will be a list of members for the website, things like username, password, contact info, bio, education, etc will be included. This is a simple design, however, there is also a need for each member to have their availability entered and store in the database as well. Availability is defined as a date and time range. Like available on 4/5/2011 from 1pm to 6pm EST, or NOT available every friday after 8pm EST. For a single user, this could be a table on its own, but for many users, Im not sure how to go about organizing the data in a manageable fashion. First thought would be to have code to create a table for each user, but that could mean alot of tables in the database in addition to the few I have for other site functions. Logically i could use the username appended to Avail_ or something for the table name ie: Avail_UserBob and then query that as needed. But im curious if anyone can think of a better option than having the potential of hundreds of tables in a single database.
edit
So general agreement would be to have a table for members, unique key being ID for instance. Then have a second table for availability (date, start time, end time, boolean for available or not, and id of member this applies to). Django might sound nice and work well, but i dont have the time to spend learning another framework while working on this project. The 2 table method seems plausable but Im worried about the extra coding required for features that will utilize the availability times to A) build a calender like page to add, edit, or remove entered values, and B) match availabilities with entries from another table that lists games. While I might have more coding, I can live with that as long as the database is sound, functional, and not so messy. Thanks for the input guys.
Not to sound like a troll, but you should take a look into using a web framework to build most of this for you. I'd suggest taking a look at Django. With it you can define the type of fields you wish to store (and how they relate) and Django builds all the SQL statements to make it so. You get a nice admin interface for free so staff can login and add/edit/etc.
You also don't have to worry about building the login/auth/change password, etc. forms. all that session stuff is taken care of by Django. You get to focus on what makes your project/app unique.
And it allow you to build your project really, really fast.
djangoproject.org
I don't have any other framework suggestions that meet your needs. I do... but I think Django will fit the bill.
Create a table to store users. Use its primary key as foreign key in other tables.
The databases are written to hold many many rows in a table. There are not optimized for table creation. So it is not a good idea to create a new table for each user. Instead give each user an unique identifier and put the availability in a separate table. Provide an additional flag to make an entry valid or invalid.
Create a table of users; then create a table of availabilities per user. Don't try to cram availabilities into the user table: that will guarantee giant grief for you later on; and you'll find you have to create an availabilities table then.
Google database normalization to get an idea why.
Take it as truth from one who has suffered such self-inflicted grief :-)