Skip to Content
Living documentation — last reviewed 2026-05-28
FeaturesFormsForms — Code Map

Forms — Code Map

All paths absolute from the repo root.

API (NestJS)

FileRole
apps/api/src/forms/forms.module.tsDI wiring. Imports MembershipsModule + R2Module; exports FormsService. The reverse hook (auto-issue) flows over EventEmitter, not DI — no forwardRef needed.
apps/api/src/forms/forms.controller.tsTwo controllers: FormsController mounted at /organizations/:orgId/forms (auth), FormsPublicController mounted at /forms/sign/:token (public, @Public()).
apps/api/src/forms/forms.service.tsDomain service. ~1070 lines. Template CRUD, instance issuance (single + bulk + auto-issue), token mint, both signing paths, signed-PDF presign, member + staff reads. Constants: SIGNING_TOKEN_BYTES=32, SIGNING_TOKEN_TTL_MS=7d.
apps/api/src/forms/pdf.service.tsPuppeteer-based Hebrew RTL PDF renderer. Singleton browser (browserPromise), closed on onModuleDestroy. Uses @sparticuz/chromium in prod; honors PUPPETEER_EXECUTABLE_PATH for macOS dev.
apps/api/src/forms/forms.service.driver.tsTest driver. Used by forms.service.unit.spec.ts.
apps/api/src/forms/forms.service.unit.spec.tsUnit tests.
apps/api/src/forms/dto/create-form.dto.tsTemplate create DTO. Compliance shape (no recurrence); check-in shape (no validityPeriodDays) enforced at the service layer in assertKindShape.
apps/api/src/forms/dto/update-form.dto.tsPatch + bump-version DTO. All fields optional.
apps/api/src/forms/dto/assign-compliance-form.dto.ts{ formId, assigneeUserId }.
apps/api/src/forms/dto/submit-form-answers.dto.ts{ answers: FormAnswers }. Detailed shape validated by Zod inside the service.

API — adjacent

FileRole
apps/api/src/r2/r2.service.tsS3 client wrapping Cloudflare R2. getComplianceBucket(), upload(key, bytes, mime, {bucket}), getPresignedUrlCached, getPresignedUploadUrl, getObjectBytes. The compliance bucket key (R2_COMPLIANCE_BUCKET_NAME) falls back to the default bucket when unset.
apps/api/src/r2/r2.module.tsGlobal. Exposes R2Service.
apps/api/src/memberships/membership-events.tsMEMBERSHIP_ACTIVATED event token. Emitted by MembershipsService and OrganizationLeadsService. Consumed by FormsService.handleMembershipActivated.
apps/api/src/auth/public.decorator.ts@Public() marker used on the /forms/sign/:token routes.
apps/api/src/uploads/uploads.service.tsAuthenticated staged-PUT presigns. Used by the in-app signing flow (signature PNG upload) — NOT by the tokenized flow (which has its own bespoke presign).
apps/api/src/ai/agent/tools/leaves/forms.tools.tsSpotter-agent tool surface for compliance — out of scope here.

Shared (@fitkit/shared)

FileRole
libs/shared/src/lib/schemas/forms.tsSource of truth for: formKindEnum, complianceStatusEnum, checkInStatusEnum, complianceTypeKeyEnum (the six FIT-158 slugs), formFieldSchema (discriminated union: text, free_text, checkbox, date, number, scale, photo, multi_choice, signature), formAnswersSchema, recurrenceSchema, createFormSchema, submitFormAnswersSchema, formResponseSchema, formInstanceResponseSchema, state machine maps complianceTransitions + checkInTransitions, helpers canTransitionCompliance / canTransitionCheckIn.
libs/shared/src/lib/schemas/forms-presets.tsPre-built FormField[] skeletons for the six compliance type-keys, labelled in Hebrew, aligned with Israeli regulatory minima (PAR-Q for health declaration, gym contract conventions for the rest).
libs/shared/src/lib/agent-schemas/forms.tsSpotter-agent tool descriptors — out of scope.
libs/shared/src/lib/utils/roles.tsisStaffRole(role).

Database (@fitkit/db)

FileRole
libs/db/src/lib/schema/forms.tsDrizzle definitions for forms, form_instances, form_signatures + relations + types. CHECK constraints + partial-unique indexes encoded here.
libs/db/src/lib/schema/enums.tsformKind (compliance, check_in), formStatus (8-value superset; CHECK constraint narrows per kind).
libs/db/drizzle/Migration journal. New forms-touching migrations land here.

Web (apps/web — Next.js)

FileRole
apps/web/src/app/[lang]/(protected)/dashboard/forms/page.tsxStaff forms list page.
apps/web/src/app/[lang]/(protected)/dashboard/forms/new/page.tsxNew template builder route.
apps/web/src/app/[lang]/(protected)/dashboard/forms/[formId]/page.tsxTemplate detail (edit, publish, bump version, assign, coverage).
apps/web/src/components/overview/forms/forms-list-page.tsxList table component.
apps/web/src/components/overview/forms/template-editor.tsxForm builder UI.
apps/web/src/components/overview/forms/template-detail-page.tsxDetail / actions panel.
apps/web/src/components/overview/forms/form-field-builder.tsxField editor (add/remove/reorder).
apps/web/src/components/overview/forms/assign-compliance-dialog.tsxSingle-member assignment + bulk-missing tab.
apps/web/src/components/overview/forms/generate-signing-link-dialog.tsxToken mint + copy-to-clipboard UI. URL: ${origin}/${lang}/forms/sign/${token}.
apps/web/src/components/overview/members/member-forms-tab.tsxPer-member audit tab on the member detail page.
apps/web/src/components/overview/members/member-forms-tab.driver.tsxDriver for member-forms-tab.int.spec.tsx.
apps/web/src/components/overview/members/member-compliance-tab.tsxMember’s own pending-forms tab (in-app authenticated signing — pending FIT-178).
apps/web/src/app/[lang]/forms/sign/[token]/page.tsxPending (FIT-178) — public signing page. Not yet present. Referenced by generate-signing-link-dialog.tsx.

i18n

FileKeys
apps/web/src/i18n/dictionaries/en.jsonforms.* block: title, subtitle, newTemplate, kind.{compliance,checkIn}, status.*, instanceStatus.*, columns.*, complianceTypeKey.*, builder.*, fieldTypes.*, detail.*, memberTab.*, assign.*, signingLink.*, publishWarning.*, autoIssue.*.
apps/web/src/i18n/dictionaries/he.jsonHebrew labels. Source of truth for the signed PDF body text fallbacks.
apps/web/src/i18n/dictionaries/ru.jsonRussian labels.

Test inventory

FileType
apps/api/src/forms/forms.service.unit.spec.tsAPI unit.
apps/web/src/components/overview/forms/template-detail-page.int.spec.tsxWeb integration.
apps/web/src/components/overview/forms/template-editor.int.spec.tsxWeb integration.
apps/web/src/components/overview/forms/assign-compliance-dialog.int.spec.tsxWeb integration.
apps/web/src/components/overview/members/member-forms-tab.int.spec.tsxWeb integration.
Playwright e2eNone yet for the signing flow — to add as part of FIT-178 QA.

Configuration

EnvPurpose
R2_ACCOUNT_ID, R2_ACCESS_KEY_ID, R2_SECRET_ACCESS_KEY, R2_BUCKET_NAMECloudflare R2 credentials.
R2_COMPLIANCE_BUCKET_NAMEDedicated bucket for signed PDFs. Falls back to R2_BUCKET_NAME in dev.
PUPPETEER_EXECUTABLE_PATHOverride Chromium binary path on macOS dev. Prod uses @sparticuz/chromium.
FRONTEND_URLUsed in the WebSocket gateway, not forms — but generate-signing-link-dialog.tsx derives the public URL from window.location.origin on the web client.