Skip to main content
Session required on every route in this page.

Collection

GET /api/forms

Query ?schoolYear=2026-2027 to scope the list. Returns { forms: FormSubmission[] } scoped by role:
  • Level 5: all forms
  • Level 4: school + assigned
  • Lower: owned, assigned, or shared
Each form is stamped with schoolYear, locked (year archived), and completedSteps (derived if empty). List payloads omit formData answers; open GET /api/forms/[id] for the full plan.

POST /api/forms

Level ≥ 4. Cannot create into an archived year.
initialOwnerEmail is Super Admin only and must be a level-4 user.

Single form

GET /api/forms/[id]

Full form plus userPermission, collaborationInfo, and active comments.
string
required
FormSubmission ObjectId.

PUT /api/forms/[id]

Update metadata/status (submit, admin review). Rejected when the year is archived.

DELETE /api/forms/[id]

Admin delete (level-gated in the route).

Steps

GET /api/forms/[id]/step/[stepNumber]

PUT /api/forms/[id]/step/[stepNumber]

See School plans. Acquires a step lock.

POST /api/forms/[id]/step/[stepNumber]/unlock

Release the caller’s lock.

Year-over-year

POST /api/forms/[id]/duplicate

Level ≥ 4. 409 + existingFormId if a target-year plan already exists.

GET /api/forms/[id]/compare?compareYear=2025-2026

Returns row diffs for attendance, temporary housing, and counseling.

POST /api/forms/[id]/attest

POST /api/forms/[id]/review-flag

Removes that id from needsUpdate.

Collaboration and review