8from statistics
import mean
21CLASS_AUTO_APPROVE = 0x01
22CLASS_AUTO_HOMEWORK = 0x02
23CLASS_REVIEW_STUDYLIST = 0x04
27 """Container class for students, courses, and teachers. This
28 permits easy searching for students to apply
and teachers to manage
33 'rid': (
'INTEGER PRIMARY KEY',
'NOT NULL',),
34 'schoolid': (
'INT',
'NOT NULL',),
40 'teachers': (
'TRANSLATION',
"NOT NULL DEFAULT ''",),
41 'rankings': (
'NEWLINELIST',
"NOT NULL DEFAULT ''",),
42 'numstudents': (
'INT',
'NOT NULL DEFAULT 0',),
43 'capacity': (
'INT',
'NOT NULL',),
44 'resettime': (
'INT',
'NOT NULL',),
45 'autohomework': (
'DICT',
"NOT NULL DEFAULT ''",),
46 'flags': (
'INT',
'NOT NULL DEFAULT 0',),
54 _dbdisplay = [
'coursenum',
'displayname',
'description']
63 """Look for any challenges that have passed endtime and calculate
69 for c
in g.db.Find(apps.learn.challenge.learn_challenge,
70 'WHERE classid = ? AND starttime < ? AND flags & ?',
74 apps.learn.challenge.CHALLENGE_NEEDS_ANALYSIS
85 """Recalculate grades for studentid and update class rankings.
89 apps.learn.classgrade.learn_classgrade,
90 'WHERE classid = ? AND userid = ?',
98 grade = apps.learn.classgrade.learn_classgrade()
107 classparticipations = []
112 persistencestreak = 0
114 homeworkcompleted = 0
117 apps.learn.challenge.learn_challenge,
118 'WHERE classid = ? AND endtime < ?',
123 fields =
'challengetype, results',
126 if studentcode
not in r.results:
127 persistencestreak = 0
130 result = r.results[studentcode]
132 if r.challengetype == apps.learn.challenge.CHALLENGE_CLASSPARTICIPATION:
133 classparticipations.append((result[
'score'], result[
'percentage']))
134 elif r.challengetype == apps.learn.challenge.CHALLENGE_HOMEWORK:
137 homeworks.append((result[2], result[3]))
139 completed = result[1] == apps.learn.challenge.CHALLENGE_COMPLETED
142 homeworkcompleted += 1
143 persistencestreak += 1
144 persistencebonus += persistencestreak
147 numhomework = numhomework,
148 homeworkcompleted = homeworkcompleted,
149 classscore = sum([x[0]
for x
in classparticipations])
if classparticipations
else 0,
150 classpercent = mean([x[1]
for x
in classparticipations])
if classparticipations
else 0,
151 reviewscore = sum([x[0]
for x
in homeworks])
if homeworks
else 0,
152 reviewpercent = mean([x[1]
for x
in homeworks])
if homeworks
else 0,
153 persistencescore = persistencebonus,
154 persistencepercent = (homeworkcompleted / numhomework * 100)
if numhomework
else 0,
159 (grade.classscore + grade.reviewscore + grade.persistencescore)
160 * (grade.classpercent / 100)
161 * (grade.reviewpercent / 100)
162 * (grade.persistencepercent / 100)
174 apps.learn.classgrade.learn_classgrade,
178 orderby =
'finalscore, classpercent, reviewpercent, persistencepercent',
183 self.
Set(rankings = newrankings)
191 """If autohomework is enabled, this function will generate a random
192 challenge every day for your students to complete.
194 If review studylist
is enabled, this will generate a challenge
195 every day using each student
's studylist.
198 if self.flags & CLASS_AUTO_HOMEWORK
or self.flags & CLASS_REVIEW_STUDYLIST:
199 currenttime = time.time()
201 currenthomework = g.db.Find(
202 apps.learn.challenge.learn_challenge,
203 'WHERE classid = ? AND starttime < ? AND endtime > ? AND challengetype = ?',
208 apps.learn.challenge.CHALLENGE_HOMEWORK,
212 needhomework = 1
if self.flags & CLASS_AUTO_HOMEWORK
else 0
213 needstudylist = 1
if self.flags & CLASS_REVIEW_STUDYLIST
else 0
215 for s
in currenthomework:
216 if self.flags & CLASS_REVIEW_STUDYLIST
and s.flags & apps.learn.challenge.CHALLENGE_USE_STUDYLIST:
218 elif self.flags & CLASS_AUTO_HOMEWORK:
221 if needhomework
or needstudylist:
222 today = datetime.datetime.now(
224 datetime.timedelta(hours = self.resettime)
228 today = today.replace(hour = 0, minute = 0, second = 0)
231 tomorrow = today.replace(day = today.day + 1)
232 except Exception
as e:
233 tomorrow = today.replace(month = today.month + 1, day = 1)
235 lessonidspool = self.autohomework[
'lessonids']
236 problemidspool = self.autohomework[
'problemids']
237 challengetypes = self.autohomework[
'challengetypes']
239 if needhomework
and (lessonidspool
or problemidspool)
and challengetypes:
240 newhomework = apps.learn.challenge.learn_challenge()
243 challengetype = apps.learn.challenge.CHALLENGE_HOMEWORK,
246 challenge = random.choice(challengetypes),
247 flags = apps.learn.challenge.CHALLENGE_NEEDS_ANALYSIS,
250 newhomework.Set(**(self.autohomework))
252 if self.autohomework[
'problemselect'] ==
'randomly':
254 lessonids = [random.choice(lessonidspool)],
256 elif self.autohomework[
'problemselect'] ==
'sequentially':
257 pasthomework = g.db.Find(
258 apps.learn.challenge.learn_challenge,
259 'WHERE classid = ? AND endtime < ? AND challengetype = ?',
263 apps.learn.challenge.CHALLENGE_HOMEWORK,
265 orderby =
'endtime DESC',
268 for p
in pasthomework:
270 lastlessonid = p.lessonids[0]
273 lastlessonpos = lessonidspool.index(lastlessonid)
275 if lastlessonpos == len(lessonidspool) - 1:
276 newhomework.Set(lessonids = [lessonidspool[0]])
278 newhomework.Set(lessonids = [lessonidspool[lastlessonpos + 1]])
279 except Exception
as e:
282 if newhomework.lessonids:
283 cardtitles = apps.learn.card.GetCardTitles(g, [
FromShortCode(x)
for x
in newhomework.lessonids])
286 newtitle[g.session.lang] =
', '.join(cardtitles.values())
288 newhomework.Set(title = newtitle)
291 newtitle[g.session.lang] = g.T.dailychallenge
293 newhomework.Set(title = newtitle)
295 g.db.Save(newhomework)
297 if needstudylist
and challengetypes:
298 newhomework = apps.learn.challenge.learn_challenge()
301 newtitle[g.session.lang] = g.T.studylist
303 newhomework.Set(**(self.autohomework))
310 challengetype = apps.learn.challenge.CHALLENGE_HOMEWORK,
313 challenge = random.choice(challengetypes),
314 flags = apps.learn.challenge.CHALLENGE_NEEDS_ANALYSIS | apps.learn.challenge.CHALLENGE_USE_STUDYLIST,
317 g.db.Save(newhomework)
Container class for students, courses, and teachers.
def __init__(self)
Initialize all fields at creation like a good programmer should.
def GenerateAutoHomework(self, g)
If autohomework is enabled, this function will generate a random challenge every day for your student...
def UpdateChallenges(self, g)
Look for any challenges that have passed endtime and calculate statistics for them.
def UpdateGrades(self, g, studentid)
Recalculate grades for studentid and update class rankings.
Base class for all database models.
def Set(self, **kwargs)
We use this method instead of direct attribute access in order to keep track of what values have been...
Throws an exception on blank values.
def FromShortCode(code, chars='0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ-_')
Turns a six character alphanumeric code into a 32-bit value.
def ToShortCode(val, chars='0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ-_')
Turns a 32-bit value into a six character alphanumeric code.