User Profile & Settings API Spec
Version: 1.0.0 Last Reviewed: 2026-02-18
Overview
Endpoints for reading and updating the authenticated user's profile and settings. The primary setting exposed at MVP is day_start_time, which controls where the "today" boundary falls for dashboard aggregation.
Endpoints
GET /api/v1/users/me
Returns the current authenticated user's profile and settings.
Auth: Bearer token required
Response 200:
{
"user": {
"id": "550e8400-e29b-41d4-a716-446655440000",
"email": "user@example.com",
"name": "Parent Name",
"timezone": "America/New_York",
"day_start_time": "07:00",
"created_at": "2026-01-01T00:00:00.000Z"
}
}
Response 401: Missing or invalid auth token
{
"error": {
"code": "UNAUTHORIZED",
"message": "Missing or invalid authorization header",
"details": []
}
}
PUT /api/v1/users/me
Updates the current authenticated user's profile and/or settings. All fields are optional — only provided fields are updated (partial update).
Auth: Bearer token required
Request Body:
{
"name": "New Name",
"timezone": "America/Chicago",
"day_start_time": "06:00"
}
Field Constraints:
| Field | Type | Constraints |
|---|---|---|
name | string | Optional. 1–100 chars, trimmed. |
timezone | string | Optional. 1–50 chars (IANA tz string, e.g. America/New_York). Server does not validate IANA format at MVP. |
day_start_time | string | Optional. HH:MM format (00:00–23:59). Controls where the "today" boundary falls. |
Response 200:
{
"user": {
"id": "550e8400-e29b-41d4-a716-446655440000",
"email": "user@example.com",
"name": "New Name",
"timezone": "America/Chicago",
"day_start_time": "06:00",
"created_at": "2026-01-01T00:00:00.000Z"
}
}
Response 400 (validation error):
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Validation failed",
"details": [
{
"field": "day_start_time",
"message": "Must be HH:MM format",
"code": "invalid_string"
}
]
}
}
Response 401: Missing or invalid auth token
Data Storage
The day_start_time field is stored in PostgreSQL as a TIME type via @db.Time(). Prisma represents this as a DateTime (using the epoch date 1970-01-01). Conversion:
- Read: Extract
HH:MMfrom the storedDateTimeusing.toISOString().substring(11, 16) - Write: Convert
HH:MMstring tonew Date("1970-01-01T${time}:00Z")
Audit Log
PUT /api/v1/users/me writes an AuditLog entry:
{
"entity_type": "user",
"entity_id": "<user-id>",
"action": "update",
"changes": { "name": "New Name" }
}
Only changed fields are included in changes.
day_start_time Semantics
The day_start_time setting defines when "today" starts for the dashboard. A value of 07:00 means:
- Today's data spans from
07:00 AMto06:59:59 AMthe next day - This aligns with typical family wake-up schedules
The dashboard already reads this field from the user record. No additional changes are required to the dashboard service when this value is updated — it is read dynamically on each request.