Automates attendance tracking and cold-call selection for both T&E and L&C classes.
| File | Type | Purpose |
|---|---|---|
| T&E (Trusts & Estates) | ||
oncall-selection.http.tsx | HTTP | Algorithmically selects 6 students for cold-calling |
oncall-notify.cron.tsx | Cron | Emails on-call list before class (3 PM) |
te-report-prompt.cron.tsx | Cron | Reminds Sarah to submit T&E report (6 PM) |
| L&C (Law & Capitalism) | ||
lc-oncall-selection.http.tsx | HTTP | Looks up preset on-call from syllabus |
lc-oncall-notify.cron.tsx | Cron | Emails on-call list before class (8 AM) |
lc-report-prompt.cron.tsx | Cron | Reminds Sarah to submit L&C report (12 PM) |
| Shared | ||
post-class-report.http.tsx | HTTP | Receives reports, updates tracking, triggers alerts |
process-form-reports-api.http.tsx | HTTP | Parses Google Form responses, calls post-class-report |
process-form-reports-schedule.cron.tsx | Cron | Triggers form processing (every 10 min) |
main.http.tsx | HTTP | Sheets connection test |
utils.tsx | Script | Shared utilities |
Set these in Val.town UI (Settings → Environment Variables):
| Variable | Purpose |
|---|---|
GOOGLE_APPLICATION_CREDENTIALS | Service account JSON (full string) |
REPORT_API_KEY | Secret key for report submissions |
POST_CLASS_REPORT_URL | URL for post-class-report.http.tsx |
PROCESS_FORM_REPORTS_URL | URL for process-form-reports-api.http.tsx |
Set in Val.town UI for each cron val. Times are UTC:
| Val | EST Time | UTC Cron |
|---|---|---|
| T&E | ||
oncall-notify | 3 PM Mon/Wed | 0 20 * * 1,3 |
te-report-prompt | 6 PM Mon/Wed | 0 23 * * 1,3 |
| L&C | ||
lc-oncall-notify | 8 AM Mon/Wed | 0 13 * * 1,3 |
lc-report-prompt | 12 PM Mon/Wed | 0 17 * * 1,3 |
Note: Adjust for DST. These are EST (UTC-5). EDT (summer) is UTC-4.
POST to post-class-report.http.tsx endpoint with:
curl -X POST "https://sahar--{hash}.web.val.run" \ -H "Content-Type: application/json" \ -H "X-API-Key: YOUR_REPORT_API_KEY" \ -d '{ "date": "2026-01-12", "class_type": "te", "cold_calls": [ {"student_name": "Alice Adams", "result": "completed", "performance": "great"}, {"student_name": "Bob Baker", "result": "absent"}, {"student_name": "Carol Chen", "result": "refused"} ], "absences": ["David Davis"] }'
Fields:
date: Class date (YYYY-MM-DD)class_type: "te" or "lc"cold_calls: Array of students called on
result: "completed" | "absent" | "refused"performance: "great" | "normal" | "bad" (only for completed)absences: Other absent students (not on on-call list)Response:
{ "success": true, "date": "2026-01-12", "cold_calls_logged": 3, "absences_logged": 1, "unprepared_processed": 0, "alerts_sent": [] }
Automatic email alerts at thresholds:
Concerning events = absent + unprepared + refused + bad performance.
Uses Google Sheet with tabs:
Shared:
T&E:
L&C:
L&C Roster tab with columns: student_name, last_name, cold_call_count, last_called, absences, concerning_eventsL&C Assignments tab with columns: date, student_nameL&C Assignments with syllabus data (one row per student per date)Example L&C Assignments:
| date | student_name |
|---|---|
| 2026-01-13 | Alice Adams |
| 2026-01-13 | Bob Baker |
| 2026-01-15 | Carol Chen |