forgecad 0.6.3 → 0.7.0

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.
Files changed (193) hide show
  1. package/README.md +2 -11
  2. package/dist/assets/{AdminPage-CeqCUUgu.js → AdminPage-DAu1C1ST.js} +250 -151
  3. package/dist/assets/{BlogPage-P_AJP0v9.js → BlogPage-CJEXL_zJ.js} +94 -70
  4. package/dist/assets/{DocsPage-CKRV2iq2.js → DocsPage-Gc_BCdqC.js} +269 -143
  5. package/dist/assets/EditorApp-D9bJvtf7.js +11338 -0
  6. package/dist/assets/{EditorApp-CnC2k4cW.css → EditorApp-DG1-oUSV.css} +459 -87
  7. package/dist/assets/{EmbedViewer-DBlzmQ5i.js → EmbedViewer-CEO8XbV8.js} +2 -4
  8. package/dist/assets/LandingPage-CdCuEOdC.js +451 -0
  9. package/dist/assets/PricingPage-BSrxu6d7.js +232 -0
  10. package/dist/assets/{SettingsPage-BqCh9JcC.js → SettingsPage-FUCSIRq6.js} +129 -5
  11. package/dist/assets/{evalWorker-Ql-aKwLA.js → evalWorker-KoR0SNKq.js} +6770 -2914
  12. package/dist/assets/{index-2hfs_ub0.css → index-CyVd1D4D.css} +227 -53
  13. package/dist/assets/{Viewport-CoB46f5R.js → index-wTEK39at.js} +31385 -6439
  14. package/dist/assets/{javascript-DCxGoE5Y.js → javascript-DAl8Gmyo.js} +1 -1
  15. package/dist/assets/{manifold-CqNMHHKO.js → manifold-B1sGWdYk.js} +4 -3
  16. package/dist/assets/{manifold-Cce9wRFz.js → manifold-D7o0N50J.js} +1 -1
  17. package/dist/assets/{manifold-D6BeHIOo.js → manifold-G5sBaXzi.js} +1 -1
  18. package/dist/assets/{reportWorker-sFEFonXf.js → reportWorker-DYcRHhv9.js} +6798 -3341
  19. package/dist/assets/{vendor-react-Dt7-aaJH.js → vendor-react-CG3i_wp0.js} +65 -8
  20. package/dist/docs-raw/generated/assembly.md +691 -112
  21. package/dist/docs-raw/generated/concepts.md +1225 -1400
  22. package/dist/docs-raw/generated/core.md +464 -1412
  23. package/dist/docs-raw/generated/curves.md +593 -117
  24. package/dist/docs-raw/generated/lib.md +38 -748
  25. package/dist/docs-raw/generated/output.md +139 -245
  26. package/dist/docs-raw/generated/sheet-metal.md +473 -21
  27. package/dist/docs-raw/generated/sketch.md +553 -349
  28. package/dist/docs-raw/generated/viewport.md +345 -303
  29. package/dist/docs-raw/generated/wood.md +104 -0
  30. package/dist/index.html +2 -2
  31. package/dist/sitemap.xml +6 -6
  32. package/dist-cli/chunk-PZ5AY32C.js +10 -0
  33. package/dist-cli/chunk-PZ5AY32C.js.map +1 -0
  34. package/dist-cli/forgecad.js +9435 -5407
  35. package/dist-cli/forgecad.js.map +1 -0
  36. package/dist-cli/solver-FV7TJZGI.js +365 -0
  37. package/dist-cli/solver-FV7TJZGI.js.map +1 -0
  38. package/dist-skill/CONTEXT.md +3186 -7145
  39. package/dist-skill/SKILL-dev.md +21 -63
  40. package/dist-skill/SKILL.md +12 -56
  41. package/dist-skill/docs/API/core/concepts.md +16 -98
  42. package/dist-skill/docs/CLI/export.md +91 -0
  43. package/dist-skill/docs/CLI/projects.md +107 -0
  44. package/dist-skill/docs/CLI/studio_publishing.md +52 -0
  45. package/dist-skill/docs/CLI/validation.md +66 -0
  46. package/dist-skill/docs/generated/assembly.md +691 -112
  47. package/dist-skill/docs/generated/core.md +464 -1412
  48. package/dist-skill/docs/generated/curves.md +593 -117
  49. package/dist-skill/docs/generated/lib.md +38 -748
  50. package/dist-skill/docs/generated/output.md +139 -245
  51. package/dist-skill/docs/generated/sheet-metal.md +473 -21
  52. package/dist-skill/docs/generated/sketch.md +553 -349
  53. package/dist-skill/docs/generated/viewport.md +345 -303
  54. package/dist-skill/docs/generated/wood.md +104 -0
  55. package/dist-skill/docs/guides/coordinate-system.md +11 -17
  56. package/dist-skill/docs/guides/geometry-conventions.md +13 -70
  57. package/dist-skill/docs/guides/modeling-recipes.md +22 -195
  58. package/dist-skill/docs/guides/positioning.md +88 -147
  59. package/dist-skill/docs-dev/API/core/concepts.md +51 -0
  60. package/dist-skill/docs-dev/API/core/sdf-advanced.md +92 -0
  61. package/dist-skill/docs-dev/API/core/sdf-primitives.md +58 -0
  62. package/dist-skill/docs-dev/API/core/sdf-workflow.md +42 -0
  63. package/dist-skill/docs-dev/CLI/export.md +91 -0
  64. package/dist-skill/docs-dev/CLI/projects.md +107 -0
  65. package/dist-skill/docs-dev/CLI/studio_publishing.md +52 -0
  66. package/dist-skill/docs-dev/CLI/validation.md +66 -0
  67. package/dist-skill/{docs → docs-dev}/blueprint-first.md +5 -0
  68. package/dist-skill/{docs → docs-dev}/coding-best-practices.md +6 -8
  69. package/dist-skill/{docs → docs-dev}/coding.md +1 -3
  70. package/dist-skill/docs-dev/generated/assembly.md +771 -0
  71. package/dist-skill/docs-dev/generated/core.md +775 -0
  72. package/dist-skill/docs-dev/generated/curves.md +688 -0
  73. package/dist-skill/docs-dev/generated/lib.md +50 -0
  74. package/dist-skill/docs-dev/generated/output.md +234 -0
  75. package/dist-skill/docs-dev/generated/sheet-metal.md +506 -0
  76. package/dist-skill/docs-dev/generated/sketch.md +801 -0
  77. package/dist-skill/docs-dev/generated/viewport.md +486 -0
  78. package/dist-skill/docs-dev/generated/wood.md +104 -0
  79. package/dist-skill/docs-dev/guides/coordinate-system.md +46 -0
  80. package/dist-skill/docs-dev/guides/geometry-conventions.md +52 -0
  81. package/dist-skill/docs-dev/guides/modeling-recipes.md +77 -0
  82. package/dist-skill/docs-dev/guides/positioning.md +151 -0
  83. package/dist-skill/{docs → docs-dev}/guides/skill-maintenance.md +21 -10
  84. package/dist-skill/{docs → docs-dev}/internals/compiler.md +5 -6
  85. package/dist-skill/{docs → docs-dev}/internals/constraint-solver-quality.md +0 -1
  86. package/dist-skill/{docs → docs-dev}/internals/constraint-solver.md +0 -1
  87. package/dist-skill/{docs → docs-dev}/internals/sketch-2d-pipeline.md +2 -3
  88. package/examples/api/attachTo-basics.forge.js +5 -5
  89. package/examples/api/boolean-operations.forge.js +3 -3
  90. package/examples/api/bounding-box-visualizer.forge.js +2 -2
  91. package/examples/api/clone-duplicate.forge.js +1 -1
  92. package/examples/api/colors-union-vs-array.forge.js +6 -6
  93. package/examples/api/connector-assembly.forge.js +4 -4
  94. package/examples/api/connector-basics.forge.js +2 -2
  95. package/examples/api/extrude-options.forge.js +4 -10
  96. package/examples/api/feature-created-faces.forge.js +6 -10
  97. package/examples/api/fillet-showcase.forge.js +1 -1
  98. package/examples/api/folded-service-panel-cover.forge.js +2 -2
  99. package/examples/api/group-test.forge.js +1 -1
  100. package/examples/api/group-vs-union.forge.js +1 -1
  101. package/examples/api/highlight-debug.forge.js +4 -0
  102. package/examples/api/js-module-pillars.js +1 -1
  103. package/examples/api/js-module-scene.js +2 -2
  104. package/examples/api/mesh-import-slats.forge.js +1 -1
  105. package/examples/api/pointAlong-orientation.forge.js +1 -1
  106. package/examples/api/profile-2020-b-slot6.forge.js +0 -1
  107. package/examples/api/route-perimeter-flange.forge.js +1 -1
  108. package/examples/api/sdf-rover-demo.forge.js +10 -10
  109. package/examples/api/sketch-on-face-demo.forge.js +2 -2
  110. package/examples/api/sketch-regions.forge.js +4 -4
  111. package/examples/api/transition-curves.forge.js +1 -1
  112. package/examples/api/variable-sweep-pure-sdf-test.forge.js +162 -0
  113. package/examples/api/variable-sweep-test.forge.js +2 -2
  114. package/examples/api/wood-joinery.forge.js +60 -0
  115. package/examples/compiler-corpus/enclosure-shell-cuts.forge.js +3 -3
  116. package/examples/compiler-corpus/fastener-plate-variants.forge.js +2 -2
  117. package/examples/experiments/drone-arm.forge.js +53 -0
  118. package/examples/furniture/adjustable-table.forge.js +2 -2
  119. package/examples/furniture/bathroom.forge.js +11 -11
  120. package/examples/furniture/chair.forge.js +1 -1
  121. package/examples/generative/crystal-growth.forge.js +2 -2
  122. package/examples/generative/frost-spires.forge.js +3 -3
  123. package/examples/generative/golden-spiral-tower.forge.js +3 -3
  124. package/examples/mechanical/3d-printer.forge.js +28 -28
  125. package/examples/mechanical/5-finger-robot-hand.forge.js +15 -15
  126. package/examples/mechanical/airplane-propeller.forge.js +2 -2
  127. package/examples/mechanical/fillet-enclosure.forge.js +1 -1
  128. package/examples/mechanical/headphone-hanger-v2.forge.js +2 -2
  129. package/examples/mechanical/robot_hand.forge.js +15 -15
  130. package/examples/mechanical/robot_hand_2.forge.js +9 -9
  131. package/examples/products/bottle.forge.js +1 -1
  132. package/examples/products/chess-set.forge.js +19 -19
  133. package/examples/products/classical-piano.forge.js +11 -11
  134. package/examples/products/clock.forge.js +12 -12
  135. package/examples/products/iphone.forge.js +8 -8
  136. package/examples/products/laptop.forge.js +15 -15
  137. package/examples/products/liquid-soap-dispenser.forge.js +18 -18
  138. package/examples/products/origami-fish.forge.js +8 -6
  139. package/examples/products/spiderman-cake.forge.js +4 -4
  140. package/examples/toolbox/bolted-joint.forge.js +2 -2
  141. package/package.json +7 -4
  142. package/dist/assets/EditorApp-B-vQvgam.js +0 -9888
  143. package/dist/assets/LandingPage-C5n9hDXI.js +0 -322
  144. package/dist/assets/PublishedModelPage-Dt7PCVBj.js +0 -146
  145. package/dist/assets/__vite-browser-external-CURh0WXD.js +0 -8
  146. package/dist/assets/deserializeRunResult-BLAFoiE0.js +0 -19365
  147. package/dist/assets/index-1CYp3zUp.js +0 -1455
  148. package/dist/docs-raw/CLI.md +0 -865
  149. package/dist-skill/docs/API/API.md +0 -1666
  150. package/dist-skill/docs/API/README.md +0 -37
  151. package/dist-skill/docs/API/assembly/assembly.md +0 -617
  152. package/dist-skill/docs/API/core/edge-queries.md +0 -130
  153. package/dist-skill/docs/API/core/parameters.md +0 -122
  154. package/dist-skill/docs/API/core/reserved-terms.md +0 -137
  155. package/dist-skill/docs/API/core/sdf.md +0 -326
  156. package/dist-skill/docs/API/core/skill-cli.md +0 -194
  157. package/dist-skill/docs/API/core/skill-guide.md +0 -205
  158. package/dist-skill/docs/API/core/specs.md +0 -186
  159. package/dist-skill/docs/API/core/topology.md +0 -372
  160. package/dist-skill/docs/API/entities.md +0 -268
  161. package/dist-skill/docs/API/output/bom.md +0 -58
  162. package/dist-skill/docs/API/output/brep-export.md +0 -87
  163. package/dist-skill/docs/API/output/dimensions.md +0 -67
  164. package/dist-skill/docs/API/output/export.md +0 -110
  165. package/dist-skill/docs/API/output/gcode.md +0 -195
  166. package/dist-skill/docs/API/runtime/viewport.md +0 -420
  167. package/dist-skill/docs/API/sheet-metal/sheet-metal.md +0 -185
  168. package/dist-skill/docs/API/sketch/anchor.md +0 -37
  169. package/dist-skill/docs/API/sketch/booleans.md +0 -91
  170. package/dist-skill/docs/API/sketch/core.md +0 -73
  171. package/dist-skill/docs/API/sketch/extrude.md +0 -62
  172. package/dist-skill/docs/API/sketch/on-face.md +0 -104
  173. package/dist-skill/docs/API/sketch/operations.md +0 -78
  174. package/dist-skill/docs/API/sketch/path.md +0 -75
  175. package/dist-skill/docs/API/sketch/primitives.md +0 -146
  176. package/dist-skill/docs/API/sketch/regions.md +0 -80
  177. package/dist-skill/docs/API/sketch/text.md +0 -108
  178. package/dist-skill/docs/API/sketch/transforms.md +0 -65
  179. package/dist-skill/docs/API/toolbox/fasteners.md +0 -129
  180. package/dist-skill/docs/CLI.md +0 -865
  181. package/dist-skill/docs/INDEX.md +0 -94
  182. package/dist-skill/docs/RELEASING.md +0 -55
  183. package/dist-skill/docs/cli-monetization.md +0 -111
  184. package/dist-skill/docs/deployment.md +0 -281
  185. package/dist-skill/docs/generated/concepts.md +0 -2112
  186. package/dist-skill/docs/internals/shape-from-slices.md +0 -152
  187. package/dist-skill/docs/platform/admin.md +0 -45
  188. package/dist-skill/docs/platform/architecture.md +0 -79
  189. package/dist-skill/docs/platform/auth.md +0 -110
  190. package/dist-skill/docs/platform/email.md +0 -67
  191. package/dist-skill/docs/platform/projects.md +0 -111
  192. package/dist-skill/docs/platform/sharing.md +0 -90
  193. package/dist-skill/docs/runbook.md +0 -345
@@ -1,345 +0,0 @@
1
- # ForgeCAD Hosted Service — Runbook
2
-
3
- Operational reference for running, testing, and troubleshooting the forgecad.io hosted service.
4
-
5
- For the full documentation index see [INDEX.md](../INDEX.md).
6
- For environment variables, Docker setup, and deployment details see [deployment.md](deployment.md).
7
- For releasing new versions see [RELEASING.md](../RELEASING.md).
8
- For platform feature docs (auth, projects, sharing, admin, email) see [platform/](../platform/).
9
-
10
- ---
11
-
12
- ## Quick Reference
13
-
14
- | What | Command |
15
- |------|---------|
16
- | Start local DB | `npm run dev:db` |
17
- | Stop local DB | `npm run dev:db:stop` |
18
- | Start API server | `npm run dev:server` |
19
- | Start frontend (with API proxy) | `npm run dev:studio` |
20
- | Run API tests | `bash scripts/test-shares-api.sh` |
21
- | Run unit tests | `npm run test:unit` |
22
- | Run full test suite | `npm test` |
23
- | Health check | `curl http://localhost:5174/api/health` |
24
- | SSH to production | `ssh hetzner` |
25
-
26
- ---
27
-
28
- ## Local Development Stack
29
-
30
- ### Minimal (editor only, no auth)
31
-
32
- ```bash
33
- npm run dev
34
- ```
35
-
36
- No database, no login. For geometry, sketches, viewer work.
37
-
38
- ### Full stack (auth, projects, sharing)
39
-
40
- Three terminals:
41
-
42
- ```bash
43
- # 1. Database
44
- npm run dev:db
45
-
46
- # 2. API server (port 5174)
47
- npm run dev:server
48
-
49
- # 3. Frontend (port 5173, proxies /api → 5174)
50
- npm run dev:studio
51
- ```
52
-
53
- Open http://localhost:5173. Dev credentials are hardcoded in `dev:server` — see [deployment.md](deployment.md#local-development).
54
-
55
- ### Verify the stack is healthy
56
-
57
- ```bash
58
- # API health
59
- curl -s http://localhost:5174/api/health | python3 -m json.tool
60
-
61
- # Database
62
- docker exec forgecad-postgresql-1 psql -U forgecad -d forgecad -c "SELECT count(*) FROM users;"
63
-
64
- # Migration state
65
- docker exec forgecad-postgresql-1 psql -U forgecad -d forgecad -c "SELECT * FROM _migrations ORDER BY id;"
66
- ```
67
-
68
- ---
69
-
70
- ## Testing
71
-
72
- ### API tests (end-to-end, from terminal)
73
-
74
- These scripts exercise the real server — no mocks, real HTTP, real database.
75
-
76
- | Script | What it tests | Prerequisites |
77
- |--------|--------------|---------------|
78
- | `scripts/test-shares-api.sh` | Publish, fetch, update, unpublish, auth enforcement | `dev:db` + `dev:server` |
79
-
80
- Run:
81
-
82
- ```bash
83
- bash scripts/test-shares-api.sh
84
- ```
85
-
86
- The script registers a fresh test user, runs through the full lifecycle, and cleans up. Each run uses a unique email so it's safe to re-run.
87
-
88
- ### Adding new API test scripts
89
-
90
- Follow the pattern in `test-shares-api.sh`:
91
-
92
- 1. Name: `scripts/test-<feature>-api.sh`
93
- 2. Check server health first (`/api/health`)
94
- 3. Register a unique test user per run
95
- 4. Use `acurl()` helper for authenticated requests
96
- 5. Assert HTTP status codes and response fields
97
- 6. Clean up (delete created resources)
98
- 7. Print colored pass/fail per step
99
-
100
- ### Unit tests
101
-
102
- ```bash
103
- npm run test:unit # vitest
104
- npm test # unit + CLI invariant checks
105
- ```
106
-
107
- ### Invariant checks (CLI)
108
-
109
- ```bash
110
- node dist-cli/forgecad.js check suite
111
- ```
112
-
113
- Runs compiler snapshots, example validation, parameter scanning, transform/dimension invariants.
114
-
115
- ---
116
-
117
- ## Database
118
-
119
- ### Migrations
120
-
121
- Migrations run automatically on server startup (`server/db/migrate.ts`). The system:
122
-
123
- 1. Maintains a `_migrations` table tracking applied migrations by sequential ID
124
- 2. Runs unapplied migrations in order on boot
125
- 3. Each migration is idempotent SQL (`CREATE TABLE IF NOT EXISTS`, `ALTER ... ADD COLUMN IF NOT EXISTS`)
126
-
127
- **To add a new migration:** append to the `MIGRATIONS` array in `server/db/migrate.ts`.
128
-
129
- ### Inspect the database locally
130
-
131
- ```bash
132
- docker exec -it forgecad-postgresql-1 psql -U forgecad -d forgecad
133
- ```
134
-
135
- Common queries:
136
-
137
- ```sql
138
- -- List tables
139
- \dt
140
-
141
- -- Users
142
- SELECT id, email, name, role, created_at FROM users;
143
-
144
- -- Projects
145
- SELECT id, slug, name, visibility, owner_id FROM projects;
146
-
147
- -- Shared/published models
148
- SELECT share_id, filename, title, owner_id, updated_at FROM shared_files;
149
-
150
- -- Audit log (recent)
151
- SELECT action, details, created_at FROM audit_log ORDER BY created_at DESC LIMIT 20;
152
-
153
- -- Migration state
154
- SELECT * FROM _migrations ORDER BY id;
155
- ```
156
-
157
- ### Reset local database
158
-
159
- ```bash
160
- npm run dev:db:stop
161
- docker volume rm forgecad_postgresql-dev-data # or the worktree-specific volume name
162
- npm run dev:db
163
- # Server will re-run all migrations on next start
164
- ```
165
-
166
- ---
167
-
168
- ## Production (Hetzner / Coolify)
169
-
170
- ### Access
171
-
172
- ```bash
173
- ssh hetzner # see ~/.ssh/config for host alias
174
- ```
175
-
176
- ### Find containers
177
-
178
- ```bash
179
- docker ps --format "{{.Names}}" | grep forge
180
- ```
181
-
182
- ### Logs
183
-
184
- ```bash
185
- # App logs (recent)
186
- docker logs --tail 200 <forgecad-container>
187
-
188
- # Follow live
189
- docker logs -f <forgecad-container>
190
-
191
- # Filter for errors
192
- docker logs <forgecad-container> 2>&1 | grep -i error | tail -20
193
- ```
194
-
195
- ### Database access in production
196
-
197
- ```bash
198
- # Get credentials from the app container's environment
199
- docker exec <forgecad-container> env | grep POSTGRES
200
-
201
- # Connect
202
- docker exec -it <postgres-container> psql -U <USER> -d forgecad
203
- ```
204
-
205
- ### Health check
206
-
207
- ```bash
208
- curl -s https://forgecad.io/api/health | python3 -m json.tool
209
- ```
210
-
211
- ### Verify a deployment landed
212
-
213
- Coolify auto-builds and deploys on push to `mainline`. This usually takes 2–5 minutes. The deploy is triggered by Coolify polling the repo (not a webhook), so the delay varies.
214
-
215
- To confirm:
216
-
217
- ```bash
218
- # 1. Check container was recently recreated (look at the "Up X minutes" status and CreatedAt)
219
- ssh hetzner 'docker ps --format "{{.Names}}\t{{.CreatedAt}}\t{{.Status}}" | grep -E "^forgecad-" | grep -v postgres'
220
-
221
- # 2. Check for healthy status
222
- ssh hetzner 'docker ps --format "{{.Names}}\t{{.Status}}" | grep -E "^forgecad-" | grep -v postgres | grep healthy'
223
-
224
- # 3. Check startup logs for errors
225
- ssh hetzner 'docker logs --tail 30 $(docker ps --format "{{.Names}}" | grep -E "^forgecad-" | grep -v postgres) 2>&1'
226
-
227
- # 4. Hit the health endpoint
228
- curl -s https://forgecad.io/api/health | python3 -m json.tool
229
-
230
- # 5. Verify specific code landed (check compiled output, not source)
231
- ssh hetzner 'docker exec $(docker ps --format "{{.Names}}" | grep -E "^forgecad-" | grep -v postgres) grep -c "YOUR_KEYWORD" /app/dist-server/routes/files.js'
232
- ```
233
-
234
- Container names change on each deploy — always discover dynamically with `docker ps | grep forgecad`. The app dir is `/app/` with compiled output in `dist/`, `dist-server/`, `dist-cli/`.
235
-
236
- ### Restart
237
-
238
- Coolify auto-deploys on push to `mainline`. For manual restart:
239
-
240
- ```bash
241
- docker restart $(docker ps --format "{{.Names}}" | grep -E "^forgecad-" | grep -v postgres)
242
- ```
243
-
244
- ### System resources
245
-
246
- ```bash
247
- df -h # disk
248
- free -h # memory
249
- docker stats --no-stream # per-container CPU/memory
250
- ```
251
-
252
- ---
253
-
254
- ## API Endpoints Reference
255
-
256
- ### Public (no auth)
257
-
258
- | Method | Route | Purpose |
259
- |--------|-------|---------|
260
- | GET | `/api/health` | Server health + uptime |
261
- | GET | `/api/shares/:shareId` | Fetch a published model |
262
-
263
- ### Auth
264
-
265
- | Method | Route | Purpose |
266
- |--------|-------|---------|
267
- | POST | `/api/auth/register` | Create account |
268
- | POST | `/api/auth/login` | Login (returns cookies) |
269
- | POST | `/api/auth/refresh` | Refresh access token |
270
- | POST | `/api/auth/logout` | Clear session |
271
- | GET | `/api/auth/session` | Current user info |
272
- | GET | `/api/auth/providers` | OAuth provider URLs |
273
- | POST | `/api/auth/callback/:provider` | OAuth callback |
274
- | POST | `/api/auth/forgot-password` | Request password reset |
275
- | POST | `/api/auth/reset-password` | Apply password reset |
276
- | GET | `/api/auth/verify-email` | Confirm email |
277
- | POST | `/api/auth/resend-verification` | Resend verification email |
278
-
279
- ### Projects (all require auth)
280
-
281
- | Method | Route | Role | Purpose |
282
- |--------|-------|------|---------|
283
- | GET | `/api/projects` | — | List user's projects |
284
- | POST | `/api/projects` | — | Create project |
285
- | GET | `/api/projects/:id` | viewer | Project details |
286
- | PATCH | `/api/projects/:id` | owner | Update project |
287
- | DELETE | `/api/projects/:id` | owner | Delete project |
288
- | GET | `/api/projects/:id/members` | viewer | List members |
289
- | POST | `/api/projects/:id/members` | owner | Add member |
290
- | PATCH | `/api/projects/:id/members/:userId` | owner | Update member role |
291
- | DELETE | `/api/projects/:id/members/:userId` | owner | Remove member |
292
-
293
- ### Files (all require auth + project role)
294
-
295
- | Method | Route | Role | Purpose |
296
- |--------|-------|------|---------|
297
- | GET | `/api/projects/:id/watch` | viewer | SSE file watcher |
298
- | POST | `/api/projects/:id/save` | editor | Save file |
299
- | POST | `/api/projects/:id/delete` | editor | Delete file |
300
- | POST | `/api/projects/:id/mkdir` | editor | Create directory |
301
- | GET | `/api/projects/:id/read-binary` | viewer | Download mesh file |
302
-
303
- ### Shares (published models)
304
-
305
- | Method | Route | Auth | Purpose |
306
- |--------|-------|------|---------|
307
- | GET | `/api/shares/:shareId` | none | Fetch published model (public) |
308
- | GET | `/api/shares` | required | List user's published models |
309
- | POST | `/api/shares` | required | Publish or update a model |
310
- | DELETE | `/api/shares/:shareId` | required (owner) | Unpublish |
311
-
312
- ---
313
-
314
- ## Troubleshooting
315
-
316
- ### Server won't start
317
-
318
- | Symptom | Cause | Fix |
319
- |---------|-------|-----|
320
- | `pino-pretty` transport error | Missing dev dependency in worktree | Use `NODE_ENV=production` or install pino-pretty |
321
- | Port 5174 already in use | Another server instance running | `lsof -i :5174` then kill the PID |
322
- | `FORGE_DB_URL` missing | Env var not set | Use `npm run dev:server` which sets it automatically |
323
- | Connection refused on :5432 | Postgres not running | `npm run dev:db` |
324
-
325
- ### Auth issues
326
-
327
- | Symptom | Cause | Fix |
328
- |---------|-------|-----|
329
- | 500 on login/register | Missing `FORGE_JWT_SECRET` | Set it (any string for dev, `openssl rand -base64 32` for prod) |
330
- | 401 on authenticated endpoints | Expired access token (15 min) | Client should auto-refresh; check refresh token cookie |
331
- | CORS errors in browser | `FORGE_ALLOWED_ORIGINS` mismatch | Must match the frontend's origin exactly |
332
-
333
- ### Email issues
334
-
335
- | Symptom | Cause | Fix |
336
- |---------|-------|-----|
337
- | No verification/reset email received; logs show `[email] To: user@...` | `RESEND_API_KEY` is empty — falling back to console log | Set `RESEND_API_KEY` in Coolify → redeploy. See [guides/email-setup.md](guides/email-setup.md) |
338
-
339
- ### Database issues
340
-
341
- | Symptom | Cause | Fix |
342
- |---------|-------|-----|
343
- | Migration fails | Schema conflict from manual changes | Reset local DB (see above) |
344
- | `relation does not exist` | Migrations didn't run | Check `_migrations` table; restart server |
345
- | Quota errors on file save | User's `storage_used_bytes` exceeded 50MB | Check with `SELECT storage_used_bytes FROM users WHERE ...` |