@donotdev/cli 0.0.13 → 0.0.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dependencies-matrix.json +357 -89
- package/dist/bin/commands/agent-setup.d.ts +6 -0
- package/dist/bin/commands/agent-setup.d.ts.map +1 -0
- package/dist/bin/commands/agent-setup.js +629 -0
- package/dist/bin/commands/agent-setup.js.map +1 -0
- package/dist/bin/commands/build.js +131 -50
- package/dist/bin/commands/bump.js +137 -49
- package/dist/bin/commands/cacheout.js +50 -21
- package/dist/bin/commands/create-app.js +270 -261
- package/dist/bin/commands/create-project.js +418 -197
- package/dist/bin/commands/deploy.js +1752 -712
- package/dist/bin/commands/dev.js +151 -35
- package/dist/bin/commands/emu.js +228 -70
- package/dist/bin/commands/format.js +50 -21
- package/dist/bin/commands/lint.js +50 -21
- package/dist/bin/commands/preview.js +155 -35
- package/dist/bin/commands/supabase-setup.d.ts +6 -0
- package/dist/bin/commands/supabase-setup.d.ts.map +1 -0
- package/dist/bin/commands/supabase-setup.js +7 -0
- package/dist/bin/commands/supabase-setup.js.map +1 -0
- package/dist/bin/commands/sync-secrets.js +224 -46
- package/dist/bin/commands/type-check.d.ts +14 -0
- package/dist/bin/commands/type-check.d.ts.map +1 -0
- package/dist/bin/commands/type-check.js +314 -0
- package/dist/bin/commands/type-check.js.map +1 -0
- package/dist/bin/commands/wai.js +7399 -11
- package/dist/bin/dndev.js +27 -2
- package/dist/bin/donotdev.js +27 -2
- package/dist/index.js +3960 -2996
- package/package.json +2 -2
- package/templates/app-demo/src/App.tsx.example +1 -0
- package/templates/app-demo/src/pages/FullPage.tsx.example +2 -2
- package/templates/app-demo/src/pages/components/DemoLayout.tsx.example +2 -2
- package/templates/app-demo/src/themes.css.example +5 -12
- package/templates/app-expo/.env.example +64 -0
- package/templates/app-expo/.expo/README.md.example +5 -0
- package/templates/app-expo/.gitignore.example +36 -0
- package/templates/app-expo/README.md.example +58 -0
- package/templates/app-expo/app/.gitkeep +2 -0
- package/templates/app-expo/app/_layout.tsx.example +41 -0
- package/templates/app-expo/app/form.tsx.example +52 -0
- package/templates/app-expo/app/index.tsx.example +89 -0
- package/templates/app-expo/app/list.tsx.example +32 -0
- package/templates/app-expo/app/profile.tsx.example +76 -0
- package/templates/app-expo/app/signin.tsx.example +53 -0
- package/templates/app-expo/app.json.example +39 -0
- package/templates/app-expo/babel.config.js.example +10 -0
- package/templates/app-expo/eas.json.example +20 -0
- package/templates/app-expo/expo-env.d.ts.example +4 -0
- package/templates/app-expo/metro.config.js.example +20 -0
- package/templates/app-expo/service-account-key.json.example +12 -0
- package/templates/app-expo/tsconfig.json.example +19 -0
- package/templates/app-next/.env.example +4 -33
- package/templates/app-next/src/app/ClientLayout.tsx.example +2 -0
- package/templates/app-next/src/app/layout.tsx.example +7 -6
- package/templates/app-next/src/globals.css.example +2 -11
- package/templates/app-next/src/pages/HomePage.tsx.example +1 -1
- package/templates/app-next/src/themes.css.example +10 -13
- package/templates/app-vite/.env.example +3 -32
- package/templates/app-vite/index.html.example +2 -24
- package/templates/app-vite/src/App.tsx.example +2 -0
- package/templates/app-vite/src/globals.css.example +2 -12
- package/templates/app-vite/src/pages/FormPageExample.tsx.example +1 -2
- package/templates/app-vite/src/pages/HomePage.tsx.example +1 -1
- package/templates/app-vite/src/themes.css.example +109 -79
- package/templates/app-vite/vercel.json.example +11 -0
- package/templates/functions-firebase/build.mjs.example +2 -72
- package/templates/functions-firebase/functions-firebase/.env.example.example +23 -25
- package/templates/functions-firebase/functions-firebase/build.mjs.example +2 -72
- package/templates/functions-firebase/functions-firebase/tsconfig.json.example +1 -1
- package/templates/functions-supabase/supabase/functions/cancel-subscription/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/change-plan/index.ts.example +11 -0
- package/templates/functions-supabase/supabase/functions/create-checkout-session/index.ts.example +11 -0
- package/templates/functions-supabase/supabase/functions/create-customer-portal/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/crud/index.ts.example +16 -0
- package/templates/functions-supabase/supabase/functions/delete-account/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/get-custom-claims/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/get-user-auth-status/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/refresh-subscription-status/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/remove-custom-claims/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/functions/set-custom-claims/index.ts.example +7 -0
- package/templates/functions-supabase/supabase/migrations/20250101000000_idempotency.sql +24 -0
- package/templates/functions-supabase/supabase/migrations/20250101000001_rate_limits.sql +22 -0
- package/templates/functions-supabase/supabase/migrations/20250101000002_cleanup_jobs.sql +28 -0
- package/templates/functions-supabase/supabase/migrations/20250101000003_operation_metrics.sql +28 -0
- package/templates/functions-vercel/functions-vercel/tsconfig.json.example +1 -1
- package/templates/functions-vercel/functions-vercel/vercel.json.example +1 -1
- package/templates/functions-vercel/vercel.json.example +1 -1
- package/templates/github/github/workflows/firebase-deploy.yml.example +1 -1
- package/templates/github/workflows/firebase-deploy.yml.example +1 -1
- package/templates/overlay-firebase/env.fragment.example +34 -0
- package/templates/overlay-firebase/env.fragment.expo.example +34 -0
- package/templates/overlay-firebase/env.fragment.nextjs.example +34 -0
- package/templates/overlay-firebase/src/config/providers.expo.ts.example +49 -0
- package/templates/overlay-firebase/src/config/providers.ts.example +23 -0
- package/templates/overlay-supabase/env.fragment.example +7 -0
- package/templates/overlay-supabase/env.fragment.expo.example +7 -0
- package/templates/overlay-supabase/env.fragment.nextjs.example +7 -0
- package/templates/overlay-supabase/src/config/providers.expo.ts.example +35 -0
- package/templates/overlay-supabase/src/config/providers.ts.example +33 -0
- package/templates/overlay-supabase/vercel.headers.example +23 -0
- package/templates/overlay-supabase/vercel.json.example +22 -0
- package/templates/overlay-vercel/env.fragment.example +34 -0
- package/templates/overlay-vercel/env.fragment.nextjs.example +34 -0
- package/templates/overlay-vercel/src/config/providers.ts.example +24 -0
- package/templates/root-consumer/.claude/agents/architect.md.example +2 -310
- package/templates/root-consumer/.claude/agents/builder.md.example +2 -326
- package/templates/root-consumer/.claude/agents/coder.md.example +2 -83
- package/templates/root-consumer/.claude/agents/extractor.md.example +2 -231
- package/templates/root-consumer/.claude/agents/polisher.md.example +2 -132
- package/templates/root-consumer/.claude/agents/prompt-engineer.md.example +2 -81
- package/templates/root-consumer/.claude/commands/brainstorm.md.example +1 -1
- package/templates/root-consumer/.claude/commands/build.md.example +1 -1
- package/templates/root-consumer/.claude/commands/design.md.example +1 -1
- package/templates/root-consumer/.claude/commands/grill.md.example +30 -0
- package/templates/root-consumer/.claude/commands/polish.md.example +1 -1
- package/templates/root-consumer/.claude/commands/techdebt.md.example +28 -0
- package/templates/root-consumer/.clinerules.example +1 -0
- package/templates/root-consumer/.cursor/rules/no-docs.mdc.example +15 -0
- package/templates/root-consumer/.cursorrules.example +1 -0
- package/templates/root-consumer/.dndev/args.json.example +6 -0
- package/templates/root-consumer/.gemini/settings.json.example +2 -2
- package/templates/root-consumer/.github/copilot-instructions.md.example +1 -0
- package/templates/root-consumer/.windsurfrules.example +1 -0
- package/templates/root-consumer/AI.md.example +25 -108
- package/templates/root-consumer/CLAUDE.md.example +1 -128
- package/templates/root-consumer/CONVENTIONS.md.example +1 -0
- package/templates/root-consumer/GEMINI.md.example +1 -0
- package/templates/root-consumer/firebase.json.example +1 -1
- package/templates/root-consumer/guides/dndev/AGENT_START_HERE.md.example +54 -0
- package/templates/root-consumer/guides/dndev/COMPONENTS_ADV.md.example +0 -18
- package/templates/root-consumer/guides/dndev/COMPONENTS_UI.md.example +1 -1
- package/templates/root-consumer/guides/dndev/ENV_SETUP.md.example +99 -30
- package/templates/root-consumer/guides/dndev/GOTCHAS.md.example +186 -0
- package/templates/root-consumer/guides/dndev/INDEX.md.example +4 -1
- package/templates/root-consumer/guides/dndev/SETUP_CRUD.md.example +143 -12
- package/templates/root-consumer/guides/dndev/SETUP_FIREBASE.md.example +9 -3
- package/templates/root-consumer/guides/dndev/SETUP_FUNCTIONS.md.example +12 -7
- package/templates/root-consumer/guides/dndev/SETUP_SOC2.md.example +234 -0
- package/templates/root-consumer/guides/dndev/SETUP_SUPABASE.md.example +124 -0
- package/templates/root-consumer/guides/dndev/SETUP_THEMES.md.example +6 -2
- package/templates/root-consumer/guides/dndev/SETUP_VERCEL.md.example +176 -0
- package/templates/root-consumer/guides/dndev/USE_ROUTING.md.example +5 -9
- package/templates/root-consumer/guides/dndev/essences_reference.css.example +174 -0
- package/templates/root-consumer/guides/wai-way/agents/builder.md.example +10 -0
- package/templates/root-consumer/guides/wai-way/agents/extractor.md.example +25 -5
- package/templates/root-consumer/guides/wai-way/agents/polisher.md.example +13 -2
- package/templates/root-consumer/guides/wai-way/blueprints/0_brainstorm.md.example +2 -2
- package/templates/root-consumer/guides/wai-way/blueprints/1_scaffold.md.example +47 -11
- package/templates/root-consumer/guides/wai-way/blueprints/3_compose.md.example +15 -4
- package/templates/root-consumer/guides/wai-way/spec_template.md.example +7 -6
- package/templates/app-payload/.env.example +0 -28
- package/templates/app-payload/README.md.example +0 -233
- package/templates/app-payload/collections/Company.ts.example +0 -125
- package/templates/app-payload/collections/Hero.ts.example +0 -62
- package/templates/app-payload/collections/Media.ts.example +0 -41
- package/templates/app-payload/collections/Products.ts.example +0 -115
- package/templates/app-payload/collections/Services.ts.example +0 -104
- package/templates/app-payload/collections/Testimonials.ts.example +0 -92
- package/templates/app-payload/collections/Users.ts.example +0 -35
- package/templates/app-payload/src/server.ts.example +0 -79
- package/templates/app-payload/tsconfig.json.example +0 -24
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Enforce AI.md
|
|
@@ -9,6 +9,26 @@
|
|
|
9
9
|
|
|
10
10
|
---
|
|
11
11
|
|
|
12
|
+
## Getting Started (for humans)
|
|
13
|
+
|
|
14
|
+
**Canonical flow:** The showcase app’s **Get Started** page is the single source of truth: `apps/showcase/src/pages/GetStartedPage.tsx` and `apps/showcase/src/pages/locales/getstarted_*.json`. Below is the same flow in short form.
|
|
15
|
+
|
|
16
|
+
1. **P0 — Prerequisites**
|
|
17
|
+
- **Runtime:** **Node.js 24** (nodejs.org) and **Bun 1.3+** (bun.sh). Both required.
|
|
18
|
+
- **IDE:** Any IDE (Cursor, VS Code, Windsurf, etc.). Need help? Use the collapsible “Need help setting up?” on the Get Started page.
|
|
19
|
+
2. **Install our CLI and create your project’s monorepo**
|
|
20
|
+
- `npm install -g @donotdev/cli`
|
|
21
|
+
- `dndev init my-app`
|
|
22
|
+
3. **Open the repo in your IDE, terminal, bun install**
|
|
23
|
+
- Start your IDE in that repo, open the terminal: `cd my-app` → `bun install`
|
|
24
|
+
4. **Enable MCP, then read AI.md and follow the flow**
|
|
25
|
+
- Talk with your agent; ask it to load the MCP (Cursor: Ctrl+Shift+P → “MCP Server” → enable “donotdev”; other IDEs: see “How to enable MCP” collapsible on the Get Started page).
|
|
26
|
+
- Then have the agent read the root **`AI.md`** and this file (**`guides/dndev/AGENT_START_HERE.md`**). Follow the phases.
|
|
27
|
+
5. **AI helps with provider; cd there, bun install, run**
|
|
28
|
+
- AI helps you choose and set up your provider (Firebase, Supabase, or custom). Then `cd` into the app directory if needed, `bun install`, and `dndev dev` / `dndev build` / `dndev deploy`.
|
|
29
|
+
|
|
30
|
+
---
|
|
31
|
+
|
|
12
32
|
## First Thing to Call: list_features()
|
|
13
33
|
|
|
14
34
|
Call **`list_features()`** before designing or coding. It lists all framework packages with a one-line summary from each README (templates, core, ui, auth, billing, etc.). Use it so you don't reinvent what the framework already provides (blog, CRUD, billing, legal pages, etc.).
|
|
@@ -63,4 +83,38 @@ Check that the user has completed environment setup:
|
|
|
63
83
|
|
|
64
84
|
If not, coach them: "Run `dndev firebase:setup` first, then follow the prompts." See [SETUP_FIREBASE.md](./SETUP_FIREBASE.md).
|
|
65
85
|
|
|
86
|
+
---
|
|
87
|
+
|
|
88
|
+
## Project Args (`.dndev/args.json`)
|
|
89
|
+
|
|
90
|
+
Generated by `dndev init`. All features ON by default — Phase 0 narrows down based on what the user actually needs.
|
|
91
|
+
|
|
92
|
+
```json
|
|
93
|
+
{
|
|
94
|
+
"platform": "firebase",
|
|
95
|
+
"strictness": "enforced",
|
|
96
|
+
"features": ["crud", "auth", "i18n", "billing", "oauth", "functions"],
|
|
97
|
+
"region": "europe-west1"
|
|
98
|
+
}
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
| Field | Values | Effect |
|
|
102
|
+
|-------|--------|--------|
|
|
103
|
+
| `platform` | `firebase`, `vercel` | Derived from builder choice |
|
|
104
|
+
| `strictness` | `enforced`, `warnings`, `permissive` | `enforced` = blocks `complete_phase` on convention violations. `warnings` = reports but allows. `permissive` = skips checks. |
|
|
105
|
+
| `features` | `crud`, `auth`, `i18n`, `billing`, `oauth`, `functions` | Filters gotchas — remove features the project doesn't use to reduce noise |
|
|
106
|
+
| `region` | any GCP region | Informational, shown in `start_phase` context |
|
|
107
|
+
|
|
108
|
+
`start_phase()` returns project args + phase-relevant gotchas automatically. `complete_phase()` respects `strictness`.
|
|
109
|
+
|
|
110
|
+
**Without MCP:** `args.json` and `GOTCHAS.md` are plain files. Any agent can read them directly.
|
|
111
|
+
|
|
112
|
+
---
|
|
113
|
+
|
|
114
|
+
## Gotchas (`guides/dndev/GOTCHAS.md`)
|
|
115
|
+
|
|
116
|
+
Common mistakes, phase-tagged. `start_phase(N)` automatically filters and returns only the gotchas relevant to phase N and your enabled features. Read the full file for reference: [GOTCHAS.md](../guides/dndev/GOTCHAS.md).
|
|
117
|
+
|
|
118
|
+
---
|
|
119
|
+
|
|
66
120
|
**Starting:** Call `list_features()` first, then `get_phase_status()` to see where you are, then `start_phase(0)` to begin.
|
|
@@ -335,24 +335,6 @@ import { StartChallengeForm } from '@donotdev/adv-comps';
|
|
|
335
335
|
/>
|
|
336
336
|
```
|
|
337
337
|
|
|
338
|
-
### Waterfall
|
|
339
|
-
|
|
340
|
-
Waterfall component with lazy loading built-in. Features clean cascade layout with diagonal staircase effect, perfect for step-by-step processes or feature showcases.
|
|
341
|
-
|
|
342
|
-
```tsx
|
|
343
|
-
import { Waterfall } from '@donotdev/adv-comps';
|
|
344
|
-
import type { WaterfallProps } from '@donotdev/adv-comps';
|
|
345
|
-
|
|
346
|
-
<Waterfall
|
|
347
|
-
items: ComponentData[]
|
|
348
|
-
className?: string
|
|
349
|
-
connectorClassName?: string
|
|
350
|
-
density?: 'compact' | 'comfortable'
|
|
351
|
-
ariaLabel?: string
|
|
352
|
-
direction?: 'horizontal' | 'descending'
|
|
353
|
-
/>
|
|
354
|
-
```
|
|
355
|
-
|
|
356
338
|
## Notes
|
|
357
339
|
|
|
358
340
|
- All components are lazy-loaded by default for optimal performance
|
|
@@ -83,7 +83,7 @@
|
|
|
83
83
|
- **usePrefetch** - Prefetch route data.
|
|
84
84
|
- **useLocation** - Get current location.
|
|
85
85
|
- **useParams** - Get route parameters.
|
|
86
|
-
- **useSearchParams** - Get URL search parameters.
|
|
86
|
+
- **useSearchParams** - Get URL search parameters. Returns `URLSearchParams` directly (NOT a tuple). Use `.get('key')` to read values.
|
|
87
87
|
- **useMatch** - Match current route pattern.
|
|
88
88
|
- **useQueryParams** - Get and set query parameters.
|
|
89
89
|
- **useRedirectGuard** - Guard against redirects.
|
|
@@ -2,16 +2,20 @@
|
|
|
2
2
|
|
|
3
3
|
**The complete onboarding flow — from `dndev init` to deployed app.**
|
|
4
4
|
|
|
5
|
+
If you haven’t run `dndev init` yet, see [AGENT_START_HERE.md](./AGENT_START_HERE.md) § **Getting started (for humans)** (P0 → Install CLI → Run AI.md → Enjoy).
|
|
6
|
+
|
|
5
7
|
---
|
|
6
8
|
|
|
7
9
|
## The Flow
|
|
8
10
|
|
|
9
11
|
```
|
|
10
|
-
bun install
|
|
11
|
-
bun dev
|
|
12
|
-
dndev firebase:setup
|
|
13
|
-
|
|
14
|
-
dndev
|
|
12
|
+
bun install -> install dependencies
|
|
13
|
+
bun dev -> start app, read the homepage setup guide
|
|
14
|
+
dndev firebase:setup -> configure Firebase project + .env
|
|
15
|
+
-- or --
|
|
16
|
+
dndev supabase:setup -> configure Supabase project + .env
|
|
17
|
+
dndev emu start -> test locally with emulators (Firebase)
|
|
18
|
+
dndev deploy -> deploy to production
|
|
15
19
|
```
|
|
16
20
|
|
|
17
21
|
---
|
|
@@ -43,29 +47,45 @@ git push -u origin main
|
|
|
43
47
|
|
|
44
48
|
---
|
|
45
49
|
|
|
46
|
-
## Step 3:
|
|
50
|
+
## Step 3: Backend Setup
|
|
51
|
+
|
|
52
|
+
### Firebase
|
|
47
53
|
|
|
48
54
|
```bash
|
|
49
55
|
dndev firebase:setup
|
|
50
56
|
```
|
|
51
57
|
|
|
52
|
-
Automates: project selection/creation, web app, SDK config
|
|
58
|
+
Automates: project selection/creation, web app, SDK config -> `.env`, `.firebaserc`.
|
|
53
59
|
|
|
54
60
|
Then 2 manual steps (CLI gives you direct links):
|
|
55
|
-
1. Download service account key
|
|
61
|
+
1. Download service account key -> save as `service-account-key.json`
|
|
56
62
|
2. Enable Auth + Firestore in Firebase Console
|
|
57
63
|
|
|
58
64
|
See [SETUP_FIREBASE.md](./SETUP_FIREBASE.md) for full details.
|
|
59
65
|
|
|
66
|
+
### Supabase
|
|
67
|
+
|
|
68
|
+
```bash
|
|
69
|
+
dndev supabase:setup
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
Asks for your **public** project URL and anon key (both safe to share -- shipped in client bundle).
|
|
73
|
+
|
|
74
|
+
Get them from: https://supabase.com/dashboard -> your project -> Settings -> API
|
|
75
|
+
|
|
76
|
+
See [SETUP_SUPABASE.md](./SETUP_SUPABASE.md) for full details (tables, RLS, `dn generate sql`). See [Secrets Philosophy](#secrets-philosophy) for how we handle secret keys.
|
|
77
|
+
|
|
60
78
|
---
|
|
61
79
|
|
|
62
80
|
## Step 4: Test Locally
|
|
63
81
|
|
|
64
82
|
```bash
|
|
65
|
-
dndev emu start
|
|
83
|
+
dndev emu start # Firebase emulators
|
|
66
84
|
```
|
|
67
85
|
|
|
68
|
-
Select Auth + Firestore + Functions.
|
|
86
|
+
Select services: Auth + Firestore + Functions. This starts Firebase emulators so you can develop without touching production.
|
|
87
|
+
|
|
88
|
+
For Supabase, development runs against your Supabase project directly (or use `supabase start` for local Supabase if installed).
|
|
69
89
|
|
|
70
90
|
---
|
|
71
91
|
|
|
@@ -74,11 +94,11 @@ Select Auth + Firestore + Functions. Develops against local emulators.
|
|
|
74
94
|
Open the project in **Cursor**, **Claude Code**, **Windsurf**, or **AntiGravity**.
|
|
75
95
|
|
|
76
96
|
The AI reads `AI.md` and follows the WAI-WAY protocol:
|
|
77
|
-
- Phase 0: Brainstorm
|
|
78
|
-
- Phase 1: Scaffold
|
|
79
|
-
- Phase 2: Entities
|
|
80
|
-
- Phase 3: Compose
|
|
81
|
-
- Phase 4: Configure
|
|
97
|
+
- Phase 0: Brainstorm -> produce a spec
|
|
98
|
+
- Phase 1: Scaffold -> create pages
|
|
99
|
+
- Phase 2: Entities -> define data models
|
|
100
|
+
- Phase 3: Compose -> build pages with components
|
|
101
|
+
- Phase 4: Configure -> generate tests, firestore rules, CI/CD
|
|
82
102
|
|
|
83
103
|
Read `guides/wai-way/WAI_WAY_CLI.md` for the full workflow.
|
|
84
104
|
|
|
@@ -90,7 +110,51 @@ Read `guides/wai-way/WAI_WAY_CLI.md` for the full workflow.
|
|
|
90
110
|
dndev deploy
|
|
91
111
|
```
|
|
92
112
|
|
|
93
|
-
Deploys hosting + functions + rules.
|
|
113
|
+
Deploys hosting + functions + rules. Syncs runtime secrets automatically before deploying functions.
|
|
114
|
+
|
|
115
|
+
---
|
|
116
|
+
|
|
117
|
+
## Secrets Philosophy
|
|
118
|
+
|
|
119
|
+
**DoNotDev follows strict rules about credentials:**
|
|
120
|
+
|
|
121
|
+
### Tier 1: Public Keys -- We Ask Directly
|
|
122
|
+
|
|
123
|
+
These are safe to share, shipped in your client JS bundle. We ask for them during setup.
|
|
124
|
+
|
|
125
|
+
| Key | Where It Goes |
|
|
126
|
+
|-----|--------------|
|
|
127
|
+
| Firebase API key, project ID, auth domain, etc. | `apps/<app>/.env` as `VITE_FIREBASE_*` |
|
|
128
|
+
| Supabase project URL | `apps/<app>/.env` as `VITE_SUPABASE_URL` |
|
|
129
|
+
| Supabase anon key (public JWT) | `apps/<app>/.env` as `VITE_SUPABASE_ANON_KEY` |
|
|
130
|
+
| Stripe publishable key | `apps/<app>/.env` as `VITE_STRIPE_PUBLISHABLE_KEY` |
|
|
131
|
+
|
|
132
|
+
### Tier 2: Secret Keys -- We NEVER Ask, We Tell You Where To Put Them
|
|
133
|
+
|
|
134
|
+
These are server-side only. We never prompt for them, never store them in client code.
|
|
135
|
+
|
|
136
|
+
| Key | Where It Goes | How To Get It |
|
|
137
|
+
|-----|--------------|---------------|
|
|
138
|
+
| Stripe secret key | `functions/.env` as `STRIPE_SECRET_KEY` | https://dashboard.stripe.com/apikeys |
|
|
139
|
+
| Stripe webhook secret | `functions/.env` as `STRIPE_WEBHOOK_SECRET` | Stripe Dashboard -> Webhooks |
|
|
140
|
+
| Supabase service_role key | `functions/.env` as `SUPABASE_SERVICE_ROLE_KEY` | Supabase Dashboard -> Settings -> API |
|
|
141
|
+
| OAuth client secrets | `functions/.env` as `*_CLIENT_SECRET` | Provider dashboard |
|
|
142
|
+
|
|
143
|
+
Then sync to your runtime:
|
|
144
|
+
|
|
145
|
+
```bash
|
|
146
|
+
dndev sync-secrets # -> Firebase Secret Manager or Vercel env
|
|
147
|
+
dndev sync-secrets --target github # -> GitHub Secrets (for CI/CD)
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
### Tier 3: Service Account Files -- Download, Place, Gitignore
|
|
151
|
+
|
|
152
|
+
| File | Where It Goes | How To Get It |
|
|
153
|
+
|------|--------------|---------------|
|
|
154
|
+
| `service-account-key.json` | App root (next to firebase.json) | Firebase Console -> Settings -> Service Accounts |
|
|
155
|
+
| `service-account-key.staging.json` | Same location, for staging | Same, from staging project |
|
|
156
|
+
|
|
157
|
+
These files are `.gitignored`. Never commit them. For CI/CD, upload the file content as a GitHub Secret and decode it in your workflow.
|
|
94
158
|
|
|
95
159
|
---
|
|
96
160
|
|
|
@@ -100,18 +164,21 @@ Deploys hosting + functions + rules. Cloud Run IAM handled automatically.
|
|
|
100
164
|
|
|
101
165
|
```
|
|
102
166
|
my-project/
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
167
|
+
+-- .env.example <-- NOT loaded by Vite (reference only)
|
|
168
|
+
+-- apps/
|
|
169
|
+
| +-- my-app/
|
|
170
|
+
| +-- .env <-- Vite reads THIS (public keys: VITE_*)
|
|
171
|
+
| +-- .env.local <-- Overrides .env (gitignored)
|
|
172
|
+
| +-- .env.staging <-- Used by dndev staging
|
|
173
|
+
| +-- .env.production <-- Production overrides
|
|
174
|
+
+-- functions/
|
|
175
|
+
+-- .env <-- Server secrets (Stripe, OAuth, service_role)
|
|
112
176
|
```
|
|
113
177
|
|
|
114
|
-
**
|
|
178
|
+
**Rules:**
|
|
179
|
+
- `VITE_*` / `NEXT_PUBLIC_*` vars -> `apps/<app>/.env` (public, shipped to browser)
|
|
180
|
+
- Server secrets -> `functions/.env` (never exposed to client)
|
|
181
|
+
- Service account files -> app root, gitignored
|
|
115
182
|
|
|
116
183
|
---
|
|
117
184
|
|
|
@@ -122,9 +189,11 @@ my-project/
|
|
|
122
189
|
| `bun dev` | Start dev server |
|
|
123
190
|
| `dndev emu start` | Start Firebase emulators |
|
|
124
191
|
| `dndev firebase:setup` | Configure Firebase project + .env |
|
|
125
|
-
| `dndev
|
|
192
|
+
| `dndev supabase:setup` | Configure Supabase project + .env |
|
|
193
|
+
| `dndev deploy` | **Firebase:** hosting + functions + rules. **Supabase:** deploys frontend to [Vercel](https://vercel.com) (via scaffolded vercel.json) and Edge Functions to Supabase. Set `VITE_SUPABASE_*` in Vercel project env. |
|
|
126
194
|
| `dndev staging` | Deploy to staging environment |
|
|
127
|
-
| `dndev sync-secrets` | Push functions/.env to Firebase
|
|
195
|
+
| `dndev sync-secrets` | Push functions/.env to runtime (Firebase/Vercel) |
|
|
196
|
+
| `dndev sync-secrets --target github` | Push secrets to GitHub Secrets (CI/CD) |
|
|
128
197
|
| `bun test` | Run tests (after Phase 4) |
|
|
129
198
|
| `bun run type-check` | TypeScript validation |
|
|
130
199
|
|
|
@@ -135,8 +204,8 @@ my-project/
|
|
|
135
204
|
| Feature | Required? | When to Set Up |
|
|
136
205
|
|---------|-----------|---------------|
|
|
137
206
|
| Git + GitHub | Recommended | Before starting development |
|
|
138
|
-
| Firebase
|
|
139
|
-
| Cloud Functions | If using
|
|
207
|
+
| Firebase or Supabase | Yes (pick one) | Before building any features |
|
|
208
|
+
| Cloud Functions | If using server logic | Before deploying functions |
|
|
140
209
|
| Stripe | If using billing | When adding payment features |
|
|
141
210
|
| GitHub Actions CI/CD | Optional | Phase 4 generates the workflow |
|
|
142
211
|
| Staging environment | Optional | When you want a test environment |
|
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
# Framework Gotchas
|
|
2
|
+
|
|
3
|
+
**Common mistakes. Read before coding. Phase tags show when each matters most.**
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## Imports [Phase 1, 2, 3]
|
|
8
|
+
|
|
9
|
+
**Server code MUST use `/server` imports — client imports crash on deploy.**
|
|
10
|
+
|
|
11
|
+
```typescript
|
|
12
|
+
// ✅ CORRECT
|
|
13
|
+
import { getFirebaseAdminFirestore } from '@donotdev/firebase/server';
|
|
14
|
+
import { handleError } from '@donotdev/core/server';
|
|
15
|
+
|
|
16
|
+
// ❌ WRONG - crashes on deploy
|
|
17
|
+
import { getFirestore } from '@donotdev/firebase';
|
|
18
|
+
import { handleError } from '@donotdev/core';
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
**Rule:** Always use `/server` suffix for `@donotdev/firebase/server`, `@donotdev/core/server`, `@donotdev/utils/server`.
|
|
22
|
+
|
|
23
|
+
**ESM only — never use `require()`.**
|
|
24
|
+
|
|
25
|
+
```typescript
|
|
26
|
+
// ❌ WRONG
|
|
27
|
+
const { something } = require('@donotdev/package');
|
|
28
|
+
|
|
29
|
+
// ✅ CORRECT
|
|
30
|
+
import { something } from '@donotdev/package';
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
**Import ordering is mandatory:**
|
|
34
|
+
1. React (values, then types)
|
|
35
|
+
2. Other vendors (values, then types)
|
|
36
|
+
3. `@donotdev/*` packages (values, then types)
|
|
37
|
+
4. Relative imports (values, then types)
|
|
38
|
+
|
|
39
|
+
One line for values, one line for types. Blank line between categories.
|
|
40
|
+
|
|
41
|
+
---
|
|
42
|
+
|
|
43
|
+
## Routing [Phase 1, 3]
|
|
44
|
+
|
|
45
|
+
**Never import from `react-router-dom` — use framework routing.**
|
|
46
|
+
|
|
47
|
+
```tsx
|
|
48
|
+
// ❌ WRONG - breaks framework features
|
|
49
|
+
import { Link, useNavigate, useParams } from 'react-router-dom';
|
|
50
|
+
|
|
51
|
+
// ✅ CORRECT
|
|
52
|
+
import { Link, useNavigate, useParams } from '@donotdev/ui/routing';
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
**Routes are auto-discovered** from `src/pages/*Page.tsx` with `pageMeta`. Don't use `<Routes>`, `<Route>`, or manual `<Outlet />`.
|
|
56
|
+
|
|
57
|
+
**Use `useRouteParam('id')` for typed route params** — not `useParams()` from react-router-dom.
|
|
58
|
+
|
|
59
|
+
**Navigation is auto-built.** Use `<DnDevNavigationMenu>` or `useNavigationItems()`. Don't build nav manually — you lose auth filtering and route discovery.
|
|
60
|
+
|
|
61
|
+
---
|
|
62
|
+
|
|
63
|
+
## Styling [Phase 3, 4]
|
|
64
|
+
|
|
65
|
+
**No inline `fontSize` or `font-size` — use `Text` level prop.**
|
|
66
|
+
|
|
67
|
+
```tsx
|
|
68
|
+
// ❌ WRONG
|
|
69
|
+
<Text style={{ fontSize: '18px' }}>Title</Text>
|
|
70
|
+
|
|
71
|
+
// ✅ CORRECT
|
|
72
|
+
<Text level="h2">Title</Text>
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Levels: `h1`, `h2`, `h3`, `h4`, `body`, `small`, `caption`. Limit to 2–3 levels per page.
|
|
76
|
+
|
|
77
|
+
**RTL: Always use `start`/`end` — never `left`/`right`.**
|
|
78
|
+
|
|
79
|
+
```css
|
|
80
|
+
/* ❌ WRONG - breaks RTL */
|
|
81
|
+
text-align: left;
|
|
82
|
+
|
|
83
|
+
/* ✅ CORRECT - works in both LTR and RTL */
|
|
84
|
+
text-align: start;
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
Same for inline styles: `textAlign: 'start'` not `textAlign: 'left'`. Same for data attributes: `data-text-align="start|center|end"`.
|
|
88
|
+
|
|
89
|
+
---
|
|
90
|
+
|
|
91
|
+
## Components [Phase 3]
|
|
92
|
+
|
|
93
|
+
**Always `lookup_symbol` before using any `@donotdev` component.** Never guess props.
|
|
94
|
+
|
|
95
|
+
Common wrong props:
|
|
96
|
+
- `Button`: no `size`, `tone`, `gap` — use `variant`, `display`
|
|
97
|
+
- `Text`: no `size`, `tone`, `color` — use `level`, `variant`
|
|
98
|
+
- `Stack`: no `spacing`, `size` — use `gap`
|
|
99
|
+
- `Card`: no `padding`, `margin`, `size` — use `title`, `subtitle`, `content`, `footer`
|
|
100
|
+
- `Grid`: no `columns` — use `cols`
|
|
101
|
+
|
|
102
|
+
**If you can't do it with framework components:** Stop. Tell the user what's missing. Don't invent custom workarounds.
|
|
103
|
+
|
|
104
|
+
---
|
|
105
|
+
|
|
106
|
+
## CRUD [Phase 2, 3]
|
|
107
|
+
|
|
108
|
+
**Hidden fields are auto-added by `defineEntity()` — don't define them manually:**
|
|
109
|
+
- `id`, `createdAt`, `updatedAt`, `createdById`, `updatedById`, `status`
|
|
110
|
+
|
|
111
|
+
**Scope field is auto-added** when `scope` is configured. Don't manually define the scope field (e.g., `companyId`).
|
|
112
|
+
|
|
113
|
+
**Custom form fields MUST use framework's `useController`:**
|
|
114
|
+
|
|
115
|
+
```typescript
|
|
116
|
+
// ❌ WRONG
|
|
117
|
+
import { useController } from 'react-hook-form';
|
|
118
|
+
|
|
119
|
+
// ✅ CORRECT
|
|
120
|
+
import { useController } from '@donotdev/crud';
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
**Form components receive `control` prop, not `field` prop.**
|
|
124
|
+
|
|
125
|
+
**Price field is structured:** `{ amount, currency, vatIncluded, discountPercent }`. Don't store computed discount amounts.
|
|
126
|
+
|
|
127
|
+
**File uploads are deferred** — files upload on form submit, not on selection. Images show optimistic blob URLs.
|
|
128
|
+
|
|
129
|
+
**Entity namespace defaults to `entity-{name}`** (lowercase). Translation files must match: `locales/entity-product_en.json`.
|
|
130
|
+
|
|
131
|
+
---
|
|
132
|
+
|
|
133
|
+
## Functions [Phase 3, 4]
|
|
134
|
+
|
|
135
|
+
**Use `createFunction` for custom functions — 3 params, everything included:**
|
|
136
|
+
|
|
137
|
+
```typescript
|
|
138
|
+
import { createFunction } from '@donotdev/functions/firebase';
|
|
139
|
+
|
|
140
|
+
export const myFunction = createFunction(schema, 'operation_name', async (data, { uid }) => {
|
|
141
|
+
// Your logic
|
|
142
|
+
});
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
**Use `createBaseFunction` only when you need custom config** (memory, timeout, region override).
|
|
146
|
+
|
|
147
|
+
**Deploy with `dndev deploy`** — not `firebase deploy`. Manual deploy causes CORS 403 on preflight because Cloud Run blocks unauthenticated OPTIONS by default.
|
|
148
|
+
|
|
149
|
+
**Naming:** Export in camelCase (`getDashboardMetrics`), operation ID in snake_case (`get_dashboard_metrics`).
|
|
150
|
+
|
|
151
|
+
**CRUD functions are one-liner:** `export const crud = createCrudFunctions(entities);` — generates all CRUD endpoints per entity. Access controlled via `entity.access`.
|
|
152
|
+
|
|
153
|
+
---
|
|
154
|
+
|
|
155
|
+
## i18n [Phase 3, 4]
|
|
156
|
+
|
|
157
|
+
**Phase 3: hardcode strings. Phase 4: add translations.** Don't i18n too early.
|
|
158
|
+
|
|
159
|
+
**Two loading strategies:**
|
|
160
|
+
- **Eager** (always loaded): `src/locales/common_en.json` — navigation, buttons, common UI
|
|
161
|
+
- **Lazy** (loaded per page): `src/pages/locales/home_en.json` — page-specific content
|
|
162
|
+
|
|
163
|
+
**Status field translations** fall back: `entity-{name}` namespace → `crud` namespace.
|
|
164
|
+
|
|
165
|
+
**Rich text uses `<Trans>` component** with supported tags only: `<accent>`, `<primary>`, `<muted>`, `<success>`, `<warning>`, `<error>`, `<bold>`, `<code>`.
|
|
166
|
+
|
|
167
|
+
**Array translations use `tList`:**
|
|
168
|
+
```tsx
|
|
169
|
+
import { tList } from '@donotdev/ui';
|
|
170
|
+
<Card content={tList(t, 'features.items', 4)} />
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
---
|
|
174
|
+
|
|
175
|
+
## Dependencies [Phase 1]
|
|
176
|
+
|
|
177
|
+
**Apps don't declare bundled deps.** Framework packages (`@donotdev/*`) provide everything. Don't add `react-router-dom`, `react-hook-form`, `valibot`, etc. to app's `package.json` — they come through framework deps.
|
|
178
|
+
|
|
179
|
+
**Environment variables:**
|
|
180
|
+
- Client: `apps/my-app/.env` (prefix with `VITE_*`)
|
|
181
|
+
- Server: `functions/.env` (secrets: `STRIPE_*`, OAuth tokens)
|
|
182
|
+
- Local overrides: `.env.local` (gitignored)
|
|
183
|
+
|
|
184
|
+
---
|
|
185
|
+
|
|
186
|
+
**When in doubt: search the codebase first, ask the user second, never guess.**
|
|
@@ -8,8 +8,11 @@
|
|
|
8
8
|
|
|
9
9
|
## Getting Started
|
|
10
10
|
|
|
11
|
-
-
|
|
11
|
+
- **Human flow:** P0 (Bun/Node + AI IDE) → Install CLI & `dndev init` → Run **AI.md** → Enjoy. See [AGENT_START_HERE.md](./AGENT_START_HERE.md) § Getting started (for humans).
|
|
12
|
+
- [ENV_SETUP.md](./ENV_SETUP.md) — After `dndev init`: env, Firebase/Supabase, deploy
|
|
13
|
+
- [GOTCHAS.md](./GOTCHAS.md) - **Common mistakes & pitfalls** (phase-tagged, read before coding)
|
|
12
14
|
- [SETUP_FIREBASE.md](./SETUP_FIREBASE.md) - Firebase project setup (`dndev firebase:setup`)
|
|
15
|
+
- [SETUP_SUPABASE.md](./SETUP_SUPABASE.md) - Supabase project setup (`dndev supabase:setup`, `dn generate sql`)
|
|
13
16
|
- [SETUP_TESTING.md](./SETUP_TESTING.md) - Test generation (Phase 4)
|
|
14
17
|
|
|
15
18
|
---
|