Event Registration
Data Entity
Description
Records a user's registration for a specific event, supporting both self-registration and coordinator-proxy registration on behalf of another user. Tracks registration lifecycle (pending, confirmed, cancelled, waitlisted) and enforces capacity limits and organisational scoping.
Data Structure
| Name | Type | Description | Constraints |
|---|---|---|---|
id |
uuid |
Primary key — globally unique identifier for the registration record | PKrequiredunique |
event_id |
uuid |
Foreign key referencing the event being registered for | required |
user_id |
uuid |
Foreign key referencing the user who is attending the event (the actual attendee, not necessarily who performed the registration action) | required |
registered_by_user_id |
uuid |
Foreign key referencing the user who performed the registration action. Equals user_id for self-registration; equals coordinator's user ID for proxy registrations. | required |
registration_type |
enum |
Whether the user registered themselves or was registered by a coordinator acting as proxy | required |
status |
enum |
Lifecycle state of the registration | required |
organisation_id |
uuid |
Tenant scoping — organisation context inherited from the event at registration time, used for multi-tenant query isolation | required |
notes |
text |
Optional free-text notes attached by the registrant or coordinator at registration time (e.g. dietary requirements, accessibility needs) | - |
cancellation_reason |
text |
Optional reason provided when a registration is cancelled. Required when status transitions to 'cancelled' via coordinator action. | - |
cancelled_at |
datetime |
Timestamp when the registration was cancelled. NULL if not cancelled. | - |
waitlist_position |
integer |
Ordinal position in the waitlist when status is 'waitlisted'. NULL for non-waitlisted registrations. Used to auto-promote to 'confirmed' when a slot opens. | - |
created_at |
datetime |
Timestamp when the registration record was created | required |
updated_at |
datetime |
Timestamp when the registration record was last modified | required |
Database Indexes
idx_event_registration_event_user
Columns: event_id, user_id
idx_event_registration_event_id
Columns: event_id
idx_event_registration_user_id
Columns: user_id
idx_event_registration_organisation_id
Columns: organisation_id
idx_event_registration_status
Columns: event_id, status
idx_event_registration_waitlist
Columns: event_id, waitlist_position
Validation Rules
event_id_must_exist
error
Validation failed
user_id_must_exist
error
Validation failed
event_must_not_be_in_past
error
Validation failed
status_transition_validity
error
Validation failed
waitlist_position_required_when_waitlisted
error
Validation failed
cancelled_at_consistency
error
Validation failed
registration_type_enum_value
error
Validation failed
Business Rules
no_duplicate_registration
A user may only register once per event. The unique index on (event_id, user_id) enforces this at the database level. Attempting a duplicate registration must return a clear error message rather than silently failing.
capacity_enforcement
A new confirmed registration is only created if the event has available capacity (current confirmed registrations < event.max_capacity). When capacity is full, incoming registrations are placed on the waitlist and assigned a waitlist_position.
proxy_registration_requires_coordinator_role
A registration with registration_type='proxy' may only be submitted by a user holding the Coordinator or Org Admin role. registered_by_user_id must differ from user_id. The backend validates the JWT role claim before persisting.
organisation_scope_isolation
The attending user (user_id) and the event (event_id) must belong to the same organisation. The organisation_id column on the registration must match the event's organisation_id to prevent cross-tenant data leakage.
waitlist_auto_promotion
When a confirmed registration is cancelled, the first waitlisted registration for that event (lowest waitlist_position) is automatically promoted to 'confirmed' and its waitlist_position set to NULL. Remaining waitlisted registrations are not renumbered.
cancellation_requires_reason_for_coordinator_action
When a coordinator cancels a registration on behalf of another user (registered_by_user_id != user_id), a cancellation_reason must be provided and persisted alongside the status transition.
optimistic_state_rollback_on_failure
The mobile client applies an optimistic pending state immediately on registration action. If the backend returns an error (capacity exceeded, duplicate, auth failure), the Event Registration Store rolls back to the prior RegistrationState.