candle-annotator/openspec/specs/user-data-isolation/spec.md
Marko Djordjevic 448b67199f Sync user-accounts delta specs to main specs
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-20 18:50:14 +01:00

4.6 KiB

ADDED Requirements

Requirement: User-scoped chart creation

When a chart is created (via CSV upload), the system SHALL associate it with the authenticated user's ID. The charts table row SHALL have user_id set to the current user's UUID.

Scenario: Upload creates user-scoped chart

  • WHEN an authenticated user uploads a CSV file
  • THEN the created chart record has user_id set to the authenticated user's ID

Scenario: User sees only their charts

  • WHEN an authenticated user requests their chart list
  • THEN only charts with user_id matching the authenticated user are returned

Requirement: User-scoped annotations

All annotation operations (create, read, delete) SHALL be filtered by the authenticated user's ID. Annotations SHALL only be visible to the user who created them.

Scenario: Create annotation scoped to user

  • WHEN an authenticated user creates an annotation
  • THEN the annotation record has user_id set to the authenticated user's ID

Scenario: Read annotations filtered by user

  • WHEN an authenticated user requests annotations for a chart
  • THEN only annotations belonging to that user (and that chart) are returned

Scenario: Delete annotation ownership check

  • WHEN an authenticated user attempts to delete an annotation
  • THEN the deletion only succeeds if the annotation belongs to the authenticated user

Requirement: User-scoped span annotations

All span annotation operations SHALL be filtered by the authenticated user's ID via the chart's user_id.

Scenario: Create span annotation scoped to user

  • WHEN an authenticated user creates a span annotation on their chart
  • THEN the span annotation is created and associated with the user's chart

Scenario: Read span annotations filtered by user

  • WHEN an authenticated user requests span annotations
  • THEN only span annotations on charts belonging to that user are returned

Requirement: User-scoped annotation types

Each user SHALL have their own set of annotation types. The annotation_types table SHALL be filtered by user_id. The unique constraint on name SHALL be changed to a composite unique constraint on (user_id, name).

Scenario: User-specific annotation types

  • WHEN an authenticated user requests their annotation types
  • THEN only annotation types with user_id matching the authenticated user are returned

Scenario: Two users with same annotation type name

  • WHEN two different users each create an annotation type named "break_up"
  • THEN both records are stored without conflict (unique per user, not globally)

Requirement: User-scoped span label types

Each user SHALL have their own set of span label types. The span_label_types table SHALL be filtered by user_id. The unique constraint on name SHALL be changed to a composite unique constraint on (user_id, name).

Scenario: User-specific span label types

  • WHEN an authenticated user requests their span label types
  • THEN only span label types with user_id matching the authenticated user are returned

Requirement: Default data seeding on registration

When a new user registers, the system SHALL seed default annotation types and span label types for that user. The defaults SHALL include: annotation types break_up (green, marker), break_down (red, marker), line (blue, line); and a starter set of span label types.

Scenario: New user gets default annotation types

  • WHEN a new user is created (via registration or first Google sign-in)
  • THEN default annotation types (break_up, break_down, line) are inserted with the new user's ID

Scenario: New user gets default span label types

  • WHEN a new user is created
  • THEN default span label types are inserted with the new user's ID

Requirement: ML service user context

When the Next.js API proxies requests to the FastAPI ML service, it SHALL include the X-User-ID header with the authenticated user's UUID. The ML service SHALL use this header to scope training runs, model storage, and experiments.

Scenario: Training request includes user ID

  • WHEN an authenticated user starts a training run via /api/training/start
  • THEN the proxy request to FastAPI includes X-User-ID: <user-uuid> header

Scenario: Prediction request includes user ID

  • WHEN an authenticated user requests prediction via /api/predict
  • THEN the proxy request to FastAPI includes X-User-ID: <user-uuid> header

Scenario: ML service scopes by user

  • WHEN the FastAPI service receives a request with X-User-ID header
  • THEN training runs and model lookups are scoped to that user ID