Files
Bookra/apps/backend
Tomas DvorakandDevin 09f780e7a6 feat(catalog): add service and staff management end-to-end
Services and staff existed as schema + booking FK targets but had no
management surface. Adds full CRUD: repository (pgx + in-memory with
matching FK semantics), catalog service validation with tenant isolation,
MaxStaff entitlement enforcement, protected API routes, OpenAPI schemas,
and dashboard screens for both entities.

Dashboard summary now resolves staff names on bookings and computes
setup completion from real configured state. Booking modal selects from
the tenant's actual services; blocked days can be scoped per staff member.

Generated with [Devin](https://devin.ai)

Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
2026-09-18 08:52:25 +02:00
..
2026-05-05 09:48:15 +02:00
2026-05-05 09:48:15 +02:00
2026-05-05 09:48:07 +02:00
2026-05-05 09:48:15 +02:00

Bookra Backend

Go + Gin API for Bookra, designed for Railway deployment with Neon Auth, Neon Postgres, and Stripe billing.

Commands

go run ./cmd/api
go build ./...
go test ./...
npm run db:migrate:status
npm run db:migrate:up

Environment

  • BOOKRA_FRONTEND_URL allowed browser origin
  • BOOKRA_DATABASE_URL Neon pooled connection
  • BOOKRA_DATABASE_DIRECT_URL Neon direct connection for migrations/admin tasks
  • BOOKRA_NEON_AUTH_URL Neon Auth base URL used for JWKS verification
  • BOOKRA_AUTH_JWT_SECRET local JWT secret for the password-auth endpoints
  • BOOKRA_JOB_RUNNER_KEY shared secret for remote job-runner calls
  • BOOKRA_EMAIL_FROM sender identity for email reminders
  • BOOKRA_SMTP_* optional SMTP transport for email delivery
  • BOOKRA_STRIPE_API_KEY Stripe secret API key
  • BOOKRA_STRIPE_WEBHOOK_SECRET Stripe webhook signing secret
  • BOOKRA_STRIPE_{STARTER,PRO,BUSINESS}_{CZK,USD}_{MONTHLY,YEARLY}_PRICE_ID Stripe price IDs
  • BOOKRA_STRIPE_SMS_{CZK,USD,...}_PRICE_ID Stripe SMS usage price IDs
  • BOOKRA_SMSMANAGER_API_KEY optional SMS Manager.cz key
  • BOOKRA_UMAMI_API_URL and BOOKRA_UMAMI_API_KEY optional analytics integration
  • BOOKRA_ADMIN_EMAIL and BOOKRA_ADMIN_KEY optional platform admin API credentials
  • BOOKRA_SENTRY_DSN optional error monitoring

See .env.example for the full list.

Notes

  • Auth verification is isolated in internal/auth.
  • OpenAPI lives in openapi/bookra.openapi.yaml.
  • SQL migrations live in migrations/ (goose).
  • Repositories are handwritten pgx in internal/db/; there is no generated query layer.
  • Goose migrations are wired through npm run db:migrate:* and use the Neon direct connection URL.
  • Reminder dispatch runs through POST /v1/internal/jobs/reminders/dispatch with X-Bookra-Job-Key.
  • BOOKRA_DEMO_MODE=true swaps the repository for deterministic in-memory demo data and authenticates all requests as demo-owner.

Production Auth

Bookra production auth uses Neon Auth directly:

  • frontend uses VITE_NEON_AUTH_URL
  • backend verifies Neon JWTs with BOOKRA_NEON_AUTH_URL

Trusted redirect domains in Neon Auth should include your frontend origin such as https://bookra.eu, plus local dev origins when needed.

Stripe Setup

Get these values from the Stripe dashboard:

  • BOOKRA_STRIPE_API_KEY: Developers -> API keys -> secret key
  • BOOKRA_STRIPE_WEBHOOK_SECRET: Developers -> Webhooks -> destination signing secret
  • BOOKRA_STRIPE_*_PRICE_ID: Product catalog -> recurring price IDs

Create one recurring price per plan/currency/interval you support:

  • starter / pro / business × czk / usd × monthly / yearly

Set the webhook destination to:

POST /v1/webhooks/stripe

Subscribe to at least: checkout.session.completed, customer.subscription.created, customer.subscription.updated, customer.subscription.deleted, invoice.payment_succeeded, invoice.payment_failed.

For local testing:

stripe listen --forward-to http://localhost:8080/v1/webhooks/stripe