Skip to content

feat: paginated notification inbox API with cursor pagination and seed data#1075

Closed
Chucks1093 wants to merge 29 commits into
StreamFi-x:mainfrom
Chucks1093:feat/issue-999-1003-1006-1014
Closed

feat: paginated notification inbox API with cursor pagination and seed data#1075
Chucks1093 wants to merge 29 commits into
StreamFi-x:mainfrom
Chucks1093:feat/issue-999-1003-1006-1014

Conversation

@Chucks1093

Copy link
Copy Markdown
Contributor

Closes #999
Closes #1003
Closes #1006
Closes #1014

What was done

GET /api/routes-f/notifications

A new paginated notification inbox endpoint for StreamFi viewers.

Query parameters:

Param Type Default Description
viewer_id string required The viewer's identifier
limit number 20 Items per page (1–100)
cursor string Notification id to start after (exclusive)

Response shape:

{
  "items": [
    {
      "id": "n_001",
      "type": "tip_received",
      "body": "CryptoKing tipped you 5 XLM during your last stream.",
      "link": "/dashboard/tips",
      "read": false,
      "created_at": "2026-06-26T10:00:00Z"
    }
  ],
  "next_cursor": "n_005",
  "unread_count": 3
}
  • items — sorted newest-first; length ≤ limit
  • next_cursor — the id of the last item on this page; null when no further pages exist
  • unread_count — total unread notifications across all pages for this viewer (not just the current page)

Notification types supported: tip_received, new_subscriber, stream_live, clip_featured, payment_confirmed, system

Validation: missing/empty viewer_id → 400; limit outside 1–100 → 400; validated via the shared validateQuery / Zod helper

app/api/routes-f/notifications/_lib/seed.ts

In-memory seed data keyed by viewer_id:

  • viewer_001 — 12 notifications (3 unread), covering all 6 notification types
  • viewer_002 — 3 notifications (2 unread)
  • Unknown viewers return an empty array

app/api/routes-f/notifications/__tests__/route.test.ts

17 unit tests covering:

  • Input validation (missing viewer_id, empty string, limit out of range)
  • Unknown viewer → empty response
  • Pagination (page 1, page 2, last page, exhausted cursor)
  • unread_count is the full-viewer total regardless of current page
  • Newest-first ordering
  • Full response shape / field type checks

Josue19-08 and others added 29 commits March 24, 2026 23:58
Implement full moderation system including:
- Ban/timeout users with duration options (1m, 5m, 10m, 1h, permanent)
- Delete messages with context menu
- Slow mode (3s, 5s, 10s, 30s intervals)
- Follower-only chat mode
- Link blocking with URL regex detection
- Active bans management panel

Database changes:
- Add chat_bans table with expires_at for timeouts
- Add slow_mode_seconds, follower_only_chat, link_blocking to users table

API endpoints:
- POST /api/streams/chat/ban - ban/timeout users
- DELETE /api/streams/chat/ban/[username] - unban users
- GET /api/streams/chat/ban - list active bans
- PATCH /api/streams/settings - update chat settings
- Updated POST /api/streams/chat with enforcement logic

UI components:
- Right-click context menu on chat messages (stream owner only)
- ChatModerationSettings panel in stream manager
- Ban list with unban functionality
- Settings toggles for follower-only and link blocking

Enforcement:
- Server-side validation for all moderation rules
- 429 responses with Retry-After headers for timeouts
- Clear error messages for banned/timed-out users
- Add mocks for permanent ban check
- Add mocks for timeout check
- Add mocks for slow mode validation
- Update combined lookup to include moderation settings
- Remove slow mode mock when slow_mode_seconds is 0
- Add streamer_id to combined lookup mock
…ration

feat: Chat Moderation Tools for Streamers
Keep both StreamAccessSettings (access-control) and ChatModerationSettings
(dev) in stream manager page, and combine index definitions in schema.sql.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…l-foundation

Feat/access control foundation
setStreamData was called without accessType and accessConfig, causing
a TS error and silently dropping access-control settings on save.
Use a functional state update to spread existing state.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Covers POST and GET handlers across all three import sources
(twitch, youtube, json). Includes edge cases for:
- invalid source / missing data fields
- user rate limit (24h) and DB errors
- overwrite_existing flag behaviour
- social_links and categories field mapping
- twitch token never persisted to DB
- youtube ssrf guard
- job status polling

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Three pre-existing errors unrelated to the import api:
- app/api/users/[username]/route.ts: password_hash destructured
  intentionally to omit it — suppress no-unused-vars
- StreamAccessSettings.tsx: add curly braces to if statements
- view-stream.tsx: add curly brace to if statement; suppress
  no-unused-vars on isCheckingAccess (set but never read)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Replace chained .replace() calls in decodeHTMLEntities with a
  single-pass regex to prevent double-unescaping (CodeQL high alert)
- Add eslint-disable-next-line on stub functions in lib/stream/access.ts
  where _-prefixed params are intentionally unused pending future issues
- Run prettier on files that had format drift

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
feat(routes-f): data import api for onboarding from other platforms
…ations-system

feat: add realtime notifications system
…on, and background jobs API

- Issue StreamFi-x#405: Shared Zod validation layer (_lib/validate.ts, _lib/schemas.ts) with validateBody/validateQuery helpers; dev-only /validate testing endpoint; import/route.ts refactored to use shared validators
- Issue StreamFi-x#399: Username conflict resolution API (check availability + suggestions, reserved/banned word list, admin dispute resolution with atomic DB transaction)
- Issue StreamFi-x#396: Background jobs API (enqueue, poll status, cancel) with cron processor, exponential backoff retry, 30-day auto-cleanup; DB migration for jobs table
Implements GET /api/routes-f/notifications with cursor-based pagination,
per-viewer seed data, and full unit test coverage.
@netlify

netlify Bot commented Jun 26, 2026

Copy link
Copy Markdown

👷 Deploy request for streamfi pending review.

Visit the deploys page to approve it

Name Link
🔨 Latest commit f4eec76

@vercel

vercel Bot commented Jun 26, 2026

Copy link
Copy Markdown

@Chucks1093 is attempting to deploy a commit to the david's projects Team on Vercel.

A member of the Team first needs to authorize it.

@github-actions

Copy link
Copy Markdown

Hi @Chucks1093 — thanks for the contribution!

This repo uses dev as the integration branch. PRs targeting main are not accepted.

Please re-open this PR against dev instead. From your branch:

  1. Click Edit on this PR title area
  2. Change the base branch from main to dev

Or open a fresh PR from the GitHub UI with dev selected as the base.

@github-actions github-actions Bot closed this Jun 26, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants