add student dataclass
This commit is contained in:
6 files changed
+124
-98
No files matched your search
+56
-55
@@ -5,6 +5,7 @@ from string import hexdigits
|
||||
|
||||
from app.util.globals import flex, Error
|
||||
from app.util.estimateGrade import getGrade
|
||||
from app.util.students import Student, studentsToDict
|
||||
|
||||
# Takes in information to create or add a new conflict
|
||||
# Returns if the particular student has a previous error
|
||||
@@ -44,12 +45,12 @@ def insertConflictSolutions(
|
||||
# Then it starts to attempt to fit all classes into a timetable, making corretions along
|
||||
# the way. Corrections being moving a students class
|
||||
def generateScheduleV3(
|
||||
students: list, # Refer to /util/students.py to see the students list structure
|
||||
courses: dict, # Refer to /util/courses.py to see the courses dictionary structure
|
||||
minReq: int = 18, # minimum requests for a class to run
|
||||
classCap: int = 30, # maximum students per class
|
||||
blockClassLimit: int = 40, # Block class limit is the number of classrooms available per block. Default 40 classes per block
|
||||
totalBlocks: int = 10, # total blocks between two semesters -> default is 10 for 5 per semester... or this can be 8 for 4 blocks per semester
|
||||
students: list[Student], # Refer to /util/students.py to see the students list structure
|
||||
courses: dict, # Refer to /util/courses.py to see the courses dictionary structure
|
||||
minReq: int = 18, # minimum requests for a class to run
|
||||
classCap: int = 30, # maximum students per class
|
||||
blockClassLimit: int = 40, # Block class limit is the number of classrooms available per block. Default 40 classes per block
|
||||
totalBlocks: int = 10, # total blocks between two semesters -> default is 10 for 5 per semester... or this can be 8 for 4 blocks per semester
|
||||
studentsDir: str = "../output/raw/students.json",
|
||||
conflictsDir: str = "../output/raw/conflicts.json",
|
||||
coursesDir: str = "../output/raw/courses.json"
|
||||
@@ -77,8 +78,8 @@ def generateScheduleV3(
|
||||
activeCourses = {}
|
||||
for student in students:
|
||||
# Tally class request
|
||||
for request in (request for request in student["requests"] if not request["alt"] and request["CrsNo"] not in flex):
|
||||
code = request["CrsNo"]
|
||||
for request in (request for request in student.Requests if not request.Alt and request.CrsNo not in flex):
|
||||
code = request.CrsNo
|
||||
courses[code]["Requests"] += 1
|
||||
# Add course to active list if enough requests
|
||||
if courses[code]["Requests"] > minReq and courses[code]["CrsNo"] not in activeCourses:
|
||||
@@ -183,9 +184,9 @@ def generateScheduleV3(
|
||||
# bias to students at the top of the list
|
||||
student = tempStudents[random.randint(0, len(tempStudents)-1)]
|
||||
|
||||
alternates = [request for request in student["requests"] if request["alt"]]
|
||||
for request in (request for request in student["requests"] if not request["alt"] and request["CrsNo"] not in flex):
|
||||
course = request["CrsNo"]
|
||||
alternates = [request for request in student.Requests if request.Alt]
|
||||
for request in (request for request in student.Requests if not request.Alt and request.CrsNo not in flex):
|
||||
course = request.CrsNo
|
||||
getAvailableCourse = True
|
||||
isAlt = False
|
||||
while getAvailableCourse:
|
||||
@@ -198,8 +199,8 @@ def generateScheduleV3(
|
||||
if len(selectedCourses[cname]["students"]) < emptyClasses[course][cname]["expectedLen"]:
|
||||
# Class exists with room for student
|
||||
selectedCourses[cname]["students"].append({
|
||||
"Pupil #": student["Pupil #"],
|
||||
"index": student["studentIndex"]
|
||||
"Pupil #": student.PupilNum,
|
||||
"index": student.StudentIndex
|
||||
})
|
||||
getAvailableCourse = False
|
||||
break
|
||||
@@ -208,7 +209,7 @@ def generateScheduleV3(
|
||||
if cname[len(cname)-1] == f"{len(emptyClasses[course])-1}":
|
||||
if len(alternates) > 0:
|
||||
# Use alternate
|
||||
course = alternates[0]["CrsNo"]
|
||||
course = alternates[0].CrsNo
|
||||
alternates.remove(alternates[0])
|
||||
isAlt = True
|
||||
break
|
||||
@@ -220,8 +221,8 @@ def generateScheduleV3(
|
||||
elif cname not in selectedCourses:
|
||||
selectedCourses[cname] = {
|
||||
"students": [{
|
||||
"Pupil #": student["Pupil #"],
|
||||
"index": student["studentIndex"]
|
||||
"Pupil #": student.PupilNum,
|
||||
"index": student.StudentIndex
|
||||
}],
|
||||
"CrsNo": course,
|
||||
"Description": courses[course]["Description"]
|
||||
@@ -232,7 +233,7 @@ def generateScheduleV3(
|
||||
elif course not in emptyClasses:
|
||||
if len(alternates) > 0:
|
||||
# Use alternate
|
||||
course = alternates[0]["CrsNo"]
|
||||
course = alternates[0].CrsNo
|
||||
alternates.remove(alternates[0])
|
||||
isAlt = True
|
||||
else:
|
||||
@@ -240,7 +241,7 @@ def generateScheduleV3(
|
||||
# handle options to solve for missing class
|
||||
getAvailableCourse = False
|
||||
|
||||
students[student["studentIndex"]]["remainingAlts"] = alternates
|
||||
students[student.StudentIndex].RemainingAlts = alternates
|
||||
tempStudents.remove(student)
|
||||
|
||||
|
||||
@@ -323,8 +324,8 @@ def generateScheduleV3(
|
||||
for block in running:
|
||||
for cname in running[block]:
|
||||
for student in running[block][cname]["students"]:
|
||||
students[student["index"]]["schedule"][block].append(cname)
|
||||
students[student["index"]]["classes"] += 1
|
||||
students[student["index"]].Schedule[block].append(cname)
|
||||
students[student["index"]].Classes += 1
|
||||
|
||||
|
||||
# Step 6 - Evaluate, move students to fix conflicts
|
||||
@@ -334,7 +335,7 @@ def generateScheduleV3(
|
||||
studentsCritical, studentsAcceptable = 0, 0
|
||||
|
||||
for student in students:
|
||||
blocks = [student["schedule"][block] for block in student["schedule"]]
|
||||
blocks = [student.Schedule[block] for block in student.Schedule]
|
||||
hasConflicts = True if sum(1 for b in blocks if len(b)>1) > 0 else False
|
||||
|
||||
# If there is no conflicts
|
||||
@@ -342,26 +343,26 @@ def generateScheduleV3(
|
||||
# or classes the student is inserted to is missing
|
||||
# no more than two classes:
|
||||
# continue to next student
|
||||
if not hasConflicts and student["classes"] == student["expectedClasses"]: continue
|
||||
elif not hasConflicts and (student["expectedClasses"]-2) <= student["classes"] < student["expectedClasses"]:
|
||||
if not hasConflicts and student.Classes == student.ExpectedClasses: continue
|
||||
elif not hasConflicts and (student.ExpectedClasses-2) <= student.Classes < student.ExpectedClasses:
|
||||
# TODO: Insert alternates if available?
|
||||
a_mc_count += 1
|
||||
acceptableCount += 1
|
||||
if not newConflict(student["Pupil #"], "", "Acceptable", "A-MC", "Missing 1-2 Classses", conflictLogs): studentsAcceptable += 1
|
||||
if not newConflict(student.PupilNum, "", "Acceptable", "A-MC", "Missing 1-2 Classses", conflictLogs): studentsAcceptable += 1
|
||||
continue
|
||||
|
||||
studentData = {
|
||||
"Pupil #": student["Pupil #"],
|
||||
"index": student["studentIndex"]
|
||||
"Pupil #": student.PupilNum,
|
||||
"index": student.StudentIndex
|
||||
}
|
||||
|
||||
if hasConflicts:
|
||||
student["classes"] = 0
|
||||
student.Classes = 0
|
||||
missing = []
|
||||
# Clear student schedule to restructure
|
||||
for block in student["schedule"]:
|
||||
[running[block][cname]["students"].remove(studentData) for cname in student["schedule"][block]]
|
||||
student["schedule"][block] = []
|
||||
for block in student.Schedule:
|
||||
[running[block][cname]["students"].remove(studentData) for cname in student.Schedule[block]]
|
||||
student.Schedule[block] = []
|
||||
|
||||
# Find class in student schedule that's run the least
|
||||
classes, runCounts = [], []
|
||||
@@ -382,9 +383,9 @@ def generateScheduleV3(
|
||||
for cname in running[block]:
|
||||
if cname[:-2] == classes[index] and len(running[block][cname]["students"]) < classCap:
|
||||
running[block][cname]["students"].append(studentData)
|
||||
student["schedule"][block].append(cname)
|
||||
student.Schedule[block].append(cname)
|
||||
availableBlocks.remove(block)
|
||||
student["classes"] += 1
|
||||
student.Classes += 1
|
||||
found = True
|
||||
break
|
||||
|
||||
@@ -402,21 +403,21 @@ def generateScheduleV3(
|
||||
if len(existsIn) > 0:
|
||||
for i, existing in enumerate(existsIn):
|
||||
if solution: break
|
||||
classOut = student["schedule"][existing][0]
|
||||
classOut = student.Schedule[existing][0]
|
||||
for block in running:
|
||||
if solution: break
|
||||
if block == existing or block not in availableBlocks: continue
|
||||
for cname in running[block]:
|
||||
if cname[:-2] == classOut[:-2] and len(running[block][cname]["students"]) < classCap:
|
||||
student["classes"] += 1
|
||||
student.Classes += 1
|
||||
|
||||
# Move to existing class elsewhere
|
||||
student["schedule"][block].append(cname)
|
||||
student.Schedule[block].append(cname)
|
||||
running[block][cname]["students"].append(studentData)
|
||||
|
||||
# Overwrite old class
|
||||
running[existing][student["schedule"][existing][0]]["students"].remove(studentData)
|
||||
student["schedule"][existing][0] = existingClassNames[i]
|
||||
running[existing][student.Schedule[existing][0]]["students"].remove(studentData)
|
||||
student.Schedule[existing][0] = existingClassNames[i]
|
||||
running[existing][existingClassNames[i]]["students"].append(studentData)
|
||||
|
||||
solution = True
|
||||
@@ -424,7 +425,7 @@ def generateScheduleV3(
|
||||
|
||||
if not solution:
|
||||
# Try alternate
|
||||
alternates = [alt["CrsNo"] for alt in students[student["studentIndex"]]["remainingAlts"] if alt["CrsNo"] not in flex and alt["CrsNo"] in courseRunInfoCopy]
|
||||
alternates = [alt.CrsNo for alt in students[student.StudentIndex].RemainingAlts if alt.CrsNo not in flex and alt.CrsNo in courseRunInfoCopy]
|
||||
if len(alternates) == 0: # If no alternates, create critical error
|
||||
c_cr_count += 1
|
||||
criticalCount += 1
|
||||
@@ -435,7 +436,7 @@ def generateScheduleV3(
|
||||
})
|
||||
|
||||
if not newConflict(
|
||||
student["Pupil #"],
|
||||
student.PupilNum,
|
||||
"", # Student Email
|
||||
"Critical", # Err type
|
||||
"C-CR", # Err code
|
||||
@@ -453,9 +454,9 @@ def generateScheduleV3(
|
||||
runCounts.append(altRunCounts[altIndex])
|
||||
|
||||
# Remove alternate from remaining alternates
|
||||
for remaining in students[student["studentIndex"]]["remainingAlts"]:
|
||||
if remaining["CrsNo"] == alternates[altIndex]:
|
||||
students[student["studentIndex"]]["remainingAlts"].remove(remaining)
|
||||
for remaining in students[student.StudentIndex].RemainingAlts:
|
||||
if remaining.CrsNo == alternates[altIndex]:
|
||||
students[student.StudentIndex].RemainingAlts.remove(remaining)
|
||||
|
||||
# Remove class after inserted or failed to insert
|
||||
classes.remove(classes[index])
|
||||
@@ -466,7 +467,7 @@ def generateScheduleV3(
|
||||
if len(missing) > 0:
|
||||
data = []
|
||||
|
||||
if student["gradelevel"] is None:
|
||||
if student.Gradelevel is None:
|
||||
for obj in missing:
|
||||
data["missing"].append({
|
||||
"CrsNo": obj["CrsNo"],
|
||||
@@ -482,7 +483,7 @@ def generateScheduleV3(
|
||||
courseInfo = running[obj['block']][cname]
|
||||
courseGrade = getGrade(courseInfo['CrsNo'], courseInfo['Description'])
|
||||
if courseGrade is None: continue
|
||||
if (student["gradelevel"] == courseGrade) or (student["gradelevel"] == 12 and courseGrade == 11):
|
||||
if (student.Gradelevel == courseGrade) or (student.Gradelevel == 12 and courseGrade == 11):
|
||||
if len(running[obj['block']][cname]["students"]) < classCap:
|
||||
blockSolution["solutions"].append({
|
||||
"CrsNo": cname,
|
||||
@@ -491,23 +492,23 @@ def generateScheduleV3(
|
||||
|
||||
data.append(blockSolution)
|
||||
|
||||
insertConflictSolutions(student["Pupil #"], conflictLogs, data)
|
||||
insertConflictSolutions(student.PupilNum, conflictLogs, data)
|
||||
|
||||
metSelfRequirements = True if student["classes"] == student["expectedClasses"] else False
|
||||
metSelfRequirements = True if student.Classes == student.ExpectedClasses else False
|
||||
if not metSelfRequirements:
|
||||
|
||||
if (student["expectedClasses"] - 2) <= student["classes"] < student["expectedClasses"]:
|
||||
if (student.ExpectedClasses - 2) <= student.Classes < student.ExpectedClasses:
|
||||
a_mc_count += 1
|
||||
acceptableCount += 1
|
||||
if not newConflict(student["Pupil #"], "", "Acceptable", "A-MC", "Missing 1-2 Classses", conflictLogs): studentsAcceptable += 1
|
||||
if not newConflict(student.PupilNum, "", "Acceptable", "A-MC", "Missing 1-2 Classses", conflictLogs): studentsAcceptable += 1
|
||||
|
||||
elif student["classes"] < (student["expectedClasses"] - 2):
|
||||
elif student.Classes < (student.ExpectedClasses - 2):
|
||||
# Difference between classes inserted to and
|
||||
# expected classes is too great
|
||||
if student["Pupil #"] in conflictLogs:
|
||||
if student.PupilNum in conflictLogs:
|
||||
c_mc_count += 1
|
||||
criticalCount += 1
|
||||
if not newConflict(student["Pupil #"], "", "Critical", "C-MC", "Missing too many Classses", conflictLogs): studentsCritical += 1
|
||||
if not newConflict(student.PupilNum, "", "Critical", "C-MC", "Missing too many Classses", conflictLogs): studentsCritical += 1
|
||||
|
||||
finalConflictLogs = {
|
||||
"Conflicts": conflictLogs,
|
||||
@@ -541,10 +542,10 @@ def generateScheduleV3(
|
||||
|
||||
# Insert flex (spare) course codes to empty blocks
|
||||
for student in students:
|
||||
for block in student["schedule"]:
|
||||
if len(student["schedule"][block]) == 0:
|
||||
for block in student.Schedule:
|
||||
if len(student.Schedule[block]) == 0:
|
||||
i = 0 if int(block[5:]) <= blockPerSem else 1
|
||||
student["schedule"][block].append(flex[i])
|
||||
student.Schedule[block].append(flex[i])
|
||||
|
||||
# Read timetable and collect data on courses
|
||||
for block in running:
|
||||
@@ -559,7 +560,7 @@ def generateScheduleV3(
|
||||
|
||||
# Update/log new student records
|
||||
with open(studentsDir, "w") as outfile:
|
||||
json.dump(students, outfile, indent=2)
|
||||
json.dump(studentsToDict(students), outfile, indent=2)
|
||||
|
||||
# Update/log new course records
|
||||
with open(coursesDir, "w") as outfile:
|
||||
|
||||
@@ -44,7 +44,7 @@ def putScheduleToWord(
|
||||
# create an instance of a word doc.
|
||||
doc = docx.Document()
|
||||
|
||||
doc.add_heading(f'Schedule for Student {student["Pupil #"]}')
|
||||
doc.add_heading(f'Schedule for Student {student.PupilNum}')
|
||||
|
||||
# Create a table object
|
||||
table = doc.add_table(rows=1, cols=3)
|
||||
@@ -62,12 +62,12 @@ def putScheduleToWord(
|
||||
table.columns[2].width = Inches(0.75)
|
||||
|
||||
for block in student['schedule']:
|
||||
courseCode = student["schedule"][block][0]
|
||||
courseCode = student.Schedule[block][0]
|
||||
if courseCode in flex: courseName = 'Study'
|
||||
else: courseName = courses[courseCode[:-2]]["Description"]
|
||||
blockNum = int(block.split('block')[1])
|
||||
semester = 2 if blockNum > 5 else 1
|
||||
if blockNum > (len(student["schedule"])/2): blockNum -= (len(student["schedule"])/2)
|
||||
if blockNum > (len(student.Schedule)/2): blockNum -= (len(student.Schedule)/2)
|
||||
row = table.add_row().cells
|
||||
row[0].text = f'{courseName}\n({courseCode})'
|
||||
row[1].text = str(blockNum)
|
||||
@@ -76,4 +76,4 @@ def putScheduleToWord(
|
||||
for row in table.rows:
|
||||
row.height = Inches(0.75)
|
||||
|
||||
doc.save(f'{output_dir}/{student["Pupil #"]}_schedule.docx')
|
||||
doc.save(f'{output_dir}/{student.PupilNum}_schedule.docx')
|
||||
@@ -1,8 +1,15 @@
|
||||
#!/usr/bin/env python3.11
|
||||
import json
|
||||
import csv
|
||||
from dataclasses import dataclass
|
||||
from app.util.estimateGrade import getGrade
|
||||
|
||||
@dataclass
|
||||
class Request:
|
||||
CrsNo: str
|
||||
Description: str
|
||||
Alt: bool
|
||||
|
||||
# Get all requested courses from data
|
||||
def getCourses(
|
||||
data_dir: str,
|
||||
|
||||
@@ -23,10 +23,10 @@ def extractGrade(string: str) -> int:
|
||||
return grade if grade is not None and grade >= 8 else None
|
||||
|
||||
# Estimage students grade based off requests
|
||||
def estimateStudentGrade(pupil: dict) -> int:
|
||||
def estimateStudentGrade(pupil) -> int:
|
||||
grades = [] # List of all possible grades
|
||||
for request in (r for r in pupil["requests"] if r not in flex):
|
||||
extractedGrade = getGrade(request["CrsNo"], request["Description"])
|
||||
for request in (r for r in pupil.Requests if r not in flex):
|
||||
extractedGrade = getGrade(request.CrsNo, request.Description)
|
||||
if extractedGrade is not None: grades.append(extractedGrade)
|
||||
|
||||
return None if len(grades) == 0 else most_frequent(grades) # Final estimate of grade
|
||||
|
||||
+48
-30
@@ -3,6 +3,26 @@ import json
|
||||
import csv
|
||||
from app.util.estimateGrade import estimateStudentGrade
|
||||
from app.util.globals import flex
|
||||
from app.util.courses import Request
|
||||
from dataclasses import dataclass, asdict
|
||||
|
||||
@dataclass
|
||||
class Student:
|
||||
PupilNum: str
|
||||
Requests: list[Request]
|
||||
Schedule: dict[str: list]
|
||||
ExpectedClasses: int
|
||||
Classes: int
|
||||
RemainingAlts: list[Request]
|
||||
StudentIndex: int
|
||||
Gradelevel: int = None # set to None since don't pass gradelevel
|
||||
|
||||
# This function converst Student.Requests to an array of dictionaries from an array of Requests
|
||||
def RequestsToDict(self) -> None: self.Requests = [asdict(r) for r in self.Requests]
|
||||
|
||||
def studentsToDict(students: list[Student]) -> list[dict]:
|
||||
[s.RequestsToDict for s in students]
|
||||
return [asdict(s) for s in students]
|
||||
|
||||
# sort data into usable dictionary
|
||||
def getStudents(
|
||||
@@ -12,56 +32,54 @@ def getStudents(
|
||||
log_dir: str = './output/raw/students.json'
|
||||
) -> list[ dict[ str: any ] ]:
|
||||
|
||||
students: list[ dict[ str: any ] ] = []
|
||||
students: list[Student] = []
|
||||
|
||||
with open(data_dir, newline='') as csvfile:
|
||||
reader = csv.DictReader(csvfile)
|
||||
for row in reader:
|
||||
exists = False
|
||||
for student in students:
|
||||
exists = True if student["Pupil #"] == row["Pupil #"] else False
|
||||
exists = True if student.PupilNum == row["Pupil #"] else False
|
||||
if exists: break
|
||||
alternate = True if row["Alternate?"] == 'TRUE' else False
|
||||
alternate = True if str(row["Alternate?"]).upper() == 'TRUE' else False
|
||||
if exists:
|
||||
if len(students[student["studentIndex"]]["requests"]) >= totalBlocks and not alternate and row["CrsNo"] not in flex: alternate = True
|
||||
students[student["studentIndex"]]["requests"].append({
|
||||
"CrsNo": row["CrsNo"],
|
||||
"Description": row["Description"],
|
||||
"alt": alternate
|
||||
})
|
||||
if row["CrsNo"] not in flex and not alternate and students[student["studentIndex"]]["expectedClasses"] < 10:
|
||||
students[student["studentIndex"]]["expectedClasses"] += 1
|
||||
if len(students[student.StudentIndex].Requests) >= totalBlocks and not alternate and row["CrsNo"] not in flex: alternate = True
|
||||
students[student.StudentIndex].Requests.append(
|
||||
Request(
|
||||
row["CrsNo"],
|
||||
row["Description"],
|
||||
alternate
|
||||
))
|
||||
if row["CrsNo"] not in flex and not alternate and students[student.StudentIndex].ExpectedClasses < 10:
|
||||
students[student.StudentIndex].ExpectedClasses += 1
|
||||
else:
|
||||
newStudent = {
|
||||
"Pupil #": row["Pupil #"],
|
||||
"requests": [{
|
||||
"CrsNo": row["CrsNo"],
|
||||
"Description": row["Description"],
|
||||
"alt": alternate
|
||||
}],
|
||||
"schedule": {},
|
||||
"expectedClasses": 1,
|
||||
"classes": 0,
|
||||
"remainingAlts": [],
|
||||
"studentIndex": len(students)
|
||||
}
|
||||
newStudent["gradelevel"] = row.get("Grade") if row.get("Grade") is not None else row.get("grade")
|
||||
for i in range(1, totalBlocks+1): newStudent["schedule"][f'block{i}'] = []
|
||||
newStudent: Student = Student(
|
||||
row["Pupil #"],
|
||||
[Request(
|
||||
row["CrsNo"],
|
||||
row["Description"],
|
||||
alternate
|
||||
)],
|
||||
{}, 1, 0, [],
|
||||
len(students)
|
||||
)
|
||||
newStudent.Gradelevel = row.get("Grade") if row.get("Grade") is not None else row.get("grade")
|
||||
for i in range(1, totalBlocks+1): newStudent.Schedule[f'block{i}'] = []
|
||||
students.append(newStudent)
|
||||
|
||||
# Estimate student grades
|
||||
for student in students:
|
||||
if student["gradelevel"] is None: student["gradelevel"] = estimateStudentGrade(student)
|
||||
if student.Gradelevel is None: student.Gradelevel = estimateStudentGrade(student)
|
||||
|
||||
if log:
|
||||
with open(log_dir, "w") as outfile:
|
||||
json.dump(students, outfile, indent=2)
|
||||
json.dump(studentsToDict(students), outfile, indent=2)
|
||||
|
||||
return students
|
||||
|
||||
# Writes all students data to csv file
|
||||
def writeStudentsToCSV(
|
||||
students: dict,
|
||||
students: list[Student],
|
||||
output_dir: str = './output/raw/csv/students.csv'
|
||||
) -> None:
|
||||
with open(output_dir, 'w') as file:
|
||||
@@ -71,5 +89,5 @@ def writeStudentsToCSV(
|
||||
writer.writerow(data)
|
||||
|
||||
for student in students:
|
||||
studentData = (student["Pupil #"], student["classes"], student["gradelevel"])
|
||||
studentData = (student.PupilNum, student.Classes, student.Gradelevel)
|
||||
writer.writerow(studentData)
|
||||
@@ -7,7 +7,7 @@ from app.util.convertRawData import putScheduleToWord, putMasterTimetable
|
||||
from app.generator import generateScheduleV3
|
||||
from app.util.globals import Error
|
||||
from app.util.courses import getCourses, writeCoursesToCSV
|
||||
from app.util.students import getStudents, writeStudentsToCSV
|
||||
from app.util.students import getStudents, writeStudentsToCSV, Student
|
||||
from app.util.errorCalculator import writeErrorsToCSV
|
||||
from app.util.validator import validateInputData
|
||||
|
||||
@@ -58,7 +58,7 @@ def start(
|
||||
eel.post_data('Collecting student information...')
|
||||
students = getStudents(
|
||||
raw_data_dir,
|
||||
log = True,
|
||||
log = False,
|
||||
totalBlocks = total_blocks,
|
||||
log_dir = './output/raw/json/students.json'
|
||||
)
|
||||
@@ -89,13 +89,13 @@ def start(
|
||||
|
||||
# Get updated students
|
||||
eel.post_data('Gathering latest data...')
|
||||
with open(f'{raw_json_dir}/students.json', 'r') as studentFile: students = json.load(studentFile)
|
||||
with open(f'{raw_json_dir}/students.json', 'r') as studentFile:
|
||||
# Unpack dictionary to Student dataclass
|
||||
students = [Student(**s) for s in json.load(studentFile)]
|
||||
with open(f'{raw_json_dir}/courses.json', 'r') as cFile: courses = json.load(cFile)
|
||||
|
||||
# call post-algorithm functions to present sorted data
|
||||
eel.post_data('Writing data to .csv files...')
|
||||
# get updated raw data
|
||||
with open(f'{raw_json_dir}/students.json', 'r') as sFile: students = json.load(sFile)
|
||||
with open(f'{raw_json_dir}/courses.json', 'r') as cFile: courses = json.load(cFile)
|
||||
writeStudentsToCSV(students, output_dir='./output/raw/csv/students.csv')
|
||||
writeCoursesToCSV(courses, output_dir='./output/raw/csv/courses.csv')
|
||||
writeErrorsToCSV(len(students), conflictsDir='./output/raw/json/conflicts.json', outputDir='./output/raw/csv/error_tracker.csv')
|
||||
|
||||
Reference in new issue
Block a user