Fujimod
브라우저에서 카메라 펌웨어를 시험하고 Fujimod SD 부팅 파일을 만든다
콘서트·코미디·워크숍·스포츠·축제 등 실시간 행사 찾기·밴드·DJ·공연자 고용
Concerts, comedy, workshops, sports and festivals — plus bands, DJs and performers for your own wedding, party or corporate event. No account needed to browse.
라이프스타일GitHub @curatixlive온라인운영자 미확인
써 보셨어요? 한 번만 눌러 주세요. 로그인은 필요 없어요.
저장소 정보는 아직 수집하지 않았습니다.
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
메이커가 쓴 소개는 위의 한 줄이 전부입니다. 더 자세한 내용은 저장소 README에서 읽을 수 있습니다. 저장소 README ↗
README 전체를 불러오는 중입니다.
README 전문 보기 ↗A production-track event ticketing & experience platform (Eventbrite/Meetup
class): organizers create events and ticket tiers, attendees book and pay,
the platform takes a fee per ticket and splits the rest to the organizer,
tickets get checked in at the door. This repo contains the foundation plus
the complete backend feature set — nine modules (accounts,
organizations, events, ticketing, booking, payments, checkin,
notifications, settlements) proving the whole stack works end to end:
architecture, caching, full-text search, correct-under-concurrency
reservations, the reserve→hold→confirm→pay money-path lifecycle with
signature-verified webhooks and automatic refunds, one-scan gate entry that
can't admit a ticket twice, event-driven exactly-once email/SMS delivery, and
organizer payouts that close the money loop (reconciled, released once, only
after the event) — with performance discipline throughout.
frontend/README.md); comes after more backend modules exist.cp .env.example .env # already has safe dummy values, edit if you like
docker compose up -d
This builds the backend image and starts Postgres, a PgBouncer in front of
it (transaction-pooling mode, TLS required — a local stand-in for
Supabase's Supavisor pooler), Redis with a TLS listener (a local stand-in for
Upstash), waits for them to be healthy, runs migrations, and starts the
dev server on http://localhost:8000.
Development lives in docker-compose.override.yml, which Compose loads
automatically — so the command above is development, and
docker compose -f docker-compose.yml up -d # production: .env is authoritative
is production (gunicorn, plus the scheduler and outbox worker; no migrate on boot).
Deployment is a configuration exercise, not a development exercise — the
same image runs all three environments and only .env differs:
| Document | Answers |
|---|---|
| DEPLOYMENT.md | How do I deploy it, and how do I undo it? |
| PRODUCTION_CHECKLIST.md | Tickable sign-off sheet before go-live. |
| OPERATIONS.md | It is deployed — how do I run it day to day? |
| ENVIRONMENT_VARIABLES.md | What is every variable, and who reads it? |
| REAL_INTEGRATIONS_AUDIT.md | What is each credential and where do I get it? |
Environment templates — copy the one for your target to .env, fill in every
<PLACEHOLDER>, and change nothing else:
| Template | For |
|---|---|
.env.example | Local development, and the canonical reference for every variable. |
.env.staging.example | Staging. |
.env.production.example | Production. |
frontend/.env.local.example · frontend/.env.production.example | The frontend's seven public variables. |
All four backend templates declare the identical variable set, enforced by
core/tests/test_env_templates.py rather than by asking.
GET /health/GET /api/schema/ — Swagger UI: /api/docs/POST /api/v1/auth/register, /login, /refresh,
/logout, GET /api/v1/auth/mePOST /api/v1/organizations/, GET /api/v1/organizations/{id},
PATCH /api/v1/organizations/{id}, GET /api/v1/organizations/ (mine,
cursor-paginated), POST /api/v1/organizations/{id}/verification,
POST /api/v1/organizations/{id}/payout-accountGET /api/v1/events (browse + full-text search ?q= + ?city= filter,
cursor-paginated), GET /api/v1/events/{id}. Organizer (authenticated):
POST /api/v1/events (draft), PATCH /api/v1/events/{id} (optimistic-
locked), POST /api/v1/events/{id}/publish, GET /api/v1/organizer/events.GET /api/v1/events/{id}/ticket-types
(tiers + live availability, short-TTL cached). Organizer:
POST /api/v1/events/{id}/ticket-types, PATCH /api/v1/ticket-types/{id}.
The reserve/release/confirm_sold primitives (per-tier row lock, zero
oversell) are an internal service API booking calls — not HTTP.POST /api/v1/bookings (reserve all items
all-or-nothing, hold, create payment order; honours an Idempotency-Key
header), GET /api/v1/bookings/{id}, POST /api/v1/bookings/{id}/cancel,
GET /api/v1/me/tickets. ConfirmBooking (issue signed-QR tickets,
idempotent) is an internal service API payments calls from the verified
webhook. A sweeper task auto-releases expired holds.POST /api/v1/payments/webhook (Razorpay only — no user
token, authenticated by HMAC signature over the raw body; verifies →
dedupes → amount-checks → confirms the booking → 200 fast, refunds
offloaded), GET /api/v1/payments/{id} (owner/organizer),
POST /api/v1/payments/{id}/refund (organizer/admin). The order carries a
Route split (organizer share on-hold until the event; platform fee retained);
hold-expired/amount-mismatch payments auto-refund — money is never kept
without a ticket.cd backend
python -m venv .venv
./.venv/Scripts/python -m pip install -e ".[dev]" # Windows
# source .venv/bin/activate && pip install -e ".[dev]" # macOS/Linux
docker compose up -d postgres redis # from repo root, in another shell
python manage.py migrate
python manage.py runserver
Everything runs with zero real credentials — every third-party
dependency (payments, storage, email, SMS, event bus, task queue) defaults
to a local/fake adapter (see .env.example's *_BACKEND/*_PROVIDER
switches). Nothing needs a Razorpay key, a GCP project, or an SMTP server
to run locally.
cd backend
./.venv/Scripts/python -m pytest --cov=core --cov=apps --cov-report=term-missing
./.venv/Scripts/python -m ruff check .
./.venv/Scripts/python -m black --check .
./.venv/Scripts/python -m mypy .
Tests need Postgres + Redis running (docker compose up -d postgres redis
from the repo root; add pgbouncer too if you want the pooled path
exercised, though tests connect directly via DIRECT_DATABASE_URL and
don't need it) — pytest-django creates and tears down its own test database
against Postgres directly, bypassing the pooler (see CLAUDE.md's dev
infrastructure section for why). One test suite (test_redis_adapter.py)
talks to real Redis to verify cache serialization; everything else uses
the local/fake adapters.
Want a deep per-request profiler instead of the built-in slow-request log?
Set ENABLE_SILK=true in .env and hit /silk/ — off by default even in
dev, since it has real overhead.
Install the git hooks once so these run automatically before every commit:
pip install pre-commit # or use the one in backend/.venv
pre-commit install
See CLAUDE.md for the full conventions doc (layering rules, how to add a module, how to add a port/adapter, why certain things are deliberately kept simple). Short version:
API (views/serializers, thin) -> Service (business rules) -> Repository (ORM) -> Models
Every third-party dependency sits behind a port (an abstract interface
in backend/core/ports/), with a local/fake adapter for dev/test and a
real adapter for production, selected at runtime by backend/config/di.py
(the single composition root) based on env-var switches. Business logic
never imports a vendor SDK directly.
backend/
config/ settings (base/dev/staging/prod/test), di.py, urls, asgi/wsgi, worker
core/ shared kernel: ports, adapters (local + real), base repo/service,
unit of work, outbox, audit, errors, pagination, logging
apps/
accounts/ reference module — copy this shape for every new module
organizations/ orgs/brands, verification, payout-account linking, caching
events/ public discovery: full-text search, edge caching,
single-flight detail cache, optimistic-locked edits
ticketing/ tiers + authoritative availability; per-tier row-lock
reserve/release/confirm primitives (zero oversell)
booking/ reserve→hold→confirm money-path lifecycle; all-or-nothing
reserve, auto-release sweeper, signed-QR ticket issuance
payments/ signature-verified Razorpay webhooks, idempotency ledger,
Route split (on-hold), auto-refunds when unfulfillable
checkin/ one-scan gate entry under a per-ticket row lock, live
attendance (cache the count, trust the DB), scan audit log
notifications/ event-driven email/SMS: exactly-once (unique dedupe_key +
claim-before-send), retry + dead-letter, templated + DLT
settlements/ closes the money loop: reconcile gross/fee/refunds/net from
payment records, release organizer payout once after the
event (recompute under lock, retry + dead-letter)
frontend/ placeholder, see frontend/README.md
private, no-storePOST /api/v1/checkin/verifyGET /api/v1/events/{id}/attendanceUSER_REGISTERED, BOOKING_CONFIRMED,
PAYMENT_REFUNDED, EVENT_PUBLISHED, PAYOUT_RELEASED) and sends templated
email/SMS through EmailPort/SmsPort. Delivery is fully async (off the
request path via the task queue), exactly-once (a unique dedupe_key +
claim-before-send row lock), with retry → dead-letter. The ticket-delivery
email (event + booking reference + QR) and OTP SMS (India DLT template per
type) live here; the welcome email was consolidated in from accounts.private, no-store): GET /api/v1/organizer/settlements
(own settlements, cursor-paginated), GET /api/v1/organizer/settlements/{event_id},
POST /api/v1/admin/settlements/{id}/release (staff-only manual trigger).
Closes the money loop: it reconciles each event's gross − fee − refunds = net from the payment records and releases the on-hold organizer payout —
recomputed authoritatively under a row lock, exactly once, and only
after the event + refund window — with retry → dead-letter (the payout runs
off the request path via a scheduled job).