Javis OS
Javis OS는 기업가를 돕는 에이전시 AI로, 업무를 지원하고 함께 성장합니다
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
개인 계정의 공개 저장소 소유자는 GitHub로 로그인해 운영자를 확인하고 소개를 직접 관리할 수 있습니다. 관리자 승인은 필요하지 않습니다.
로그인한 뒤 확인 파일을 만들어 이 저장소의 기본 브랜치에 30분 안에 커밋해 주세요. 다른 브랜치나 포크의 파일은 인정하지 않습니다. 파일을 올린 뒤 아래에서 확인하면 관리자 승인 없이 관리할 수 있습니다. 자격을 유지하려면 파일을 남겨 두세요.
로그인이 필요하면 로그인 화면으로 이동합니다. 로그인 후 이곳으로 돌아와 원하는 확인 버튼을 다시 눌러 주세요.
프로젝트 폴더에서 /nomorevibe verify를 실행하면 소유권을 확인하고 소개를 직접 관리할 수 있습니다.
1분 만에 확인하기메이커가 쓴 소개는 위의 한 줄이 전부입니다. 더 자세한 내용은 저장소 README에서 읽을 수 있습니다. 저장소 README ↗
README 전체를 불러오는 중입니다.
README 전문 보기 ↗Multi-sided marketplace for the DIY / local live music scene. Bands sync calendars, assemble 3–4 act bills on mutually open dates, pitch turnkey packages to venues, and hold each other accountable via a double-blind 3-way rating system.
Full product spec: bandmeld PRD.md.
Stack: Next.js 16 (App Router) · React 19 · Tailwind 4 · Supabase (@supabase/ssr) · TypeScript (strict).
| Phase | Scope | Status |
|---|---|---|
| 1 — Trojan Horse | Member calendar sync · Band EPK · Shareable public band page | In progress (this repo) |
| 2 — Network | Band-to-band Bill Builder · Local photographer directory · 3-way ratings | Not started |
| 3 — Venue marketplace | Shareable pitch pages · Inbound open-slot board · Verified draw stats | Not started |
| 4 — Mobile + monetization | React Native app · Escrow / door splits | Not started |
Built:
create_band RPC (makes creator admin, enforces unique slug) + create-band formsync_band_open_dates RPC (next 366 days, member unavailability → actively_seeking) + preferred gig days filterband-assets storage bucket (logo / press / rider), admin-write / public-readactively_seeking ↔ penciled_in ↔ booked) + conflict detection — app/dashboard/bands/[bandId]/availability/page.tsxband_invites table, email-locked tokens, /invite/[token] accept flow preserving token through sign-up — app/invite/[token]/page.tsx.ics upload-only import — app/dashboard/availability/import/ics/page.tsx, lib/ics.ts (on feat/apple-ics-fallback)feat/vault-oauth-tokens)fix/last-admin-guard)Still open:
npm install
cp .env.example .env.local # fill in URL + publishable key
# Apply both migrations to your Supabase project
npx supabase login
npx supabase link --project-ref <your-ref>
npm run db:push # runs supabase/migrations/* in order
npm run db:types # optional: regenerate types from the live DB
npm run dev
No CLI? Paste the two files in supabase/migrations/ into the SQL Editor, in order.
Auth settings (Supabase dashboard):
http://localhost:3001 (add your Vercel URL later), and add http://localhost:3001/auth/confirm and http://localhost:3001/auth/google/callback to Redirect URLs.{{ .SiteURL }}/auth/confirm?token_hash={{ .TokenHash }}&type=email&next=/dashboardUsers can click Connect Google Calendar on /dashboard/availability to link their Google account and pull busy events into member_unavailabilities. Setup is a one-time dance:
Google Cloud Console
calendar.events scope)..../auth/calendar.events (covers both reading the user's events for import AND writing confirmed show dates back to their calendar). Save.https://<your-ref>.supabase.co/auth/v1/callback (yes, Supabase's, not ours — Supabase proxies the flow).Supabase dashboard
http://localhost:3001/auth/google/callback (and the prod equivalent later).This app's .env.local — same values as step 2, needed server-side to refresh access tokens:
GOOGLE_CLIENT_ID=...
GOOGLE_CLIENT_SECRET=...
The flow: user clicks the button → supabase.auth.linkIdentity('google', …) (not signInWithOAuth, so we don't create a second account) → Google consent → /auth/google/callback captures provider_token + provider_refresh_token into public.google_calendar_connections → redirects to /dashboard/availability/import for review. Preselect rules (one-offs + 2+ day blocks on, recurring series off) match band snap PRD.md §3.1.
proxy.ts Refreshes Supabase session; guards /dashboard (Next 16 name for middleware.ts)
utils/supabase/
client.ts Browser client for "use client" components
server.ts Per-request server client + getUserId()/requireUserId()
proxy.ts updateSession() used by root proxy.ts
env.ts Fails loudly on missing env vars
types/
database.types.ts Database type (same format as `supabase gen types`)
index.ts Aliases: Band, Profile, GigStatus, PublicEpk, ActionResult…
lib/
epk.ts getPublicEpk(slug) — cached, shared by page + metadata
embeds.ts Spotify / YouTube URL → safe embed URL
components/auth/auth-form.tsx Client form: useActionState + sonner toasts
app/
(auth)/login, signup, actions.ts Server Actions: signIn / signUp / signOut
auth/confirm/route.ts Email-link → session (the only route handler)
dashboard/ Auth-guarded: band list, new band, band settings, availability
bands/[slug]/ Public EPK (+ not-found)
supabase/migrations/
20261022000000_initial_schema.sql Original schema
20261022000100_rls_and_rpc.sql RLS fixes, create_band, availability engine, storage
20261024000000_google_calendar.sql google_calendar_connections (OAuth tokens, owner-only RLS)
lib/google-calendar.ts Google Calendar v3 client: token refresh, event list, classify
app/auth/google/callback/ OAuth landing: exchanges code → stores provider tokens
await createClient() from utils/supabase/server. No /api/* routes.ActionResult → shown with toast in a client component.supabase.rpc("create_band", {...}) returns the new band id — direct INSERT is blocked on purpose (the RPC also makes you admin). Unique-slug clash = Postgres error code 23505.supabase.rpc("sync_band_open_dates", { p_band_id }) (admins). Covers the next 366 days: adds free dates as actively_seeking, removes seeking dates that now conflict, and never touches penciled_in / booked / unavailable.profiles from public pages.band-assets, path {band_id}/{logo|press|rider}/{file}. Only that band's admins can write; files are publicly readable.getClaims() (verifies JWT), never getSession()..github/workflows/db-migrate.yml runs supabase db push on every push to master that touches supabase/migrations/**. Set these repo secrets (GitHub → Settings → Secrets and variables → Actions):
SUPABASE_ACCESS_TOKEN — personal access token from https://supabase.com/dashboard/account/tokensSUPABASE_PROJECT_REF — the 20-char slug from the Supabase dashboard URLSUPABASE_DB_PASSWORD — database password (Supabase → Settings → Database)Already-applied migrations are no-ops, so the workflow is safe to re-run (or trigger via Actions → Supabase migrations → Run workflow).
user_role enum exists but no column uses it yet (likely profiles.primary_role once venues/creatives onboard).YYYY-MM-DD strings. Standardize before shipping both widely.