New GET /events/{token}/attendees endpoint returns attendee names when
a valid organizer token is provided (403 otherwise). The frontend
conditionally renders the list below the attendee count for organizers,
silently degrading for visitors.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
73 lines
2.3 KiB
Markdown
73 lines
2.3 KiB
Markdown
# Data Model: View Attendee List (011)
|
|
|
|
**Date**: 2026-03-08
|
|
|
|
## Entities
|
|
|
|
### Rsvp (existing — no schema changes)
|
|
|
|
The attendee list feature reads from the existing `rsvps` table. No new tables or columns are required.
|
|
|
|
| Field | Type | Constraints | Notes |
|
|
|-------|------|-------------|-------|
|
|
| id | BIGSERIAL | PK, auto-increment | Chronological order proxy |
|
|
| rsvp_token | UUID | UNIQUE, NOT NULL | Public identifier |
|
|
| event_id | BIGINT | FK → events.id, NOT NULL | CASCADE DELETE |
|
|
| name | VARCHAR(100) | NOT NULL | Display name shown to organizer |
|
|
|
|
**Existing indexes**: `idx_rsvps_event_id` (on `event_id`), `idx_rsvps_rsvp_token` (on `rsvp_token`).
|
|
|
|
### Event (existing — no schema changes)
|
|
|
|
The `organizer_token` column on the `events` table is used for authorization. The endpoint verifies that the provided organizer token matches the event's stored token.
|
|
|
|
| Field | Type | Notes |
|
|
|-------|------|-------|
|
|
| organizer_token | UUID | UNIQUE, NOT NULL — used for attendee list authorization |
|
|
|
|
## Query Patterns
|
|
|
|
### Get attendees by event token
|
|
|
|
```sql
|
|
SELECT r.name
|
|
FROM rsvps r
|
|
JOIN events e ON r.event_id = e.id
|
|
WHERE e.event_token = :eventToken
|
|
ORDER BY r.id ASC;
|
|
```
|
|
|
|
**Performance**: Uses existing `idx_rsvps_event_id` index. Expected result set is small (spec assumes small-to-medium events, no pagination needed).
|
|
|
|
### Organizer token verification
|
|
|
|
```sql
|
|
SELECT e.organizer_token
|
|
FROM events e
|
|
WHERE e.event_token = :eventToken;
|
|
```
|
|
|
|
Already implemented in `EventService.getByEventToken()` — the event entity includes the organizer token. The use case compares the provided token against the stored one.
|
|
|
|
## Domain Model Changes
|
|
|
|
### New Outbound Port Method
|
|
|
|
```java
|
|
// RsvpRepository (existing interface)
|
|
List<Rsvp> findByEventId(Long eventId); // NEW
|
|
```
|
|
|
|
### New Inbound Port
|
|
|
|
```java
|
|
// GetAttendeesUseCase (new interface)
|
|
List<String> getAttendeeNames(EventToken eventToken, OrganizerToken organizerToken);
|
|
```
|
|
|
|
Returns a list of attendee display names. Throws `EventNotFoundException` if event token is invalid. Throws `AccessDeniedException` (or similar) if organizer token does not match.
|
|
|
|
## No Migration Required
|
|
|
|
All required data structures already exist from changeset `003-create-rsvps-table.xml`. This feature only adds read access to existing data.
|