MySQL tables pattern for event calendar - mysql

I've been developing a PHP app recently that is aimed at helping Doctors & patients getting in touch and also uses FullCalendar for the doctor So he can manage his events.
My problem is: as I learned coding by myself, I have not learned how to decide whether to use this or that DB organisation.
Currently, the app creates a new table for each new subscription (Doctors only) that is named event_[$doctor_id] but I have to admit I'm scared by the perspective of having 3000 users!
My needs are:
keep a ref for each event during 2 years after its date (but not necessarily in the same dB table)
events younger than 6 months need to be visible in the calendar
to avoid errors, events are never (almost) deleted from the db - they are just disabled in order to allow the user to repair a 2 weeks old mistake
I Was considering using date named tables like "201303" for all the events taking place in March 2013, and then use a bot every month that will somehow save the oldest information (6 months + old) in a specific table or even in a file.
But as the changes might take me a few hours, I'd appreciate some advice from you people!

Related

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

Database design for weekly time tracking

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

Better to add separate tables for multiple users?

I am relatively new to database design so I am still learning a lot. What I am working on is an online time card clock. I am just messing around with it to learn more. My full time job is working for my uncle operating heavy equipment and he has expressed some headaches to me. When going over time cards several employees hand writing is hard to read, several employees don't add the hours correctly so he always has to double check their math, plus some people don't hand in the time sheets on time. Most of the employees have smart phones so my solution is to just make a simple website that has a button for "Clocking in" and "Clocking out" it would also contain several text fields to describe what the employee operated that day and the job site they were on. All of this will be added to a database that will be emailed to the boss at the end of the work week. My question is what would be the best way to setup a database for this? Should I add a separate table for each employee or keep it all in one table? There will be about 20 employees that will use the site. Thanks in advance for any help.
General database principles:
Think about object orientation. Classes of objects.
An "Employee" is one such class, therefore you should have one table that stores employees.
An "Event" such as clocking in or clocking out is a general class of two specific cases, e.g. ClockIn and ClockOut.
You could consider one table to store an Event with a field for the date and time of the event, one field for the employee (a foreign key), one field indicating whether it's in or out
You could alternatively consider one table for ClockIn, one for ClockOut, but this may not be advantageous depending on how you wish to scan the data later when printing reports. I'd personally recommend against this approach, just point out that it's an option.
Ideally, every table should have a numeric primary key
Think of key-value pairs
Employee
1 Jon Doe
2 Juan Gomez
etc...
Event
1 2012-11-29 08:59 Clock In 2
This translates to Juan Gomez clocking in today just before 9am

How to lock a database after a particular time from accepting an entry?

Okay..
I am making a web base application,that will be connected to a sms gateway.
It is basically an attendance app for colleges.
The Attendance will be updated using a sms by the teacher.
Now,the main part-
What I want to do is,the teacher should not be able to correct the attendance after 10minutes of sending the 1st message.i.e,the database should accept a correction or new message for the same class and the same teacher only for 10 minutes after the 1st attendance is recieved in the database.
So only recieving from a particular number should be blocked and also only if it is for the same class...
I hope the question is clear :o
Thankyou
This is not the sort of thing that you should be enforcing at the DB level, it belongs in your application code. If you can't connect time, number & class together in your DB, it's time to change your schema.
As Sean McSomething mentioned, this is not done at database level, this is business logic that should be checked just before interacting with a database. The best practice actually is to simply add a column time_created and before updating simply check if NOW() and time_created interval is less than 10 minutes. It's a pretty trivial job, but don't bother trying to do this in database with some stored procedures or other stuff, as it will make your application almost un-debuggable and very sloppy.
Check if there is a row with active number and active class, if there are no - insert, if there are any - check if this row's time_created is greater than 10 minutes ago, if it's not - update, ignore otherwise.

Creating a students' record database for a school

I'm trying to create a student database for a school. I have everything I need except for one thing...
-- When a school year and semester ends. Since the tables I currently have are for records of the current school year, I'm trying to find a way to permanently keep those records so that even after the student graduates, his/her information will still be stored in the DB.
Can anyone give me an idea of how I should build it? I just need to be able to visualize the structure of the database.
If the data have to be in your OLTP-system, add an extra field in your table, indicating the school year:
REF_SCHOOL_YEAR
Create a new table with all the school years:
ID_SCHOOL_YEAR
STARTING_YEAR
ENDING_YEAR
Now your application can easily get the current year (where NOW() between STARTING_YEAR AND ENDING_YEAR) and query the table using that ID_SCHOOL_YEAR.
If the data don't need to be accessible via your application, just stored "for recordkeeping purposes", OLAP (a datawarehouse) might be a better solution.
One tool that has helped me is for mysql but will help you visualize. It's called Mysql workbench. Also, try to learn about e-r diagrams and how to think-relational.
As for the specifics, I think Konerak is rigt.