Zod Schemas
The @neemias/schemas package contains all Zod schemas shared between frontend and backend. These schemas are the single source of truth for data validation, TypeScript types, and OpenAPI specification generation.
Primitives
PhoneEntry
Phone entry with number and qualifier (e.g., "Mobile", "WhatsApp").
| Field | Type | Constraints |
|---|---|---|
number | string | min 1, max 20 |
qualifier | string | min 1, max 50 |
Address
Student residential address (LGPD data — PII).
| Field | Type | Constraints |
|---|---|---|
street | string | max 255, default "" |
number | string | max 20, default "" |
complement | string | max 255, default "" |
neighborhood | string | max 255, default "" |
city | string | max 255, default "" |
state | string | max 2, default "" |
zip | string | max 10, default "" |
Helper constant: EMPTY_ADDRESS — Address object with all fields empty.
EncryptedPayload
AES-GCM encrypted payload for sensitive data at rest.
| Field | Type |
|---|---|
ciphertext | string |
iv | string |
keyVersion | number (integer) |
Core entities
Student
Student — central entity of the system. Contains PII (LGPD) and non-PII fields.
PII fields (LGPD): displayName, photoRef, guardianName, guardianNameAlt, birthDate, phones, address, allergies, specialNeeds
| Field | Type | Constraints |
|---|---|---|
studentId | string | UUID |
displayName | string | min 1, max 140 — PII |
photoRef | string | default "" — PII (biometric data) |
status | StudentStatus | enum |
guardianName | string | min 1, max 200 — PII |
guardianNameAlt | string (optional) | max 200 — PII |
birthDate | string (optional) | — PII |
phones | PhoneEntry[] | default [] — PII |
address | Address | default EMPTY_ADDRESS — PII |
classId | string (optional) | UUID |
nucleusParticipates | boolean | default false |
nucleusRegion | NucleusRegion (optional) | enum |
nucleusName | string (optional) | max 200 |
allergies | string (optional) | max 1000 — PII |
specialNeeds | string (optional) | max 1000 — PII |
familyMembershipStatus | FamilyMembershipStatus | default "DESCONHECIDO" |
createdAt | string | ISO 8601 datetime |
updatedAt | string | ISO 8601 datetime |
createdBy | string | UUID |
deletedAt | string (optional) | — |
deletedBy | string (optional) | UUID |
Class (Turma)
| Field | Type | Constraints |
|---|---|---|
classId | string | UUID |
name | string | min 1, max 100 |
ageMin | number (optional) | integer, 0–99 |
ageMax | number (optional) | integer, 0–99 |
status | enum | "ACTIVE" | "DELETED" |
createdAt | string | ISO 8601 datetime |
updatedAt | string | ISO 8601 datetime |
Nucleus (Núcleo)
| Field | Type | Constraints |
|---|---|---|
nucleusId | string | UUID |
region | NucleusRegion | enum |
name | string | min 1, max 200 |
status | enum | "ACTIVE" | "DELETED" |
createdAt | string | ISO 8601 datetime |
updatedAt | string | ISO 8601 datetime |
ClassSlot
| Field | Type | Constraints |
|---|---|---|
slotId | string | UUID |
dayOfWeek | number | integer, 0–6 |
startTime | string | regex HH:MM |
label | string | min 1, max 100 |
sessionDate | string (optional) | — |
status | SlotStatus | enum |
createdAt | string | ISO 8601 datetime |
updatedAt | string | ISO 8601 datetime |
ClassSession
| Field | Type | Constraints |
|---|---|---|
sessionId | string | UUID |
slotId | string | UUID |
sessionDate | string | regex YYYY-MM-DD |
createdAt | string | ISO 8601 datetime |
SessionOption (display helper)
| Field | Type |
|---|---|
sessionId | string (UUID) |
slotId | string (UUID) |
label | string |
sessionDate | string |
dayOfWeek | number (0–6) |
startTime | string |
Events and audit
AttendanceEvent
Attendance record (present/absent).
| Field | Type | Constraints |
|---|---|---|
eventId | string | UUID |
studentId | string | UUID |
classSessionId | string | UUID |
actionType | AttendanceActionType | enum |
actorId | string | UUID |
actorRole | string | — |
timestamp | string | ISO 8601 datetime |
syncState | SyncState | default "SYNCED" |
isConflictLoser | boolean | default false |
conflictSupersededBy | string (optional) | UUID |
StudentEvent
Audit event for student changes. Includes optional encryption for sensitive data.
| Field | Type | Constraints |
|---|---|---|
eventId | string | UUID |
studentId | string | UUID |
eventType | StudentEventType | enum |
actorId | string | UUID |
actorRole | string | — |
timestamp | string | ISO 8601 datetime |
changePayload | Record<string, unknown> | default {} |
justification | string (optional) | max 500 |
encryptedChangePayload | EncryptedPayload (optional) | — |
encryptedJustification | EncryptedPayload (optional) | — |
syncState | SyncState | default "SYNCED" |
isConflictLoser | boolean | default false |
UserEvent
Audit event for user changes.
| Field | Type | Constraints |
|---|---|---|
eventId | string | UUID |
userId | string | UUID |
eventType | UserEventType | enum |
actorId | string | UUID |
actorRole | string | — |
timestamp | string | ISO 8601 datetime |
changePayload | Record<string, unknown> | default {} |
encryptedChangePayload | EncryptedPayload (optional) | — |
syncState | SyncState | default "SYNCED" |
isConflictLoser | boolean | default false |
Offline sync
SyncQueueEntry
Entry in the offline → online sync queue.
| Field | Type | Constraints |
|---|---|---|
queueId | string | UUID |
eventId | string | UUID |
entityType | enum | "ATTENDANCE_EVENT" | "STUDENT_EVENT" | "USER_EVENT" |
actionType | string | min 1 |
actorId | string | UUID |
actorRole | string | — |
enqueuedAt | string | ISO 8601 datetime |
syncState | SyncState | default "PENDING" |
retryCount | number | integer ≥ 0, default 0 |
failureCode | string (optional) | — |
failureReason | string (optional) | — |
lastAttemptAt | string (optional) | ISO 8601 datetime |
Authentication and session
Session
Authenticated user session.
| Field | Type | Constraints |
|---|---|---|
sessionId | string | UUID |
userId | string | UUID |
role | string | — |
issuedAt | string | ISO 8601 datetime |
expiresAt | string | ISO 8601 datetime |
state | enum | "ACTIVE" | "EXPIRED" | "REVOKED" |
lastValidatedAt | string (optional) | ISO 8601 datetime |
backendRefreshToken | string (optional) | — |
csrfToken | string (optional) | — |
encryptedSessionSecrets | EncryptedPayload (optional) | — |
backendAuthMode | enum (optional) | "bearer" | "cookie" |
LocalUser
User stored locally (IndexedDB) for offline operation.
| Field | Type | Constraints |
|---|---|---|
userId | string | UUID |
username | string | min 1, max 100 |
email | string (optional) | |
displayName | string | min 1, max 140 |
passwordHash | string (optional) | — |
encryptedCredentials | EncryptedPayload (optional) | — |
cryptoKeyVersion | number (optional) | integer |
keyRotatedAt | string (optional) | ISO 8601 datetime |
role | string | — |
status | UserStatus | enum |
createdAt | string | ISO 8601 datetime |
createdBy | string | null | UUID or null |
updatedAt | string | ISO 8601 datetime |
deactivatedAt | string (optional) | ISO 8601 datetime |
deactivatedBy | string (optional) | UUID |
Other schemas
Role (dynamic role — v0.26.0+)
| Field | Type | Constraints |
|---|---|---|
name | string | min 1, max 50 |
displayName | string | min 1, max 100 |
permissions | string[] | — |
isSystem | boolean | default false |
createdAt | string | ISO 8601 datetime |
updatedAt | string | ISO 8601 datetime |
LocaleResource
Internationalization (i18n) resource.
| Field | Type | Constraints |
|---|---|---|
localeCode | string | min 2, max 10 |
key | string | min 1 |
translatedText | string | — |
Source: packages/schemas/src/entities.ts