App Store: https://apps.apple.com/us/app/deennotes-ai/id6767057471 · Web companion: https://deennotesai.netlify.app/
Project snapshot: DeenNotes AI is a shipped iPhone/iPad app for Islamic reflection, Quran study, prayer planning, journaling, reminders, and AI-assisted note organization. The product is intentionally scoped as a reflection and productivity companion—not a source of fatwas or religious rulings.
Current product: App Store version 1.0.4 · React Native / Expo mobile app · Next.js web companion/API · Supabase Auth/Postgres/RLS · RevenueCat subscriptions · pluggable AI providers.
What it demonstrates: shipping a real consumer mobile product end-to-end: native app UX, authentication, subscriptions, Quran/audio features, prayer utilities, AI-assisted structured output, privacy/security hardening, and App Store release operations.
DeenNotes AI is live on the Apple App Store.
- App Store: https://apps.apple.com/us/app/deennotes-ai/id6767057471
- Web companion: https://deennotesai.netlify.app/
- Current mobile source version: 1.0.4
- Platforms: iPhone and iPad
- Capture khutbah, lecture, Quran reflection, halaqa, reminder, or personal journal notes.
- Turn rough notes into structured reflections, summaries, reminders, takeaways, and action steps.
- Read Quran with Arabic ayahs, translations, and audio support.
- Organize the day with prayer tools, Salah Planner, reminders, Qibla, and beginner-friendly Learning Mode.
- Save account-owned reflections securely with Supabase Auth + RLS.
- Unlock premium features through RevenueCat-backed App Store subscriptions.
iPhone / iPad (React Native + Expo)
│
├──────────────► RevenueCat ─────► App Store subscriptions
│
▼
Next.js web/API
│ │ │
▼ ▼ ▼
Supabase AI Quran services
Auth/DB providers/content/audio
+ RLS
See docs/ARCHITECTURE.md for the system boundaries and production responsibilities.
- CHANGELOG.md — production release history
- ROADMAP.md — shipped, improving, and exploring
- docs/README.md — current vs. historical product documentation
- CONTRIBUTING.md — development and review expectations
- SECURITY.md — vulnerability and secret-handling policy
- .github/workflows/ci.yml — automated web/mobile verification
- React Native + Expo Router mobile app in
apps/mobile - Next.js companion web app and server routes
- Supabase Auth + owner-scoped Postgres RLS
- RevenueCat iOS subscription integration
- pluggable AI provider selection instead of one hard-coded model vendor
- structured AI output validation for predictable reflections
- Quran reading/audio, local recording, prayer reminders, Qibla, and Salah Planner flows
- public-repo secret hygiene and deployment checks
- product guardrail: reflection/organization support, not fatwas or rulings
The technical challenge is broader than summarization: DeenNotes combines mobile product UX, faith-sensitive scope, subscriptions, account security, audio/device capabilities, and reliable AI output in one shipped consumer app.
DeenNotes AI is mobile-first: the shipped React Native / Expo app is the primary product, with a Next.js web companion and API supporting the broader experience.
Treat this repo as safe to make public: tracked files must not contain database passwords, Supabase service_role or secret keys, AI provider keys, JWTs, or real Project Refs. Clone .env.example to .env.local (or .env), add your values only on your machine, and rely on .gitignore (.env* with an exception for .env.example). The Next.js app uses the anon/publishable client key with RLS; SUPABASE_SERVICE_ROLE_KEY is optional and not used by app routes—never prefix it with NEXT_PUBLIC_.
Every pull request is set up to run GitHub CI for:
- root TypeScript verification
- Vitest tests
- mobile TypeScript verification
- a production-style Next.js build using safe CI placeholder configuration
Dependency update PRs are managed by Dependabot. Pull requests and issues use repository templates, and CODEOWNERS routes changes to the maintainer.
Deployment is deliberately separate from CI. A passing GitHub check or merged pull request is not treated as permission to publish a Netlify or App Store release.
For ongoing releases and maintenance:
- Database — Keep Supabase migrations in
supabase/migrations/as the source of truth and verify RLS remains enabled on account-owned tables. - Auth — Keep Supabase Site URL and redirect allowlists aligned with the production web companion and mobile deep-link flow.
- Environment — Keep public/publishable Supabase values client-safe and all service-role / AI provider secrets server-side.
- AI — Smoke-test structured reflection generation after provider or prompt changes.
- Mobile — Run the Expo typecheck/doctor flow and verify sign-in, Reflect, Quran/audio, Prayer/Salah Planner, Premium/restore, and Settings before an App Store submission.
- Positioning — Keep product copy scoped to journaling, reflection, study, and productivity support rather than religious rulings.
- React Native + Expo 54
- Expo Router
- TypeScript
- Supabase Auth/Postgres
- RevenueCat
- Sentry
- Next.js App Router
- TypeScript + Tailwind CSS
- Supabase Auth + Postgres (RLS)
- Pluggable AI: OpenAI, Anthropic, or Groq (
AI_PROVIDER) - Netlify
- Node.js 20+
- A Supabase project
- An API key for at least one AI provider
- Optional: Supabase CLI for
db push - Optional: Netlify CLI (installed in this repo as a dev dependency — use
npm run ntl -- …from the repo root)
From the repo root, the CLI is available without a global install:
npm run ntl -- --version
npm run ntl -- status
npm run ntl -- link
npm run netlify:deploy
npm run netlify:deploy:prodFor non-interactive use (agents, CI, scripts), set NETLIFY_AUTH_TOKEN in .env.local (create a personal access token under Netlify → User settings → Applications). For a one-time interactive login on your machine: npm run ntl -- login.
From the repo root (after installing the CLI):
For this project, use your Supabase dashboard Project Ref when linking locally. Find it under Project Settings → General (not the full database password).
supabase login
supabase init
supabase link --project-ref YOUR_PROJECT_REF
supabase db pushsupabase initcreatessupabase/config.tomlif you do not already have it; keep migration SQL insupabase/migrations/as the source of truth.
If supabase db push fails with “already exists” (you already ran 001_init.sql in the SQL Editor), the remote DB matches that migration but Supabase’s history does not yet. Mark it applied, then push again:
supabase migration repair 001 --status applied --linked
supabase db pushUse 002 instead of 001 if only the second migration was applied manually. Run supabase migration list to see local vs remote status.
Run in SQL Editor (or supabase db execute):
-- Tables exist in public schema
select table_name
from information_schema.tables
where table_schema = 'public'
and table_name in ('profiles', 'deen_notes', 'saved_share_cards')
order by table_name;
-- RLS enabled (relrowsecurity should be true for each)
select c.relname as table_name, c.relrowsecurity as rls_enabled
from pg_class c
join pg_namespace n on n.oid = c.relnamespace
where n.nspname = 'public'
and c.relkind = 'r'
and c.relname in ('profiles', 'deen_notes', 'saved_share_cards')
order by 1;Expect three rows in the first query and rls_enabled = true for all three in the second. Policies in the migrations scope access by auth.uid() for tenant-owned rows.
-
Clone and install
npm install
-
Configure Supabase
- Settings → API: copy project URL (e.g.
https://YOUR_PROJECT_REF.supabase.co) and the publishable client key (or legacy anon key — same permission level; never theservice_rolekey forNEXT_PUBLIC_*). - Authentication → URL configuration: set local development redirects for
http://localhost:3000and production redirects forhttps://deennotesai.netlify.appplus the mobile deep-link/callback flow. - Redirects:
http://localhost:3000/auth/callback(andhttps://your-domain.com/auth/callbackin production).
- Settings → API: copy project URL (e.g.
-
Database
- Option A — SQL Editor: run
supabase/migrations/001_init.sqland, if needed,002_short_summary_main_reminder.sql. - Option B — CLI: use Supabase CLI workflow and confirm with the verification SQL.
If Postgres errors on
execute functionfor triggers, useexecute procedurefor the same trigger names (see Supabase/Postgres docs for your version). - Option A — SQL Editor: run
-
Environment variables
cp .env.example .env.local
Fill in at minimum:
NEXT_PUBLIC_SUPABASE_URL,NEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEY(preferred) orNEXT_PUBLIC_SUPABASE_ANON_KEY,AI_PROVIDER, the matching model env (OPENAI_MODEL/ANTHROPIC_MODEL/GROQ_MODEL), and that provider’s API key. Do not commit.env.local. -
Auth for local dev
- Under Authentication → Providers → Email, consider disabling Confirm email while developing so sign-up can log in immediately. Re-enable for production.
-
Run the app
npm run dev
Open http://localhost:3000.
- The production web companion is hosted at
https://deennotesai.netlify.app. - Configure the Netlify project with the same required server/client environment variables documented in
.env.example. - Keep
SUPABASE_SERVICE_ROLE_KEYserver-only and never expose it through aNEXT_PUBLIC_*variable. - Keep Supabase Site URL / redirect allowlists synchronized with the Netlify production URL.
- Documentation-only commits can use
[skip netlify]to avoid unnecessary production builds.
Before closing out a release, follow docs/DEPLOY_CHECKLIST.md (commit/push → confirm Netlify commit → curl route health).
- In the site’s Environment variables, set
NEXT_PUBLIC_SUPABASE_URLandNEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEYfor your Supabase project. - If
NEXT_PUBLIC_SUPABASE_ANON_KEYmight be wrong or from another project, remove it. The app uses publishable first when it is non-empty, but deleting a bad anon avoids confusion and mistaken “which key is live?” during rollouts. - Run Deploys → Clear cache and deploy site after any
NEXT_PUBLIC_*change so the new values are inlined into the client bundle. - After deploy, hard refresh the site and sign in again so session cookies match the deployed URL and keys.
From the repo you can also use npm run netlify:deploy:prod (see Netlify CLI); env vars are still managed in the Netlify UI or via npm run ntl -- env:set … when authenticated.
| Command | Description |
|---|---|
npm run dev |
Dev server |
npm run build |
Production build |
npm run start |
Start production |
npm run lint |
ESLint |
npm run test |
Vitest (AI schema) |
DeenNotes is for organizing Islamic learning and personal reflection. It does not provide fatwas or religious rulings. Users should consult a qualified scholar or imam for religious decisions.
Copyright © 2026 Baheem Ferrell. All rights reserved. This public repository is viewable for portfolio, review, and collaboration purposes; it is not released under an open-source license. See LICENSE.