{"id":50013552,"url":"https://github.com/criticalpathtech/prayer","last_synced_at":"2026-06-01T04:01:20.051Z","repository":{"id":358594373,"uuid":"1229461721","full_name":"CriticalPathTech/prayer","owner":"CriticalPathTech","description":"A quiet, invite-only prayer wall for a single church. Public source, free to self-host, or hosted at prays.online. ","archived":false,"fork":false,"pushed_at":"2026-06-01T01:12:01.000Z","size":882,"stargazers_count":1,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-06-01T02:17:49.729Z","etag":null,"topics":["church","faith","multi-tenant","postgresql","react","self-hosted","typescript"],"latest_commit_sha":null,"homepage":"https://prays.online","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/CriticalPathTech.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-05-05T04:17:53.000Z","updated_at":"2026-06-01T01:07:56.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/CriticalPathTech/prayer","commit_stats":null,"previous_names":["criticalpathtech/prayer"],"tags_count":5,"template":false,"template_full_name":null,"purl":"pkg:github/CriticalPathTech/prayer","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/CriticalPathTech%2Fprayer","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/CriticalPathTech%2Fprayer/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/CriticalPathTech%2Fprayer/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/CriticalPathTech%2Fprayer/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/CriticalPathTech","download_url":"https://codeload.github.com/CriticalPathTech/prayer/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/CriticalPathTech%2Fprayer/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":33759178,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-01T02:00:06.963Z","response_time":115,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["church","faith","multi-tenant","postgresql","react","self-hosted","typescript"],"created_at":"2026-05-20T02:08:16.942Z","updated_at":"2026-06-01T04:01:20.045Z","avatar_url":"https://github.com/CriticalPathTech.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Prayer\n\nPrivate, invite-only prayer-request app for church communities. Source-available\nunder the Elastic License 2.0 (see [LICENSE](LICENSE)), self-hostable, runs\nentirely on your laptop with no external accounts.\n\n## What's inside\n\n- Prayer feed with three sort modes (newest / updated / popular)\n- Private one-on-one comment threads (only the author and commenter see them; moderators can peek)\n- Six emoji reactions, \"I prayed\" tally, anonymous posts, expiring requests\n- Invite-only signup with seat-capped invite codes\n- Mobile-friendly UI, accessible by default\n\n## Quickstart (Docker, ~2 min)\n\n**Prerequisites:** Docker (Desktop or Engine) and `pnpm` (only needed for the bootstrap step). No external accounts required.\n\n```bash\ndocker compose up -d --build                  # build and start: postgres + gotrue + minio + api + web\npnpm install                                  # local node_modules for the bootstrap CLI\npnpm admin:create-org --slug hope             # create the org (default slug)\npnpm bootstrap --slug hope                    # seed 5 users + 10 sample posts + 6 comments\n```\n\nOpen \u003chttp://localhost:5173\u003e and sign in as `hopesu@example.com` with password `prayer-dev-local`.\n\n`pnpm bootstrap` is idempotent — re-running it never duplicates data and never resets passwords.\n\n### What you just started\n\n| Service    | Port        | What it is                                                                                                                      |\n| ---------- | ----------- | ------------------------------------------------------------------------------------------------------------------------------- |\n| `postgres` | 5432        | App data (`public.*`) + GoTrue's auth (`auth.*`)                                                                                |\n| `gotrue`   | 9999        | Self-hosted Supabase Auth — issues JWTs, no email needed                                                                        |\n| `minio`    | 9000 / 9001 | S3-compatible avatar storage. Console: \u003chttp://localhost:9001\u003e — dev-only creds: `prayer-dev-local` / `prayer-dev-local-secret` |\n| `api`      | 3001        | Express + Kysely backend (`/healthz` for a quick check)                                                                         |\n| `web`      | 5173        | Vite + React frontend, served by nginx in the image                                                                             |\n\nHealth-check the stack:\n\n```bash\ndocker compose ps                                # all five services healthy\ncurl -fs http://localhost:3001/healthz | jq      # api\ncurl -fs http://localhost:9999/.well-known/jwks.json | jq '.keys | length'   # gotrue\ncurl -fs http://localhost:9000/minio/health/live    # minio\n```\n\n## Default users (after `pnpm bootstrap`)\n\nAll emails follow the pattern `\u003cslug\u003e\u003crole-suffix\u003e@\u003cdomain\u003e`. With the default\nslug `hope` and default domain `example.com`:\n\n| Email                  | Role         | Password           |\n| ---------------------- | ------------ | ------------------ |\n| `hopesu@example.com`   | `super_user` | `prayer-dev-local` |\n| `hopemod1@example.com` | `moderator`  | `prayer-dev-local` |\n| `hopemod2@example.com` | `moderator`  | `prayer-dev-local` |\n| `hopemem1@example.com` | `member`     | `prayer-dev-local` |\n| `hopemem2@example.com` | `member`     | `prayer-dev-local` |\n\nTo use a different slug or domain, pass `--slug \u003cyourchurch\u003e` and set\n`BOOTSTRAP_EMAIL_DOMAIN=yourdomain.org` (or pass `--domain`). Two churches in\nthe same DB will never collide on email because the slug prefixes the local\npart.\n\nSign in as different users to see how moderator vs. member views differ.\n\n## Other dev modes\n\nThe Quickstart above is **Mode A** — everything in containers, built locally. Two other workflows exist:\n\n**Mode B — local web against a remote API.** UI changes without running the backend:\n\n```bash\nPROD_API_URL=https://api.your-instance.example.com pnpm dev:remote\n```\n\n**Mode C — native local for fastest iteration.** Persistent services in containers, api+web run natively with hot reload:\n\n```bash\ndocker compose up -d postgres gotrue   # persistent services\npnpm install\npnpm bootstrap                         # seed once\npnpm dev                               # api :3001 + web :5173 native\n```\n\n## Common tasks\n\n```bash\ndocker compose down                    # stop everything\ndocker compose down -v                 # stop and wipe all data\ndocker compose logs -f api             # tail logs\n\npnpm test                              # vitest across all workspaces\npnpm build                             # tsc -b across project refs (CI runs this)\npnpm typecheck                         # types only\npnpm lint                              # eslint\npnpm format                            # prettier --write\n```\n\n## Stopping and starting fresh\n\n```bash\ndocker compose down -v                 # wipe data\ndocker compose up -d --build           # rebuild and start\npnpm bootstrap                         # reseed\n```\n\n## Project layout\n\n```\napps/api          Express + Kysely backend\napps/web          Vite + React frontend\npackages/db       Kysely schema, migrations, bootstrap script\npackages/shared   Zod-validated env parsers shared across api + web\ndocker/           Compose init scripts + GoTrue JWK fixtures (storage runs in MinIO)\ndocs/             Self-hosting guide\n```\n\n## More\n\n- [`docs/self-hosting.md`](docs/self-hosting.md) — generic deployment guide for the OSS Docker stack\n- [`CONTRIBUTING.md`](CONTRIBUTING.md) — how to set up a dev environment, run tests, open a PR\n- [`SECURITY.md`](SECURITY.md) — vulnerability reporting (please don't use the public issue tracker)\n- [`CLAUDE.md`](CLAUDE.md) — project guide for Claude Code sessions\n\n## License\n\n[Elastic License 2.0](LICENSE). Source-available, free to self-host and modify.\nThe license forbids offering this code as a hosted multi-tenant service to\nthird parties — please reach out if you have a different use case in mind.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fcriticalpathtech%2Fprayer","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fcriticalpathtech%2Fprayer","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fcriticalpathtech%2Fprayer/lists"}