Event Participant
Data Entity
Description
Join record tracking which users are registered for a given event, including sign-up status, proxy registrations by coordinators, and attendance confirmation. Enforces per-event capacity and duplicate-registration constraints.
Data Structure
| Name | Type | Description | Constraints |
|---|---|---|---|
id |
uuid |
Surrogate primary key | PKrequiredunique |
event_id |
uuid |
Foreign key to the events table. Identifies which event this participation record belongs to. | required |
user_id |
uuid |
Foreign key to the users table. Identifies the peer mentor or coordinator who is participating. | required |
registered_by_user_id |
uuid |
Foreign key to users. Populated when a coordinator registers this participant on their behalf (proxy sign-up). NULL if the user self-registered. | - |
status |
enum |
Current registration state for this participant. | required |
is_proxy_registration |
boolean |
True when a coordinator registered this participant on their behalf. Denormalised from registered_by_user_id for fast query filtering. | required |
signed_up_at |
datetime |
Timestamp (UTC) when the registration record was created. | required |
cancelled_at |
datetime |
Timestamp (UTC) when the participant cancelled their registration. NULL if not cancelled. | - |
attended_at |
datetime |
Timestamp (UTC) when attendance was confirmed post-event. NULL until marked by coordinator. | - |
waitlist_position |
integer |
Position in the waitlist queue when status is 'waitlisted'. NULL for directly registered participants. | - |
notes |
text |
Optional free-text notes about this participant's registration (e.g. dietary needs, accessibility requirements). | - |
organization_id |
uuid |
Tenant isolation key. Matches the organization of the event. Enables org-scoped queries without joining to events. | required |
created_at |
datetime |
Row creation timestamp (UTC). Identical to signed_up_at for self-registrations; may differ for data migrations. | required |
updated_at |
datetime |
Row last-modified timestamp (UTC). Updated on any status change. | required |
Database Indexes
idx_event_participants_event_user
Columns: event_id, user_id
idx_event_participants_event_id
Columns: event_id
idx_event_participants_user_id
Columns: user_id
idx_event_participants_org_status
Columns: organization_id, status
idx_event_participants_registered_by
Columns: registered_by_user_id
Validation Rules
event_id_must_exist
error
Validation failed
user_id_must_exist
error
Validation failed
registered_by_must_exist
error
Validation failed
valid_status_transition
error
Validation failed
cancelled_at_required_on_cancel
error
Validation failed
waitlist_position_positive
error
Validation failed
notes_length
error
Validation failed
Business Rules
no_duplicate_registration
A user may hold at most one active (non-cancelled) registration per event. Enforced by the unique index on (event_id, user_id) and a pre-insert check in the service layer.
capacity_enforcement
When an event has a max_capacity set, new registrations that would exceed capacity are automatically placed in status 'waitlisted' rather than rejected.
no_signup_after_event_start
Registrations are rejected if the event start_datetime has already passed. Coordinators with proxy-registration permission may override this for late administrative corrections.
waitlist_auto_promotion
When a registered participant cancels, the first waitlisted participant (lowest waitlist_position) is automatically promoted to status 'registered' and notified via push.
proxy_requires_coordinator_role
Setting registered_by_user_id to a different user than user_id is only permitted when the requesting user holds the Coordinator role within the same organization.
attendance_only_post_event
attended_at may only be set after the event's scheduled start_datetime has passed. Prevents premature attendance marking.
org_scoped_registration
A participant may only be registered for events belonging to an organization they are a member of. Prevents cross-tenant registration.