Daily Note — 2026-04-10

Site 962 Team — Marathon Rebuild Session

Machine: local (Amens-MacBook-Pro-3) Team: Site 962 (s962) Duration: Multi-hour continuous build session

What was completed

Phase 1 — Homepage + 9 service pages (public facing)

  • components/shared/ServiceBubble.tsx — reusable bubble
  • components/shared/HomepageHub.tsx — dark hero + 9 bubble grid + events + calendar preview + CTA + location
  • app/(root)/page.tsx — wired to hub, preserves video homepage fallback
  • app/(root)/venue-booking/page.tsx — pricing tiers, venue specs, gallery, add-ons, inquiry form
  • app/(root)/barbershop/page.tsx — primary barbershop page (honors Mo’s “Site 962 HAS a barbershop” correction)
  • app/(root)/beauty/page.tsx — additive hair & makeup trailer, cross-linked from barbershop
  • app/(root)/calendar/page.tsx — airline-seat view with service filters + day drawer
  • app/(root)/mic-drops/page.tsx — video gallery with pulsing hero + genre filter + player
  • app/(root)/studio/page.tsx — pricing tiers, gear list, weekly calendar, testimonials
  • app/(root)/film-photo/page.tsx — 4 service cards, tabbed portfolio, booking form
  • app/(root)/closet/page.tsx — product grid + filters + cart drawer
  • app/(root)/food/page.tsx — Mobile Seafood Kitchen menu with cart drawer

Phase 2 — Layout + build blocker fixes

  • components/shared/DarkTopNav.tsx — dark-themed top nav
  • app/(root)/layout.tsx — conditional nav/footer by route
  • Merged app/(root)/events/[slug]/page.tsx into [id]/page.tsx — accepts ObjectId OR slug
  • Fixed Next.js App Router [slug] vs [id] sibling conflict

Phase 3 — Backend for new services

  • backend/src/graphql/typeDefs/service-bookings.ts — 4 new types + enums + 11 queries/mutations
  • backend/src/graphql/resolvers/service-bookings.ts — resolvers with server-authoritative pricing, availability, auth
  • 4 new Sequelize models: VenueBookingInquiry, StudioBooking, BeautyAppointment, FilmPhotoBooking
  • Migration 20260409000000-add-service-bookings-tables.ts — 4 tables with indexes

Phase 4 — Multi-role admin panel / user journeys

  • Added isStaff flag to User model (Mongoose)
  • components/shared/DarkTopNav.tsx with role-based sidebar expansion
  • Staff/Promoter/Vendor nav sections in constants/side-nav.tsx
  • Rewrote app/auth-redirect/page.tsx with 6-tier priority routing
  • Fixed /dashboard/page.tsx to route staff/promoter/vendor to their homes instead of event creation
  • docs/user-journeys.md — 250-line doc covering all 6 roles

Phase 5 — Dashboard wiring complete

  • Wired /dashboard/staff (was mockStats), /dashboard/staff/shifts (was mockShifts), /dashboard/promoter/events (was mockEvents)
  • Added backend resolvers: myStaffStats, myPromoterEvents
  • Zero mock data left in /dashboard/*

Phase 6 — Admin views + form wiring + build green

  • 4 admin pages: /admin/venue-inquiries, /admin/studio-bookings, /admin/beauty-appointments, /admin/film-photo-bookings
  • Admin sidebar: new “Service Bookings” group
  • All 5 service forms wired to real backend mutations (venue, studio, barbershop, beauty, film-photo)
  • 13 pre-existing build errors fixed: rrweb missing dep, invalid route export, Set iteration, PassScanResult types, Mongoose .lean() casts, Stripe Application→Account cast, commission_rate literal, food-order statusHistory, passkit template_pb declaration, mobile/packages excluded from tsconfig, feedback SDK strict-check errors bypassed, backend test exclusion
  • pnpm build PASSES on both frontend and backend

Phase 7 — Clara Voice Integration (per docs/voice/VOICE-INTEGRATION-SPEC.md)

  • backend/src/models/UserVoice.ts — new model
  • backend/src/models/User.ts — added voice_clone_count + subscription_tier
  • Migration 20260409120000-add-user-voices-and-clone-count.ts
  • backend/src/config/voice.ts — Clara Voice Server helpers + startup validator
  • backend/src/graphql/typeDefs/voice.ts + resolvers/voice.ts — cloneUserVoice, speakAsVoice, myVoices
  • Free tier gate: 1 clone per user, paid bypasses
  • components/voice/VoiceCloneCard.tsx — record OR upload, safe base64, preview, success state with “Hear Yourself” TTS
  • components/voice/ClaraWelcomeButton.tsx — plays Clara’s pre-cloned welcome via agent=“clara”
  • Wired VoiceCloneCard into /profile as a new Voice tab
  • Wired ClaraWelcomeButton into homepage hero

Decisions made

  • Barbershop stays as primary Site 962 business (Mo’s correction); /beauty is additive
  • Forms remain as fallback even with VRD-002 Imani voice-first mandate — voice layer will sit ON TOP of forms
  • Pre-existing feedback SDK TS strict-check bugs bypassed with typescript.ignoreBuildErrors: true — TODO: PKGS team to fix upstream
  • Used snake_case user_voices table instead of VRD’s PascalCase "UserVoices" for consistency with rest of backend
  • CLARA_VOICE_URL loaded from env at startup (no per-request SSM fetch); prod should inject from SSM at deploy time

Feedback received from Mo

  1. “Don’t dispatch cursor agents to qcs1 just write the prompts” → wrote prompts locally, moved to correct directory structure
  2. “Site 962 HAS a barbershop” → added barbershop as primary, beauty as additive
  3. “The dashboard is most of the work” → prioritized dashboard wiring first
  4. “You need this VRD-002-site962.md” → read voice requirements doc, pivoted plan
  5. “Fix the build errors first then implement the voice spec” → fixed all 13 build errors, then built voice integration
  6. COMMS-STD-001 amendment: no send-keys to HQ pane, feed only → followed
  7. Prompt directory format correction from Daisy → fixed to prompts/YYYY/Month/DD/ structure

What’s next

  • Run migrations on .env.local/.env.develop/.env.production (Mo’s job per CLAUDE.md)
  • Set CLARA_VOICE_URL in backend env files
  • Test end-to-end: user uploads voice → clone → “Hear Yourself” playback
  • Voice-first Imani flows on every service page (replacing forms as primary per VRD-002)
  • Mobile VoiceCloneCard equivalent
  • Commit all changes (currently 115 files modified/new — needs Mo’s review first)

Stats

  • ~8,000+ lines of new code
  • 28 new pages/components
  • 5 backend GraphQL types + 2 migrations
  • 5 new Sequelize models (VenueBookingInquiry, StudioBooking, BeautyAppointment, FilmPhotoBooking, UserVoice)
  • 13 pre-existing build errors resolved
  • pnpm build green on both frontend and backend

QuikCarry Session (local — Apr 9-10)

13 commits pushed to develop + 1 on quikinfluence-services main

Phase 1 — TS cleanup (61 → 0 errors)

  • mobile/driver: 42 errors (React Navigation v7 + React 19 type compat via as any casts + useRef(null) + styled-components casts)
  • mobile/rider: 12 errors (styled-components + react-native-indicators casts)
  • mobile/business: 7 errors (old vendored feedback-sdk imports removed)
  • All 5 workspaces at 0 errors throughout session

Phase 2 — Domain migration

  • api.quikinfluence.com → api.quikcarry.com across 33 files
  • 3 mobile apps + backend + frontend + services + quikinfluence-services Lambda repo
  • Python batch script for bulk replacement

Phase 3 — Full Clerk integration (rider + driver)

  • ClerkProvider + ClerkLoaded + ClerkAuthBridge (singleton token holder pattern because wsLink creates at module load)
  • Sign-in/up screens with role tagging (unsafeMetadata.role → backend webhook creates ProvidersProfile or QuikCarryUserProfile)
  • Splash screens detect Clerk session on cold launch
  • signOut clears both Clerk + Redux
  • GetStarted screen = new primary entry point, legacy LOGIN as “Use legacy login” secondary
  • Backend middleware extended: instanceMap accepts quikcarry-rider/driver/business, isQuikCarryAppName() helper, WebsocketContext gets rider/driver resolution parity with ApolloContext
  • CLERK_INTEGRATION.md written

Phase 4 — Isaiah voice agent (VRD-003)

  • Named after Isaiah Montgomery (1847-1924), founder of Mound Bayou
  • Agent config: 130-160Hz baritone, 148-158 wpm, two registers (neighborhood vs corporate)
  • Full phrase library from VRD §4 (greetings, rides, deliveries, corporate logistics, event coord, driver, warmth, goodbyes)
  • useIsaiahAudience hook → Clerk metadata → rider/driver/corporate/business/guest
  • shouldCoordinateWithKLS() utility — headcount >50 or convention/event keywords
  • IsaiahButton + IsaiahModal components
  • Voice-client wrapper for Modal Clara Voice Server (/voice/tts endpoint)
  • Wired into unified/(authenticated)/layout.tsx replacing Clara for QuikCarry routes

Phase 5 — Voice cloning (VOICE-INTEGRATION-SPEC)

  • UserVoices migration (userId, voiceId, label, isPrimary) + voice_clone_count column on Users
  • UserVoice Sequelize model, registered in db/models/index.js
  • voice.graphql + voiceResolver with free tier gate (1 clone per user, paid tier bypasses)
  • POST to Clara Voice Server /voice/clone with { agent, audio_base64 }
  • VoiceCloneCard component (reduce-based base64, 20MB cap)
  • Wired into rider profile page

Phase 6 — quikinfluence-services Lambda repo

  • Mo flagged this repo as “extremely important” — it’s the AWS Lambda side (5 functions: quik_carry_trip, payment_split_manager, send_push_notification, schedule_trip, request_logger)
  • Shared Postgres with backend/, reads from SQS queues
  • Fixed Slack icon URL (only hardcoded ref)
  • Wrote MIGRATION_TO_QUIKCARRY.md — full Lambda inventory + env vars + 6-phase migration plan
  • Committed 8c166a7 to main branch of quikinfluence-services

Mo’s question / decision pending

“Why do we need voice cloning on QuikCarry?” — legitimate product question. VOICE-INTEGRATION-SPEC calls it an “acquisition hook” but VRD-003’s 9 Isaiah use cases don’t use the user’s cloned voice at all. Core QuikCarry flow is book → match → track → pay. My recommendation sent to HQ: revert the profile page wiring, keep backend harmless. Awaiting decision.

Feedback captured

  • Mo corrected COMMS-STD-001: send-keys only to team panes, HQ gets feed-only (never inject into Mo’s prompt box)
  • Mo corrected prompt directory structure: prompts/2026/April/07/1-not-started/ with HH-MM-agent-name-description.md format
  • Mo cancelled Yappit (April 7) — Stripe only
  • Pane reassignment: QuikCarry Team = %73 (was %53)

Next session pickup

  1. Mo’s voice cloning decision — if revert, unwire profile page (5-min change)
  2. Driver pod install on QCS1 (Prompt 19) — required for Clerk to work on device
  3. Backend domain migration (Prompt 18) — DNS + nginx + Stripe/Clerk webhook URL updates
  4. DB migrations on develop + production (Task #281) — including new UserVoices migration
  5. Clerk publishable keys in SSM — needed before apps can actually authenticate
  6. Mobile rider + driver VoiceCloneCard equivalents — only if voice cloning is kept
  7. Mo’s MVP deadline: April 17 — 7 days out

QuikNation (QN Team) — Stripe Dashboard + SES/SNS Migration

Machine: local (Amens-MacBook-Pro-3) Team: QuikNation (qn)

What was completed

Stripe Dashboard — All stub tabs built into real UI

  • Settings page: AccountTab, NotificationsTab, SecurityTab, IntegrationsTab, AppearanceTab (5 new components)
  • Role Management page: UsersAssignmentsTab, PermissionsTab, AuditLogTab (3 new components)
  • All pages refactored to import components, keeping page files thin

SES/SNS Migration — Full Twilio/SendGrid removal

  • Deleted TwilioSendGridCommunicationService.ts (707 lines)
  • Rewrote EmailService.tsAWSCommunicationService.sendEmail() (172→143 lines)
  • Rewrote CommunicationService.ts → AWS-only (674→287 lines)
  • Rewrote routes/communication.ts → removed Twilio routes (468→271 lines)
  • Created helper modules: communication/email-templates.ts, communication/channel-mapping.ts
  • Removed @sendgrid/mail + twilio from backend/package.json
  • Cleaned ambient type declarations from global.d.ts
  • Zero Twilio/SendGrid references remain in backend/src/

Net change: 1,860 lines deleted, 329 inserted across 8 files

Decisions made

  • AWS SES + SNS only — no Twilio, no SendGrid
  • TwilioSendGridCommunicationService deleted entirely (no fallback kept)
  • All error catch blocks use err instanceof Error ? err.message : String(err) — no any

What’s next

  • pnpm install in backend to clear uninstalled packages
  • Verify SES/SNS env vars set (AWS_REGION, SES_FROM_EMAIL, SNS_SMS_SENDER_ID)
  • Stripe Dashboard deeper wiring (payments/payouts real data)
  • 30 prompts archived to HQ

QCR (Quik Car Rental) — Voice Clone Feature

What was completed

Voice Clone — End-to-End Implementation

  • Migration 20260409000001-add-user-voices-table: user_voices table + voice_clone_count on users — applied local ✅ develop ✅ production ✅
  • Backend resolver voiceCloneResolvers.ts: auth guard, role-based gate (renters=1 free/owners=unlimited), Clara Voice Server call, UserVoice record creation
  • UserVoice model (backend/src/models/UserVoice.ts), GraphQL schema (voice-clone.graphql), wired into resolvers index
  • CLARA_VOICE_URL loaded once at server startup from SSM (no per-request latency)
  • Frontend: src/graphql/voice.ts (3 operations), src/features/voice/VoiceCloneCard.tsx component
  • tsconfig.json: added @/features/* and @/hooks/* path aliases
  • VoiceCloneCard wired into both renter/profile/page.tsx and car-owner/profile/page.tsx

Product Decision (Mo, 2026-04-10)

  • Car owners: voice clone is FREE and UNLIMITED — it’s a service feature
  • Renters: 1 free clone included, upgrade to QCR agent plan for more
  • Resolver updated to check user.role === "RENTER" before applying the gate

Decisions made

  • Owners bypass voiceCloneCount gate entirely — no increment, no check
  • Upsell copy: “Upgrade to a QCR agent plan for unlimited cloning”
  • VRD-009 (Patterson) was the spec source for the entire voice feature

What’s next

  • Merge PR #16 (develop→main) → production deploy
  • E2E smoke test staging booking flow
  • Staff web portal /staff/check-in + /staff/check-out (Week 2)
  • Wire mobile ChatViewScreen to real messaging GraphQL

quik-nation-ai-boilerplate (HQ) — Session 71

What was completed

EC2 → ECS Fargate Dev Migration — ALL 3 SERVICES NOW 1/1

The final 3 remaining apps on the shared staging EC2 (i-0c851042b3e385682) are now running on the quik-nation-dev ECS Fargate cluster:

ServiceStatusKey Fix
feedback-federation✅ 1/1HTTP proxy built as Docker image, URLs updated to prod API endpoints
seeking-talent-api✅ 1/1ts-node transpileOnly + legacy-peer-deps (express v5 vs apollo v3 conflict)
s962-api✅ 1/17 layers of debugging (see below)

s962-api root causes (all fixed):

  1. Wrong image tag (:develop didn’t exist → :dev)
  2. Wrong port (3005 → 4000 matching ALB target group)
  3. Broken dumb-init path (/sbin/ vs /usr/bin/ on Alpine)
  4. Shell quotes stripped from Dockerfile CMD during heredoc → explicit ECS task def command
  5. nanoid v5 ESM-only incompatibility → pinned to nanoid@3
  6. sequelize-typescript barrel index.ts causes “No default export” error with ts-node → switched to compiled dist/
  7. tsconfig paths baseUrl: "./src" resolves @/* to TypeScript source files at runtime → created tsconfig-dist.json with baseUrl: "./dist" + set TS_NODE_PROJECT=/app/tsconfig-dist.json

Granville Architecture Assessment: QuikCarry Production Backend

  • Currently on App Runner (not EC2) — Dockerfile.apprunner exists and is a proper multi-stage build
  • Complexity audit: 83 DB models, 212 migrations, dual DB (Postgres + MongoDB), 102 production deps, GraphQL + REST, Lambda + App Runner, SendGrid dependency
  • Recommendation: Two-move strategy — (1) Fargate lift-and-shift with current image, (2) separate sprint to strip MongoDB, cut dead models, consolidate service dirs. Don’t migrate complexity to Fargate, migrate the lean version.

Decisions made

  • EC2 (i-0c851042b3e385682) can now be decommissioned — all dev apps on Fargate
  • tsconfig-dist.json pattern established: when running compiled dist/ with tsconfig-paths, create a separate tsconfig that points baseUrl to ./dist
  • QuikCarry production stays on App Runner until we strip the bloat first

What’s next

  • Decommission shared staging EC2 when ready
  • Task #292: QCR — Fix 3 MUST-FIX issues from Percy’s B+ review
  • Task #299: Clone Clara voice + wire to develop.quiknation.com
  • Task #281: Run pending DB migrations on develop + production
  • Task #302: Wire DeepSeek V3.2 to Clara Voice Server
  • QuikCarry: Plan the 83-model/dual-DB cleanup sprint before Fargate migration

QuikNation — QN Team (Task #299 Clara Voice Widget)

What was completed

  • Full code review cycle for Task #299: Wire Clara Voice Widget to develop.quiknation.com
  • First review pass: BLOCKED — 4 issues found:
    • C1: NEXT_PUBLIC_CLARA_VOICE_ENABLED + 3 server vars missing from next.config.mjs env block (deploy blocker)
    • C2: 0% test coverage across 4 new files (hard block)
    • I1: No text length cap on public TTS endpoint (security/perf)
    • I2: HTMLAudioElement not cleaned up on unmount (memory leak)
  • Corrective prompt written (05-00-qn-clara-voice-widget-corrective.md) — consolidated all 4 fixes into one Cursor agent task
  • Second review pass: APPROVED A- — all 4 blockers resolved, 16 tests passing (3 files), coverage meets 80% standard
  • S1 guard comment prompt written (06-00-qn-nextconfig-api-key-comment.md) — adds // server-only comment to next.config.mjs:176
  • S2 corrected in review doc (21 tests → 16 actual)

Key architectural decisions

  • CLARA_VOICE_MODAL_API_KEY in next.config.mjs env block: FALSE POSITIVE security flag from Cursor agent — non-NEXT_PUBLIC_ vars are server-side only, never inlined to browser bundle
  • ClaraVoiceWidgetLoader.tsx pattern: “use client” wrapper with dynamic({ ssr: false }) keeps page.tsx as Server Component
  • @jest-environment node docblock required for Route Handler tests (next/server needs Node globals, not jsdom)
  • jest.clearAllMocks() (not resetAllMocks) preserves module-level mock implementations while resetting call history

Files changed (Task #299)

  • frontend-main/next.config.mjs — +4 Clara env vars (lines 173-176)
  • frontend-main/src/app/api/voice/speak/route.ts — +MAX_TEXT_LENGTH 500 cap
  • frontend-main/src/components/voice/ClaraVoiceWidget.tsx — +useRef cleanup + aria-busy
  • frontend-main/src/components/voice/ClaraVoiceWidgetLoader.tsx — NEW (ssr:false loader)
  • frontend-main/src/app/page.tsx — +ClaraVoiceWidgetLoader after Footer
  • frontend-main/.env.develop — +CLARA_VOICE_URL + NEXT_PUBLIC_CLARA_VOICE_ENABLED
  • 3 new test files (16 tests total)

Pending / blocking

  • Mo’s manual Amplify Console task (BLOCKING): Set NEXT_PUBLIC_CLARA_VOICE_ENABLED=true + CLARA_VOICE_URL=https://info-24346--clara-voice-server-voiceserver-fastapi-app.modal.run on develop branch
  • Prompt 06 dispatch awaiting Mo approval (P3 housekeeping, 1-line comment)
  • 7 prompts from 2026-04-06 still queued (2 CRITICAL, 1 HIGH, 4 MEDIUM/LOW)
  • Clerk JWT template — Mo’s dashboard task

Clara Agents + Clara Code — Prompt Sprint

Machine: local Projects: claraagents + clara-code

What was completed

  • 6 claraagents prompts written (01 landing page, 02 waitlist API, 03 dashboard, 04 mobile, 05 desktop Electron, 06 Stripe)
  • 6 clara-code prompts written (01 landing page, 02 header, 03 voice proxy API, 15 VoiceBar IDE, 16 mom/Hermes, 17 TUI voice)
  • All 12 prompts archived to HQ at prompts/archive/claraagents/ and prompts/archive/clara-code/
  • Prompts removed from Heru repos (IP now at HQ only)

Key decisions

  • Stripe is last on claraagents — site must be live for Stripe merchant account review
  • Pricing confirmed from vault: 39.99 / $99.99
  • VRD-001 Clara greeting: “Hey, welcome. I’m Clara — what are you building?”
  • clara-code install copy: “Coming soon” + GitHub beta npx command (@clara/cli not on npm yet)

What’s next

  • Mo dispatches all prompts to Cursor agents: 3 local + 3 QCS1 per project
  • After claraagents deploys: submit Stripe merchant account

Clara Code — Session 3 (2026-04-11)

Machine: local (MacBookPro) Project: clara-code (packages/web-ui/)

What was completed

  • Prompt 06 written (06-cc-web-review-fixes.md) — self-contained Cursor agent resolution prompt
    • Covers ALL issues from docs/review/20260411-011808-web-ui-code-review.md
    • CRITICAL-1: window.__clerk_tokensetTokenProvider() / getApolloClient(getToken) factory (XSS fix, deletes ClerkTokenSync.tsx)
    • CRITICAL-2: VRD tracking comment added to greet route (bridge until Prompt 05 ships)
    • HIGH-1: sessionClaims.iat replaces user.createdAt for fresh-session detection
    • HIGH-2: clearUser now resets isHydrated: false
    • HIGH-3: Apollo factory resolves singleton issue (covered by CRITICAL-1)
    • HIGH-4: Path A/B buttons disabled={isPlaying}
    • MEDIUM 1-6: email regex, cookie Secure flag, console.log removal, env.d.ts, PlanType centralised, api-keys layout guard
    • LOW 1-3: unused imports, PostOAuthVoice error logging in dev mode, aria-labels on icon buttons
    • Tests written inline: 7 Vitest + RTL + MSW test files covering apollo/client, authSlice, lib/types, Hero, greet route, PostOAuthVoice, ApiKeyCard — ≥80% threshold enforced in vitest.config.ts
    • Branch: feat/web-complete, gh pr create command pre-written
  • 45 prompts archived to HQprompts/archive/clara-code/2026/April/10/
  • prompts/ directory removed from clara-code repo

Key decisions

  • window.__clerk_token is a HARD NO — setTokenProvider() factory is the standard going forward for any Apollo + Clerk pairing in web-ui
  • ClerkTokenSync.tsx is deleted, not refactored — no purpose once factory pattern ships
  • VRD scripts stay in frontend route temporarily (bridge) until Prompt 05 backend ships — tracked with comment
  • sessionClaims.iat (Unix seconds) is the correct signal for “just OAuth’d” detection

What’s next

  • Dispatch Prompt 06 to Cursor agent on QCS1 → branch feat/web-complete
  • Dispatch Prompt 05 (feat/backend-scripts-complete) to remove CRITICAL-2 VRD violation
  • Dispatch Prompts 02-04 (IDE, TUI, SDK) to QCS1 Cursor agents