mysql database logic - mysql

My question is more of trying to understand what and how I can get something done. Here's the thing:
I got a job to build this application for a school to manage student bio data, work-out and handle student information and basic finance management.
Based on requirements I got from meets with my client, I have an ERD of a proposed MySQL Database with 23 different tables. The one part I would like to understand quickly is displaying data based on school terms. There are 3 terms in a year, each with its own summaries at the end of each term. At the end of 3 terms, a year has gone by and a student is promoted or demoted.
So my question is, how can I render my data to show 3 different terms and also to create a new year working out how to either promote a student or make the student repeat the class its in?

23 different tables? I'd like to see that model.
I don't think you should have one table per term. You'll have to keep adding tables every term, every year.
Sounds like a transcript table should have term and year columns that are incremented or decremented as a student progresses through. It should also have a foreign key relationship with its student: it's a 1:1 between a student and their transcript.
I would have a separate transcript table because I'd prefer keeping it separate from basic personal information about a student. A transcript would refer to the courses taken each term, the grade received for each, and calculate overall progress. If I queried for the transcript for an individual student, I should be able to see every year, every term, every course, every grade in reverse chronological order.

Related

How to SELECT next available award from available awards

I am in process of designing my database.
It's a simple online course, which users can earn points by achieving certain goals. For instance, if a user passes a quiz with score over 90, then 50 'iq' points are awarded to student.
My specific question here is, How would I find out the NEXT available award, and how many points are needed to obtain award.
So here is my idea of the tables (very truncated here for brevity of course):
Users table
id
name
points_balance
Awards table
This table holds all available awards.
id
award_name
points
award_sql
The award_sql column holds a sql statement to run to find out if the user is eligible for this award. For example, I could add a sql statement here to check to see if the user logged in three consecutive days. If true, user eligible for this award.
User_awards
Holds the awards a user already obtained
id
user_id
award_id
date_awarded
So the ideal query would do the following:
Check to see if the user qualifies for the award and doesn't already have it
Based on the list returned above, I need to know which which award is CLOSEST in points.
Schema Is Rough Draft
The table structure above is just my first draft.
I am new to writing SQL
If there is a better way to design my tables, I'd love to hear your suggestion.
Thank you for looking. I have looked into using the MIN function, but that's kinda above my skill set right now.
I would design my Awards tables as below:
Instead of the column "award_sql" in Awards table it would be better to have something like "award_status". This column will have a value "y" or "n" based on the user qualifying for the award.
In this design awards.award_status gets populated or loaded after login_history,quiz_results,referral_table and the remaining dependent tables are loaded. Use the award clause SQL to populate award_status column.

SQL attendance database design

I am currently designing a database in mariaDb that will be used in a Meteor app (woth sequelize orm) for tracking the attendance of students in a school.
I'm not sure is the most effective way as there are few exceptions on my case:
teachers can move and reorganise their schedule as they please, and also because the student pay for each lesson (and certain type of absence), I can't use a "exclusion way" (eg only record absence, so no record = present)
the most important query needed is attendance per student, and I need to have it every time I open my app for every student.
second most important is a monthly attendance per teacher. (This one is needed on demand)
(not db related) I need to track the students presence by groups of 10 (every lessons they have to pay again)
The estimated starting size is 20 teachers, 250 students, 500 attendance/week, (every student has two lessons) 37 weeks,( max size double students and lessons).
Is running 250 queries (find) on a 20000row table time consuming?
Is on student table having a lesson_counter field that is updated every time an attendance is recorded a good idea?
Many thanks!
UPDATE:
there is a possible optimization to be made? This should represent a base for a possible email and invoice system both towards students and teachers
There are many possible improvements to your design. Let me start by answering your specific questions:
Is running 250 queries (find) on a 20000row table time consuming?
No. On modern hardware, querying 20.000 rows is going to be fast. If you have a decent indexing strategy, the queries should return in 10s of milliseconds.
Is on student table having a lesson_counter field that is updated
every time an attendance is recorded a good idea?
No, it's a bad idea - on the assumption that you want a report for each student showing when they attended or missed a lesson, you have to store that data anyway. Keeping a counter is duplicating that information.
I suggest a design like the following.
An "attendance" and "absence" are logically separate things; you can model them in a single table with a flag. I've modeled them separately because I see them as different things in the business domain, with different attributes (absence has a reason code), and potentially different behaviour (for instance, an absence might have a workflow for sending an email). I prefer to have things that are logically separate in separate tables.
Student
-------
student_id
name
...
Lesson
------
lesson_id
subject
teacher_id (if only one teacher can teach a lesson)
....
enrollment
---------
lesson_id
student_id
start_datetime (or you might have the concept of "term")
end_datetime
lesson_session
-------
lesson_session_id
lesson_id
start_datetime
end_datetime
location
teacher_id (in case more than one teacher can teach a lesson)
attendance
--------
lesson_session_id
student_id
absence
------------
lesson_session_id
student_id
reason (or might be a foreign key to reasons table)

What's a good DB design schema for advanced attendance?

First off, I did read this post What is a good database design (schema) for a attendance database? but it doesn't fit my needs and I'm struggling to adapt it to my scenario.
I will try to explain in brief.
Let's take a school (sort of):
School has courses with a starting and an ending date
Students can be "subscribed" to multiple courses
A subscription doesn't necessary start from the beginning nor ending at the end of the course.
The student can be attended punctually (independently of the subscription) or transferred punctually in an another course.
I came with this design in mind:
My idea:
When transferring punctually a student, I can change the course_id
I can create an attendee without subscription_id, on demand
My problem:
With this design, It's seems over complicated and to see who's coming to a course, I see only two solutions.
Count the number of subscription, add the number of attendees present, remove the number of attendees absent.
Use a queue worker to create all the attendees and count the number of present attendee.
What would it be the easier way or what better schema could I use?

Redundancy vs. Flexibility

I am new to MySQL database and I'm collaborating with my former CSCI teacher to make a student database that holds his student grades history. My original idea was to have a Students table (studentID, firstname, lastname, middlename, gender), a Course table (courseID, course_description), a Grades table (studentID, courseID, year, final_grade), and then tables for AssignmentScores, TestScores, QuizScores, and ExerciseScores. Each of these tables would of course have a studentID, courseID, year, and section (code used by the school to define the semester and period) field, along with the scores earned by the students.
The problem with this approach is that in a perfect world, all courses would have the same number of assignments, exercises, tests, and quizes, and they all would have the same point value, however, as we all know, this is not a perfect world. For instance, there are a couple of courses that have assignments labeled 1a, and 1b both worth five points each as opposed to the normal 10 points each for 10 assignments (labeled 1 through 10). This is also the first year he started keeping track of exercises, and all classes do not have the same number of exercises, nor are they always worth the same point value.
In order to allow for flexibility, we decided to make a table containing general course information with a courseID, year, section, type (to designate quiz, assignment, test, or exercise), number (1a, 1b, or 1,2,3 etc...), and a maxpoints field (to hold the max point value per item). We would then also have a table for individual scores which would have basically the same fields but instead of max points there would an earnedpoints field (to hold the students scores on a particular item). He would then of course have to enter every courses details, every year, regardless of if it was different then the previous year's.
For the two courses he is currently teaching, that amounts to 90 rows per table with much of the data seemingly redundant.
Doing it this way seems to have a lot of redundant information, but I don't see any other way that allows for past, present, or future flexibility. One of the reasons I am doing this project is in hopes of using it to show prospective employers and I thought the point of a relational database was to minimize redundant information, and I don't want prospective employers to look at this and say, "what an idiot."
So my question to the stackoverflow community is, "is there a better way to do this?"

Creating a database system for a high school containing students records

I am building a student database for a high school. I have been able to solve most of my problems with the exception of one.
The tables I currently have are for records of the current school term. I am trying to find a way to permanently keep records for the first term, second term, third term and even after the student graduates. Student information will still be stored in the database permanently.
Please can anyone give me an idea of how I should build it?
Add a field "Term", where you write the term, which this record is for.
I think the most logical way is to have Year (calendar year) and Term (semester term: Spring, Summer, Fall) fields associated to each student. This way you could fully distinguish attendance by either calendar year or term. For graduation status you could add either graduation flag or graduation date, or both.
ADDED:
In response to comment below. Yes, I think it does make more sense to track prospective students and enrolled academic students separately. You either can track those in a stand along table or implement additional fields to the existing table. As an example, you could have a field person_status as enrolled, graduated, prospective.
Your ultimate structure really depends on what level of detail you try to achieve.