db-model-router 1.0.2 → 1.0.4
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/README.md +317 -202
- package/docs/SKILL.md +250 -33
- package/docs/adapters/cockroachdb.md +1 -1
- package/docs/adapters/dynamodb.md +1 -1
- package/docs/adapters/mongodb.md +1 -1
- package/docs/adapters/mssql.md +1 -1
- package/docs/adapters/oracle.md +1 -1
- package/docs/adapters/postgres.md +1 -1
- package/docs/adapters/redis.md +1 -1
- package/docs/adapters/sqlite3.md +1 -1
- package/package.json +12 -6
- package/src/cli/commands/diff.js +114 -0
- package/src/cli/commands/doctor.js +181 -0
- package/src/cli/commands/generate-llm-docs.js +418 -0
- package/src/cli/commands/generate.js +240 -0
- package/src/cli/commands/help.js +180 -0
- package/src/cli/commands/init.js +181 -0
- package/src/cli/commands/inspect.js +222 -0
- package/src/cli/diff-engine.js +198 -0
- package/src/cli/flags.js +112 -0
- package/src/cli/generate-model.js +5 -4
- package/src/cli/generate-route.js +255 -14
- package/src/cli/init/dependencies.js +92 -0
- package/src/cli/init/generators.js +1791 -0
- package/src/cli/init/prompt.js +191 -0
- package/src/cli/init.js +404 -0
- package/src/cli/main.js +175 -0
- package/src/commons/model.js +5 -6
- package/src/commons/route.js +24 -0
- package/src/index.js +2 -0
- package/src/schema/schema-parser.js +78 -0
- package/src/schema/schema-printer.js +77 -0
- package/src/schema/schema-to-meta.js +78 -0
- package/src/schema/schema-validator.js +255 -0
- package/src/serve.js +5 -3
- package/docs/README.md +0 -208
- package/src/cli/generate-app.js +0 -359
package/README.md
CHANGED
|
@@ -2,11 +2,26 @@
|
|
|
2
2
|
|
|
3
3
|
A database-agnostic REST API generator for Node.js. Works with Express or ultimate-express (a high-performance drop-in replacement). Define a model, get a full CRUD API with filtering, pagination, and bulk operations — backed by any of 9 supported databases.
|
|
4
4
|
|
|
5
|
+
## Build a REST API with AI
|
|
6
|
+
|
|
7
|
+
This library is designed to be driven by an AI assistant. Give it a prompt like this:
|
|
8
|
+
|
|
9
|
+
```
|
|
10
|
+
Use db-model-router to build a REST API for a task management app with postgres.
|
|
11
|
+
I need: users (name, email, password_hash), projects (name, description, owner_id → users),
|
|
12
|
+
and tasks (title, status, priority, project_id → projects, assignee_id → users).
|
|
13
|
+
Scaffold the project, write the migrations, generate models and routes with parent-child
|
|
14
|
+
relationships for projects.tasks, and make sure everything runs.
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
For the LLM skill reference, see [SKILL.md](./docs/SKILL.md).
|
|
18
|
+
|
|
5
19
|
## Supported Adapters
|
|
6
20
|
|
|
7
21
|
| Adapter | Module Key | Driver | Install |
|
|
8
22
|
| --------------------------------------------- | ------------- | ------------------------ | ---------------------------------------------------------------------- |
|
|
9
23
|
| [MySQL](#mysql-example) | `mysql` | mysql2 | `npm i db-model-router mysql2` |
|
|
24
|
+
| MariaDB | `mariadb` | mysql2 | `npm i db-model-router mysql2` |
|
|
10
25
|
| [PostgreSQL](./docs/adapters/postgres.md) | `postgres` | pg | `npm i db-model-router pg` |
|
|
11
26
|
| [SQLite3](./docs/adapters/sqlite3.md) | `sqlite3` | better-sqlite3 | `npm i db-model-router better-sqlite3` |
|
|
12
27
|
| [MongoDB](./docs/adapters/mongodb.md) | `mongodb` | mongodb | `npm i db-model-router mongodb` |
|
|
@@ -55,6 +70,306 @@ npm install db-model-router @aws-sdk/client-dynamodb @aws-sdk/lib-dynamodb
|
|
|
55
70
|
|
|
56
71
|
Both `express` and `ultimate-express` are optional peer dependencies. The library auto-detects which one is installed (preferring `ultimate-express` when both are present). All database drivers are also optional peer dependencies, so your `node_modules` stays lean.
|
|
57
72
|
|
|
73
|
+
## Quick Start
|
|
74
|
+
|
|
75
|
+
The fastest way to start a new project:
|
|
76
|
+
|
|
77
|
+
```bash
|
|
78
|
+
# Scaffold a project interactively
|
|
79
|
+
npx db-model-router init
|
|
80
|
+
|
|
81
|
+
# Or fully non-interactive from a schema file
|
|
82
|
+
db-model-router init --from dbmr.schema.json --yes --no-install
|
|
83
|
+
db-model-router generate --from dbmr.schema.json
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
After scaffolding:
|
|
87
|
+
|
|
88
|
+
```bash
|
|
89
|
+
# 1. Edit .env with your database credentials
|
|
90
|
+
# 2. Start developing
|
|
91
|
+
npm run dev
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
## Schema-Driven Workflow
|
|
95
|
+
|
|
96
|
+
Instead of running multiple CLI commands manually, you can define your entire project in a single `dbmr.schema.json` file and let the CLI generate everything from it.
|
|
97
|
+
|
|
98
|
+
### The Schema File
|
|
99
|
+
|
|
100
|
+
`dbmr.schema.json` is a declarative JSON file that describes your adapter, framework, tables, columns, relationships, and options — all in one place:
|
|
101
|
+
|
|
102
|
+
```json
|
|
103
|
+
{
|
|
104
|
+
"adapter": "postgres",
|
|
105
|
+
"framework": "express",
|
|
106
|
+
"options": {
|
|
107
|
+
"session": "redis",
|
|
108
|
+
"rateLimiting": true,
|
|
109
|
+
"helmet": true,
|
|
110
|
+
"logger": true,
|
|
111
|
+
"loki": false
|
|
112
|
+
},
|
|
113
|
+
"tables": {
|
|
114
|
+
"users": {
|
|
115
|
+
"columns": {
|
|
116
|
+
"user_id": "auto_increment",
|
|
117
|
+
"name": "required|string",
|
|
118
|
+
"email": "required|string",
|
|
119
|
+
"age": "integer",
|
|
120
|
+
"is_deleted": "boolean",
|
|
121
|
+
"created_at": "datetime",
|
|
122
|
+
"updated_at": "datetime"
|
|
123
|
+
},
|
|
124
|
+
"pk": "user_id",
|
|
125
|
+
"unique": ["email"],
|
|
126
|
+
"softDelete": "is_deleted",
|
|
127
|
+
"timestamps": {
|
|
128
|
+
"created_at": "created_at",
|
|
129
|
+
"modified_at": "updated_at"
|
|
130
|
+
}
|
|
131
|
+
},
|
|
132
|
+
"posts": {
|
|
133
|
+
"columns": {
|
|
134
|
+
"post_id": "auto_increment",
|
|
135
|
+
"title": "required|string",
|
|
136
|
+
"body": "string",
|
|
137
|
+
"user_id": "required|integer",
|
|
138
|
+
"created_at": "datetime",
|
|
139
|
+
"modified_at": "datetime"
|
|
140
|
+
},
|
|
141
|
+
"pk": "post_id",
|
|
142
|
+
"unique": ["post_id"]
|
|
143
|
+
}
|
|
144
|
+
},
|
|
145
|
+
"relationships": [
|
|
146
|
+
{ "parent": "users", "child": "posts", "foreignKey": "user_id" }
|
|
147
|
+
]
|
|
148
|
+
}
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
Table entries support these fields:
|
|
152
|
+
|
|
153
|
+
| Field | Required | Description |
|
|
154
|
+
| ------------ | -------- | ------------------------------------------------------------------------ |
|
|
155
|
+
| `columns` | Yes | Object mapping column names to Column_Rule strings (include ALL columns) |
|
|
156
|
+
| `pk` | Yes | Primary key column name (convention: `<table>_id`) |
|
|
157
|
+
| `unique` | No | Array of unique constraint columns (defaults to `[pk]`) |
|
|
158
|
+
| `softDelete` | No | Column name used for soft-delete |
|
|
159
|
+
| `timestamps` | No | Object with `created_at` and `modified_at` column name mapping |
|
|
160
|
+
|
|
161
|
+
Column rules use the format `(required|)?(string|integer|numeric|boolean|object|datetime|auto_increment)`.
|
|
162
|
+
|
|
163
|
+
- `auto_increment` — auto-incrementing PK (SERIAL in Postgres, AUTO_INCREMENT in MySQL/MariaDB)
|
|
164
|
+
- `datetime` — date/time columns (TIMESTAMP, DATETIME, DATE)
|
|
165
|
+
- `required|<type>` — NOT NULL constraint on insert/update
|
|
166
|
+
|
|
167
|
+
### Unified CLI: `db-model-router`
|
|
168
|
+
|
|
169
|
+
The `db-model-router` command is the unified entry point with five subcommands:
|
|
170
|
+
|
|
171
|
+
```bash
|
|
172
|
+
db-model-router <subcommand> [flags]
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
| Subcommand | Description |
|
|
176
|
+
| ---------- | ------------------------------------------------------------------- |
|
|
177
|
+
| `init` | Scaffold a new project (optionally from a schema file) |
|
|
178
|
+
| `inspect` | Introspect a live database and produce a `dbmr.schema.json` |
|
|
179
|
+
| `generate` | Generate models, routes, tests, and OpenAPI spec from the schema |
|
|
180
|
+
| `doctor` | Validate schema, check dependencies, verify generated files in sync |
|
|
181
|
+
| `diff` | Preview what changes regeneration would make (read-only) |
|
|
182
|
+
|
|
183
|
+
#### Universal Flags
|
|
184
|
+
|
|
185
|
+
All subcommands accept these flags:
|
|
186
|
+
|
|
187
|
+
| Flag | Description |
|
|
188
|
+
| -------------- | ----------------------------------------------------------- |
|
|
189
|
+
| `--yes` | Accept all defaults, suppress interactive prompts |
|
|
190
|
+
| `--json` | Output machine-readable JSON instead of human-readable text |
|
|
191
|
+
| `--dry-run` | Preview actions without writing files or running commands |
|
|
192
|
+
| `--no-install` | Skip `npm install` (applies to commands that would run it) |
|
|
193
|
+
| `--help` | Show usage information for the subcommand |
|
|
194
|
+
|
|
195
|
+
#### Quick Workflow Example
|
|
196
|
+
|
|
197
|
+
```bash
|
|
198
|
+
# 1. Introspect an existing database into a schema file
|
|
199
|
+
db-model-router inspect --type postgres --env .env
|
|
200
|
+
|
|
201
|
+
# 2. (Optional) Edit dbmr.schema.json to add relationships, tweak columns, etc.
|
|
202
|
+
|
|
203
|
+
# 3. Generate all artifacts from the schema
|
|
204
|
+
db-model-router generate --from dbmr.schema.json
|
|
205
|
+
|
|
206
|
+
# 4. Check everything is in sync
|
|
207
|
+
db-model-router doctor --from dbmr.schema.json
|
|
208
|
+
|
|
209
|
+
# 5. Preview what a regeneration would change
|
|
210
|
+
db-model-router diff --from dbmr.schema.json
|
|
211
|
+
```
|
|
212
|
+
|
|
213
|
+
Or start a brand-new project from a schema file:
|
|
214
|
+
|
|
215
|
+
```bash
|
|
216
|
+
# Scaffold project + generate everything in one go
|
|
217
|
+
db-model-router init --from dbmr.schema.json --yes --no-install
|
|
218
|
+
db-model-router generate --from dbmr.schema.json
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
### Command Reference
|
|
222
|
+
|
|
223
|
+
#### `init`
|
|
224
|
+
|
|
225
|
+
Scaffold a new project from a schema file or interactively. Generates an ESM-based project (`"type": "module"` in package.json) with Docker support.
|
|
226
|
+
|
|
227
|
+
| Flag / Arg | Description |
|
|
228
|
+
| -------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
229
|
+
| `--from <path>` | Read adapter, framework, and options from a `dbmr.schema.json` file |
|
|
230
|
+
| `--framework <name>` | Express framework: `express` or `ultimate-express` |
|
|
231
|
+
| `--database <name>` | Database adapter: `mysql`, `mariadb`, `postgres`, `sqlite3`, `mongodb`, `mssql`, `cockroachdb`, `oracle`, `redis`, `dynamodb` |
|
|
232
|
+
| `--db <name>` | Alias for `--database` |
|
|
233
|
+
| `--session <type>` | Session store: `memory`, `redis`, `database` |
|
|
234
|
+
| `--output <dir>` | Directory for backend source files (relative to cwd). `package.json` and `app.js` stay in root; `commons/`, `route/`, `middleware/`, `migrations/` go inside this folder. |
|
|
235
|
+
| `--rateLimiting` | Enable rate limiting via `express-rate-limit` (default: yes) |
|
|
236
|
+
| `--helmet` | Enable Helmet security headers (default: yes) |
|
|
237
|
+
| `--logger` | Enable Winston request logger (default: yes) |
|
|
238
|
+
| `--loki` | Enable Grafana Loki log transport + Loki/Grafana in docker-compose (default: no, only asked when `--logger` is enabled) |
|
|
239
|
+
|
|
240
|
+
```bash
|
|
241
|
+
# Non-interactive with output directory
|
|
242
|
+
db-model-router init --framework express --database postgres --output backend --yes
|
|
243
|
+
|
|
244
|
+
# With Loki logging
|
|
245
|
+
db-model-router init --database postgres --logger --loki --yes
|
|
246
|
+
|
|
247
|
+
# From schema, skip install
|
|
248
|
+
db-model-router init --from dbmr.schema.json --yes --no-install
|
|
249
|
+
|
|
250
|
+
# Dry run to preview files
|
|
251
|
+
db-model-router init --from dbmr.schema.json --dry-run
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
Generated project structure (with `--output backend`):
|
|
255
|
+
|
|
256
|
+
```
|
|
257
|
+
├── package.json # root (type: "module")
|
|
258
|
+
├── app.js # ESM entry point
|
|
259
|
+
├── .env / .env.example
|
|
260
|
+
├── .gitignore
|
|
261
|
+
├── Dockerfile # node:alpine production image
|
|
262
|
+
├── .dockerignore
|
|
263
|
+
├── docker-compose.yml # database + CloudBeaver + optional Loki/Grafana
|
|
264
|
+
├── .cloudbeaver/
|
|
265
|
+
│ └── data-sources.json # auto-connects CloudBeaver to your DB
|
|
266
|
+
├── .grafana/ # (only when --loki)
|
|
267
|
+
│ └── datasources.yml # auto-connects Grafana to Loki
|
|
268
|
+
└── backend/
|
|
269
|
+
├── commons/
|
|
270
|
+
│ ├── db.js # database init, connect, global.db
|
|
271
|
+
│ ├── session.js # session configuration
|
|
272
|
+
│ ├── security.js # helmet, rate limiting, custom headers
|
|
273
|
+
│ ├── migrate.js # migration runner (importable + standalone script)
|
|
274
|
+
│ └── add_migration.js # migration creator (importable + standalone script)
|
|
275
|
+
├── middleware/
|
|
276
|
+
│ └── logger.js # Winston logger (+ Loki transport when LOKI_HOST is set)
|
|
277
|
+
├── route/
|
|
278
|
+
│ ├── index.js # central route mounting
|
|
279
|
+
│ └── health.js # GET /health with DB connectivity check
|
|
280
|
+
└── migrations/
|
|
281
|
+
└── <timestamp>_create_migrations_table.sql
|
|
282
|
+
```
|
|
283
|
+
|
|
284
|
+
Docker services included automatically:
|
|
285
|
+
|
|
286
|
+
| Service | When | Port | Description |
|
|
287
|
+
| ----------- | ------------------------------------- | ------ | -------------------------------------- |
|
|
288
|
+
| Database | Always (except sqlite3) | Varies | Selected database with random password |
|
|
289
|
+
| Redis | `--session redis` (if DB isn't redis) | 6379 | Session store |
|
|
290
|
+
| CloudBeaver | SQL/MongoDB databases | 8978 | Web-based DB admin, auto-connected |
|
|
291
|
+
| Loki | `--loki` | 3100 | Log aggregation |
|
|
292
|
+
| Grafana | `--loki` | 3001 | Log visualization, Loki pre-configured |
|
|
293
|
+
|
|
294
|
+
npm scripts added: `start`, `dev`, `test`, `migrate`, `add_migration`, `docker:build`, `docker:up`, `docker:down`.
|
|
295
|
+
|
|
296
|
+
#### `inspect`
|
|
297
|
+
|
|
298
|
+
Introspect a live database and produce a `dbmr.schema.json` file.
|
|
299
|
+
|
|
300
|
+
| Flag / Arg | Description |
|
|
301
|
+
| ------------------ | ---------------------------------------------------------------------------------------------------------------------- |
|
|
302
|
+
| `--type <adapter>` | Database adapter to introspect (required): `mysql`, `mariadb`, `postgres`, `sqlite3`, `mssql`, `oracle`, `cockroachdb` |
|
|
303
|
+
| `--env <path>` | Path to `.env` file for database connection parameters |
|
|
304
|
+
| `--out <path>` | Output file path (default: `dbmr.schema.json`) |
|
|
305
|
+
| `--tables <list>` | Comma-separated list of tables to include (omit for all) |
|
|
306
|
+
|
|
307
|
+
```bash
|
|
308
|
+
db-model-router inspect --type postgres --env .env
|
|
309
|
+
db-model-router inspect --type sqlite3 --out schema.json --tables users,posts
|
|
310
|
+
db-model-router inspect --type mysql --json
|
|
311
|
+
```
|
|
312
|
+
|
|
313
|
+
#### `generate`
|
|
314
|
+
|
|
315
|
+
Generate models, routes, tests, OpenAPI spec, and LLM docs from a schema file. All generated code is ESM (`import`/`export`).
|
|
316
|
+
|
|
317
|
+
| Flag / Arg | Description |
|
|
318
|
+
| --------------- | ------------------------------------------------------------ |
|
|
319
|
+
| `--from <path>` | Path to schema file (default: `dbmr.schema.json`) |
|
|
320
|
+
| `--models` | Generate only model files |
|
|
321
|
+
| `--routes` | Generate only route files (including child routes and index) |
|
|
322
|
+
| `--openapi` | Generate only OpenAPI spec |
|
|
323
|
+
| `--tests` | Generate only test files |
|
|
324
|
+
| `--llm-docs` | Generate only LLM documentation (`llms.txt` + `docs/llm.md`) |
|
|
325
|
+
|
|
326
|
+
When no artifact flags are provided, all artifact types are generated.
|
|
327
|
+
|
|
328
|
+
```bash
|
|
329
|
+
db-model-router generate --from dbmr.schema.json
|
|
330
|
+
db-model-router generate --models --dry-run
|
|
331
|
+
db-model-router generate --routes --tests
|
|
332
|
+
db-model-router generate --from dbmr.schema.json --json
|
|
333
|
+
```
|
|
334
|
+
|
|
335
|
+
#### `doctor`
|
|
336
|
+
|
|
337
|
+
Validate schema, check adapter driver dependencies, and verify generated files are in sync.
|
|
338
|
+
|
|
339
|
+
| Flag / Arg | Description |
|
|
340
|
+
| --------------- | ------------------------------------------------- |
|
|
341
|
+
| `--from <path>` | Path to schema file (default: `dbmr.schema.json`) |
|
|
342
|
+
|
|
343
|
+
```bash
|
|
344
|
+
db-model-router doctor --from dbmr.schema.json
|
|
345
|
+
db-model-router doctor --json
|
|
346
|
+
```
|
|
347
|
+
|
|
348
|
+
Reports three checks: schema validation, dependency check, sync check.
|
|
349
|
+
|
|
350
|
+
#### `diff`
|
|
351
|
+
|
|
352
|
+
Preview changes between the current generated files and what the schema would produce. Read-only.
|
|
353
|
+
|
|
354
|
+
| Flag / Arg | Description |
|
|
355
|
+
| --------------- | ------------------------------------------------- |
|
|
356
|
+
| `--from <path>` | Path to schema file (default: `dbmr.schema.json`) |
|
|
357
|
+
|
|
358
|
+
```bash
|
|
359
|
+
db-model-router diff --from dbmr.schema.json
|
|
360
|
+
db-model-router diff --json
|
|
361
|
+
```
|
|
362
|
+
|
|
363
|
+
#### `help`
|
|
364
|
+
|
|
365
|
+
Show help for any command.
|
|
366
|
+
|
|
367
|
+
```bash
|
|
368
|
+
db-model-router help # general overview with per-command flags
|
|
369
|
+
db-model-router help init # detailed help for init
|
|
370
|
+
db-model-router init --help # same as above
|
|
371
|
+
```
|
|
372
|
+
|
|
58
373
|
## MySQL Example
|
|
59
374
|
|
|
60
375
|
### 1. Connect
|
|
@@ -109,13 +424,14 @@ app.use("/users", route(users));
|
|
|
109
424
|
app.listen(3000);
|
|
110
425
|
```
|
|
111
426
|
|
|
112
|
-
This creates
|
|
427
|
+
This creates 9 endpoints:
|
|
113
428
|
|
|
114
429
|
| Method | Path | Description |
|
|
115
430
|
| ------ | ------------ | ------------------------------- |
|
|
116
431
|
| GET | `/users/:id` | Get one record by PK |
|
|
117
432
|
| POST | `/users/add` | Insert a single record |
|
|
118
433
|
| PUT | `/users/:id` | Update a single record |
|
|
434
|
+
| PATCH | `/users/:id` | Partial update a single record |
|
|
119
435
|
| DELETE | `/users/:id` | Delete a single record |
|
|
120
436
|
| GET | `/users/` | List with pagination |
|
|
121
437
|
| POST | `/users/` | Bulk insert (`{ data: [...] }`) |
|
|
@@ -274,207 +590,6 @@ The model and route APIs remain identical across all adapters. See the individua
|
|
|
274
590
|
- [Redis](./docs/adapters/redis.md)
|
|
275
591
|
- [DynamoDB](./docs/adapters/dynamodb.md)
|
|
276
592
|
|
|
277
|
-
## CLI Tools
|
|
278
|
-
|
|
279
|
-
Three CLI commands are included to scaffold models, routes, and full apps from an existing database.
|
|
280
|
-
|
|
281
|
-
### generate-app
|
|
282
|
-
|
|
283
|
-
The fastest way to go from database to running API. Scaffolds a complete Express REST API project in a single command — introspects your database, generates models and routes (including parent-child relationships), and creates the app entry point, middleware, environment config, and project structure.
|
|
284
|
-
|
|
285
|
-
```bash
|
|
286
|
-
# Full app from MySQL
|
|
287
|
-
db-model-router-generate-app --type mysql --env .env
|
|
288
|
-
|
|
289
|
-
# SQLite3 into a specific directory
|
|
290
|
-
db-model-router-generate-app --type sqlite3 --database ./myapp.db --output ./my-api
|
|
291
|
-
|
|
292
|
-
# Postgres with specific tables and relationships
|
|
293
|
-
db-model-router-generate-app --type postgres --env .env --tables users,posts,posts.comments
|
|
294
|
-
```
|
|
295
|
-
|
|
296
|
-
Options:
|
|
297
|
-
|
|
298
|
-
| Option | Description |
|
|
299
|
-
| ------------ | ------------------------------------------------------------------------------- |
|
|
300
|
-
| `--type` | Database type (mysql, postgres, sqlite3, mssql, oracle, cockroachdb) [required] |
|
|
301
|
-
| `--output` | Output directory (default: current directory) |
|
|
302
|
-
| `--host` | Database host |
|
|
303
|
-
| `--port` | Database port |
|
|
304
|
-
| `--database` | Database name or file path |
|
|
305
|
-
| `--user` | Database user |
|
|
306
|
-
| `--password` | Database password |
|
|
307
|
-
| `--schema` | Schema name (postgres only) |
|
|
308
|
-
| `--tables` | Comma-separated tables, supports `parent.child` notation for relationships |
|
|
309
|
-
| `--env` | Path to .env file for DB connection |
|
|
310
|
-
|
|
311
|
-
Generated project structure:
|
|
312
|
-
|
|
313
|
-
```
|
|
314
|
-
my-api/
|
|
315
|
-
app.js # Express app with init(), db.connect(), middleware, error handler, health check
|
|
316
|
-
.env.example # Pre-filled environment template for your DB type
|
|
317
|
-
.gitignore # node_modules, .env, *.db
|
|
318
|
-
middleware/
|
|
319
|
-
logger.js # Request logger (method, URL, status, response time)
|
|
320
|
-
models/
|
|
321
|
-
users.js # Auto-generated from DB introspection
|
|
322
|
-
posts.js
|
|
323
|
-
index.js
|
|
324
|
-
routes/
|
|
325
|
-
users.js # Auto-generated route files
|
|
326
|
-
posts.js
|
|
327
|
-
index.js
|
|
328
|
-
openapi.json # OpenAPI 3.0 spec
|
|
329
|
-
migrations/
|
|
330
|
-
README.md # Placeholder for migration scripts
|
|
331
|
-
sessions/
|
|
332
|
-
README.md # Placeholder for session config
|
|
333
|
-
```
|
|
334
|
-
|
|
335
|
-
When `--tables` includes parent-child notation (e.g., `posts.comments`), the routes directory also includes scoped child route files and nested route mounting — see [Parent-Child Relationships](#parent-child-relationships-foreign-keys) below.
|
|
336
|
-
|
|
337
|
-
To start the generated app:
|
|
338
|
-
|
|
339
|
-
```bash
|
|
340
|
-
cp .env.example .env # edit with your DB credentials
|
|
341
|
-
npm install
|
|
342
|
-
node app.js
|
|
343
|
-
```
|
|
344
|
-
|
|
345
|
-
### generate-model
|
|
346
|
-
|
|
347
|
-
Connects to your database, introspects all tables, and generates model files with validation rules, primary keys, unique constraints, and auto-detected options (safeDelete, timestamps). This is called automatically by `generate-app`, but can be used standalone.
|
|
348
|
-
|
|
349
|
-
```bash
|
|
350
|
-
# Basic usage
|
|
351
|
-
db-model-router-generate-model --type mysql --host localhost --database mydb --user root --password secret
|
|
352
|
-
|
|
353
|
-
# Using an .env file
|
|
354
|
-
db-model-router-generate-model --type postgres --env .env --output ./src/models
|
|
355
|
-
|
|
356
|
-
# SQLite3
|
|
357
|
-
db-model-router-generate-model --type sqlite3 --database ./myapp.db --output ./models
|
|
358
|
-
|
|
359
|
-
# Only specific tables
|
|
360
|
-
db-model-router-generate-model --type mysql --env .env --tables users,posts,comments
|
|
361
|
-
```
|
|
362
|
-
|
|
363
|
-
Options:
|
|
364
|
-
|
|
365
|
-
| Option | Description |
|
|
366
|
-
| ------------ | ----------------------------------------------------------------------------- |
|
|
367
|
-
| `--type` | Database type (mysql, postgres, sqlite3, mssql, oracle, cockroachdb) |
|
|
368
|
-
| `--host` | Database host (default: localhost) |
|
|
369
|
-
| `--port` | Database port |
|
|
370
|
-
| `--database` | Database name (or file path for sqlite3) |
|
|
371
|
-
| `--user` | Database user |
|
|
372
|
-
| `--password` | Database password |
|
|
373
|
-
| `--schema` | Schema name (postgres only, default: public) |
|
|
374
|
-
| `--output` | Output directory (default: ./models) |
|
|
375
|
-
| `--tables` | Comma-separated list of tables to generate (supports `parent.child` notation) |
|
|
376
|
-
| `--env` | Path to .env file to load |
|
|
377
|
-
|
|
378
|
-
Auto-detection:
|
|
379
|
-
|
|
380
|
-
- Columns with `DEFAULT` values are marked as optional (not `required`)
|
|
381
|
-
- Timestamp columns (`created_at`, `updated_at`, `modified_at`, `createdAt`, etc.) are excluded from the model structure and added to the option object
|
|
382
|
-
- Soft-delete columns (`is_deleted`, `deleted`, `is_active`, `archived`, etc.) are excluded from the structure and set as `safeDelete` in the option
|
|
383
|
-
- Multi-column unique indexes are correctly grouped for the unique constraint parameter
|
|
384
|
-
|
|
385
|
-
Generated output:
|
|
386
|
-
|
|
387
|
-
```
|
|
388
|
-
models/
|
|
389
|
-
users.js # model(db, "users", {...}, "user_id", ["email"], { safeDelete: "is_deleted", ... })
|
|
390
|
-
posts.js # model(db, "posts", {...}, "post_id", ["post_id"])
|
|
391
|
-
index.js # exports { users, posts }
|
|
392
|
-
```
|
|
393
|
-
|
|
394
|
-
### generate-route
|
|
395
|
-
|
|
396
|
-
Generates Express route files for each model. If models don't exist yet, it auto-generates them first. Also generates an OpenAPI 3.0 spec (`openapi.json`) from the model metadata. This is called automatically by `generate-app`, but can be used standalone.
|
|
397
|
-
|
|
398
|
-
```bash
|
|
399
|
-
# From existing models
|
|
400
|
-
db-model-router-generate-route --models ./models --output ./routes
|
|
401
|
-
|
|
402
|
-
# Auto-generate models + routes in one step
|
|
403
|
-
db-model-router-generate-route --type mysql --env .env --models ./models --output ./routes
|
|
404
|
-
|
|
405
|
-
# SQLite3 one-liner
|
|
406
|
-
db-model-router-generate-route --type sqlite3 --database ./myapp.db
|
|
407
|
-
```
|
|
408
|
-
|
|
409
|
-
Options:
|
|
410
|
-
|
|
411
|
-
| Option | Description |
|
|
412
|
-
| ------------ | -------------------------------------------------------------------------- |
|
|
413
|
-
| `--models` | Path to models directory (default: ./models) |
|
|
414
|
-
| `--output` | Output directory for routes (default: ./routes) |
|
|
415
|
-
| `--type` | Database type — triggers model generation if models are missing |
|
|
416
|
-
| `--host` | Database host (passed to model generation) |
|
|
417
|
-
| `--port` | Database port (passed to model generation) |
|
|
418
|
-
| `--database` | Database name or file path (passed to model generation) |
|
|
419
|
-
| `--user` | Database user (passed to model generation) |
|
|
420
|
-
| `--password` | Database password (passed to model generation) |
|
|
421
|
-
| `--schema` | Schema name (passed to model generation) |
|
|
422
|
-
| `--tables` | Comma-separated tables, supports `parent.child` notation for relationships |
|
|
423
|
-
| `--env` | Path to .env file (passed to model generation) |
|
|
424
|
-
|
|
425
|
-
#### Parent-Child Relationships (Foreign Keys)
|
|
426
|
-
|
|
427
|
-
Use dot notation in `--tables` to declare parent-child relationships. This works in `generate-route`, `generate-app`, and `generate-model`. The generator creates nested routes that automatically scope child queries by the parent's foreign key.
|
|
428
|
-
|
|
429
|
-
```bash
|
|
430
|
-
# Declare that comments belong to posts
|
|
431
|
-
db-model-router-generate-route --type mysql --env .env --tables users,posts,posts.comments
|
|
432
|
-
|
|
433
|
-
# Same via generate-app
|
|
434
|
-
db-model-router-generate-app --type mysql --env .env --tables users,posts,posts.comments
|
|
435
|
-
```
|
|
436
|
-
|
|
437
|
-
The FK column is derived by convention: `<parent_singular>_id` (e.g., `posts.comments` → `post_id`).
|
|
438
|
-
|
|
439
|
-
This generates:
|
|
440
|
-
|
|
441
|
-
```
|
|
442
|
-
routes/
|
|
443
|
-
users.js # route(users)
|
|
444
|
-
posts.js # route(posts)
|
|
445
|
-
comments.js # route(comments) — direct access
|
|
446
|
-
comments_child_of_posts.js # route(comments, { post_id: "params.post_id" }) — scoped
|
|
447
|
-
index.js # mounts all routes
|
|
448
|
-
openapi.json # OpenAPI 3.0 spec
|
|
449
|
-
```
|
|
450
|
-
|
|
451
|
-
The generated `index.js` mounts both nested and top-level routes:
|
|
452
|
-
|
|
453
|
-
```js
|
|
454
|
-
// Nested: GET /api/posts/:post_id/comments — returns only comments for that post
|
|
455
|
-
router.use("/posts/:post_id/comments", commentsChildRoute);
|
|
456
|
-
|
|
457
|
-
// Direct: GET /api/comments — returns all comments
|
|
458
|
-
router.use("/comments", commentsRoute);
|
|
459
|
-
```
|
|
460
|
-
|
|
461
|
-
The child route file uses payload override to scope every query:
|
|
462
|
-
|
|
463
|
-
```js
|
|
464
|
-
// comments_child_of_posts.js
|
|
465
|
-
module.exports = route(comments, { post_id: "params.post_id" });
|
|
466
|
-
```
|
|
467
|
-
|
|
468
|
-
#### Generated output (without relationships)
|
|
469
|
-
|
|
470
|
-
```
|
|
471
|
-
routes/
|
|
472
|
-
users.js # route(users)
|
|
473
|
-
posts.js # route(posts)
|
|
474
|
-
index.js # express.Router() mounting all routes at /users, /posts, etc.
|
|
475
|
-
openapi.json # OpenAPI 3.0 spec
|
|
476
|
-
```
|
|
477
|
-
|
|
478
593
|
## Environment Setup (Docker)
|
|
479
594
|
|
|
480
595
|
A `docker-compose.yml` is included for running all supported databases locally:
|