Use the original UID format consistently across API, username, and store validation so UUID-based callers continue to work. Regenerate API documentation and add regression coverage for UUID memo IDs.
Validate new user-provided IDs using the AIP-122 format while retaining legacy UID compatibility. Correct resource annotations and canonical names returned by user stats.
Rework ListUsers to match the ListMemos pagination contract: opaque
PageToken, normalizePageSize, DB-level limit+1 look-ahead, and a
next_page_token. Adds Offset to store.FindUser with an OFFSET clause in
all three dialects, and an `id DESC` ORDER BY tiebreaker so offset pages
stay stable when created_ts ties.
Also align pagination across list endpoints:
- Bump DefaultPageSize 10 -> 50 to match the documented default; use
normalizePageSize in ListAttachments.
- Remove the never-implemented total_size field from all six list
responses (ListUsers, ListAttachments, ListMemoComments,
ListMemoReactions, ListUserSettings, ListPersonalAccessTokens) and
regenerate.
- useListUsers now pages through next_page_token so the admin members
view still loads every user past the default page size.
Migrates attachment and avatar binary serving from gRPC endpoints to a new dedicated HTTP fileserver package, fixing Safari video playback issues and improving architectural separation.
Key changes:
- Created server/router/fileserver package for all binary file serving
- Removed GetAttachmentBinary and GetUserAvatar gRPC endpoints from proto
- Implemented native HTTP handlers with full range request support
- Added authentication support (session cookies + JWT) to fileserver
- New avatar endpoint supports lookup by user ID or username
- Eliminated duplicate auth constants (imports from api/v1)
HTTP endpoints:
- Attachments: /file/attachments/:uid/:filename (unchanged URL)
- Avatars: /file/users/:identifier/avatar (new URL format)
This fixes Safari video/audio playback by using http.ServeContent() which properly handles HTTP 206 Partial Content responses and range request headers.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>