seedorm 0.2.0 → 0.2.1
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 +56 -44
- package/dist/bin/seedorm.cjs +6 -1
- package/dist/index.cjs +5 -0
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +5 -0
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
# seedorm
|
|
2
2
|
|
|
3
|
-
Development-first ORM that lets you start with a JSON file and migrate to any SQL database by changing one line of config. No rewrites.
|
|
3
|
+
Development-first ORM that lets you start with a JSON file and migrate to any SQL database by changing one line of config. No rewrites. No drama.
|
|
4
4
|
|
|
5
5
|
## Why
|
|
6
6
|
|
|
7
|
-
Every project starts the same way: you need to store data, but you don't want to set up a database just to prototype. SeedORM lets you start building immediately with a local JSON file, then switch to a real database when you're ready
|
|
7
|
+
Every project starts the same way: you need to store data, but you don't want to set up a database just to prototype. SeedORM lets you start building immediately with a local JSON file, then switch to a real database when you're ready. Your application code doesn't change. Not one line.
|
|
8
8
|
|
|
9
9
|
## Quick start
|
|
10
10
|
|
|
@@ -15,37 +15,41 @@ npm install seedorm
|
|
|
15
15
|
```typescript
|
|
16
16
|
import { SeedORM, FieldType } from "seedorm";
|
|
17
17
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
},
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
18
|
+
async function main() {
|
|
19
|
+
const db = new SeedORM();
|
|
20
|
+
await db.connect();
|
|
21
|
+
|
|
22
|
+
const User = db.model({
|
|
23
|
+
name: "User",
|
|
24
|
+
collection: "users",
|
|
25
|
+
schema: {
|
|
26
|
+
name: { type: FieldType.String, required: true },
|
|
27
|
+
email: { type: FieldType.String, unique: true },
|
|
28
|
+
role: { type: FieldType.String, enum: ["admin", "user"], default: "user" },
|
|
29
|
+
},
|
|
30
|
+
});
|
|
31
|
+
await User.init();
|
|
32
|
+
|
|
33
|
+
// Create
|
|
34
|
+
const alice = await User.create({ name: "Alice", email: "alice@example.com" });
|
|
35
|
+
|
|
36
|
+
// Query with MongoDB-style operators
|
|
37
|
+
const admins = await User.find({
|
|
38
|
+
filter: { role: { $eq: "admin" } },
|
|
39
|
+
sort: { name: 1 },
|
|
40
|
+
limit: 10,
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
// Update
|
|
44
|
+
await User.update(alice.id, { role: "admin" });
|
|
45
|
+
|
|
46
|
+
// Delete
|
|
47
|
+
await User.delete(alice.id);
|
|
48
|
+
|
|
49
|
+
await db.disconnect();
|
|
50
|
+
}
|
|
47
51
|
|
|
48
|
-
|
|
52
|
+
main();
|
|
49
53
|
```
|
|
50
54
|
|
|
51
55
|
## Relations
|
|
@@ -87,8 +91,8 @@ const user = await User.findById("usr_abc123", {
|
|
|
87
91
|
});
|
|
88
92
|
|
|
89
93
|
// Manage many-to-many links
|
|
90
|
-
await User.associate("
|
|
91
|
-
await User.dissociate("
|
|
94
|
+
await User.associate("usr_abc123", "roles", "rol_editor");
|
|
95
|
+
await User.dissociate("usr_abc123", "roles", "rol_editor");
|
|
92
96
|
```
|
|
93
97
|
|
|
94
98
|
**Relation types:** `hasOne`, `hasMany`, `belongsTo`, `manyToMany`
|
|
@@ -123,14 +127,14 @@ SeedORM exports string enums for type-safe definitions. Plain strings also work
|
|
|
123
127
|
|
|
124
128
|
## Features
|
|
125
129
|
|
|
126
|
-
- **Zero-config start
|
|
127
|
-
- **Schema validation
|
|
128
|
-
- **Relations
|
|
129
|
-
- **Query operators
|
|
130
|
-
- **CLI tools
|
|
131
|
-
- **Migration engine
|
|
132
|
-
- **Pluggable adapters
|
|
133
|
-
- **TypeScript
|
|
130
|
+
- **Zero-config start**: data lives in a JSON file, no database setup needed
|
|
131
|
+
- **Schema validation**: type checking, required fields, unique constraints, min/max, enums
|
|
132
|
+
- **Relations**: `hasOne`, `hasMany`, `belongsTo`, `manyToMany` with eager loading via `include`
|
|
133
|
+
- **Query operators**: `$eq`, `$ne`, `$gt`, `$gte`, `$lt`, `$lte`, `$in`, `$nin`, `$like`, `$exists`
|
|
134
|
+
- **CLI tools**: `seedorm init`, `seedorm start` (REST server), `seedorm studio` (visual UI)
|
|
135
|
+
- **Migration engine**: `migrate create`, `migrate up`, `migrate to` (SQL export)
|
|
136
|
+
- **Pluggable adapters**: PostgreSQL built-in, MySQL and SQLite coming soon. Drivers are lazy-loaded and optional.
|
|
137
|
+
- **TypeScript**: written in TypeScript with full type exports, dual CJS/ESM output
|
|
134
138
|
|
|
135
139
|
## CLI
|
|
136
140
|
|
|
@@ -165,7 +169,7 @@ When running `seedorm start`, the following endpoints are available:
|
|
|
165
169
|
| `GET` | `/api/:collection` | List documents (supports `?filter=`, `?sort=`, `?limit=`, `?offset=`) |
|
|
166
170
|
| `GET` | `/api/:collection/:id` | Get document by ID |
|
|
167
171
|
| `POST` | `/api/:collection` | Create document |
|
|
168
|
-
| `PATCH` | `/api/:collection/:id` | Update document |
|
|
172
|
+
| `PUT/PATCH` | `/api/:collection/:id` | Update document |
|
|
169
173
|
| `DELETE` | `/api/:collection/:id` | Delete document |
|
|
170
174
|
|
|
171
175
|
## Requirements
|
|
@@ -174,6 +178,14 @@ When running `seedorm start`, the following endpoints are available:
|
|
|
174
178
|
- `pg` (optional, only needed for PostgreSQL adapter)
|
|
175
179
|
- `mysql2` (optional, only needed for MySQL adapter)
|
|
176
180
|
|
|
181
|
+
## Links
|
|
182
|
+
|
|
183
|
+
- [Documentation](https://seedorm.io/docs)
|
|
184
|
+
- [Getting Started](https://seedorm.io/docs/getting-started)
|
|
185
|
+
- [API Reference](https://seedorm.io/docs/api)
|
|
186
|
+
- [CLI Reference](https://seedorm.io/docs/cli)
|
|
187
|
+
- [Tutorial](https://seedorm.io/docs/tutorial)
|
|
188
|
+
|
|
177
189
|
## License
|
|
178
190
|
|
|
179
|
-
Apache 2.0
|
|
191
|
+
Apache 2.0
|
package/dist/bin/seedorm.cjs
CHANGED
|
@@ -4369,6 +4369,11 @@ var Model = class {
|
|
|
4369
4369
|
}
|
|
4370
4370
|
async init() {
|
|
4371
4371
|
await this.adapter.createCollection(this.collection, this.schema);
|
|
4372
|
+
for (const rel of Object.values(this.relations)) {
|
|
4373
|
+
if (rel.type === "manyToMany" /* ManyToMany */ && rel.joinCollection) {
|
|
4374
|
+
await this.adapter.createCollection(rel.joinCollection, {});
|
|
4375
|
+
}
|
|
4376
|
+
}
|
|
4372
4377
|
}
|
|
4373
4378
|
generateId() {
|
|
4374
4379
|
return `${this.prefix}_${nanoid(12)}`;
|
|
@@ -5650,7 +5655,7 @@ async function studioCommand(options) {
|
|
|
5650
5655
|
// src/cli/index.ts
|
|
5651
5656
|
function createCLI() {
|
|
5652
5657
|
const program3 = new Command();
|
|
5653
|
-
program3.name("seedorm").description("Development-first ORM \u2014 start with JSON, migrate to PostgreSQL/MySQL").version("0.1
|
|
5658
|
+
program3.name("seedorm").description("Development-first ORM \u2014 start with JSON, migrate to PostgreSQL/MySQL").version("0.2.1");
|
|
5654
5659
|
program3.command("init").description("Initialize a new seedorm project").option("-f, --force", "Overwrite existing config").action(initCommand);
|
|
5655
5660
|
program3.command("start").description("Start the development REST API server").option("-p, --port <port>", "Port to listen on", "4100").action(startCommand);
|
|
5656
5661
|
const migrate = program3.command("migrate").description("Migration commands");
|
package/dist/index.cjs
CHANGED
|
@@ -631,6 +631,11 @@ var Model = class {
|
|
|
631
631
|
}
|
|
632
632
|
async init() {
|
|
633
633
|
await this.adapter.createCollection(this.collection, this.schema);
|
|
634
|
+
for (const rel of Object.values(this.relations)) {
|
|
635
|
+
if (rel.type === "manyToMany" /* ManyToMany */ && rel.joinCollection) {
|
|
636
|
+
await this.adapter.createCollection(rel.joinCollection, {});
|
|
637
|
+
}
|
|
638
|
+
}
|
|
634
639
|
}
|
|
635
640
|
generateId() {
|
|
636
641
|
return `${this.prefix}_${(0, import_nanoid.nanoid)(12)}`;
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/types.ts","../src/errors.ts","../src/query/operators.ts","../src/adapters/postgres/pg-connection.ts","../src/adapters/postgres/pg-query-builder.ts","../src/adapters/postgres/postgres-adapter.ts","../src/index.ts","../src/seedorm.ts","../src/model/model.ts","../src/model/schema.ts","../src/model/field-types.ts","../src/adapters/json/json-adapter.ts","../src/query/filter.ts","../src/adapters/json/file-engine.ts","../src/adapters/json/indexer.ts"],"sourcesContent":["// ── Field & Schema Types ──\n\nexport enum FieldType {\n String = \"string\",\n Number = \"number\",\n Boolean = \"boolean\",\n Date = \"date\",\n Json = \"json\",\n Array = \"array\",\n}\n\nexport interface FieldDefinition {\n type: FieldType;\n required?: boolean;\n unique?: boolean;\n index?: boolean;\n default?: unknown;\n minLength?: number;\n maxLength?: number;\n min?: number;\n max?: number;\n enum?: unknown[];\n}\n\nexport interface SchemaDefinition {\n [field: string]: FieldType | FieldDefinition;\n}\n\nexport interface NormalizedField {\n type: FieldType;\n required: boolean;\n unique: boolean;\n index: boolean;\n default?: unknown;\n minLength?: number;\n maxLength?: number;\n min?: number;\n max?: number;\n enum?: unknown[];\n}\n\nexport interface NormalizedSchema {\n [field: string]: NormalizedField;\n}\n\n// ── Document ──\n\nexport interface Document {\n id: string;\n createdAt: string;\n updatedAt: string;\n [key: string]: unknown;\n}\n\n// ── Query / Filter ──\n\nexport interface FilterOperators {\n $eq?: unknown;\n $ne?: unknown;\n $gt?: number | string | Date;\n $gte?: number | string | Date;\n $lt?: number | string | Date;\n $lte?: number | string | Date;\n $in?: unknown[];\n $nin?: unknown[];\n $like?: string;\n $exists?: boolean;\n}\n\nexport type FieldFilter = FilterOperators | unknown;\n\nexport interface FilterQuery {\n [field: string]: FieldFilter;\n}\n\nexport interface SortOption {\n [field: string]: 1 | -1;\n}\n\nexport interface FindOptions {\n filter?: FilterQuery;\n sort?: SortOption;\n limit?: number;\n offset?: number;\n include?: string[];\n}\n\n// ── Relations ──\n\nexport enum RelationType {\n HasOne = \"hasOne\",\n HasMany = \"hasMany\",\n BelongsTo = \"belongsTo\",\n ManyToMany = \"manyToMany\",\n}\n\nexport interface RelationDefinition {\n type: RelationType;\n model: string;\n foreignKey: string;\n joinCollection?: string;\n relatedKey?: string;\n}\n\nexport interface RelationsDefinition {\n [name: string]: RelationDefinition;\n}\n\n// ── Model Definition ──\n\nexport interface ModelDefinition {\n name: string;\n collection: string;\n schema: SchemaDefinition;\n timestamps?: boolean;\n prefix?: string;\n relations?: RelationsDefinition;\n}\n\n// ── Storage Adapter ──\n\nexport interface StorageAdapter {\n connect(): Promise<void>;\n disconnect(): Promise<void>;\n\n insert(collection: string, doc: Document): Promise<Document>;\n findById(collection: string, id: string): Promise<Document | null>;\n find(collection: string, options: FindOptions): Promise<Document[]>;\n count(collection: string, filter?: FilterQuery): Promise<number>;\n update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null>;\n delete(collection: string, id: string): Promise<boolean>;\n deleteMany(collection: string, filter: FilterQuery): Promise<number>;\n\n createCollection(collection: string, schema: NormalizedSchema): Promise<void>;\n dropCollection(collection: string): Promise<void>;\n listCollections(): Promise<string[]>;\n}\n\n// ── Config ──\n\nexport enum AdapterType {\n Json = \"json\",\n Postgres = \"postgres\",\n MySQL = \"mysql\",\n}\n\nexport interface JsonAdapterConfig {\n adapter: AdapterType.Json;\n path?: string;\n}\n\nexport interface PostgresAdapterConfig {\n adapter: AdapterType.Postgres;\n url: string;\n}\n\nexport interface MySQLAdapterConfig {\n adapter: AdapterType.MySQL;\n url: string;\n}\n\nexport type AdapterConfig =\n | JsonAdapterConfig\n | PostgresAdapterConfig\n | MySQLAdapterConfig;\n\nexport interface SeedORMConfig {\n adapter: AdapterConfig;\n migrationsDir?: string;\n}\n\n// ── Migration ──\n\nexport interface MigrationStep {\n type:\n | \"createCollection\"\n | \"dropCollection\"\n | \"addField\"\n | \"dropField\"\n | \"alterField\"\n | \"addIndex\"\n | \"dropIndex\";\n collection: string;\n field?: string;\n schema?: NormalizedField;\n oldSchema?: NormalizedField;\n}\n\nexport interface Migration {\n id: string;\n name: string;\n timestamp: number;\n up: MigrationStep[];\n down: MigrationStep[];\n}\n\nexport interface MigrationRecord {\n id: string;\n name: string;\n appliedAt: string;\n}\n","export class SeedORMError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"SeedORMError\";\n }\n}\n\nexport class ValidationError extends SeedORMError {\n public field: string;\n public reason: string;\n\n constructor(field: string, reason: string) {\n super(`Validation error on \"${field}\": ${reason}`);\n this.name = \"ValidationError\";\n this.field = field;\n this.reason = reason;\n }\n}\n\nexport class AdapterError extends SeedORMError {\n public adapter: string;\n\n constructor(adapter: string, message: string) {\n super(`[${adapter}] ${message}`);\n this.name = \"AdapterError\";\n this.adapter = adapter;\n }\n}\n\nexport class CollectionNotFoundError extends SeedORMError {\n constructor(collection: string) {\n super(`Collection \"${collection}\" not found`);\n this.name = \"CollectionNotFoundError\";\n }\n}\n\nexport class DocumentNotFoundError extends SeedORMError {\n constructor(collection: string, id: string) {\n super(`Document \"${id}\" not found in \"${collection}\"`);\n this.name = \"DocumentNotFoundError\";\n }\n}\n\nexport class UniqueConstraintError extends SeedORMError {\n public field: string;\n public value: unknown;\n\n constructor(collection: string, field: string, value: unknown) {\n super(\n `Unique constraint violation on \"${collection}.${field}\": value ${JSON.stringify(value)} already exists`,\n );\n this.name = \"UniqueConstraintError\";\n this.field = field;\n this.value = value;\n }\n}\n","import type { FilterOperators } from \"../types.js\";\n\ntype OperatorFn = (fieldValue: unknown, operand: unknown) => boolean;\n\nconst operators: Record<string, OperatorFn> = {\n $eq: (val, op) => val === op,\n\n $ne: (val, op) => val !== op,\n\n $gt: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val > op;\n if (typeof val === \"string\" && typeof op === \"string\") return val > op;\n return false;\n },\n\n $gte: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val >= op;\n if (typeof val === \"string\" && typeof op === \"string\") return val >= op;\n return false;\n },\n\n $lt: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val < op;\n if (typeof val === \"string\" && typeof op === \"string\") return val < op;\n return false;\n },\n\n $lte: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val <= op;\n if (typeof val === \"string\" && typeof op === \"string\") return val <= op;\n return false;\n },\n\n $in: (val, op) => {\n if (!Array.isArray(op)) return false;\n return op.includes(val);\n },\n\n $nin: (val, op) => {\n if (!Array.isArray(op)) return true;\n return !op.includes(val);\n },\n\n $like: (val, op) => {\n if (typeof val !== \"string\" || typeof op !== \"string\") return false;\n // Convert SQL-like pattern to regex: % → .*, _ → .\n const escaped = op.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\");\n const pattern = escaped.replace(/%/g, \".*\").replace(/_/g, \".\");\n return new RegExp(`^${pattern}$`, \"i\").test(val);\n },\n\n $exists: (val, op) => {\n const exists = val !== undefined && val !== null;\n return op ? exists : !exists;\n },\n};\n\nexport function applyOperator(\n key: string,\n fieldValue: unknown,\n operand: unknown,\n): boolean {\n const fn = operators[key];\n if (!fn) throw new Error(`Unknown operator: ${key}`);\n return fn(fieldValue, operand);\n}\n\nexport function isOperatorObject(value: unknown): value is FilterOperators {\n if (value === null || typeof value !== \"object\" || Array.isArray(value))\n return false;\n return Object.keys(value as object).some((k) => k.startsWith(\"$\"));\n}\n\nexport const OPERATORS = Object.keys(operators);\n","import { AdapterError } from \"../../errors.js\";\n\n// pg is an optional peer dependency\nlet pgModule: typeof import(\"pg\") | null = null;\n\nasync function loadPg(): Promise<typeof import(\"pg\")> {\n if (pgModule) return pgModule;\n try {\n pgModule = await import(\"pg\");\n return pgModule;\n } catch {\n throw new AdapterError(\n \"postgres\",\n 'The \"pg\" package is required for PostgreSQL. Install it with: npm install pg',\n );\n }\n}\n\nexport class PgConnection {\n private pool: import(\"pg\").Pool | null = null;\n private url: string;\n\n constructor(url: string) {\n this.url = url;\n }\n\n async connect(): Promise<void> {\n const pg = await loadPg();\n this.pool = new pg.Pool({ connectionString: this.url });\n // Test the connection\n const client = await this.pool.connect();\n client.release();\n }\n\n async disconnect(): Promise<void> {\n if (this.pool) {\n await this.pool.end();\n this.pool = null;\n }\n }\n\n async query<T extends Record<string, unknown> = Record<string, unknown>>(\n text: string,\n params?: unknown[],\n ): Promise<{ rows: T[]; rowCount: number }> {\n if (!this.pool) {\n throw new AdapterError(\"postgres\", \"Not connected\");\n }\n const result = await this.pool.query(text, params);\n return { rows: result.rows as T[], rowCount: result.rowCount ?? 0 };\n }\n}\n","import type { FilterQuery, FindOptions, SortOption } from \"../../types.js\";\nimport { isOperatorObject } from \"../../query/operators.js\";\n\ninterface BuiltQuery {\n text: string;\n params: unknown[];\n}\n\nexport function buildSelect(\n collection: string,\n options: FindOptions,\n): BuiltQuery {\n const params: unknown[] = [];\n let text = `SELECT * FROM \"${collection}\"`;\n\n if (options.filter && Object.keys(options.filter).length > 0) {\n const where = buildWhere(options.filter, params);\n text += ` WHERE ${where}`;\n }\n\n if (options.sort) {\n text += ` ORDER BY ${buildOrderBy(options.sort)}`;\n }\n\n if (options.limit !== undefined) {\n params.push(options.limit);\n text += ` LIMIT $${params.length}`;\n }\n\n if (options.offset !== undefined) {\n params.push(options.offset);\n text += ` OFFSET $${params.length}`;\n }\n\n return { text, params };\n}\n\nexport function buildCount(\n collection: string,\n filter?: FilterQuery,\n): BuiltQuery {\n const params: unknown[] = [];\n let text = `SELECT COUNT(*) as count FROM \"${collection}\"`;\n\n if (filter && Object.keys(filter).length > 0) {\n const where = buildWhere(filter, params);\n text += ` WHERE ${where}`;\n }\n\n return { text, params };\n}\n\nfunction buildWhere(filter: FilterQuery, params: unknown[]): string {\n const conditions: string[] = [];\n\n for (const [field, condition] of Object.entries(filter)) {\n if (isOperatorObject(condition)) {\n for (const [op, value] of Object.entries(\n condition as Record<string, unknown>,\n )) {\n conditions.push(buildOperator(field, op, value, params));\n }\n } else {\n params.push(condition);\n conditions.push(`\"${field}\" = $${params.length}`);\n }\n }\n\n return conditions.join(\" AND \");\n}\n\nfunction buildOperator(\n field: string,\n op: string,\n value: unknown,\n params: unknown[],\n): string {\n switch (op) {\n case \"$eq\":\n params.push(value);\n return `\"${field}\" = $${params.length}`;\n case \"$ne\":\n params.push(value);\n return `\"${field}\" != $${params.length}`;\n case \"$gt\":\n params.push(value);\n return `\"${field}\" > $${params.length}`;\n case \"$gte\":\n params.push(value);\n return `\"${field}\" >= $${params.length}`;\n case \"$lt\":\n params.push(value);\n return `\"${field}\" < $${params.length}`;\n case \"$lte\":\n params.push(value);\n return `\"${field}\" <= $${params.length}`;\n case \"$in\":\n params.push(value);\n return `\"${field}\" = ANY($${params.length})`;\n case \"$nin\":\n params.push(value);\n return `\"${field}\" != ALL($${params.length})`;\n case \"$like\":\n params.push(value);\n return `\"${field}\" ILIKE $${params.length}`;\n case \"$exists\":\n return value\n ? `\"${field}\" IS NOT NULL`\n : `\"${field}\" IS NULL`;\n default:\n throw new Error(`Unknown operator: ${op}`);\n }\n}\n\nfunction buildOrderBy(sort: SortOption): string {\n return Object.entries(sort)\n .map(([field, dir]) => `\"${field}\" ${dir === 1 ? \"ASC\" : \"DESC\"}`)\n .join(\", \");\n}\n","import {\n FieldType,\n type Document,\n type FilterQuery,\n type FindOptions,\n type NormalizedField,\n type NormalizedSchema,\n type StorageAdapter,\n} from \"../../types.js\";\nimport { CollectionNotFoundError } from \"../../errors.js\";\nimport { PgConnection } from \"./pg-connection.js\";\nimport { buildSelect, buildCount } from \"./pg-query-builder.js\";\n\nfunction fieldToSQLType(field: NormalizedField): string {\n switch (field.type) {\n case FieldType.String:\n return field.maxLength ? `VARCHAR(${field.maxLength})` : \"TEXT\";\n case FieldType.Number:\n return \"DOUBLE PRECISION\";\n case FieldType.Boolean:\n return \"BOOLEAN\";\n case FieldType.Date:\n return \"TIMESTAMPTZ\";\n case FieldType.Json:\n case FieldType.Array:\n return \"JSONB\";\n default:\n return \"TEXT\";\n }\n}\n\nexport class PostgresAdapter implements StorageAdapter {\n private conn: PgConnection;\n\n constructor(url: string) {\n this.conn = new PgConnection(url);\n }\n\n async connect(): Promise<void> {\n await this.conn.connect();\n }\n\n async disconnect(): Promise<void> {\n await this.conn.disconnect();\n }\n\n async createCollection(\n collection: string,\n schema: NormalizedSchema,\n ): Promise<void> {\n const columns = [\n `\"id\" TEXT PRIMARY KEY`,\n `\"createdAt\" TIMESTAMPTZ NOT NULL DEFAULT NOW()`,\n `\"updatedAt\" TIMESTAMPTZ NOT NULL DEFAULT NOW()`,\n ];\n\n for (const [name, def] of Object.entries(schema)) {\n let col = `\"${name}\" ${fieldToSQLType(def)}`;\n if (def.required) col += \" NOT NULL\";\n if (def.unique) col += \" UNIQUE\";\n columns.push(col);\n }\n\n await this.conn.query(\n `CREATE TABLE IF NOT EXISTS \"${collection}\" (${columns.join(\", \")})`,\n );\n\n // Create indexes\n for (const [name, def] of Object.entries(schema)) {\n if (def.index && !def.unique) {\n await this.conn.query(\n `CREATE INDEX IF NOT EXISTS \"idx_${collection}_${name}\" ON \"${collection}\" (\"${name}\")`,\n );\n }\n }\n }\n\n async dropCollection(collection: string): Promise<void> {\n await this.conn.query(`DROP TABLE IF EXISTS \"${collection}\" CASCADE`);\n }\n\n async listCollections(): Promise<string[]> {\n const { rows } = await this.conn.query<{ tablename: string }>(\n `SELECT tablename FROM pg_tables WHERE schemaname = 'public'`,\n );\n return rows.map((r) => r.tablename);\n }\n\n async insert(collection: string, doc: Document): Promise<Document> {\n const keys = Object.keys(doc);\n const cols = keys.map((k) => `\"${k}\"`).join(\", \");\n const placeholders = keys.map((_, i) => `$${i + 1}`).join(\", \");\n const values = keys.map((k) => {\n const v = doc[k];\n return typeof v === \"object\" && v !== null && !(v instanceof Date)\n ? JSON.stringify(v)\n : v;\n });\n\n const { rows } = await this.conn.query<Document>(\n `INSERT INTO \"${collection}\" (${cols}) VALUES (${placeholders}) RETURNING *`,\n values,\n );\n return rows[0]!;\n }\n\n async findById(\n collection: string,\n id: string,\n ): Promise<Document | null> {\n const { rows } = await this.conn.query<Document>(\n `SELECT * FROM \"${collection}\" WHERE \"id\" = $1`,\n [id],\n );\n return rows[0] ?? null;\n }\n\n async find(\n collection: string,\n options: FindOptions,\n ): Promise<Document[]> {\n const q = buildSelect(collection, options);\n const { rows } = await this.conn.query<Document>(q.text, q.params);\n return rows;\n }\n\n async count(collection: string, filter?: FilterQuery): Promise<number> {\n const q = buildCount(collection, filter);\n const { rows } = await this.conn.query<{ count: string }>(\n q.text,\n q.params,\n );\n return parseInt(rows[0]!.count, 10);\n }\n\n async update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null> {\n const entries = Object.entries(data).filter(([k]) => k !== \"id\");\n if (entries.length === 0) return this.findById(collection, id);\n\n const sets = entries.map(([k], i) => `\"${k}\" = $${i + 1}`).join(\", \");\n const values = entries.map(([, v]) =>\n typeof v === \"object\" && v !== null && !(v instanceof Date)\n ? JSON.stringify(v)\n : v,\n );\n values.push(id);\n\n const { rows } = await this.conn.query<Document>(\n `UPDATE \"${collection}\" SET ${sets} WHERE \"id\" = $${values.length} RETURNING *`,\n values,\n );\n return rows[0] ?? null;\n }\n\n async delete(collection: string, id: string): Promise<boolean> {\n const { rowCount } = await this.conn.query(\n `DELETE FROM \"${collection}\" WHERE \"id\" = $1`,\n [id],\n );\n return rowCount > 0;\n }\n\n async deleteMany(\n collection: string,\n filter: FilterQuery,\n ): Promise<number> {\n const q = buildSelect(collection, { filter });\n // Convert SELECT to DELETE\n const deleteText = q.text.replace(/^SELECT \\* FROM/, \"DELETE FROM\");\n const { rowCount } = await this.conn.query(deleteText, q.params);\n return rowCount;\n }\n}\n","export { SeedORM } from \"./seedorm.js\";\nexport { Model } from \"./model/model.js\";\nexport { JsonAdapter } from \"./adapters/json/json-adapter.js\";\nexport { PostgresAdapter } from \"./adapters/postgres/postgres-adapter.js\";\nexport { normalizeSchema, validateDocument } from \"./model/schema.js\";\n\n// Enums (value exports)\nexport { FieldType, RelationType, AdapterType } from \"./types.js\";\n\n// Types\nexport type {\n Document,\n FieldDefinition,\n FilterQuery,\n FilterOperators,\n FindOptions,\n ModelDefinition,\n NormalizedField,\n NormalizedSchema,\n SeedORMConfig,\n SchemaDefinition,\n SortOption,\n StorageAdapter,\n AdapterConfig,\n Migration,\n MigrationStep,\n MigrationRecord,\n RelationDefinition,\n RelationsDefinition,\n} from \"./types.js\";\n\n// Errors\nexport {\n SeedORMError,\n ValidationError,\n AdapterError,\n CollectionNotFoundError,\n DocumentNotFoundError,\n UniqueConstraintError,\n} from \"./errors.js\";\n","import {\n AdapterType,\n type AdapterConfig,\n type ModelDefinition,\n type SeedORMConfig,\n type StorageAdapter,\n} from \"./types.js\";\nimport { SeedORMError } from \"./errors.js\";\nimport { Model } from \"./model/model.js\";\nimport { JsonAdapter } from \"./adapters/json/json-adapter.js\";\nimport * as path from \"node:path\";\n\nexport class SeedORM {\n private config: SeedORMConfig;\n private adapter: StorageAdapter | null = null;\n private models = new Map<string, Model>();\n private connected = false;\n\n constructor(config?: Partial<SeedORMConfig>) {\n this.config = {\n adapter: config?.adapter ?? { adapter: AdapterType.Json, path: \"./data\" },\n migrationsDir: config?.migrationsDir ?? \"./migrations\",\n };\n }\n\n private async createAdapter(adapterConfig: AdapterConfig): Promise<StorageAdapter> {\n switch (adapterConfig.adapter) {\n case AdapterType.Json: {\n const dbPath = path.resolve(\n adapterConfig.path ?? \"./data\",\n \"seedorm.json\",\n );\n return new JsonAdapter(dbPath);\n }\n case AdapterType.Postgres: {\n const { PostgresAdapter } = await import(\"./adapters/postgres/postgres-adapter.js\");\n return new PostgresAdapter(adapterConfig.url);\n }\n case AdapterType.MySQL:\n throw new SeedORMError(\n 'MySQL adapter requires the \"mysql2\" package. Install it with: npm install mysql2',\n );\n default:\n throw new SeedORMError(\n `Unknown adapter: ${(adapterConfig as { adapter: string }).adapter}`,\n );\n }\n }\n\n async connect(): Promise<void> {\n if (this.connected) return;\n this.adapter = await this.createAdapter(this.config.adapter);\n await this.adapter.connect();\n this.connected = true;\n\n // Re-init existing models\n for (const model of this.models.values()) {\n await model.init();\n }\n }\n\n async disconnect(): Promise<void> {\n if (!this.connected || !this.adapter) return;\n await this.adapter.disconnect();\n this.connected = false;\n this.adapter = null;\n }\n\n model(definition: ModelDefinition): Model {\n if (this.models.has(definition.name)) {\n return this.models.get(definition.name)!;\n }\n\n if (!this.adapter) {\n throw new SeedORMError(\n \"Not connected. Call db.connect() before defining models.\",\n );\n }\n\n const model = new Model(definition, this.adapter, this);\n this.models.set(definition.name, model);\n return model;\n }\n\n getModel(name: string): Model | undefined {\n return this.models.get(name);\n }\n\n getAdapter(): StorageAdapter {\n if (!this.adapter) {\n throw new SeedORMError(\"Not connected.\");\n }\n return this.adapter;\n }\n\n getConfig(): SeedORMConfig {\n return this.config;\n }\n}\n","import { nanoid } from \"nanoid\";\nimport {\n RelationType,\n type Document,\n type FilterQuery,\n type FindOptions,\n type ModelDefinition,\n type NormalizedSchema,\n type RelationDefinition,\n type RelationsDefinition,\n type StorageAdapter,\n} from \"../types.js\";\nimport { DocumentNotFoundError, SeedORMError } from \"../errors.js\";\nimport { normalizeSchema, validateDocument } from \"./schema.js\";\n\ninterface SeedORMInstance {\n getModel(name: string): Model | undefined;\n getAdapter(): StorageAdapter;\n}\n\nexport class Model {\n public readonly name: string;\n public readonly collection: string;\n public readonly schema: NormalizedSchema;\n public readonly prefix: string;\n public readonly relations: RelationsDefinition;\n private adapter: StorageAdapter;\n private timestamps: boolean;\n private db: SeedORMInstance | null;\n\n constructor(definition: ModelDefinition, adapter: StorageAdapter, db?: SeedORMInstance) {\n this.name = definition.name;\n this.collection = definition.collection;\n this.schema = normalizeSchema(definition.schema);\n this.prefix = definition.prefix ?? definition.collection.slice(0, 3);\n this.adapter = adapter;\n this.timestamps = definition.timestamps !== false;\n this.relations = definition.relations ?? {};\n this.db = db ?? null;\n }\n\n async init(): Promise<void> {\n await this.adapter.createCollection(this.collection, this.schema);\n }\n\n private generateId(): string {\n return `${this.prefix}_${nanoid(12)}`;\n }\n\n private resolveRelation(relationName: string): { rel: RelationDefinition; relatedModel: Model } {\n const rel = this.relations[relationName];\n if (!rel) {\n throw new SeedORMError(`Unknown relation \"${relationName}\" on model \"${this.name}\"`);\n }\n if (!this.db) {\n throw new SeedORMError(\"Cannot resolve relations without a SeedORM instance\");\n }\n const relatedModel = this.db.getModel(rel.model);\n if (!relatedModel) {\n throw new SeedORMError(`Related model \"${rel.model}\" not found. Make sure it is defined before querying.`);\n }\n return { rel, relatedModel };\n }\n\n private async populate(docs: Document[], includeList: string[]): Promise<Document[]> {\n if (includeList.length === 0 || docs.length === 0) return docs;\n\n // Shallow-clone docs to avoid mutating the adapter's internal store\n docs = docs.map((d) => ({ ...d }));\n\n for (const relationName of includeList) {\n const { rel, relatedModel } = this.resolveRelation(relationName);\n\n switch (rel.type) {\n case RelationType.HasMany: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const grouped = new Map<string, Document[]>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!grouped.has(fk)) grouped.set(fk, []);\n grouped.get(fk)!.push(r);\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n\n case RelationType.HasOne: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!map.has(fk)) map.set(fk, r);\n }\n for (const doc of docs) {\n doc[relationName] = map.get(doc.id) ?? null;\n }\n break;\n }\n\n case RelationType.BelongsTo: {\n const fkValues = [...new Set(docs.map((d) => d[rel.foreignKey] as string).filter(Boolean))];\n if (fkValues.length === 0) {\n for (const doc of docs) doc[relationName] = null;\n break;\n }\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: fkValues } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n map.set(r.id, r);\n }\n for (const doc of docs) {\n const fk = doc[rel.foreignKey] as string;\n doc[relationName] = map.get(fk) ?? null;\n }\n break;\n }\n\n case RelationType.ManyToMany: {\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const parentIds = docs.map((d) => d.id);\n const joinRows = await this.adapter.find(rel.joinCollection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const relatedIds = [...new Set(joinRows.map((r) => r[rel.relatedKey!] as string))];\n const relatedDocs =\n relatedIds.length > 0\n ? await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: relatedIds } },\n })\n : [];\n const relatedMap = new Map<string, Document>();\n for (const r of relatedDocs) relatedMap.set(r.id, r);\n\n const grouped = new Map<string, Document[]>();\n for (const row of joinRows) {\n const parentId = row[rel.foreignKey] as string;\n const relatedId = row[rel.relatedKey!] as string;\n const relatedDoc = relatedMap.get(relatedId);\n if (relatedDoc) {\n if (!grouped.has(parentId)) grouped.set(parentId, []);\n grouped.get(parentId)!.push(relatedDoc);\n }\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n }\n }\n\n return docs;\n }\n\n async create(data: Record<string, unknown>): Promise<Document> {\n const validated = validateDocument(data, this.schema);\n const now = new Date().toISOString();\n const doc: Document = {\n ...validated,\n id: this.generateId(),\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(this.collection, doc);\n }\n\n async createMany(\n items: Record<string, unknown>[],\n ): Promise<Document[]> {\n const results: Document[] = [];\n for (const item of items) {\n results.push(await this.create(item));\n }\n return results;\n }\n\n async findById(id: string, options?: { include?: string[] }): Promise<Document | null> {\n const doc = await this.adapter.findById(this.collection, id);\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async findByIdOrThrow(id: string, options?: { include?: string[] }): Promise<Document> {\n const doc = await this.findById(id, options);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async findOne(filter: FilterQuery, options?: { include?: string[] }): Promise<Document | null> {\n const results = await this.adapter.find(this.collection, {\n filter,\n limit: 1,\n });\n const doc = results[0] ?? null;\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async find(options: FindOptions = {}): Promise<Document[]> {\n const { include, ...adapterOptions } = options;\n const docs = await this.adapter.find(this.collection, adapterOptions);\n if (!include?.length) return docs;\n return this.populate(docs, include);\n }\n\n async findAll(): Promise<Document[]> {\n return this.adapter.find(this.collection, {});\n }\n\n async count(filter?: FilterQuery): Promise<number> {\n return this.adapter.count(this.collection, filter);\n }\n\n async update(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document | null> {\n const validated = validateDocument(data, this.schema, true);\n if (this.timestamps) {\n validated.updatedAt = new Date().toISOString();\n }\n return this.adapter.update(this.collection, id, validated);\n }\n\n async updateOrThrow(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document> {\n const doc = await this.update(id, data);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async delete(id: string): Promise<boolean> {\n return this.adapter.delete(this.collection, id);\n }\n\n async deleteMany(filter: FilterQuery): Promise<number> {\n return this.adapter.deleteMany(this.collection, filter);\n }\n\n async associate(id: string, relationName: string, relatedId: string): Promise<Document> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`associate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const now = new Date().toISOString();\n const joinDoc: Document = {\n id: `${this.prefix}rel_${nanoid(12)}`,\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(rel.joinCollection, joinDoc);\n }\n\n async dissociate(id: string, relationName: string, relatedId: string): Promise<number> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`dissociate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n return this.adapter.deleteMany(rel.joinCollection, {\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n });\n }\n}\n","import {\n FieldType,\n type FieldDefinition,\n type NormalizedField,\n type NormalizedSchema,\n type SchemaDefinition,\n} from \"../types.js\";\nimport { ValidationError } from \"../errors.js\";\nimport { coerceFieldValue, validateFieldType } from \"./field-types.js\";\n\nexport function normalizeSchema(schema: SchemaDefinition): NormalizedSchema {\n const normalized: NormalizedSchema = {};\n\n for (const [field, def] of Object.entries(schema)) {\n if (typeof def === \"string\") {\n normalized[field] = {\n type: def as FieldType,\n required: false,\n unique: false,\n index: false,\n };\n } else {\n const d = def as FieldDefinition;\n normalized[field] = {\n type: d.type,\n required: d.required ?? false,\n unique: d.unique ?? false,\n index: d.index ?? d.unique ?? false,\n ...(d.default !== undefined && { default: d.default }),\n ...(d.minLength !== undefined && { minLength: d.minLength }),\n ...(d.maxLength !== undefined && { maxLength: d.maxLength }),\n ...(d.min !== undefined && { min: d.min }),\n ...(d.max !== undefined && { max: d.max }),\n ...(d.enum !== undefined && { enum: d.enum }),\n };\n }\n }\n\n return normalized;\n}\n\nexport function validateDocument(\n data: Record<string, unknown>,\n schema: NormalizedSchema,\n isUpdate = false,\n): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n\n for (const [field, def] of Object.entries(schema)) {\n let value = data[field];\n\n // Apply default\n if (value === undefined && def.default !== undefined && !isUpdate) {\n value =\n typeof def.default === \"function\"\n ? (def.default as () => unknown)()\n : def.default;\n }\n\n // Required check (skip on partial updates)\n if (!isUpdate && def.required && (value === undefined || value === null)) {\n throw new ValidationError(field, \"field is required\");\n }\n\n // Skip unset fields on update\n if (value === undefined) continue;\n\n // Type check\n const typeErr = validateFieldType(value, def.type);\n if (typeErr) throw new ValidationError(field, typeErr);\n\n // String constraints\n if (def.type === \"string\" && typeof value === \"string\") {\n if (def.minLength !== undefined && value.length < def.minLength) {\n throw new ValidationError(\n field,\n `minimum length is ${def.minLength}, got ${value.length}`,\n );\n }\n if (def.maxLength !== undefined && value.length > def.maxLength) {\n throw new ValidationError(\n field,\n `maximum length is ${def.maxLength}, got ${value.length}`,\n );\n }\n }\n\n // Number constraints\n if (def.type === \"number\" && typeof value === \"number\") {\n if (def.min !== undefined && value < def.min) {\n throw new ValidationError(field, `minimum value is ${def.min}`);\n }\n if (def.max !== undefined && value > def.max) {\n throw new ValidationError(field, `maximum value is ${def.max}`);\n }\n }\n\n // Enum check\n if (def.enum && !def.enum.includes(value)) {\n throw new ValidationError(\n field,\n `value must be one of: ${def.enum.join(\", \")}`,\n );\n }\n\n result[field] = coerceFieldValue(value, def.type);\n }\n\n // On update, pass through non-schema fields that were provided\n // (for id, createdAt, updatedAt)\n if (isUpdate) {\n for (const [key, val] of Object.entries(data)) {\n if (!(key in schema) && val !== undefined) {\n result[key] = val;\n }\n }\n }\n\n return result;\n}\n","import { FieldType } from \"../types.js\";\n\nexport function validateFieldType(\n value: unknown,\n type: FieldType,\n): string | null {\n if (value === undefined || value === null) return null; // handled by required check\n\n switch (type) {\n case FieldType.String:\n if (typeof value !== \"string\") return `expected string, got ${typeof value}`;\n break;\n case FieldType.Number:\n if (typeof value !== \"number\" || Number.isNaN(value))\n return `expected number, got ${typeof value}`;\n break;\n case FieldType.Boolean:\n if (typeof value !== \"boolean\")\n return `expected boolean, got ${typeof value}`;\n break;\n case FieldType.Date:\n if (typeof value === \"string\") {\n if (Number.isNaN(Date.parse(value))) return `invalid date string`;\n } else if (!(value instanceof Date)) {\n return `expected date string or Date, got ${typeof value}`;\n }\n break;\n case FieldType.Json:\n // Any non-undefined value is valid JSON\n break;\n case FieldType.Array:\n if (!Array.isArray(value)) return `expected array, got ${typeof value}`;\n break;\n default:\n return `unknown type: ${type as string}`;\n }\n\n return null;\n}\n\nexport function coerceFieldValue(value: unknown, type: FieldType): unknown {\n if (value === undefined || value === null) return value;\n\n if (type === FieldType.Date && value instanceof Date) {\n return value.toISOString();\n }\n\n return value;\n}\n","import type {\n Document,\n FilterQuery,\n FindOptions,\n NormalizedSchema,\n StorageAdapter,\n} from \"../../types.js\";\nimport { AdapterError, CollectionNotFoundError } from \"../../errors.js\";\nimport { applyFindOptions, countWithFilter } from \"../../query/filter.js\";\nimport { FileEngine } from \"./file-engine.js\";\nimport { Indexer } from \"./indexer.js\";\n\nexport class JsonAdapter implements StorageAdapter {\n private engine: FileEngine;\n private indexer = new Indexer();\n private schemas = new Map<string, NormalizedSchema>();\n\n constructor(filePath: string) {\n this.engine = new FileEngine(filePath);\n }\n\n async connect(): Promise<void> {\n await this.engine.load();\n }\n\n async disconnect(): Promise<void> {\n await this.engine.flushIfDirty();\n }\n\n async createCollection(\n collection: string,\n schema: NormalizedSchema,\n ): Promise<void> {\n this.engine.createCollection(collection);\n this.schemas.set(collection, schema);\n\n // Set up indexes\n for (const [field, def] of Object.entries(schema)) {\n if (def.index || def.unique) {\n this.indexer.setupIndex(\n collection,\n field,\n def.unique,\n this.engine.getCollection(collection),\n );\n }\n }\n\n await this.engine.flush();\n }\n\n async dropCollection(collection: string): Promise<void> {\n this.engine.dropCollection(collection);\n this.indexer.dropCollection(collection);\n this.schemas.delete(collection);\n await this.engine.flush();\n }\n\n async listCollections(): Promise<string[]> {\n return this.engine.listCollections();\n }\n\n async insert(collection: string, doc: Document): Promise<Document> {\n const docs = this.getCollectionOrThrow(collection);\n\n // Check unique constraints via indexer\n this.indexer.onInsert(collection, doc);\n\n docs.push(doc);\n this.engine.markDirty();\n await this.engine.flush();\n return doc;\n }\n\n async findById(\n collection: string,\n id: string,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n return docs.find((d) => d.id === id) ?? null;\n }\n\n async find(\n collection: string,\n options: FindOptions,\n ): Promise<Document[]> {\n const docs = this.getCollectionOrThrow(collection);\n return applyFindOptions(docs, options);\n }\n\n async count(collection: string, filter?: FilterQuery): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n return countWithFilter(docs, filter);\n }\n\n async update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return null;\n\n const oldDoc = docs[index]!;\n const newDoc = { ...oldDoc, ...data, id: oldDoc.id };\n\n // Check unique constraints\n this.indexer.onUpdate(collection, oldDoc, newDoc);\n\n docs[index] = newDoc;\n this.engine.markDirty();\n await this.engine.flush();\n return newDoc;\n }\n\n async delete(collection: string, id: string): Promise<boolean> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return false;\n\n this.indexer.onDelete(collection, docs[index]!);\n docs.splice(index, 1);\n this.engine.markDirty();\n await this.engine.flush();\n return true;\n }\n\n async deleteMany(\n collection: string,\n filter: FilterQuery,\n ): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n const matching = applyFindOptions(docs, { filter });\n\n for (const doc of matching) {\n this.indexer.onDelete(collection, doc);\n }\n\n const ids = new Set(matching.map((d) => d.id));\n const remaining = docs.filter((d) => !ids.has(d.id));\n const deleted = docs.length - remaining.length;\n\n // Replace array contents in-place\n docs.length = 0;\n docs.push(...remaining);\n\n if (deleted > 0) {\n this.engine.markDirty();\n await this.engine.flush();\n }\n\n return deleted;\n }\n\n private getCollectionOrThrow(collection: string): Document[] {\n if (!this.engine.hasCollection(collection)) {\n throw new CollectionNotFoundError(collection);\n }\n return this.engine.getCollection(collection);\n }\n}\n","import type { Document, FilterQuery, FindOptions, SortOption } from \"../types.js\";\nimport { applyOperator, isOperatorObject } from \"./operators.js\";\n\nfunction matchesFilter(doc: Document, filter: FilterQuery): boolean {\n for (const [field, condition] of Object.entries(filter)) {\n const value = doc[field];\n\n if (isOperatorObject(condition)) {\n for (const [op, operand] of Object.entries(\n condition as Record<string, unknown>,\n )) {\n if (!applyOperator(op, value, operand)) return false;\n }\n } else {\n // Shorthand: { field: value } is equivalent to { field: { $eq: value } }\n if (value !== condition) return false;\n }\n }\n return true;\n}\n\nfunction sortDocuments(docs: Document[], sort: SortOption): Document[] {\n const entries = Object.entries(sort);\n return [...docs].sort((a, b) => {\n for (const [field, dir] of entries) {\n const av = a[field];\n const bv = b[field];\n if (av === bv) continue;\n if (av === undefined || av === null) return dir;\n if (bv === undefined || bv === null) return -dir;\n if (av < bv) return -dir;\n if (av > bv) return dir;\n }\n return 0;\n });\n}\n\nexport function applyFindOptions(\n docs: Document[],\n options: FindOptions,\n): Document[] {\n let result = docs;\n\n if (options.filter) {\n result = result.filter((doc) => matchesFilter(doc, options.filter!));\n }\n\n if (options.sort) {\n result = sortDocuments(result, options.sort);\n }\n\n if (options.offset) {\n result = result.slice(options.offset);\n }\n\n if (options.limit !== undefined) {\n result = result.slice(0, options.limit);\n }\n\n return result;\n}\n\nexport function countWithFilter(\n docs: Document[],\n filter?: FilterQuery,\n): number {\n if (!filter) return docs.length;\n return docs.filter((doc) => matchesFilter(doc, filter)).length;\n}\n\nexport { matchesFilter };\n","import * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport writeFileAtomic from \"write-file-atomic\";\nimport type { Document } from \"../../types.js\";\n\nexport interface FileData {\n [collection: string]: Document[];\n}\n\nexport class FileEngine {\n private filePath: string;\n private data: FileData = {};\n private writeQueue: Promise<void> = Promise.resolve();\n private dirty = false;\n\n constructor(filePath: string) {\n this.filePath = path.resolve(filePath);\n }\n\n async load(): Promise<void> {\n try {\n const raw = fs.readFileSync(this.filePath, \"utf-8\");\n this.data = JSON.parse(raw) as FileData;\n } catch (err: unknown) {\n if ((err as NodeJS.ErrnoException).code === \"ENOENT\") {\n this.data = {};\n await this.flush();\n } else {\n throw err;\n }\n }\n }\n\n getData(): FileData {\n return this.data;\n }\n\n getCollection(name: string): Document[] {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n return this.data[name];\n }\n\n hasCollection(name: string): boolean {\n return name in this.data;\n }\n\n createCollection(name: string): void {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n }\n\n dropCollection(name: string): void {\n delete this.data[name];\n }\n\n listCollections(): string[] {\n return Object.keys(this.data);\n }\n\n markDirty(): void {\n this.dirty = true;\n }\n\n async flush(): Promise<void> {\n this.writeQueue = this.writeQueue.then(async () => {\n const dir = path.dirname(this.filePath);\n if (!fs.existsSync(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n await writeFileAtomic(\n this.filePath,\n JSON.stringify(this.data, null, 2) + \"\\n\",\n );\n this.dirty = false;\n });\n return this.writeQueue;\n }\n\n async flushIfDirty(): Promise<void> {\n if (this.dirty) {\n await this.flush();\n }\n }\n}\n","import type { Document } from \"../../types.js\";\nimport { UniqueConstraintError } from \"../../errors.js\";\n\ninterface FieldIndex {\n field: string;\n unique: boolean;\n map: Map<unknown, Set<string>>; // value → set of doc IDs\n}\n\nexport class Indexer {\n private indexes = new Map<string, Map<string, FieldIndex>>(); // collection → field → index\n\n setupIndex(\n collection: string,\n field: string,\n unique: boolean,\n docs: Document[],\n ): void {\n if (!this.indexes.has(collection)) {\n this.indexes.set(collection, new Map());\n }\n const colIndexes = this.indexes.get(collection)!;\n\n const idx: FieldIndex = { field, unique, map: new Map() };\n\n for (const doc of docs) {\n const val = doc[field];\n if (val === undefined || val === null) continue;\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n\n colIndexes.set(field, idx);\n }\n\n onInsert(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val === undefined || val === null) continue;\n\n if (idx.unique && idx.map.has(val) && idx.map.get(val)!.size > 0) {\n throw new UniqueConstraintError(collection, idx.field, val);\n }\n\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n }\n\n onUpdate(\n collection: string,\n oldDoc: Document,\n newDoc: Document,\n ): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const oldVal = oldDoc[idx.field];\n const newVal = newDoc[idx.field];\n\n if (oldVal === newVal) continue;\n\n // Remove old\n if (oldVal !== undefined && oldVal !== null) {\n idx.map.get(oldVal)?.delete(oldDoc.id);\n }\n\n // Add new\n if (newVal !== undefined && newVal !== null) {\n if (\n idx.unique &&\n idx.map.has(newVal) &&\n idx.map.get(newVal)!.size > 0\n ) {\n throw new UniqueConstraintError(collection, idx.field, newVal);\n }\n if (!idx.map.has(newVal)) {\n idx.map.set(newVal, new Set());\n }\n idx.map.get(newVal)!.add(newDoc.id);\n }\n }\n }\n\n onDelete(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val !== undefined && val !== null) {\n idx.map.get(val)?.delete(doc.id);\n }\n }\n }\n\n findByValue(\n collection: string,\n field: string,\n value: unknown,\n ): Set<string> | undefined {\n return this.indexes.get(collection)?.get(field)?.map.get(value);\n }\n\n dropCollection(collection: string): void {\n this.indexes.delete(collection);\n }\n}\n"],"mappings":"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","names":["FieldType","RelationType","AdapterType","writeFileAtomic","path","PostgresAdapter"]}
|
|
1
|
+
{"version":3,"sources":["../src/types.ts","../src/errors.ts","../src/query/operators.ts","../src/adapters/postgres/pg-connection.ts","../src/adapters/postgres/pg-query-builder.ts","../src/adapters/postgres/postgres-adapter.ts","../src/index.ts","../src/seedorm.ts","../src/model/model.ts","../src/model/schema.ts","../src/model/field-types.ts","../src/adapters/json/json-adapter.ts","../src/query/filter.ts","../src/adapters/json/file-engine.ts","../src/adapters/json/indexer.ts"],"sourcesContent":["// ── Field & Schema Types ──\n\nexport enum FieldType {\n String = \"string\",\n Number = \"number\",\n Boolean = \"boolean\",\n Date = \"date\",\n Json = \"json\",\n Array = \"array\",\n}\n\nexport interface FieldDefinition {\n type: FieldType;\n required?: boolean;\n unique?: boolean;\n index?: boolean;\n default?: unknown;\n minLength?: number;\n maxLength?: number;\n min?: number;\n max?: number;\n enum?: unknown[];\n}\n\nexport interface SchemaDefinition {\n [field: string]: FieldType | FieldDefinition;\n}\n\nexport interface NormalizedField {\n type: FieldType;\n required: boolean;\n unique: boolean;\n index: boolean;\n default?: unknown;\n minLength?: number;\n maxLength?: number;\n min?: number;\n max?: number;\n enum?: unknown[];\n}\n\nexport interface NormalizedSchema {\n [field: string]: NormalizedField;\n}\n\n// ── Document ──\n\nexport interface Document {\n id: string;\n createdAt: string;\n updatedAt: string;\n [key: string]: unknown;\n}\n\n// ── Query / Filter ──\n\nexport interface FilterOperators {\n $eq?: unknown;\n $ne?: unknown;\n $gt?: number | string | Date;\n $gte?: number | string | Date;\n $lt?: number | string | Date;\n $lte?: number | string | Date;\n $in?: unknown[];\n $nin?: unknown[];\n $like?: string;\n $exists?: boolean;\n}\n\nexport type FieldFilter = FilterOperators | unknown;\n\nexport interface FilterQuery {\n [field: string]: FieldFilter;\n}\n\nexport interface SortOption {\n [field: string]: 1 | -1;\n}\n\nexport interface FindOptions {\n filter?: FilterQuery;\n sort?: SortOption;\n limit?: number;\n offset?: number;\n include?: string[];\n}\n\n// ── Relations ──\n\nexport enum RelationType {\n HasOne = \"hasOne\",\n HasMany = \"hasMany\",\n BelongsTo = \"belongsTo\",\n ManyToMany = \"manyToMany\",\n}\n\nexport interface RelationDefinition {\n type: RelationType;\n model: string;\n foreignKey: string;\n joinCollection?: string;\n relatedKey?: string;\n}\n\nexport interface RelationsDefinition {\n [name: string]: RelationDefinition;\n}\n\n// ── Model Definition ──\n\nexport interface ModelDefinition {\n name: string;\n collection: string;\n schema: SchemaDefinition;\n timestamps?: boolean;\n prefix?: string;\n relations?: RelationsDefinition;\n}\n\n// ── Storage Adapter ──\n\nexport interface StorageAdapter {\n connect(): Promise<void>;\n disconnect(): Promise<void>;\n\n insert(collection: string, doc: Document): Promise<Document>;\n findById(collection: string, id: string): Promise<Document | null>;\n find(collection: string, options: FindOptions): Promise<Document[]>;\n count(collection: string, filter?: FilterQuery): Promise<number>;\n update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null>;\n delete(collection: string, id: string): Promise<boolean>;\n deleteMany(collection: string, filter: FilterQuery): Promise<number>;\n\n createCollection(collection: string, schema: NormalizedSchema): Promise<void>;\n dropCollection(collection: string): Promise<void>;\n listCollections(): Promise<string[]>;\n}\n\n// ── Config ──\n\nexport enum AdapterType {\n Json = \"json\",\n Postgres = \"postgres\",\n MySQL = \"mysql\",\n}\n\nexport interface JsonAdapterConfig {\n adapter: AdapterType.Json;\n path?: string;\n}\n\nexport interface PostgresAdapterConfig {\n adapter: AdapterType.Postgres;\n url: string;\n}\n\nexport interface MySQLAdapterConfig {\n adapter: AdapterType.MySQL;\n url: string;\n}\n\nexport type AdapterConfig =\n | JsonAdapterConfig\n | PostgresAdapterConfig\n | MySQLAdapterConfig;\n\nexport interface SeedORMConfig {\n adapter: AdapterConfig;\n migrationsDir?: string;\n}\n\n// ── Migration ──\n\nexport interface MigrationStep {\n type:\n | \"createCollection\"\n | \"dropCollection\"\n | \"addField\"\n | \"dropField\"\n | \"alterField\"\n | \"addIndex\"\n | \"dropIndex\";\n collection: string;\n field?: string;\n schema?: NormalizedField;\n oldSchema?: NormalizedField;\n}\n\nexport interface Migration {\n id: string;\n name: string;\n timestamp: number;\n up: MigrationStep[];\n down: MigrationStep[];\n}\n\nexport interface MigrationRecord {\n id: string;\n name: string;\n appliedAt: string;\n}\n","export class SeedORMError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"SeedORMError\";\n }\n}\n\nexport class ValidationError extends SeedORMError {\n public field: string;\n public reason: string;\n\n constructor(field: string, reason: string) {\n super(`Validation error on \"${field}\": ${reason}`);\n this.name = \"ValidationError\";\n this.field = field;\n this.reason = reason;\n }\n}\n\nexport class AdapterError extends SeedORMError {\n public adapter: string;\n\n constructor(adapter: string, message: string) {\n super(`[${adapter}] ${message}`);\n this.name = \"AdapterError\";\n this.adapter = adapter;\n }\n}\n\nexport class CollectionNotFoundError extends SeedORMError {\n constructor(collection: string) {\n super(`Collection \"${collection}\" not found`);\n this.name = \"CollectionNotFoundError\";\n }\n}\n\nexport class DocumentNotFoundError extends SeedORMError {\n constructor(collection: string, id: string) {\n super(`Document \"${id}\" not found in \"${collection}\"`);\n this.name = \"DocumentNotFoundError\";\n }\n}\n\nexport class UniqueConstraintError extends SeedORMError {\n public field: string;\n public value: unknown;\n\n constructor(collection: string, field: string, value: unknown) {\n super(\n `Unique constraint violation on \"${collection}.${field}\": value ${JSON.stringify(value)} already exists`,\n );\n this.name = \"UniqueConstraintError\";\n this.field = field;\n this.value = value;\n }\n}\n","import type { FilterOperators } from \"../types.js\";\n\ntype OperatorFn = (fieldValue: unknown, operand: unknown) => boolean;\n\nconst operators: Record<string, OperatorFn> = {\n $eq: (val, op) => val === op,\n\n $ne: (val, op) => val !== op,\n\n $gt: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val > op;\n if (typeof val === \"string\" && typeof op === \"string\") return val > op;\n return false;\n },\n\n $gte: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val >= op;\n if (typeof val === \"string\" && typeof op === \"string\") return val >= op;\n return false;\n },\n\n $lt: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val < op;\n if (typeof val === \"string\" && typeof op === \"string\") return val < op;\n return false;\n },\n\n $lte: (val, op) => {\n if (typeof val === \"number\" && typeof op === \"number\") return val <= op;\n if (typeof val === \"string\" && typeof op === \"string\") return val <= op;\n return false;\n },\n\n $in: (val, op) => {\n if (!Array.isArray(op)) return false;\n return op.includes(val);\n },\n\n $nin: (val, op) => {\n if (!Array.isArray(op)) return true;\n return !op.includes(val);\n },\n\n $like: (val, op) => {\n if (typeof val !== \"string\" || typeof op !== \"string\") return false;\n // Convert SQL-like pattern to regex: % → .*, _ → .\n const escaped = op.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\");\n const pattern = escaped.replace(/%/g, \".*\").replace(/_/g, \".\");\n return new RegExp(`^${pattern}$`, \"i\").test(val);\n },\n\n $exists: (val, op) => {\n const exists = val !== undefined && val !== null;\n return op ? exists : !exists;\n },\n};\n\nexport function applyOperator(\n key: string,\n fieldValue: unknown,\n operand: unknown,\n): boolean {\n const fn = operators[key];\n if (!fn) throw new Error(`Unknown operator: ${key}`);\n return fn(fieldValue, operand);\n}\n\nexport function isOperatorObject(value: unknown): value is FilterOperators {\n if (value === null || typeof value !== \"object\" || Array.isArray(value))\n return false;\n return Object.keys(value as object).some((k) => k.startsWith(\"$\"));\n}\n\nexport const OPERATORS = Object.keys(operators);\n","import { AdapterError } from \"../../errors.js\";\n\n// pg is an optional peer dependency\nlet pgModule: typeof import(\"pg\") | null = null;\n\nasync function loadPg(): Promise<typeof import(\"pg\")> {\n if (pgModule) return pgModule;\n try {\n pgModule = await import(\"pg\");\n return pgModule;\n } catch {\n throw new AdapterError(\n \"postgres\",\n 'The \"pg\" package is required for PostgreSQL. Install it with: npm install pg',\n );\n }\n}\n\nexport class PgConnection {\n private pool: import(\"pg\").Pool | null = null;\n private url: string;\n\n constructor(url: string) {\n this.url = url;\n }\n\n async connect(): Promise<void> {\n const pg = await loadPg();\n this.pool = new pg.Pool({ connectionString: this.url });\n // Test the connection\n const client = await this.pool.connect();\n client.release();\n }\n\n async disconnect(): Promise<void> {\n if (this.pool) {\n await this.pool.end();\n this.pool = null;\n }\n }\n\n async query<T extends Record<string, unknown> = Record<string, unknown>>(\n text: string,\n params?: unknown[],\n ): Promise<{ rows: T[]; rowCount: number }> {\n if (!this.pool) {\n throw new AdapterError(\"postgres\", \"Not connected\");\n }\n const result = await this.pool.query(text, params);\n return { rows: result.rows as T[], rowCount: result.rowCount ?? 0 };\n }\n}\n","import type { FilterQuery, FindOptions, SortOption } from \"../../types.js\";\nimport { isOperatorObject } from \"../../query/operators.js\";\n\ninterface BuiltQuery {\n text: string;\n params: unknown[];\n}\n\nexport function buildSelect(\n collection: string,\n options: FindOptions,\n): BuiltQuery {\n const params: unknown[] = [];\n let text = `SELECT * FROM \"${collection}\"`;\n\n if (options.filter && Object.keys(options.filter).length > 0) {\n const where = buildWhere(options.filter, params);\n text += ` WHERE ${where}`;\n }\n\n if (options.sort) {\n text += ` ORDER BY ${buildOrderBy(options.sort)}`;\n }\n\n if (options.limit !== undefined) {\n params.push(options.limit);\n text += ` LIMIT $${params.length}`;\n }\n\n if (options.offset !== undefined) {\n params.push(options.offset);\n text += ` OFFSET $${params.length}`;\n }\n\n return { text, params };\n}\n\nexport function buildCount(\n collection: string,\n filter?: FilterQuery,\n): BuiltQuery {\n const params: unknown[] = [];\n let text = `SELECT COUNT(*) as count FROM \"${collection}\"`;\n\n if (filter && Object.keys(filter).length > 0) {\n const where = buildWhere(filter, params);\n text += ` WHERE ${where}`;\n }\n\n return { text, params };\n}\n\nfunction buildWhere(filter: FilterQuery, params: unknown[]): string {\n const conditions: string[] = [];\n\n for (const [field, condition] of Object.entries(filter)) {\n if (isOperatorObject(condition)) {\n for (const [op, value] of Object.entries(\n condition as Record<string, unknown>,\n )) {\n conditions.push(buildOperator(field, op, value, params));\n }\n } else {\n params.push(condition);\n conditions.push(`\"${field}\" = $${params.length}`);\n }\n }\n\n return conditions.join(\" AND \");\n}\n\nfunction buildOperator(\n field: string,\n op: string,\n value: unknown,\n params: unknown[],\n): string {\n switch (op) {\n case \"$eq\":\n params.push(value);\n return `\"${field}\" = $${params.length}`;\n case \"$ne\":\n params.push(value);\n return `\"${field}\" != $${params.length}`;\n case \"$gt\":\n params.push(value);\n return `\"${field}\" > $${params.length}`;\n case \"$gte\":\n params.push(value);\n return `\"${field}\" >= $${params.length}`;\n case \"$lt\":\n params.push(value);\n return `\"${field}\" < $${params.length}`;\n case \"$lte\":\n params.push(value);\n return `\"${field}\" <= $${params.length}`;\n case \"$in\":\n params.push(value);\n return `\"${field}\" = ANY($${params.length})`;\n case \"$nin\":\n params.push(value);\n return `\"${field}\" != ALL($${params.length})`;\n case \"$like\":\n params.push(value);\n return `\"${field}\" ILIKE $${params.length}`;\n case \"$exists\":\n return value\n ? `\"${field}\" IS NOT NULL`\n : `\"${field}\" IS NULL`;\n default:\n throw new Error(`Unknown operator: ${op}`);\n }\n}\n\nfunction buildOrderBy(sort: SortOption): string {\n return Object.entries(sort)\n .map(([field, dir]) => `\"${field}\" ${dir === 1 ? \"ASC\" : \"DESC\"}`)\n .join(\", \");\n}\n","import {\n FieldType,\n type Document,\n type FilterQuery,\n type FindOptions,\n type NormalizedField,\n type NormalizedSchema,\n type StorageAdapter,\n} from \"../../types.js\";\nimport { CollectionNotFoundError } from \"../../errors.js\";\nimport { PgConnection } from \"./pg-connection.js\";\nimport { buildSelect, buildCount } from \"./pg-query-builder.js\";\n\nfunction fieldToSQLType(field: NormalizedField): string {\n switch (field.type) {\n case FieldType.String:\n return field.maxLength ? `VARCHAR(${field.maxLength})` : \"TEXT\";\n case FieldType.Number:\n return \"DOUBLE PRECISION\";\n case FieldType.Boolean:\n return \"BOOLEAN\";\n case FieldType.Date:\n return \"TIMESTAMPTZ\";\n case FieldType.Json:\n case FieldType.Array:\n return \"JSONB\";\n default:\n return \"TEXT\";\n }\n}\n\nexport class PostgresAdapter implements StorageAdapter {\n private conn: PgConnection;\n\n constructor(url: string) {\n this.conn = new PgConnection(url);\n }\n\n async connect(): Promise<void> {\n await this.conn.connect();\n }\n\n async disconnect(): Promise<void> {\n await this.conn.disconnect();\n }\n\n async createCollection(\n collection: string,\n schema: NormalizedSchema,\n ): Promise<void> {\n const columns = [\n `\"id\" TEXT PRIMARY KEY`,\n `\"createdAt\" TIMESTAMPTZ NOT NULL DEFAULT NOW()`,\n `\"updatedAt\" TIMESTAMPTZ NOT NULL DEFAULT NOW()`,\n ];\n\n for (const [name, def] of Object.entries(schema)) {\n let col = `\"${name}\" ${fieldToSQLType(def)}`;\n if (def.required) col += \" NOT NULL\";\n if (def.unique) col += \" UNIQUE\";\n columns.push(col);\n }\n\n await this.conn.query(\n `CREATE TABLE IF NOT EXISTS \"${collection}\" (${columns.join(\", \")})`,\n );\n\n // Create indexes\n for (const [name, def] of Object.entries(schema)) {\n if (def.index && !def.unique) {\n await this.conn.query(\n `CREATE INDEX IF NOT EXISTS \"idx_${collection}_${name}\" ON \"${collection}\" (\"${name}\")`,\n );\n }\n }\n }\n\n async dropCollection(collection: string): Promise<void> {\n await this.conn.query(`DROP TABLE IF EXISTS \"${collection}\" CASCADE`);\n }\n\n async listCollections(): Promise<string[]> {\n const { rows } = await this.conn.query<{ tablename: string }>(\n `SELECT tablename FROM pg_tables WHERE schemaname = 'public'`,\n );\n return rows.map((r) => r.tablename);\n }\n\n async insert(collection: string, doc: Document): Promise<Document> {\n const keys = Object.keys(doc);\n const cols = keys.map((k) => `\"${k}\"`).join(\", \");\n const placeholders = keys.map((_, i) => `$${i + 1}`).join(\", \");\n const values = keys.map((k) => {\n const v = doc[k];\n return typeof v === \"object\" && v !== null && !(v instanceof Date)\n ? JSON.stringify(v)\n : v;\n });\n\n const { rows } = await this.conn.query<Document>(\n `INSERT INTO \"${collection}\" (${cols}) VALUES (${placeholders}) RETURNING *`,\n values,\n );\n return rows[0]!;\n }\n\n async findById(\n collection: string,\n id: string,\n ): Promise<Document | null> {\n const { rows } = await this.conn.query<Document>(\n `SELECT * FROM \"${collection}\" WHERE \"id\" = $1`,\n [id],\n );\n return rows[0] ?? null;\n }\n\n async find(\n collection: string,\n options: FindOptions,\n ): Promise<Document[]> {\n const q = buildSelect(collection, options);\n const { rows } = await this.conn.query<Document>(q.text, q.params);\n return rows;\n }\n\n async count(collection: string, filter?: FilterQuery): Promise<number> {\n const q = buildCount(collection, filter);\n const { rows } = await this.conn.query<{ count: string }>(\n q.text,\n q.params,\n );\n return parseInt(rows[0]!.count, 10);\n }\n\n async update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null> {\n const entries = Object.entries(data).filter(([k]) => k !== \"id\");\n if (entries.length === 0) return this.findById(collection, id);\n\n const sets = entries.map(([k], i) => `\"${k}\" = $${i + 1}`).join(\", \");\n const values = entries.map(([, v]) =>\n typeof v === \"object\" && v !== null && !(v instanceof Date)\n ? JSON.stringify(v)\n : v,\n );\n values.push(id);\n\n const { rows } = await this.conn.query<Document>(\n `UPDATE \"${collection}\" SET ${sets} WHERE \"id\" = $${values.length} RETURNING *`,\n values,\n );\n return rows[0] ?? null;\n }\n\n async delete(collection: string, id: string): Promise<boolean> {\n const { rowCount } = await this.conn.query(\n `DELETE FROM \"${collection}\" WHERE \"id\" = $1`,\n [id],\n );\n return rowCount > 0;\n }\n\n async deleteMany(\n collection: string,\n filter: FilterQuery,\n ): Promise<number> {\n const q = buildSelect(collection, { filter });\n // Convert SELECT to DELETE\n const deleteText = q.text.replace(/^SELECT \\* FROM/, \"DELETE FROM\");\n const { rowCount } = await this.conn.query(deleteText, q.params);\n return rowCount;\n }\n}\n","export { SeedORM } from \"./seedorm.js\";\nexport { Model } from \"./model/model.js\";\nexport { JsonAdapter } from \"./adapters/json/json-adapter.js\";\nexport { PostgresAdapter } from \"./adapters/postgres/postgres-adapter.js\";\nexport { normalizeSchema, validateDocument } from \"./model/schema.js\";\n\n// Enums (value exports)\nexport { FieldType, RelationType, AdapterType } from \"./types.js\";\n\n// Types\nexport type {\n Document,\n FieldDefinition,\n FilterQuery,\n FilterOperators,\n FindOptions,\n ModelDefinition,\n NormalizedField,\n NormalizedSchema,\n SeedORMConfig,\n SchemaDefinition,\n SortOption,\n StorageAdapter,\n AdapterConfig,\n Migration,\n MigrationStep,\n MigrationRecord,\n RelationDefinition,\n RelationsDefinition,\n} from \"./types.js\";\n\n// Errors\nexport {\n SeedORMError,\n ValidationError,\n AdapterError,\n CollectionNotFoundError,\n DocumentNotFoundError,\n UniqueConstraintError,\n} from \"./errors.js\";\n","import {\n AdapterType,\n type AdapterConfig,\n type ModelDefinition,\n type SeedORMConfig,\n type StorageAdapter,\n} from \"./types.js\";\nimport { SeedORMError } from \"./errors.js\";\nimport { Model } from \"./model/model.js\";\nimport { JsonAdapter } from \"./adapters/json/json-adapter.js\";\nimport * as path from \"node:path\";\n\nexport class SeedORM {\n private config: SeedORMConfig;\n private adapter: StorageAdapter | null = null;\n private models = new Map<string, Model>();\n private connected = false;\n\n constructor(config?: Partial<SeedORMConfig>) {\n this.config = {\n adapter: config?.adapter ?? { adapter: AdapterType.Json, path: \"./data\" },\n migrationsDir: config?.migrationsDir ?? \"./migrations\",\n };\n }\n\n private async createAdapter(adapterConfig: AdapterConfig): Promise<StorageAdapter> {\n switch (adapterConfig.adapter) {\n case AdapterType.Json: {\n const dbPath = path.resolve(\n adapterConfig.path ?? \"./data\",\n \"seedorm.json\",\n );\n return new JsonAdapter(dbPath);\n }\n case AdapterType.Postgres: {\n const { PostgresAdapter } = await import(\"./adapters/postgres/postgres-adapter.js\");\n return new PostgresAdapter(adapterConfig.url);\n }\n case AdapterType.MySQL:\n throw new SeedORMError(\n 'MySQL adapter requires the \"mysql2\" package. Install it with: npm install mysql2',\n );\n default:\n throw new SeedORMError(\n `Unknown adapter: ${(adapterConfig as { adapter: string }).adapter}`,\n );\n }\n }\n\n async connect(): Promise<void> {\n if (this.connected) return;\n this.adapter = await this.createAdapter(this.config.adapter);\n await this.adapter.connect();\n this.connected = true;\n\n // Re-init existing models\n for (const model of this.models.values()) {\n await model.init();\n }\n }\n\n async disconnect(): Promise<void> {\n if (!this.connected || !this.adapter) return;\n await this.adapter.disconnect();\n this.connected = false;\n this.adapter = null;\n }\n\n model(definition: ModelDefinition): Model {\n if (this.models.has(definition.name)) {\n return this.models.get(definition.name)!;\n }\n\n if (!this.adapter) {\n throw new SeedORMError(\n \"Not connected. Call db.connect() before defining models.\",\n );\n }\n\n const model = new Model(definition, this.adapter, this);\n this.models.set(definition.name, model);\n return model;\n }\n\n getModel(name: string): Model | undefined {\n return this.models.get(name);\n }\n\n getAdapter(): StorageAdapter {\n if (!this.adapter) {\n throw new SeedORMError(\"Not connected.\");\n }\n return this.adapter;\n }\n\n getConfig(): SeedORMConfig {\n return this.config;\n }\n}\n","import { nanoid } from \"nanoid\";\nimport {\n RelationType,\n type Document,\n type FilterQuery,\n type FindOptions,\n type ModelDefinition,\n type NormalizedSchema,\n type RelationDefinition,\n type RelationsDefinition,\n type StorageAdapter,\n} from \"../types.js\";\nimport { DocumentNotFoundError, SeedORMError } from \"../errors.js\";\nimport { normalizeSchema, validateDocument } from \"./schema.js\";\n\ninterface SeedORMInstance {\n getModel(name: string): Model | undefined;\n getAdapter(): StorageAdapter;\n}\n\nexport class Model {\n public readonly name: string;\n public readonly collection: string;\n public readonly schema: NormalizedSchema;\n public readonly prefix: string;\n public readonly relations: RelationsDefinition;\n private adapter: StorageAdapter;\n private timestamps: boolean;\n private db: SeedORMInstance | null;\n\n constructor(definition: ModelDefinition, adapter: StorageAdapter, db?: SeedORMInstance) {\n this.name = definition.name;\n this.collection = definition.collection;\n this.schema = normalizeSchema(definition.schema);\n this.prefix = definition.prefix ?? definition.collection.slice(0, 3);\n this.adapter = adapter;\n this.timestamps = definition.timestamps !== false;\n this.relations = definition.relations ?? {};\n this.db = db ?? null;\n }\n\n async init(): Promise<void> {\n await this.adapter.createCollection(this.collection, this.schema);\n\n // Create join collections for manyToMany relations\n for (const rel of Object.values(this.relations)) {\n if (rel.type === RelationType.ManyToMany && rel.joinCollection) {\n await this.adapter.createCollection(rel.joinCollection, {});\n }\n }\n }\n\n private generateId(): string {\n return `${this.prefix}_${nanoid(12)}`;\n }\n\n private resolveRelation(relationName: string): { rel: RelationDefinition; relatedModel: Model } {\n const rel = this.relations[relationName];\n if (!rel) {\n throw new SeedORMError(`Unknown relation \"${relationName}\" on model \"${this.name}\"`);\n }\n if (!this.db) {\n throw new SeedORMError(\"Cannot resolve relations without a SeedORM instance\");\n }\n const relatedModel = this.db.getModel(rel.model);\n if (!relatedModel) {\n throw new SeedORMError(`Related model \"${rel.model}\" not found. Make sure it is defined before querying.`);\n }\n return { rel, relatedModel };\n }\n\n private async populate(docs: Document[], includeList: string[]): Promise<Document[]> {\n if (includeList.length === 0 || docs.length === 0) return docs;\n\n // Shallow-clone docs to avoid mutating the adapter's internal store\n docs = docs.map((d) => ({ ...d }));\n\n for (const relationName of includeList) {\n const { rel, relatedModel } = this.resolveRelation(relationName);\n\n switch (rel.type) {\n case RelationType.HasMany: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const grouped = new Map<string, Document[]>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!grouped.has(fk)) grouped.set(fk, []);\n grouped.get(fk)!.push(r);\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n\n case RelationType.HasOne: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!map.has(fk)) map.set(fk, r);\n }\n for (const doc of docs) {\n doc[relationName] = map.get(doc.id) ?? null;\n }\n break;\n }\n\n case RelationType.BelongsTo: {\n const fkValues = [...new Set(docs.map((d) => d[rel.foreignKey] as string).filter(Boolean))];\n if (fkValues.length === 0) {\n for (const doc of docs) doc[relationName] = null;\n break;\n }\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: fkValues } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n map.set(r.id, r);\n }\n for (const doc of docs) {\n const fk = doc[rel.foreignKey] as string;\n doc[relationName] = map.get(fk) ?? null;\n }\n break;\n }\n\n case RelationType.ManyToMany: {\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const parentIds = docs.map((d) => d.id);\n const joinRows = await this.adapter.find(rel.joinCollection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const relatedIds = [...new Set(joinRows.map((r) => r[rel.relatedKey!] as string))];\n const relatedDocs =\n relatedIds.length > 0\n ? await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: relatedIds } },\n })\n : [];\n const relatedMap = new Map<string, Document>();\n for (const r of relatedDocs) relatedMap.set(r.id, r);\n\n const grouped = new Map<string, Document[]>();\n for (const row of joinRows) {\n const parentId = row[rel.foreignKey] as string;\n const relatedId = row[rel.relatedKey!] as string;\n const relatedDoc = relatedMap.get(relatedId);\n if (relatedDoc) {\n if (!grouped.has(parentId)) grouped.set(parentId, []);\n grouped.get(parentId)!.push(relatedDoc);\n }\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n }\n }\n\n return docs;\n }\n\n async create(data: Record<string, unknown>): Promise<Document> {\n const validated = validateDocument(data, this.schema);\n const now = new Date().toISOString();\n const doc: Document = {\n ...validated,\n id: this.generateId(),\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(this.collection, doc);\n }\n\n async createMany(\n items: Record<string, unknown>[],\n ): Promise<Document[]> {\n const results: Document[] = [];\n for (const item of items) {\n results.push(await this.create(item));\n }\n return results;\n }\n\n async findById(id: string, options?: { include?: string[] }): Promise<Document | null> {\n const doc = await this.adapter.findById(this.collection, id);\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async findByIdOrThrow(id: string, options?: { include?: string[] }): Promise<Document> {\n const doc = await this.findById(id, options);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async findOne(filter: FilterQuery, options?: { include?: string[] }): Promise<Document | null> {\n const results = await this.adapter.find(this.collection, {\n filter,\n limit: 1,\n });\n const doc = results[0] ?? null;\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async find(options: FindOptions = {}): Promise<Document[]> {\n const { include, ...adapterOptions } = options;\n const docs = await this.adapter.find(this.collection, adapterOptions);\n if (!include?.length) return docs;\n return this.populate(docs, include);\n }\n\n async findAll(): Promise<Document[]> {\n return this.adapter.find(this.collection, {});\n }\n\n async count(filter?: FilterQuery): Promise<number> {\n return this.adapter.count(this.collection, filter);\n }\n\n async update(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document | null> {\n const validated = validateDocument(data, this.schema, true);\n if (this.timestamps) {\n validated.updatedAt = new Date().toISOString();\n }\n return this.adapter.update(this.collection, id, validated);\n }\n\n async updateOrThrow(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document> {\n const doc = await this.update(id, data);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async delete(id: string): Promise<boolean> {\n return this.adapter.delete(this.collection, id);\n }\n\n async deleteMany(filter: FilterQuery): Promise<number> {\n return this.adapter.deleteMany(this.collection, filter);\n }\n\n async associate(id: string, relationName: string, relatedId: string): Promise<Document> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`associate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const now = new Date().toISOString();\n const joinDoc: Document = {\n id: `${this.prefix}rel_${nanoid(12)}`,\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(rel.joinCollection, joinDoc);\n }\n\n async dissociate(id: string, relationName: string, relatedId: string): Promise<number> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`dissociate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n return this.adapter.deleteMany(rel.joinCollection, {\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n });\n }\n}\n","import {\n FieldType,\n type FieldDefinition,\n type NormalizedField,\n type NormalizedSchema,\n type SchemaDefinition,\n} from \"../types.js\";\nimport { ValidationError } from \"../errors.js\";\nimport { coerceFieldValue, validateFieldType } from \"./field-types.js\";\n\nexport function normalizeSchema(schema: SchemaDefinition): NormalizedSchema {\n const normalized: NormalizedSchema = {};\n\n for (const [field, def] of Object.entries(schema)) {\n if (typeof def === \"string\") {\n normalized[field] = {\n type: def as FieldType,\n required: false,\n unique: false,\n index: false,\n };\n } else {\n const d = def as FieldDefinition;\n normalized[field] = {\n type: d.type,\n required: d.required ?? false,\n unique: d.unique ?? false,\n index: d.index ?? d.unique ?? false,\n ...(d.default !== undefined && { default: d.default }),\n ...(d.minLength !== undefined && { minLength: d.minLength }),\n ...(d.maxLength !== undefined && { maxLength: d.maxLength }),\n ...(d.min !== undefined && { min: d.min }),\n ...(d.max !== undefined && { max: d.max }),\n ...(d.enum !== undefined && { enum: d.enum }),\n };\n }\n }\n\n return normalized;\n}\n\nexport function validateDocument(\n data: Record<string, unknown>,\n schema: NormalizedSchema,\n isUpdate = false,\n): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n\n for (const [field, def] of Object.entries(schema)) {\n let value = data[field];\n\n // Apply default\n if (value === undefined && def.default !== undefined && !isUpdate) {\n value =\n typeof def.default === \"function\"\n ? (def.default as () => unknown)()\n : def.default;\n }\n\n // Required check (skip on partial updates)\n if (!isUpdate && def.required && (value === undefined || value === null)) {\n throw new ValidationError(field, \"field is required\");\n }\n\n // Skip unset fields on update\n if (value === undefined) continue;\n\n // Type check\n const typeErr = validateFieldType(value, def.type);\n if (typeErr) throw new ValidationError(field, typeErr);\n\n // String constraints\n if (def.type === \"string\" && typeof value === \"string\") {\n if (def.minLength !== undefined && value.length < def.minLength) {\n throw new ValidationError(\n field,\n `minimum length is ${def.minLength}, got ${value.length}`,\n );\n }\n if (def.maxLength !== undefined && value.length > def.maxLength) {\n throw new ValidationError(\n field,\n `maximum length is ${def.maxLength}, got ${value.length}`,\n );\n }\n }\n\n // Number constraints\n if (def.type === \"number\" && typeof value === \"number\") {\n if (def.min !== undefined && value < def.min) {\n throw new ValidationError(field, `minimum value is ${def.min}`);\n }\n if (def.max !== undefined && value > def.max) {\n throw new ValidationError(field, `maximum value is ${def.max}`);\n }\n }\n\n // Enum check\n if (def.enum && !def.enum.includes(value)) {\n throw new ValidationError(\n field,\n `value must be one of: ${def.enum.join(\", \")}`,\n );\n }\n\n result[field] = coerceFieldValue(value, def.type);\n }\n\n // On update, pass through non-schema fields that were provided\n // (for id, createdAt, updatedAt)\n if (isUpdate) {\n for (const [key, val] of Object.entries(data)) {\n if (!(key in schema) && val !== undefined) {\n result[key] = val;\n }\n }\n }\n\n return result;\n}\n","import { FieldType } from \"../types.js\";\n\nexport function validateFieldType(\n value: unknown,\n type: FieldType,\n): string | null {\n if (value === undefined || value === null) return null; // handled by required check\n\n switch (type) {\n case FieldType.String:\n if (typeof value !== \"string\") return `expected string, got ${typeof value}`;\n break;\n case FieldType.Number:\n if (typeof value !== \"number\" || Number.isNaN(value))\n return `expected number, got ${typeof value}`;\n break;\n case FieldType.Boolean:\n if (typeof value !== \"boolean\")\n return `expected boolean, got ${typeof value}`;\n break;\n case FieldType.Date:\n if (typeof value === \"string\") {\n if (Number.isNaN(Date.parse(value))) return `invalid date string`;\n } else if (!(value instanceof Date)) {\n return `expected date string or Date, got ${typeof value}`;\n }\n break;\n case FieldType.Json:\n // Any non-undefined value is valid JSON\n break;\n case FieldType.Array:\n if (!Array.isArray(value)) return `expected array, got ${typeof value}`;\n break;\n default:\n return `unknown type: ${type as string}`;\n }\n\n return null;\n}\n\nexport function coerceFieldValue(value: unknown, type: FieldType): unknown {\n if (value === undefined || value === null) return value;\n\n if (type === FieldType.Date && value instanceof Date) {\n return value.toISOString();\n }\n\n return value;\n}\n","import type {\n Document,\n FilterQuery,\n FindOptions,\n NormalizedSchema,\n StorageAdapter,\n} from \"../../types.js\";\nimport { AdapterError, CollectionNotFoundError } from \"../../errors.js\";\nimport { applyFindOptions, countWithFilter } from \"../../query/filter.js\";\nimport { FileEngine } from \"./file-engine.js\";\nimport { Indexer } from \"./indexer.js\";\n\nexport class JsonAdapter implements StorageAdapter {\n private engine: FileEngine;\n private indexer = new Indexer();\n private schemas = new Map<string, NormalizedSchema>();\n\n constructor(filePath: string) {\n this.engine = new FileEngine(filePath);\n }\n\n async connect(): Promise<void> {\n await this.engine.load();\n }\n\n async disconnect(): Promise<void> {\n await this.engine.flushIfDirty();\n }\n\n async createCollection(\n collection: string,\n schema: NormalizedSchema,\n ): Promise<void> {\n this.engine.createCollection(collection);\n this.schemas.set(collection, schema);\n\n // Set up indexes\n for (const [field, def] of Object.entries(schema)) {\n if (def.index || def.unique) {\n this.indexer.setupIndex(\n collection,\n field,\n def.unique,\n this.engine.getCollection(collection),\n );\n }\n }\n\n await this.engine.flush();\n }\n\n async dropCollection(collection: string): Promise<void> {\n this.engine.dropCollection(collection);\n this.indexer.dropCollection(collection);\n this.schemas.delete(collection);\n await this.engine.flush();\n }\n\n async listCollections(): Promise<string[]> {\n return this.engine.listCollections();\n }\n\n async insert(collection: string, doc: Document): Promise<Document> {\n const docs = this.getCollectionOrThrow(collection);\n\n // Check unique constraints via indexer\n this.indexer.onInsert(collection, doc);\n\n docs.push(doc);\n this.engine.markDirty();\n await this.engine.flush();\n return doc;\n }\n\n async findById(\n collection: string,\n id: string,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n return docs.find((d) => d.id === id) ?? null;\n }\n\n async find(\n collection: string,\n options: FindOptions,\n ): Promise<Document[]> {\n const docs = this.getCollectionOrThrow(collection);\n return applyFindOptions(docs, options);\n }\n\n async count(collection: string, filter?: FilterQuery): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n return countWithFilter(docs, filter);\n }\n\n async update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return null;\n\n const oldDoc = docs[index]!;\n const newDoc = { ...oldDoc, ...data, id: oldDoc.id };\n\n // Check unique constraints\n this.indexer.onUpdate(collection, oldDoc, newDoc);\n\n docs[index] = newDoc;\n this.engine.markDirty();\n await this.engine.flush();\n return newDoc;\n }\n\n async delete(collection: string, id: string): Promise<boolean> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return false;\n\n this.indexer.onDelete(collection, docs[index]!);\n docs.splice(index, 1);\n this.engine.markDirty();\n await this.engine.flush();\n return true;\n }\n\n async deleteMany(\n collection: string,\n filter: FilterQuery,\n ): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n const matching = applyFindOptions(docs, { filter });\n\n for (const doc of matching) {\n this.indexer.onDelete(collection, doc);\n }\n\n const ids = new Set(matching.map((d) => d.id));\n const remaining = docs.filter((d) => !ids.has(d.id));\n const deleted = docs.length - remaining.length;\n\n // Replace array contents in-place\n docs.length = 0;\n docs.push(...remaining);\n\n if (deleted > 0) {\n this.engine.markDirty();\n await this.engine.flush();\n }\n\n return deleted;\n }\n\n private getCollectionOrThrow(collection: string): Document[] {\n if (!this.engine.hasCollection(collection)) {\n throw new CollectionNotFoundError(collection);\n }\n return this.engine.getCollection(collection);\n }\n}\n","import type { Document, FilterQuery, FindOptions, SortOption } from \"../types.js\";\nimport { applyOperator, isOperatorObject } from \"./operators.js\";\n\nfunction matchesFilter(doc: Document, filter: FilterQuery): boolean {\n for (const [field, condition] of Object.entries(filter)) {\n const value = doc[field];\n\n if (isOperatorObject(condition)) {\n for (const [op, operand] of Object.entries(\n condition as Record<string, unknown>,\n )) {\n if (!applyOperator(op, value, operand)) return false;\n }\n } else {\n // Shorthand: { field: value } is equivalent to { field: { $eq: value } }\n if (value !== condition) return false;\n }\n }\n return true;\n}\n\nfunction sortDocuments(docs: Document[], sort: SortOption): Document[] {\n const entries = Object.entries(sort);\n return [...docs].sort((a, b) => {\n for (const [field, dir] of entries) {\n const av = a[field];\n const bv = b[field];\n if (av === bv) continue;\n if (av === undefined || av === null) return dir;\n if (bv === undefined || bv === null) return -dir;\n if (av < bv) return -dir;\n if (av > bv) return dir;\n }\n return 0;\n });\n}\n\nexport function applyFindOptions(\n docs: Document[],\n options: FindOptions,\n): Document[] {\n let result = docs;\n\n if (options.filter) {\n result = result.filter((doc) => matchesFilter(doc, options.filter!));\n }\n\n if (options.sort) {\n result = sortDocuments(result, options.sort);\n }\n\n if (options.offset) {\n result = result.slice(options.offset);\n }\n\n if (options.limit !== undefined) {\n result = result.slice(0, options.limit);\n }\n\n return result;\n}\n\nexport function countWithFilter(\n docs: Document[],\n filter?: FilterQuery,\n): number {\n if (!filter) return docs.length;\n return docs.filter((doc) => matchesFilter(doc, filter)).length;\n}\n\nexport { matchesFilter };\n","import * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport writeFileAtomic from \"write-file-atomic\";\nimport type { Document } from \"../../types.js\";\n\nexport interface FileData {\n [collection: string]: Document[];\n}\n\nexport class FileEngine {\n private filePath: string;\n private data: FileData = {};\n private writeQueue: Promise<void> = Promise.resolve();\n private dirty = false;\n\n constructor(filePath: string) {\n this.filePath = path.resolve(filePath);\n }\n\n async load(): Promise<void> {\n try {\n const raw = fs.readFileSync(this.filePath, \"utf-8\");\n this.data = JSON.parse(raw) as FileData;\n } catch (err: unknown) {\n if ((err as NodeJS.ErrnoException).code === \"ENOENT\") {\n this.data = {};\n await this.flush();\n } else {\n throw err;\n }\n }\n }\n\n getData(): FileData {\n return this.data;\n }\n\n getCollection(name: string): Document[] {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n return this.data[name];\n }\n\n hasCollection(name: string): boolean {\n return name in this.data;\n }\n\n createCollection(name: string): void {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n }\n\n dropCollection(name: string): void {\n delete this.data[name];\n }\n\n listCollections(): string[] {\n return Object.keys(this.data);\n }\n\n markDirty(): void {\n this.dirty = true;\n }\n\n async flush(): Promise<void> {\n this.writeQueue = this.writeQueue.then(async () => {\n const dir = path.dirname(this.filePath);\n if (!fs.existsSync(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n await writeFileAtomic(\n this.filePath,\n JSON.stringify(this.data, null, 2) + \"\\n\",\n );\n this.dirty = false;\n });\n return this.writeQueue;\n }\n\n async flushIfDirty(): Promise<void> {\n if (this.dirty) {\n await this.flush();\n }\n }\n}\n","import type { Document } from \"../../types.js\";\nimport { UniqueConstraintError } from \"../../errors.js\";\n\ninterface FieldIndex {\n field: string;\n unique: boolean;\n map: Map<unknown, Set<string>>; // value → set of doc IDs\n}\n\nexport class Indexer {\n private indexes = new Map<string, Map<string, FieldIndex>>(); // collection → field → index\n\n setupIndex(\n collection: string,\n field: string,\n unique: boolean,\n docs: Document[],\n ): void {\n if (!this.indexes.has(collection)) {\n this.indexes.set(collection, new Map());\n }\n const colIndexes = this.indexes.get(collection)!;\n\n const idx: FieldIndex = { field, unique, map: new Map() };\n\n for (const doc of docs) {\n const val = doc[field];\n if (val === undefined || val === null) continue;\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n\n colIndexes.set(field, idx);\n }\n\n onInsert(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val === undefined || val === null) continue;\n\n if (idx.unique && idx.map.has(val) && idx.map.get(val)!.size > 0) {\n throw new UniqueConstraintError(collection, idx.field, val);\n }\n\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n }\n\n onUpdate(\n collection: string,\n oldDoc: Document,\n newDoc: Document,\n ): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const oldVal = oldDoc[idx.field];\n const newVal = newDoc[idx.field];\n\n if (oldVal === newVal) continue;\n\n // Remove old\n if (oldVal !== undefined && oldVal !== null) {\n idx.map.get(oldVal)?.delete(oldDoc.id);\n }\n\n // Add new\n if (newVal !== undefined && newVal !== null) {\n if (\n idx.unique &&\n idx.map.has(newVal) &&\n idx.map.get(newVal)!.size > 0\n ) {\n throw new UniqueConstraintError(collection, idx.field, newVal);\n }\n if (!idx.map.has(newVal)) {\n idx.map.set(newVal, new Set());\n }\n idx.map.get(newVal)!.add(newDoc.id);\n }\n }\n }\n\n onDelete(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val !== undefined && val !== null) {\n idx.map.get(val)?.delete(doc.id);\n }\n }\n }\n\n findByValue(\n collection: string,\n field: string,\n value: unknown,\n ): Set<string> | undefined {\n return this.indexes.get(collection)?.get(field)?.map.get(value);\n }\n\n dropCollection(collection: string): void {\n this.indexes.delete(collection);\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,IAEY,WAuFA,cAuDA;AAhJZ;AAAA;AAAA;AAEO,IAAK,YAAL,kBAAKA,eAAL;AACL,MAAAA,WAAA,YAAS;AACT,MAAAA,WAAA,YAAS;AACT,MAAAA,WAAA,aAAU;AACV,MAAAA,WAAA,UAAO;AACP,MAAAA,WAAA,UAAO;AACP,MAAAA,WAAA,WAAQ;AANE,aAAAA;AAAA,OAAA;AAuFL,IAAK,eAAL,kBAAKC,kBAAL;AACL,MAAAA,cAAA,YAAS;AACT,MAAAA,cAAA,aAAU;AACV,MAAAA,cAAA,eAAY;AACZ,MAAAA,cAAA,gBAAa;AAJH,aAAAA;AAAA,OAAA;AAuDL,IAAK,cAAL,kBAAKC,iBAAL;AACL,MAAAA,aAAA,UAAO;AACP,MAAAA,aAAA,cAAW;AACX,MAAAA,aAAA,WAAQ;AAHE,aAAAA;AAAA,OAAA;AAAA;AAAA;;;AChJZ,IAAa,cAOA,iBAYA,cAUA,yBAOA,uBAOA;AA3Cb;AAAA;AAAA;AAAO,IAAM,eAAN,cAA2B,MAAM;AAAA,MACtC,YAAY,SAAiB;AAC3B,cAAM,OAAO;AACb,aAAK,OAAO;AAAA,MACd;AAAA,IACF;AAEO,IAAM,kBAAN,cAA8B,aAAa;AAAA,MACzC;AAAA,MACA;AAAA,MAEP,YAAY,OAAe,QAAgB;AACzC,cAAM,wBAAwB,KAAK,MAAM,MAAM,EAAE;AACjD,aAAK,OAAO;AACZ,aAAK,QAAQ;AACb,aAAK,SAAS;AAAA,MAChB;AAAA,IACF;AAEO,IAAM,eAAN,cAA2B,aAAa;AAAA,MACtC;AAAA,MAEP,YAAY,SAAiB,SAAiB;AAC5C,cAAM,IAAI,OAAO,KAAK,OAAO,EAAE;AAC/B,aAAK,OAAO;AACZ,aAAK,UAAU;AAAA,MACjB;AAAA,IACF;AAEO,IAAM,0BAAN,cAAsC,aAAa;AAAA,MACxD,YAAY,YAAoB;AAC9B,cAAM,eAAe,UAAU,aAAa;AAC5C,aAAK,OAAO;AAAA,MACd;AAAA,IACF;AAEO,IAAM,wBAAN,cAAoC,aAAa;AAAA,MACtD,YAAY,YAAoB,IAAY;AAC1C,cAAM,aAAa,EAAE,mBAAmB,UAAU,GAAG;AACrD,aAAK,OAAO;AAAA,MACd;AAAA,IACF;AAEO,IAAM,wBAAN,cAAoC,aAAa;AAAA,MAC/C;AAAA,MACA;AAAA,MAEP,YAAY,YAAoB,OAAe,OAAgB;AAC7D;AAAA,UACE,mCAAmC,UAAU,IAAI,KAAK,YAAY,KAAK,UAAU,KAAK,CAAC;AAAA,QACzF;AACA,aAAK,OAAO;AACZ,aAAK,QAAQ;AACb,aAAK,QAAQ;AAAA,MACf;AAAA,IACF;AAAA;AAAA;;;ACEO,SAAS,cACd,KACA,YACA,SACS;AACT,QAAM,KAAK,UAAU,GAAG;AACxB,MAAI,CAAC,GAAI,OAAM,IAAI,MAAM,qBAAqB,GAAG,EAAE;AACnD,SAAO,GAAG,YAAY,OAAO;AAC/B;AAEO,SAAS,iBAAiB,OAA0C;AACzE,MAAI,UAAU,QAAQ,OAAO,UAAU,YAAY,MAAM,QAAQ,KAAK;AACpE,WAAO;AACT,SAAO,OAAO,KAAK,KAAe,EAAE,KAAK,CAAC,MAAM,EAAE,WAAW,GAAG,CAAC;AACnE;AAvEA,IAIM,WAqEO;AAzEb;AAAA;AAAA;AAIA,IAAM,YAAwC;AAAA,MAC5C,KAAK,CAAC,KAAK,OAAO,QAAQ;AAAA,MAE1B,KAAK,CAAC,KAAK,OAAO,QAAQ;AAAA,MAE1B,KAAK,CAAC,KAAK,OAAO;AAChB,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,MAAM;AACpE,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,MAAM;AACpE,eAAO;AAAA,MACT;AAAA,MAEA,MAAM,CAAC,KAAK,OAAO;AACjB,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,OAAO;AACrE,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,OAAO;AACrE,eAAO;AAAA,MACT;AAAA,MAEA,KAAK,CAAC,KAAK,OAAO;AAChB,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,MAAM;AACpE,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,MAAM;AACpE,eAAO;AAAA,MACT;AAAA,MAEA,MAAM,CAAC,KAAK,OAAO;AACjB,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,OAAO;AACrE,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO,OAAO;AACrE,eAAO;AAAA,MACT;AAAA,MAEA,KAAK,CAAC,KAAK,OAAO;AAChB,YAAI,CAAC,MAAM,QAAQ,EAAE,EAAG,QAAO;AAC/B,eAAO,GAAG,SAAS,GAAG;AAAA,MACxB;AAAA,MAEA,MAAM,CAAC,KAAK,OAAO;AACjB,YAAI,CAAC,MAAM,QAAQ,EAAE,EAAG,QAAO;AAC/B,eAAO,CAAC,GAAG,SAAS,GAAG;AAAA,MACzB;AAAA,MAEA,OAAO,CAAC,KAAK,OAAO;AAClB,YAAI,OAAO,QAAQ,YAAY,OAAO,OAAO,SAAU,QAAO;AAE9D,cAAM,UAAU,GAAG,QAAQ,uBAAuB,MAAM;AACxD,cAAM,UAAU,QAAQ,QAAQ,MAAM,IAAI,EAAE,QAAQ,MAAM,GAAG;AAC7D,eAAO,IAAI,OAAO,IAAI,OAAO,KAAK,GAAG,EAAE,KAAK,GAAG;AAAA,MACjD;AAAA,MAEA,SAAS,CAAC,KAAK,OAAO;AACpB,cAAM,SAAS,QAAQ,UAAa,QAAQ;AAC5C,eAAO,KAAK,SAAS,CAAC;AAAA,MACxB;AAAA,IACF;AAkBO,IAAM,YAAY,OAAO,KAAK,SAAS;AAAA;AAAA;;;ACpE9C,eAAe,SAAuC;AACpD,MAAI,SAAU,QAAO;AACrB,MAAI;AACF,eAAW,MAAM,OAAO,IAAI;AAC5B,WAAO;AAAA,EACT,QAAQ;AACN,UAAM,IAAI;AAAA,MACR;AAAA,MACA;AAAA,IACF;AAAA,EACF;AACF;AAhBA,IAGI,UAeS;AAlBb;AAAA;AAAA;AAAA;AAGA,IAAI,WAAuC;AAepC,IAAM,eAAN,MAAmB;AAAA,MAChB,OAAiC;AAAA,MACjC;AAAA,MAER,YAAY,KAAa;AACvB,aAAK,MAAM;AAAA,MACb;AAAA,MAEA,MAAM,UAAyB;AAC7B,cAAM,KAAK,MAAM,OAAO;AACxB,aAAK,OAAO,IAAI,GAAG,KAAK,EAAE,kBAAkB,KAAK,IAAI,CAAC;AAEtD,cAAM,SAAS,MAAM,KAAK,KAAK,QAAQ;AACvC,eAAO,QAAQ;AAAA,MACjB;AAAA,MAEA,MAAM,aAA4B;AAChC,YAAI,KAAK,MAAM;AACb,gBAAM,KAAK,KAAK,IAAI;AACpB,eAAK,OAAO;AAAA,QACd;AAAA,MACF;AAAA,MAEA,MAAM,MACJ,MACA,QAC0C;AAC1C,YAAI,CAAC,KAAK,MAAM;AACd,gBAAM,IAAI,aAAa,YAAY,eAAe;AAAA,QACpD;AACA,cAAM,SAAS,MAAM,KAAK,KAAK,MAAM,MAAM,MAAM;AACjD,eAAO,EAAE,MAAM,OAAO,MAAa,UAAU,OAAO,YAAY,EAAE;AAAA,MACpE;AAAA,IACF;AAAA;AAAA;;;AC3CO,SAAS,YACd,YACA,SACY;AACZ,QAAM,SAAoB,CAAC;AAC3B,MAAI,OAAO,kBAAkB,UAAU;AAEvC,MAAI,QAAQ,UAAU,OAAO,KAAK,QAAQ,MAAM,EAAE,SAAS,GAAG;AAC5D,UAAM,QAAQ,WAAW,QAAQ,QAAQ,MAAM;AAC/C,YAAQ,UAAU,KAAK;AAAA,EACzB;AAEA,MAAI,QAAQ,MAAM;AAChB,YAAQ,aAAa,aAAa,QAAQ,IAAI,CAAC;AAAA,EACjD;AAEA,MAAI,QAAQ,UAAU,QAAW;AAC/B,WAAO,KAAK,QAAQ,KAAK;AACzB,YAAQ,WAAW,OAAO,MAAM;AAAA,EAClC;AAEA,MAAI,QAAQ,WAAW,QAAW;AAChC,WAAO,KAAK,QAAQ,MAAM;AAC1B,YAAQ,YAAY,OAAO,MAAM;AAAA,EACnC;AAEA,SAAO,EAAE,MAAM,OAAO;AACxB;AAEO,SAAS,WACd,YACA,QACY;AACZ,QAAM,SAAoB,CAAC;AAC3B,MAAI,OAAO,kCAAkC,UAAU;AAEvD,MAAI,UAAU,OAAO,KAAK,MAAM,EAAE,SAAS,GAAG;AAC5C,UAAM,QAAQ,WAAW,QAAQ,MAAM;AACvC,YAAQ,UAAU,KAAK;AAAA,EACzB;AAEA,SAAO,EAAE,MAAM,OAAO;AACxB;AAEA,SAAS,WAAW,QAAqB,QAA2B;AAClE,QAAM,aAAuB,CAAC;AAE9B,aAAW,CAAC,OAAO,SAAS,KAAK,OAAO,QAAQ,MAAM,GAAG;AACvD,QAAI,iBAAiB,SAAS,GAAG;AAC/B,iBAAW,CAAC,IAAI,KAAK,KAAK,OAAO;AAAA,QAC/B;AAAA,MACF,GAAG;AACD,mBAAW,KAAK,cAAc,OAAO,IAAI,OAAO,MAAM,CAAC;AAAA,MACzD;AAAA,IACF,OAAO;AACL,aAAO,KAAK,SAAS;AACrB,iBAAW,KAAK,IAAI,KAAK,QAAQ,OAAO,MAAM,EAAE;AAAA,IAClD;AAAA,EACF;AAEA,SAAO,WAAW,KAAK,OAAO;AAChC;AAEA,SAAS,cACP,OACA,IACA,OACA,QACQ;AACR,UAAQ,IAAI;AAAA,IACV,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,QAAQ,OAAO,MAAM;AAAA,IACvC,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,SAAS,OAAO,MAAM;AAAA,IACxC,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,QAAQ,OAAO,MAAM;AAAA,IACvC,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,SAAS,OAAO,MAAM;AAAA,IACxC,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,QAAQ,OAAO,MAAM;AAAA,IACvC,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,SAAS,OAAO,MAAM;AAAA,IACxC,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,YAAY,OAAO,MAAM;AAAA,IAC3C,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,aAAa,OAAO,MAAM;AAAA,IAC5C,KAAK;AACH,aAAO,KAAK,KAAK;AACjB,aAAO,IAAI,KAAK,YAAY,OAAO,MAAM;AAAA,IAC3C,KAAK;AACH,aAAO,QACH,IAAI,KAAK,kBACT,IAAI,KAAK;AAAA,IACf;AACE,YAAM,IAAI,MAAM,qBAAqB,EAAE,EAAE;AAAA,EAC7C;AACF;AAEA,SAAS,aAAa,MAA0B;AAC9C,SAAO,OAAO,QAAQ,IAAI,EACvB,IAAI,CAAC,CAAC,OAAO,GAAG,MAAM,IAAI,KAAK,KAAK,QAAQ,IAAI,QAAQ,MAAM,EAAE,EAChE,KAAK,IAAI;AACd;AAtHA;AAAA;AAAA;AACA;AAAA;AAAA;;;ACDA;AAAA;AAAA;AAAA;AAaA,SAAS,eAAe,OAAgC;AACtD,UAAQ,MAAM,MAAM;AAAA,IAClB;AACE,aAAO,MAAM,YAAY,WAAW,MAAM,SAAS,MAAM;AAAA,IAC3D;AACE,aAAO;AAAA,IACT;AACE,aAAO;AAAA,IACT;AACE,aAAO;AAAA,IACT;AAAA,IACA;AACE,aAAO;AAAA,IACT;AACE,aAAO;AAAA,EACX;AACF;AA7BA,IA+Ba;AA/Bb;AAAA;AAAA;AAAA;AAUA;AACA;AAoBO,IAAM,kBAAN,MAAgD;AAAA,MAC7C;AAAA,MAER,YAAY,KAAa;AACvB,aAAK,OAAO,IAAI,aAAa,GAAG;AAAA,MAClC;AAAA,MAEA,MAAM,UAAyB;AAC7B,cAAM,KAAK,KAAK,QAAQ;AAAA,MAC1B;AAAA,MAEA,MAAM,aAA4B;AAChC,cAAM,KAAK,KAAK,WAAW;AAAA,MAC7B;AAAA,MAEA,MAAM,iBACJ,YACA,QACe;AACf,cAAM,UAAU;AAAA,UACd;AAAA,UACA;AAAA,UACA;AAAA,QACF;AAEA,mBAAW,CAAC,MAAM,GAAG,KAAK,OAAO,QAAQ,MAAM,GAAG;AAChD,cAAI,MAAM,IAAI,IAAI,KAAK,eAAe,GAAG,CAAC;AAC1C,cAAI,IAAI,SAAU,QAAO;AACzB,cAAI,IAAI,OAAQ,QAAO;AACvB,kBAAQ,KAAK,GAAG;AAAA,QAClB;AAEA,cAAM,KAAK,KAAK;AAAA,UACd,+BAA+B,UAAU,MAAM,QAAQ,KAAK,IAAI,CAAC;AAAA,QACnE;AAGA,mBAAW,CAAC,MAAM,GAAG,KAAK,OAAO,QAAQ,MAAM,GAAG;AAChD,cAAI,IAAI,SAAS,CAAC,IAAI,QAAQ;AAC5B,kBAAM,KAAK,KAAK;AAAA,cACd,mCAAmC,UAAU,IAAI,IAAI,SAAS,UAAU,OAAO,IAAI;AAAA,YACrF;AAAA,UACF;AAAA,QACF;AAAA,MACF;AAAA,MAEA,MAAM,eAAe,YAAmC;AACtD,cAAM,KAAK,KAAK,MAAM,yBAAyB,UAAU,WAAW;AAAA,MACtE;AAAA,MAEA,MAAM,kBAAqC;AACzC,cAAM,EAAE,KAAK,IAAI,MAAM,KAAK,KAAK;AAAA,UAC/B;AAAA,QACF;AACA,eAAO,KAAK,IAAI,CAAC,MAAM,EAAE,SAAS;AAAA,MACpC;AAAA,MAEA,MAAM,OAAO,YAAoB,KAAkC;AACjE,cAAM,OAAO,OAAO,KAAK,GAAG;AAC5B,cAAM,OAAO,KAAK,IAAI,CAAC,MAAM,IAAI,CAAC,GAAG,EAAE,KAAK,IAAI;AAChD,cAAM,eAAe,KAAK,IAAI,CAAC,GAAG,MAAM,IAAI,IAAI,CAAC,EAAE,EAAE,KAAK,IAAI;AAC9D,cAAM,SAAS,KAAK,IAAI,CAAC,MAAM;AAC7B,gBAAM,IAAI,IAAI,CAAC;AACf,iBAAO,OAAO,MAAM,YAAY,MAAM,QAAQ,EAAE,aAAa,QACzD,KAAK,UAAU,CAAC,IAChB;AAAA,QACN,CAAC;AAED,cAAM,EAAE,KAAK,IAAI,MAAM,KAAK,KAAK;AAAA,UAC/B,gBAAgB,UAAU,MAAM,IAAI,aAAa,YAAY;AAAA,UAC7D;AAAA,QACF;AACA,eAAO,KAAK,CAAC;AAAA,MACf;AAAA,MAEA,MAAM,SACJ,YACA,IAC0B;AAC1B,cAAM,EAAE,KAAK,IAAI,MAAM,KAAK,KAAK;AAAA,UAC/B,kBAAkB,UAAU;AAAA,UAC5B,CAAC,EAAE;AAAA,QACL;AACA,eAAO,KAAK,CAAC,KAAK;AAAA,MACpB;AAAA,MAEA,MAAM,KACJ,YACA,SACqB;AACrB,cAAM,IAAI,YAAY,YAAY,OAAO;AACzC,cAAM,EAAE,KAAK,IAAI,MAAM,KAAK,KAAK,MAAgB,EAAE,MAAM,EAAE,MAAM;AACjE,eAAO;AAAA,MACT;AAAA,MAEA,MAAM,MAAM,YAAoB,QAAuC;AACrE,cAAM,IAAI,WAAW,YAAY,MAAM;AACvC,cAAM,EAAE,KAAK,IAAI,MAAM,KAAK,KAAK;AAAA,UAC/B,EAAE;AAAA,UACF,EAAE;AAAA,QACJ;AACA,eAAO,SAAS,KAAK,CAAC,EAAG,OAAO,EAAE;AAAA,MACpC;AAAA,MAEA,MAAM,OACJ,YACA,IACA,MAC0B;AAC1B,cAAM,UAAU,OAAO,QAAQ,IAAI,EAAE,OAAO,CAAC,CAAC,CAAC,MAAM,MAAM,IAAI;AAC/D,YAAI,QAAQ,WAAW,EAAG,QAAO,KAAK,SAAS,YAAY,EAAE;AAE7D,cAAM,OAAO,QAAQ,IAAI,CAAC,CAAC,CAAC,GAAG,MAAM,IAAI,CAAC,QAAQ,IAAI,CAAC,EAAE,EAAE,KAAK,IAAI;AACpE,cAAM,SAAS,QAAQ;AAAA,UAAI,CAAC,CAAC,EAAE,CAAC,MAC9B,OAAO,MAAM,YAAY,MAAM,QAAQ,EAAE,aAAa,QAClD,KAAK,UAAU,CAAC,IAChB;AAAA,QACN;AACA,eAAO,KAAK,EAAE;AAEd,cAAM,EAAE,KAAK,IAAI,MAAM,KAAK,KAAK;AAAA,UAC/B,WAAW,UAAU,SAAS,IAAI,kBAAkB,OAAO,MAAM;AAAA,UACjE;AAAA,QACF;AACA,eAAO,KAAK,CAAC,KAAK;AAAA,MACpB;AAAA,MAEA,MAAM,OAAO,YAAoB,IAA8B;AAC7D,cAAM,EAAE,SAAS,IAAI,MAAM,KAAK,KAAK;AAAA,UACnC,gBAAgB,UAAU;AAAA,UAC1B,CAAC,EAAE;AAAA,QACL;AACA,eAAO,WAAW;AAAA,MACpB;AAAA,MAEA,MAAM,WACJ,YACA,QACiB;AACjB,cAAM,IAAI,YAAY,YAAY,EAAE,OAAO,CAAC;AAE5C,cAAM,aAAa,EAAE,KAAK,QAAQ,mBAAmB,aAAa;AAClE,cAAM,EAAE,SAAS,IAAI,MAAM,KAAK,KAAK,MAAM,YAAY,EAAE,MAAM;AAC/D,eAAO;AAAA,MACT;AAAA,IACF;AAAA;AAAA;;;AChLA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACAA;AAOA;;;ACPA,oBAAuB;AACvB;AAWA;;;ACLA;;;ACPA;AAEO,SAAS,kBACd,OACA,MACe;AACf,MAAI,UAAU,UAAa,UAAU,KAAM,QAAO;AAElD,UAAQ,MAAM;AAAA,IACZ;AACE,UAAI,OAAO,UAAU,SAAU,QAAO,wBAAwB,OAAO,KAAK;AAC1E;AAAA,IACF;AACE,UAAI,OAAO,UAAU,YAAY,OAAO,MAAM,KAAK;AACjD,eAAO,wBAAwB,OAAO,KAAK;AAC7C;AAAA,IACF;AACE,UAAI,OAAO,UAAU;AACnB,eAAO,yBAAyB,OAAO,KAAK;AAC9C;AAAA,IACF;AACE,UAAI,OAAO,UAAU,UAAU;AAC7B,YAAI,OAAO,MAAM,KAAK,MAAM,KAAK,CAAC,EAAG,QAAO;AAAA,MAC9C,WAAW,EAAE,iBAAiB,OAAO;AACnC,eAAO,qCAAqC,OAAO,KAAK;AAAA,MAC1D;AACA;AAAA,IACF;AAEE;AAAA,IACF;AACE,UAAI,CAAC,MAAM,QAAQ,KAAK,EAAG,QAAO,uBAAuB,OAAO,KAAK;AACrE;AAAA,IACF;AACE,aAAO,iBAAiB,IAAc;AAAA,EAC1C;AAEA,SAAO;AACT;AAEO,SAAS,iBAAiB,OAAgB,MAA0B;AACzE,MAAI,UAAU,UAAa,UAAU,KAAM,QAAO;AAElD,MAAI,8BAA2B,iBAAiB,MAAM;AACpD,WAAO,MAAM,YAAY;AAAA,EAC3B;AAEA,SAAO;AACT;;;ADtCO,SAAS,gBAAgB,QAA4C;AAC1E,QAAM,aAA+B,CAAC;AAEtC,aAAW,CAAC,OAAO,GAAG,KAAK,OAAO,QAAQ,MAAM,GAAG;AACjD,QAAI,OAAO,QAAQ,UAAU;AAC3B,iBAAW,KAAK,IAAI;AAAA,QAClB,MAAM;AAAA,QACN,UAAU;AAAA,QACV,QAAQ;AAAA,QACR,OAAO;AAAA,MACT;AAAA,IACF,OAAO;AACL,YAAM,IAAI;AACV,iBAAW,KAAK,IAAI;AAAA,QAClB,MAAM,EAAE;AAAA,QACR,UAAU,EAAE,YAAY;AAAA,QACxB,QAAQ,EAAE,UAAU;AAAA,QACpB,OAAO,EAAE,SAAS,EAAE,UAAU;AAAA,QAC9B,GAAI,EAAE,YAAY,UAAa,EAAE,SAAS,EAAE,QAAQ;AAAA,QACpD,GAAI,EAAE,cAAc,UAAa,EAAE,WAAW,EAAE,UAAU;AAAA,QAC1D,GAAI,EAAE,cAAc,UAAa,EAAE,WAAW,EAAE,UAAU;AAAA,QAC1D,GAAI,EAAE,QAAQ,UAAa,EAAE,KAAK,EAAE,IAAI;AAAA,QACxC,GAAI,EAAE,QAAQ,UAAa,EAAE,KAAK,EAAE,IAAI;AAAA,QACxC,GAAI,EAAE,SAAS,UAAa,EAAE,MAAM,EAAE,KAAK;AAAA,MAC7C;AAAA,IACF;AAAA,EACF;AAEA,SAAO;AACT;AAEO,SAAS,iBACd,MACA,QACA,WAAW,OACc;AACzB,QAAM,SAAkC,CAAC;AAEzC,aAAW,CAAC,OAAO,GAAG,KAAK,OAAO,QAAQ,MAAM,GAAG;AACjD,QAAI,QAAQ,KAAK,KAAK;AAGtB,QAAI,UAAU,UAAa,IAAI,YAAY,UAAa,CAAC,UAAU;AACjE,cACE,OAAO,IAAI,YAAY,aAClB,IAAI,QAA0B,IAC/B,IAAI;AAAA,IACZ;AAGA,QAAI,CAAC,YAAY,IAAI,aAAa,UAAU,UAAa,UAAU,OAAO;AACxE,YAAM,IAAI,gBAAgB,OAAO,mBAAmB;AAAA,IACtD;AAGA,QAAI,UAAU,OAAW;AAGzB,UAAM,UAAU,kBAAkB,OAAO,IAAI,IAAI;AACjD,QAAI,QAAS,OAAM,IAAI,gBAAgB,OAAO,OAAO;AAGrD,QAAI,IAAI,SAAS,YAAY,OAAO,UAAU,UAAU;AACtD,UAAI,IAAI,cAAc,UAAa,MAAM,SAAS,IAAI,WAAW;AAC/D,cAAM,IAAI;AAAA,UACR;AAAA,UACA,qBAAqB,IAAI,SAAS,SAAS,MAAM,MAAM;AAAA,QACzD;AAAA,MACF;AACA,UAAI,IAAI,cAAc,UAAa,MAAM,SAAS,IAAI,WAAW;AAC/D,cAAM,IAAI;AAAA,UACR;AAAA,UACA,qBAAqB,IAAI,SAAS,SAAS,MAAM,MAAM;AAAA,QACzD;AAAA,MACF;AAAA,IACF;AAGA,QAAI,IAAI,SAAS,YAAY,OAAO,UAAU,UAAU;AACtD,UAAI,IAAI,QAAQ,UAAa,QAAQ,IAAI,KAAK;AAC5C,cAAM,IAAI,gBAAgB,OAAO,oBAAoB,IAAI,GAAG,EAAE;AAAA,MAChE;AACA,UAAI,IAAI,QAAQ,UAAa,QAAQ,IAAI,KAAK;AAC5C,cAAM,IAAI,gBAAgB,OAAO,oBAAoB,IAAI,GAAG,EAAE;AAAA,MAChE;AAAA,IACF;AAGA,QAAI,IAAI,QAAQ,CAAC,IAAI,KAAK,SAAS,KAAK,GAAG;AACzC,YAAM,IAAI;AAAA,QACR;AAAA,QACA,yBAAyB,IAAI,KAAK,KAAK,IAAI,CAAC;AAAA,MAC9C;AAAA,IACF;AAEA,WAAO,KAAK,IAAI,iBAAiB,OAAO,IAAI,IAAI;AAAA,EAClD;AAIA,MAAI,UAAU;AACZ,eAAW,CAAC,KAAK,GAAG,KAAK,OAAO,QAAQ,IAAI,GAAG;AAC7C,UAAI,EAAE,OAAO,WAAW,QAAQ,QAAW;AACzC,eAAO,GAAG,IAAI;AAAA,MAChB;AAAA,IACF;AAAA,EACF;AAEA,SAAO;AACT;;;ADnGO,IAAM,QAAN,MAAY;AAAA,EACD;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACR;AAAA,EACA;AAAA,EACA;AAAA,EAER,YAAY,YAA6B,SAAyB,IAAsB;AACtF,SAAK,OAAO,WAAW;AACvB,SAAK,aAAa,WAAW;AAC7B,SAAK,SAAS,gBAAgB,WAAW,MAAM;AAC/C,SAAK,SAAS,WAAW,UAAU,WAAW,WAAW,MAAM,GAAG,CAAC;AACnE,SAAK,UAAU;AACf,SAAK,aAAa,WAAW,eAAe;AAC5C,SAAK,YAAY,WAAW,aAAa,CAAC;AAC1C,SAAK,KAAK,MAAM;AAAA,EAClB;AAAA,EAEA,MAAM,OAAsB;AAC1B,UAAM,KAAK,QAAQ,iBAAiB,KAAK,YAAY,KAAK,MAAM;AAGhE,eAAW,OAAO,OAAO,OAAO,KAAK,SAAS,GAAG;AAC/C,UAAI,IAAI,0CAAoC,IAAI,gBAAgB;AAC9D,cAAM,KAAK,QAAQ,iBAAiB,IAAI,gBAAgB,CAAC,CAAC;AAAA,MAC5D;AAAA,IACF;AAAA,EACF;AAAA,EAEQ,aAAqB;AAC3B,WAAO,GAAG,KAAK,MAAM,QAAI,sBAAO,EAAE,CAAC;AAAA,EACrC;AAAA,EAEQ,gBAAgB,cAAwE;AAC9F,UAAM,MAAM,KAAK,UAAU,YAAY;AACvC,QAAI,CAAC,KAAK;AACR,YAAM,IAAI,aAAa,qBAAqB,YAAY,eAAe,KAAK,IAAI,GAAG;AAAA,IACrF;AACA,QAAI,CAAC,KAAK,IAAI;AACZ,YAAM,IAAI,aAAa,qDAAqD;AAAA,IAC9E;AACA,UAAM,eAAe,KAAK,GAAG,SAAS,IAAI,KAAK;AAC/C,QAAI,CAAC,cAAc;AACjB,YAAM,IAAI,aAAa,kBAAkB,IAAI,KAAK,uDAAuD;AAAA,IAC3G;AACA,WAAO,EAAE,KAAK,aAAa;AAAA,EAC7B;AAAA,EAEA,MAAc,SAAS,MAAkB,aAA4C;AACnF,QAAI,YAAY,WAAW,KAAK,KAAK,WAAW,EAAG,QAAO;AAG1D,WAAO,KAAK,IAAI,CAAC,OAAO,EAAE,GAAG,EAAE,EAAE;AAEjC,eAAW,gBAAgB,aAAa;AACtC,YAAM,EAAE,KAAK,aAAa,IAAI,KAAK,gBAAgB,YAAY;AAE/D,cAAQ,IAAI,MAAM;AAAA,QAChB,8BAA2B;AACzB,gBAAM,YAAY,KAAK,IAAI,CAAC,MAAM,EAAE,EAAE;AACtC,gBAAM,UAAU,MAAM,KAAK,QAAQ,KAAK,aAAa,YAAY;AAAA,YAC/D,QAAQ,EAAE,CAAC,IAAI,UAAU,GAAG,EAAE,KAAK,UAAU,EAAE;AAAA,UACjD,CAAC;AACD,gBAAM,UAAU,oBAAI,IAAwB;AAC5C,qBAAW,KAAK,SAAS;AACvB,kBAAM,KAAK,EAAE,IAAI,UAAU;AAC3B,gBAAI,CAAC,QAAQ,IAAI,EAAE,EAAG,SAAQ,IAAI,IAAI,CAAC,CAAC;AACxC,oBAAQ,IAAI,EAAE,EAAG,KAAK,CAAC;AAAA,UACzB;AACA,qBAAW,OAAO,MAAM;AACtB,gBAAI,YAAY,IAAI,QAAQ,IAAI,IAAI,EAAE,KAAK,CAAC;AAAA,UAC9C;AACA;AAAA,QACF;AAAA,QAEA,4BAA0B;AACxB,gBAAM,YAAY,KAAK,IAAI,CAAC,MAAM,EAAE,EAAE;AACtC,gBAAM,UAAU,MAAM,KAAK,QAAQ,KAAK,aAAa,YAAY;AAAA,YAC/D,QAAQ,EAAE,CAAC,IAAI,UAAU,GAAG,EAAE,KAAK,UAAU,EAAE;AAAA,UACjD,CAAC;AACD,gBAAM,MAAM,oBAAI,IAAsB;AACtC,qBAAW,KAAK,SAAS;AACvB,kBAAM,KAAK,EAAE,IAAI,UAAU;AAC3B,gBAAI,CAAC,IAAI,IAAI,EAAE,EAAG,KAAI,IAAI,IAAI,CAAC;AAAA,UACjC;AACA,qBAAW,OAAO,MAAM;AACtB,gBAAI,YAAY,IAAI,IAAI,IAAI,IAAI,EAAE,KAAK;AAAA,UACzC;AACA;AAAA,QACF;AAAA,QAEA,kCAA6B;AAC3B,gBAAM,WAAW,CAAC,GAAG,IAAI,IAAI,KAAK,IAAI,CAAC,MAAM,EAAE,IAAI,UAAU,CAAW,EAAE,OAAO,OAAO,CAAC,CAAC;AAC1F,cAAI,SAAS,WAAW,GAAG;AACzB,uBAAW,OAAO,KAAM,KAAI,YAAY,IAAI;AAC5C;AAAA,UACF;AACA,gBAAM,UAAU,MAAM,KAAK,QAAQ,KAAK,aAAa,YAAY;AAAA,YAC/D,QAAQ,EAAE,IAAI,EAAE,KAAK,SAAS,EAAE;AAAA,UAClC,CAAC;AACD,gBAAM,MAAM,oBAAI,IAAsB;AACtC,qBAAW,KAAK,SAAS;AACvB,gBAAI,IAAI,EAAE,IAAI,CAAC;AAAA,UACjB;AACA,qBAAW,OAAO,MAAM;AACtB,kBAAM,KAAK,IAAI,IAAI,UAAU;AAC7B,gBAAI,YAAY,IAAI,IAAI,IAAI,EAAE,KAAK;AAAA,UACrC;AACA;AAAA,QACF;AAAA,QAEA,oCAA8B;AAC5B,cAAI,CAAC,IAAI,kBAAkB,CAAC,IAAI,YAAY;AAC1C,kBAAM,IAAI;AAAA,cACR,wBAAwB,YAAY;AAAA,YACtC;AAAA,UACF;AACA,gBAAM,YAAY,KAAK,IAAI,CAAC,MAAM,EAAE,EAAE;AACtC,gBAAM,WAAW,MAAM,KAAK,QAAQ,KAAK,IAAI,gBAAgB;AAAA,YAC3D,QAAQ,EAAE,CAAC,IAAI,UAAU,GAAG,EAAE,KAAK,UAAU,EAAE;AAAA,UACjD,CAAC;AACD,gBAAM,aAAa,CAAC,GAAG,IAAI,IAAI,SAAS,IAAI,CAAC,MAAM,EAAE,IAAI,UAAW,CAAW,CAAC,CAAC;AACjF,gBAAM,cACJ,WAAW,SAAS,IAChB,MAAM,KAAK,QAAQ,KAAK,aAAa,YAAY;AAAA,YAC/C,QAAQ,EAAE,IAAI,EAAE,KAAK,WAAW,EAAE;AAAA,UACpC,CAAC,IACD,CAAC;AACP,gBAAM,aAAa,oBAAI,IAAsB;AAC7C,qBAAW,KAAK,YAAa,YAAW,IAAI,EAAE,IAAI,CAAC;AAEnD,gBAAM,UAAU,oBAAI,IAAwB;AAC5C,qBAAW,OAAO,UAAU;AAC1B,kBAAM,WAAW,IAAI,IAAI,UAAU;AACnC,kBAAM,YAAY,IAAI,IAAI,UAAW;AACrC,kBAAM,aAAa,WAAW,IAAI,SAAS;AAC3C,gBAAI,YAAY;AACd,kBAAI,CAAC,QAAQ,IAAI,QAAQ,EAAG,SAAQ,IAAI,UAAU,CAAC,CAAC;AACpD,sBAAQ,IAAI,QAAQ,EAAG,KAAK,UAAU;AAAA,YACxC;AAAA,UACF;AACA,qBAAW,OAAO,MAAM;AACtB,gBAAI,YAAY,IAAI,QAAQ,IAAI,IAAI,EAAE,KAAK,CAAC;AAAA,UAC9C;AACA;AAAA,QACF;AAAA,MACF;AAAA,IACF;AAEA,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,OAAO,MAAkD;AAC7D,UAAM,YAAY,iBAAiB,MAAM,KAAK,MAAM;AACpD,UAAM,OAAM,oBAAI,KAAK,GAAE,YAAY;AACnC,UAAM,MAAgB;AAAA,MACpB,GAAG;AAAA,MACH,IAAI,KAAK,WAAW;AAAA,MACpB,WAAW;AAAA,MACX,WAAW;AAAA,IACb;AACA,WAAO,KAAK,QAAQ,OAAO,KAAK,YAAY,GAAG;AAAA,EACjD;AAAA,EAEA,MAAM,WACJ,OACqB;AACrB,UAAM,UAAsB,CAAC;AAC7B,eAAW,QAAQ,OAAO;AACxB,cAAQ,KAAK,MAAM,KAAK,OAAO,IAAI,CAAC;AAAA,IACtC;AACA,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,SAAS,IAAY,SAA4D;AACrF,UAAM,MAAM,MAAM,KAAK,QAAQ,SAAS,KAAK,YAAY,EAAE;AAC3D,QAAI,CAAC,OAAO,CAAC,SAAS,SAAS,OAAQ,QAAO;AAC9C,UAAM,CAAC,SAAS,IAAI,MAAM,KAAK,SAAS,CAAC,GAAG,GAAG,QAAQ,OAAO;AAC9D,WAAO,aAAa;AAAA,EACtB;AAAA,EAEA,MAAM,gBAAgB,IAAY,SAAqD;AACrF,UAAM,MAAM,MAAM,KAAK,SAAS,IAAI,OAAO;AAC3C,QAAI,CAAC,IAAK,OAAM,IAAI,sBAAsB,KAAK,YAAY,EAAE;AAC7D,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,QAAQ,QAAqB,SAA4D;AAC7F,UAAM,UAAU,MAAM,KAAK,QAAQ,KAAK,KAAK,YAAY;AAAA,MACvD;AAAA,MACA,OAAO;AAAA,IACT,CAAC;AACD,UAAM,MAAM,QAAQ,CAAC,KAAK;AAC1B,QAAI,CAAC,OAAO,CAAC,SAAS,SAAS,OAAQ,QAAO;AAC9C,UAAM,CAAC,SAAS,IAAI,MAAM,KAAK,SAAS,CAAC,GAAG,GAAG,QAAQ,OAAO;AAC9D,WAAO,aAAa;AAAA,EACtB;AAAA,EAEA,MAAM,KAAK,UAAuB,CAAC,GAAwB;AACzD,UAAM,EAAE,SAAS,GAAG,eAAe,IAAI;AACvC,UAAM,OAAO,MAAM,KAAK,QAAQ,KAAK,KAAK,YAAY,cAAc;AACpE,QAAI,CAAC,SAAS,OAAQ,QAAO;AAC7B,WAAO,KAAK,SAAS,MAAM,OAAO;AAAA,EACpC;AAAA,EAEA,MAAM,UAA+B;AACnC,WAAO,KAAK,QAAQ,KAAK,KAAK,YAAY,CAAC,CAAC;AAAA,EAC9C;AAAA,EAEA,MAAM,MAAM,QAAuC;AACjD,WAAO,KAAK,QAAQ,MAAM,KAAK,YAAY,MAAM;AAAA,EACnD;AAAA,EAEA,MAAM,OACJ,IACA,MAC0B;AAC1B,UAAM,YAAY,iBAAiB,MAAM,KAAK,QAAQ,IAAI;AAC1D,QAAI,KAAK,YAAY;AACnB,gBAAU,aAAY,oBAAI,KAAK,GAAE,YAAY;AAAA,IAC/C;AACA,WAAO,KAAK,QAAQ,OAAO,KAAK,YAAY,IAAI,SAAS;AAAA,EAC3D;AAAA,EAEA,MAAM,cACJ,IACA,MACmB;AACnB,UAAM,MAAM,MAAM,KAAK,OAAO,IAAI,IAAI;AACtC,QAAI,CAAC,IAAK,OAAM,IAAI,sBAAsB,KAAK,YAAY,EAAE;AAC7D,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,OAAO,IAA8B;AACzC,WAAO,KAAK,QAAQ,OAAO,KAAK,YAAY,EAAE;AAAA,EAChD;AAAA,EAEA,MAAM,WAAW,QAAsC;AACrD,WAAO,KAAK,QAAQ,WAAW,KAAK,YAAY,MAAM;AAAA,EACxD;AAAA,EAEA,MAAM,UAAU,IAAY,cAAsB,WAAsC;AACtF,UAAM,EAAE,IAAI,IAAI,KAAK,gBAAgB,YAAY;AACjD,QAAI,IAAI,wCAAkC;AACxC,YAAM,IAAI,aAAa,gEAAgE,IAAI,IAAI,GAAG;AAAA,IACpG;AACA,QAAI,CAAC,IAAI,kBAAkB,CAAC,IAAI,YAAY;AAC1C,YAAM,IAAI;AAAA,QACR,wBAAwB,YAAY;AAAA,MACtC;AAAA,IACF;AACA,UAAM,OAAM,oBAAI,KAAK,GAAE,YAAY;AACnC,UAAM,UAAoB;AAAA,MACxB,IAAI,GAAG,KAAK,MAAM,WAAO,sBAAO,EAAE,CAAC;AAAA,MACnC,CAAC,IAAI,UAAU,GAAG;AAAA,MAClB,CAAC,IAAI,UAAU,GAAG;AAAA,MAClB,WAAW;AAAA,MACX,WAAW;AAAA,IACb;AACA,WAAO,KAAK,QAAQ,OAAO,IAAI,gBAAgB,OAAO;AAAA,EACxD;AAAA,EAEA,MAAM,WAAW,IAAY,cAAsB,WAAoC;AACrF,UAAM,EAAE,IAAI,IAAI,KAAK,gBAAgB,YAAY;AACjD,QAAI,IAAI,wCAAkC;AACxC,YAAM,IAAI,aAAa,iEAAiE,IAAI,IAAI,GAAG;AAAA,IACrG;AACA,QAAI,CAAC,IAAI,kBAAkB,CAAC,IAAI,YAAY;AAC1C,YAAM,IAAI;AAAA,QACR,wBAAwB,YAAY;AAAA,MACtC;AAAA,IACF;AACA,WAAO,KAAK,QAAQ,WAAW,IAAI,gBAAgB;AAAA,MACjD,CAAC,IAAI,UAAU,GAAG;AAAA,MAClB,CAAC,IAAI,UAAU,GAAG;AAAA,IACpB,CAAC;AAAA,EACH;AACF;;;AGrSA;;;ACNA;AAEA,SAAS,cAAc,KAAe,QAA8B;AAClE,aAAW,CAAC,OAAO,SAAS,KAAK,OAAO,QAAQ,MAAM,GAAG;AACvD,UAAM,QAAQ,IAAI,KAAK;AAEvB,QAAI,iBAAiB,SAAS,GAAG;AAC/B,iBAAW,CAAC,IAAI,OAAO,KAAK,OAAO;AAAA,QACjC;AAAA,MACF,GAAG;AACD,YAAI,CAAC,cAAc,IAAI,OAAO,OAAO,EAAG,QAAO;AAAA,MACjD;AAAA,IACF,OAAO;AAEL,UAAI,UAAU,UAAW,QAAO;AAAA,IAClC;AAAA,EACF;AACA,SAAO;AACT;AAEA,SAAS,cAAc,MAAkB,MAA8B;AACrE,QAAM,UAAU,OAAO,QAAQ,IAAI;AACnC,SAAO,CAAC,GAAG,IAAI,EAAE,KAAK,CAAC,GAAG,MAAM;AAC9B,eAAW,CAAC,OAAO,GAAG,KAAK,SAAS;AAClC,YAAM,KAAK,EAAE,KAAK;AAClB,YAAM,KAAK,EAAE,KAAK;AAClB,UAAI,OAAO,GAAI;AACf,UAAI,OAAO,UAAa,OAAO,KAAM,QAAO;AAC5C,UAAI,OAAO,UAAa,OAAO,KAAM,QAAO,CAAC;AAC7C,UAAI,KAAK,GAAI,QAAO,CAAC;AACrB,UAAI,KAAK,GAAI,QAAO;AAAA,IACtB;AACA,WAAO;AAAA,EACT,CAAC;AACH;AAEO,SAAS,iBACd,MACA,SACY;AACZ,MAAI,SAAS;AAEb,MAAI,QAAQ,QAAQ;AAClB,aAAS,OAAO,OAAO,CAAC,QAAQ,cAAc,KAAK,QAAQ,MAAO,CAAC;AAAA,EACrE;AAEA,MAAI,QAAQ,MAAM;AAChB,aAAS,cAAc,QAAQ,QAAQ,IAAI;AAAA,EAC7C;AAEA,MAAI,QAAQ,QAAQ;AAClB,aAAS,OAAO,MAAM,QAAQ,MAAM;AAAA,EACtC;AAEA,MAAI,QAAQ,UAAU,QAAW;AAC/B,aAAS,OAAO,MAAM,GAAG,QAAQ,KAAK;AAAA,EACxC;AAEA,SAAO;AACT;AAEO,SAAS,gBACd,MACA,QACQ;AACR,MAAI,CAAC,OAAQ,QAAO,KAAK;AACzB,SAAO,KAAK,OAAO,CAAC,QAAQ,cAAc,KAAK,MAAM,CAAC,EAAE;AAC1D;;;ACpEA,SAAoB;AACpB,WAAsB;AACtB,+BAA4B;AAOrB,IAAM,aAAN,MAAiB;AAAA,EACd;AAAA,EACA,OAAiB,CAAC;AAAA,EAClB,aAA4B,QAAQ,QAAQ;AAAA,EAC5C,QAAQ;AAAA,EAEhB,YAAY,UAAkB;AAC5B,SAAK,WAAgB,aAAQ,QAAQ;AAAA,EACvC;AAAA,EAEA,MAAM,OAAsB;AAC1B,QAAI;AACF,YAAM,MAAS,gBAAa,KAAK,UAAU,OAAO;AAClD,WAAK,OAAO,KAAK,MAAM,GAAG;AAAA,IAC5B,SAAS,KAAc;AACrB,UAAK,IAA8B,SAAS,UAAU;AACpD,aAAK,OAAO,CAAC;AACb,cAAM,KAAK,MAAM;AAAA,MACnB,OAAO;AACL,cAAM;AAAA,MACR;AAAA,IACF;AAAA,EACF;AAAA,EAEA,UAAoB;AAClB,WAAO,KAAK;AAAA,EACd;AAAA,EAEA,cAAc,MAA0B;AACtC,QAAI,CAAC,KAAK,KAAK,IAAI,GAAG;AACpB,WAAK,KAAK,IAAI,IAAI,CAAC;AAAA,IACrB;AACA,WAAO,KAAK,KAAK,IAAI;AAAA,EACvB;AAAA,EAEA,cAAc,MAAuB;AACnC,WAAO,QAAQ,KAAK;AAAA,EACtB;AAAA,EAEA,iBAAiB,MAAoB;AACnC,QAAI,CAAC,KAAK,KAAK,IAAI,GAAG;AACpB,WAAK,KAAK,IAAI,IAAI,CAAC;AAAA,IACrB;AAAA,EACF;AAAA,EAEA,eAAe,MAAoB;AACjC,WAAO,KAAK,KAAK,IAAI;AAAA,EACvB;AAAA,EAEA,kBAA4B;AAC1B,WAAO,OAAO,KAAK,KAAK,IAAI;AAAA,EAC9B;AAAA,EAEA,YAAkB;AAChB,SAAK,QAAQ;AAAA,EACf;AAAA,EAEA,MAAM,QAAuB;AAC3B,SAAK,aAAa,KAAK,WAAW,KAAK,YAAY;AACjD,YAAM,MAAW,aAAQ,KAAK,QAAQ;AACtC,UAAI,CAAI,cAAW,GAAG,GAAG;AACvB,QAAG,aAAU,KAAK,EAAE,WAAW,KAAK,CAAC;AAAA,MACvC;AACA,gBAAM,yBAAAC;AAAA,QACJ,KAAK;AAAA,QACL,KAAK,UAAU,KAAK,MAAM,MAAM,CAAC,IAAI;AAAA,MACvC;AACA,WAAK,QAAQ;AAAA,IACf,CAAC;AACD,WAAO,KAAK;AAAA,EACd;AAAA,EAEA,MAAM,eAA8B;AAClC,QAAI,KAAK,OAAO;AACd,YAAM,KAAK,MAAM;AAAA,IACnB;AAAA,EACF;AACF;;;ACrFA;AAQO,IAAM,UAAN,MAAc;AAAA,EACX,UAAU,oBAAI,IAAqC;AAAA;AAAA,EAE3D,WACE,YACA,OACA,QACA,MACM;AACN,QAAI,CAAC,KAAK,QAAQ,IAAI,UAAU,GAAG;AACjC,WAAK,QAAQ,IAAI,YAAY,oBAAI,IAAI,CAAC;AAAA,IACxC;AACA,UAAM,aAAa,KAAK,QAAQ,IAAI,UAAU;AAE9C,UAAM,MAAkB,EAAE,OAAO,QAAQ,KAAK,oBAAI,IAAI,EAAE;AAExD,eAAW,OAAO,MAAM;AACtB,YAAM,MAAM,IAAI,KAAK;AACrB,UAAI,QAAQ,UAAa,QAAQ,KAAM;AACvC,UAAI,CAAC,IAAI,IAAI,IAAI,GAAG,GAAG;AACrB,YAAI,IAAI,IAAI,KAAK,oBAAI,IAAI,CAAC;AAAA,MAC5B;AACA,UAAI,IAAI,IAAI,GAAG,EAAG,IAAI,IAAI,EAAE;AAAA,IAC9B;AAEA,eAAW,IAAI,OAAO,GAAG;AAAA,EAC3B;AAAA,EAEA,SAAS,YAAoB,KAAqB;AAChD,UAAM,aAAa,KAAK,QAAQ,IAAI,UAAU;AAC9C,QAAI,CAAC,WAAY;AAEjB,eAAW,CAAC,EAAE,GAAG,KAAK,YAAY;AAChC,YAAM,MAAM,IAAI,IAAI,KAAK;AACzB,UAAI,QAAQ,UAAa,QAAQ,KAAM;AAEvC,UAAI,IAAI,UAAU,IAAI,IAAI,IAAI,GAAG,KAAK,IAAI,IAAI,IAAI,GAAG,EAAG,OAAO,GAAG;AAChE,cAAM,IAAI,sBAAsB,YAAY,IAAI,OAAO,GAAG;AAAA,MAC5D;AAEA,UAAI,CAAC,IAAI,IAAI,IAAI,GAAG,GAAG;AACrB,YAAI,IAAI,IAAI,KAAK,oBAAI,IAAI,CAAC;AAAA,MAC5B;AACA,UAAI,IAAI,IAAI,GAAG,EAAG,IAAI,IAAI,EAAE;AAAA,IAC9B;AAAA,EACF;AAAA,EAEA,SACE,YACA,QACA,QACM;AACN,UAAM,aAAa,KAAK,QAAQ,IAAI,UAAU;AAC9C,QAAI,CAAC,WAAY;AAEjB,eAAW,CAAC,EAAE,GAAG,KAAK,YAAY;AAChC,YAAM,SAAS,OAAO,IAAI,KAAK;AAC/B,YAAM,SAAS,OAAO,IAAI,KAAK;AAE/B,UAAI,WAAW,OAAQ;AAGvB,UAAI,WAAW,UAAa,WAAW,MAAM;AAC3C,YAAI,IAAI,IAAI,MAAM,GAAG,OAAO,OAAO,EAAE;AAAA,MACvC;AAGA,UAAI,WAAW,UAAa,WAAW,MAAM;AAC3C,YACE,IAAI,UACJ,IAAI,IAAI,IAAI,MAAM,KAClB,IAAI,IAAI,IAAI,MAAM,EAAG,OAAO,GAC5B;AACA,gBAAM,IAAI,sBAAsB,YAAY,IAAI,OAAO,MAAM;AAAA,QAC/D;AACA,YAAI,CAAC,IAAI,IAAI,IAAI,MAAM,GAAG;AACxB,cAAI,IAAI,IAAI,QAAQ,oBAAI,IAAI,CAAC;AAAA,QAC/B;AACA,YAAI,IAAI,IAAI,MAAM,EAAG,IAAI,OAAO,EAAE;AAAA,MACpC;AAAA,IACF;AAAA,EACF;AAAA,EAEA,SAAS,YAAoB,KAAqB;AAChD,UAAM,aAAa,KAAK,QAAQ,IAAI,UAAU;AAC9C,QAAI,CAAC,WAAY;AAEjB,eAAW,CAAC,EAAE,GAAG,KAAK,YAAY;AAChC,YAAM,MAAM,IAAI,IAAI,KAAK;AACzB,UAAI,QAAQ,UAAa,QAAQ,MAAM;AACrC,YAAI,IAAI,IAAI,GAAG,GAAG,OAAO,IAAI,EAAE;AAAA,MACjC;AAAA,IACF;AAAA,EACF;AAAA,EAEA,YACE,YACA,OACA,OACyB;AACzB,WAAO,KAAK,QAAQ,IAAI,UAAU,GAAG,IAAI,KAAK,GAAG,IAAI,IAAI,KAAK;AAAA,EAChE;AAAA,EAEA,eAAe,YAA0B;AACvC,SAAK,QAAQ,OAAO,UAAU;AAAA,EAChC;AACF;;;AHvGO,IAAM,cAAN,MAA4C;AAAA,EACzC;AAAA,EACA,UAAU,IAAI,QAAQ;AAAA,EACtB,UAAU,oBAAI,IAA8B;AAAA,EAEpD,YAAY,UAAkB;AAC5B,SAAK,SAAS,IAAI,WAAW,QAAQ;AAAA,EACvC;AAAA,EAEA,MAAM,UAAyB;AAC7B,UAAM,KAAK,OAAO,KAAK;AAAA,EACzB;AAAA,EAEA,MAAM,aAA4B;AAChC,UAAM,KAAK,OAAO,aAAa;AAAA,EACjC;AAAA,EAEA,MAAM,iBACJ,YACA,QACe;AACf,SAAK,OAAO,iBAAiB,UAAU;AACvC,SAAK,QAAQ,IAAI,YAAY,MAAM;AAGnC,eAAW,CAAC,OAAO,GAAG,KAAK,OAAO,QAAQ,MAAM,GAAG;AACjD,UAAI,IAAI,SAAS,IAAI,QAAQ;AAC3B,aAAK,QAAQ;AAAA,UACX;AAAA,UACA;AAAA,UACA,IAAI;AAAA,UACJ,KAAK,OAAO,cAAc,UAAU;AAAA,QACtC;AAAA,MACF;AAAA,IACF;AAEA,UAAM,KAAK,OAAO,MAAM;AAAA,EAC1B;AAAA,EAEA,MAAM,eAAe,YAAmC;AACtD,SAAK,OAAO,eAAe,UAAU;AACrC,SAAK,QAAQ,eAAe,UAAU;AACtC,SAAK,QAAQ,OAAO,UAAU;AAC9B,UAAM,KAAK,OAAO,MAAM;AAAA,EAC1B;AAAA,EAEA,MAAM,kBAAqC;AACzC,WAAO,KAAK,OAAO,gBAAgB;AAAA,EACrC;AAAA,EAEA,MAAM,OAAO,YAAoB,KAAkC;AACjE,UAAM,OAAO,KAAK,qBAAqB,UAAU;AAGjD,SAAK,QAAQ,SAAS,YAAY,GAAG;AAErC,SAAK,KAAK,GAAG;AACb,SAAK,OAAO,UAAU;AACtB,UAAM,KAAK,OAAO,MAAM;AACxB,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,SACJ,YACA,IAC0B;AAC1B,UAAM,OAAO,KAAK,qBAAqB,UAAU;AACjD,WAAO,KAAK,KAAK,CAAC,MAAM,EAAE,OAAO,EAAE,KAAK;AAAA,EAC1C;AAAA,EAEA,MAAM,KACJ,YACA,SACqB;AACrB,UAAM,OAAO,KAAK,qBAAqB,UAAU;AACjD,WAAO,iBAAiB,MAAM,OAAO;AAAA,EACvC;AAAA,EAEA,MAAM,MAAM,YAAoB,QAAuC;AACrE,UAAM,OAAO,KAAK,qBAAqB,UAAU;AACjD,WAAO,gBAAgB,MAAM,MAAM;AAAA,EACrC;AAAA,EAEA,MAAM,OACJ,YACA,IACA,MAC0B;AAC1B,UAAM,OAAO,KAAK,qBAAqB,UAAU;AACjD,UAAM,QAAQ,KAAK,UAAU,CAAC,MAAM,EAAE,OAAO,EAAE;AAC/C,QAAI,UAAU,GAAI,QAAO;AAEzB,UAAM,SAAS,KAAK,KAAK;AACzB,UAAM,SAAS,EAAE,GAAG,QAAQ,GAAG,MAAM,IAAI,OAAO,GAAG;AAGnD,SAAK,QAAQ,SAAS,YAAY,QAAQ,MAAM;AAEhD,SAAK,KAAK,IAAI;AACd,SAAK,OAAO,UAAU;AACtB,UAAM,KAAK,OAAO,MAAM;AACxB,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,OAAO,YAAoB,IAA8B;AAC7D,UAAM,OAAO,KAAK,qBAAqB,UAAU;AACjD,UAAM,QAAQ,KAAK,UAAU,CAAC,MAAM,EAAE,OAAO,EAAE;AAC/C,QAAI,UAAU,GAAI,QAAO;AAEzB,SAAK,QAAQ,SAAS,YAAY,KAAK,KAAK,CAAE;AAC9C,SAAK,OAAO,OAAO,CAAC;AACpB,SAAK,OAAO,UAAU;AACtB,UAAM,KAAK,OAAO,MAAM;AACxB,WAAO;AAAA,EACT;AAAA,EAEA,MAAM,WACJ,YACA,QACiB;AACjB,UAAM,OAAO,KAAK,qBAAqB,UAAU;AACjD,UAAM,WAAW,iBAAiB,MAAM,EAAE,OAAO,CAAC;AAElD,eAAW,OAAO,UAAU;AAC1B,WAAK,QAAQ,SAAS,YAAY,GAAG;AAAA,IACvC;AAEA,UAAM,MAAM,IAAI,IAAI,SAAS,IAAI,CAAC,MAAM,EAAE,EAAE,CAAC;AAC7C,UAAM,YAAY,KAAK,OAAO,CAAC,MAAM,CAAC,IAAI,IAAI,EAAE,EAAE,CAAC;AACnD,UAAM,UAAU,KAAK,SAAS,UAAU;AAGxC,SAAK,SAAS;AACd,SAAK,KAAK,GAAG,SAAS;AAEtB,QAAI,UAAU,GAAG;AACf,WAAK,OAAO,UAAU;AACtB,YAAM,KAAK,OAAO,MAAM;AAAA,IAC1B;AAEA,WAAO;AAAA,EACT;AAAA,EAEQ,qBAAqB,YAAgC;AAC3D,QAAI,CAAC,KAAK,OAAO,cAAc,UAAU,GAAG;AAC1C,YAAM,IAAI,wBAAwB,UAAU;AAAA,IAC9C;AACA,WAAO,KAAK,OAAO,cAAc,UAAU;AAAA,EAC7C;AACF;;;AJvJA,IAAAC,QAAsB;AAEf,IAAM,UAAN,MAAc;AAAA,EACX;AAAA,EACA,UAAiC;AAAA,EACjC,SAAS,oBAAI,IAAmB;AAAA,EAChC,YAAY;AAAA,EAEpB,YAAY,QAAiC;AAC3C,SAAK,SAAS;AAAA,MACZ,SAAS,QAAQ,WAAW,EAAE,4BAA2B,MAAM,SAAS;AAAA,MACxE,eAAe,QAAQ,iBAAiB;AAAA,IAC1C;AAAA,EACF;AAAA,EAEA,MAAc,cAAc,eAAuD;AACjF,YAAQ,cAAc,SAAS;AAAA,MAC7B,wBAAuB;AACrB,cAAM,SAAc;AAAA,UAClB,cAAc,QAAQ;AAAA,UACtB;AAAA,QACF;AACA,eAAO,IAAI,YAAY,MAAM;AAAA,MAC/B;AAAA,MACA,gCAA2B;AACzB,cAAM,EAAE,iBAAAC,iBAAgB,IAAI,MAAM;AAClC,eAAO,IAAIA,iBAAgB,cAAc,GAAG;AAAA,MAC9C;AAAA,MACA;AACE,cAAM,IAAI;AAAA,UACR;AAAA,QACF;AAAA,MACF;AACE,cAAM,IAAI;AAAA,UACR,oBAAqB,cAAsC,OAAO;AAAA,QACpE;AAAA,IACJ;AAAA,EACF;AAAA,EAEA,MAAM,UAAyB;AAC7B,QAAI,KAAK,UAAW;AACpB,SAAK,UAAU,MAAM,KAAK,cAAc,KAAK,OAAO,OAAO;AAC3D,UAAM,KAAK,QAAQ,QAAQ;AAC3B,SAAK,YAAY;AAGjB,eAAW,SAAS,KAAK,OAAO,OAAO,GAAG;AACxC,YAAM,MAAM,KAAK;AAAA,IACnB;AAAA,EACF;AAAA,EAEA,MAAM,aAA4B;AAChC,QAAI,CAAC,KAAK,aAAa,CAAC,KAAK,QAAS;AACtC,UAAM,KAAK,QAAQ,WAAW;AAC9B,SAAK,YAAY;AACjB,SAAK,UAAU;AAAA,EACjB;AAAA,EAEA,MAAM,YAAoC;AACxC,QAAI,KAAK,OAAO,IAAI,WAAW,IAAI,GAAG;AACpC,aAAO,KAAK,OAAO,IAAI,WAAW,IAAI;AAAA,IACxC;AAEA,QAAI,CAAC,KAAK,SAAS;AACjB,YAAM,IAAI;AAAA,QACR;AAAA,MACF;AAAA,IACF;AAEA,UAAM,QAAQ,IAAI,MAAM,YAAY,KAAK,SAAS,IAAI;AACtD,SAAK,OAAO,IAAI,WAAW,MAAM,KAAK;AACtC,WAAO;AAAA,EACT;AAAA,EAEA,SAAS,MAAiC;AACxC,WAAO,KAAK,OAAO,IAAI,IAAI;AAAA,EAC7B;AAAA,EAEA,aAA6B;AAC3B,QAAI,CAAC,KAAK,SAAS;AACjB,YAAM,IAAI,aAAa,gBAAgB;AAAA,IACzC;AACA,WAAO,KAAK;AAAA,EACd;AAAA,EAEA,YAA2B;AACzB,WAAO,KAAK;AAAA,EACd;AACF;;;AD/FA;AAIA;AAyBA;","names":["FieldType","RelationType","AdapterType","writeFileAtomic","path","PostgresAdapter"]}
|
package/dist/index.js
CHANGED
|
@@ -160,6 +160,11 @@ var Model = class {
|
|
|
160
160
|
}
|
|
161
161
|
async init() {
|
|
162
162
|
await this.adapter.createCollection(this.collection, this.schema);
|
|
163
|
+
for (const rel of Object.values(this.relations)) {
|
|
164
|
+
if (rel.type === "manyToMany" /* ManyToMany */ && rel.joinCollection) {
|
|
165
|
+
await this.adapter.createCollection(rel.joinCollection, {});
|
|
166
|
+
}
|
|
167
|
+
}
|
|
163
168
|
}
|
|
164
169
|
generateId() {
|
|
165
170
|
return `${this.prefix}_${nanoid(12)}`;
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/model/model.ts","../src/model/field-types.ts","../src/model/schema.ts","../src/query/filter.ts","../src/adapters/json/file-engine.ts","../src/adapters/json/indexer.ts","../src/adapters/json/json-adapter.ts","../src/seedorm.ts"],"sourcesContent":["import { nanoid } from \"nanoid\";\nimport {\n RelationType,\n type Document,\n type FilterQuery,\n type FindOptions,\n type ModelDefinition,\n type NormalizedSchema,\n type RelationDefinition,\n type RelationsDefinition,\n type StorageAdapter,\n} from \"../types.js\";\nimport { DocumentNotFoundError, SeedORMError } from \"../errors.js\";\nimport { normalizeSchema, validateDocument } from \"./schema.js\";\n\ninterface SeedORMInstance {\n getModel(name: string): Model | undefined;\n getAdapter(): StorageAdapter;\n}\n\nexport class Model {\n public readonly name: string;\n public readonly collection: string;\n public readonly schema: NormalizedSchema;\n public readonly prefix: string;\n public readonly relations: RelationsDefinition;\n private adapter: StorageAdapter;\n private timestamps: boolean;\n private db: SeedORMInstance | null;\n\n constructor(definition: ModelDefinition, adapter: StorageAdapter, db?: SeedORMInstance) {\n this.name = definition.name;\n this.collection = definition.collection;\n this.schema = normalizeSchema(definition.schema);\n this.prefix = definition.prefix ?? definition.collection.slice(0, 3);\n this.adapter = adapter;\n this.timestamps = definition.timestamps !== false;\n this.relations = definition.relations ?? {};\n this.db = db ?? null;\n }\n\n async init(): Promise<void> {\n await this.adapter.createCollection(this.collection, this.schema);\n }\n\n private generateId(): string {\n return `${this.prefix}_${nanoid(12)}`;\n }\n\n private resolveRelation(relationName: string): { rel: RelationDefinition; relatedModel: Model } {\n const rel = this.relations[relationName];\n if (!rel) {\n throw new SeedORMError(`Unknown relation \"${relationName}\" on model \"${this.name}\"`);\n }\n if (!this.db) {\n throw new SeedORMError(\"Cannot resolve relations without a SeedORM instance\");\n }\n const relatedModel = this.db.getModel(rel.model);\n if (!relatedModel) {\n throw new SeedORMError(`Related model \"${rel.model}\" not found. Make sure it is defined before querying.`);\n }\n return { rel, relatedModel };\n }\n\n private async populate(docs: Document[], includeList: string[]): Promise<Document[]> {\n if (includeList.length === 0 || docs.length === 0) return docs;\n\n // Shallow-clone docs to avoid mutating the adapter's internal store\n docs = docs.map((d) => ({ ...d }));\n\n for (const relationName of includeList) {\n const { rel, relatedModel } = this.resolveRelation(relationName);\n\n switch (rel.type) {\n case RelationType.HasMany: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const grouped = new Map<string, Document[]>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!grouped.has(fk)) grouped.set(fk, []);\n grouped.get(fk)!.push(r);\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n\n case RelationType.HasOne: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!map.has(fk)) map.set(fk, r);\n }\n for (const doc of docs) {\n doc[relationName] = map.get(doc.id) ?? null;\n }\n break;\n }\n\n case RelationType.BelongsTo: {\n const fkValues = [...new Set(docs.map((d) => d[rel.foreignKey] as string).filter(Boolean))];\n if (fkValues.length === 0) {\n for (const doc of docs) doc[relationName] = null;\n break;\n }\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: fkValues } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n map.set(r.id, r);\n }\n for (const doc of docs) {\n const fk = doc[rel.foreignKey] as string;\n doc[relationName] = map.get(fk) ?? null;\n }\n break;\n }\n\n case RelationType.ManyToMany: {\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const parentIds = docs.map((d) => d.id);\n const joinRows = await this.adapter.find(rel.joinCollection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const relatedIds = [...new Set(joinRows.map((r) => r[rel.relatedKey!] as string))];\n const relatedDocs =\n relatedIds.length > 0\n ? await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: relatedIds } },\n })\n : [];\n const relatedMap = new Map<string, Document>();\n for (const r of relatedDocs) relatedMap.set(r.id, r);\n\n const grouped = new Map<string, Document[]>();\n for (const row of joinRows) {\n const parentId = row[rel.foreignKey] as string;\n const relatedId = row[rel.relatedKey!] as string;\n const relatedDoc = relatedMap.get(relatedId);\n if (relatedDoc) {\n if (!grouped.has(parentId)) grouped.set(parentId, []);\n grouped.get(parentId)!.push(relatedDoc);\n }\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n }\n }\n\n return docs;\n }\n\n async create(data: Record<string, unknown>): Promise<Document> {\n const validated = validateDocument(data, this.schema);\n const now = new Date().toISOString();\n const doc: Document = {\n ...validated,\n id: this.generateId(),\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(this.collection, doc);\n }\n\n async createMany(\n items: Record<string, unknown>[],\n ): Promise<Document[]> {\n const results: Document[] = [];\n for (const item of items) {\n results.push(await this.create(item));\n }\n return results;\n }\n\n async findById(id: string, options?: { include?: string[] }): Promise<Document | null> {\n const doc = await this.adapter.findById(this.collection, id);\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async findByIdOrThrow(id: string, options?: { include?: string[] }): Promise<Document> {\n const doc = await this.findById(id, options);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async findOne(filter: FilterQuery, options?: { include?: string[] }): Promise<Document | null> {\n const results = await this.adapter.find(this.collection, {\n filter,\n limit: 1,\n });\n const doc = results[0] ?? null;\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async find(options: FindOptions = {}): Promise<Document[]> {\n const { include, ...adapterOptions } = options;\n const docs = await this.adapter.find(this.collection, adapterOptions);\n if (!include?.length) return docs;\n return this.populate(docs, include);\n }\n\n async findAll(): Promise<Document[]> {\n return this.adapter.find(this.collection, {});\n }\n\n async count(filter?: FilterQuery): Promise<number> {\n return this.adapter.count(this.collection, filter);\n }\n\n async update(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document | null> {\n const validated = validateDocument(data, this.schema, true);\n if (this.timestamps) {\n validated.updatedAt = new Date().toISOString();\n }\n return this.adapter.update(this.collection, id, validated);\n }\n\n async updateOrThrow(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document> {\n const doc = await this.update(id, data);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async delete(id: string): Promise<boolean> {\n return this.adapter.delete(this.collection, id);\n }\n\n async deleteMany(filter: FilterQuery): Promise<number> {\n return this.adapter.deleteMany(this.collection, filter);\n }\n\n async associate(id: string, relationName: string, relatedId: string): Promise<Document> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`associate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const now = new Date().toISOString();\n const joinDoc: Document = {\n id: `${this.prefix}rel_${nanoid(12)}`,\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(rel.joinCollection, joinDoc);\n }\n\n async dissociate(id: string, relationName: string, relatedId: string): Promise<number> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`dissociate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n return this.adapter.deleteMany(rel.joinCollection, {\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n });\n }\n}\n","import { FieldType } from \"../types.js\";\n\nexport function validateFieldType(\n value: unknown,\n type: FieldType,\n): string | null {\n if (value === undefined || value === null) return null; // handled by required check\n\n switch (type) {\n case FieldType.String:\n if (typeof value !== \"string\") return `expected string, got ${typeof value}`;\n break;\n case FieldType.Number:\n if (typeof value !== \"number\" || Number.isNaN(value))\n return `expected number, got ${typeof value}`;\n break;\n case FieldType.Boolean:\n if (typeof value !== \"boolean\")\n return `expected boolean, got ${typeof value}`;\n break;\n case FieldType.Date:\n if (typeof value === \"string\") {\n if (Number.isNaN(Date.parse(value))) return `invalid date string`;\n } else if (!(value instanceof Date)) {\n return `expected date string or Date, got ${typeof value}`;\n }\n break;\n case FieldType.Json:\n // Any non-undefined value is valid JSON\n break;\n case FieldType.Array:\n if (!Array.isArray(value)) return `expected array, got ${typeof value}`;\n break;\n default:\n return `unknown type: ${type as string}`;\n }\n\n return null;\n}\n\nexport function coerceFieldValue(value: unknown, type: FieldType): unknown {\n if (value === undefined || value === null) return value;\n\n if (type === FieldType.Date && value instanceof Date) {\n return value.toISOString();\n }\n\n return value;\n}\n","import {\n FieldType,\n type FieldDefinition,\n type NormalizedField,\n type NormalizedSchema,\n type SchemaDefinition,\n} from \"../types.js\";\nimport { ValidationError } from \"../errors.js\";\nimport { coerceFieldValue, validateFieldType } from \"./field-types.js\";\n\nexport function normalizeSchema(schema: SchemaDefinition): NormalizedSchema {\n const normalized: NormalizedSchema = {};\n\n for (const [field, def] of Object.entries(schema)) {\n if (typeof def === \"string\") {\n normalized[field] = {\n type: def as FieldType,\n required: false,\n unique: false,\n index: false,\n };\n } else {\n const d = def as FieldDefinition;\n normalized[field] = {\n type: d.type,\n required: d.required ?? false,\n unique: d.unique ?? false,\n index: d.index ?? d.unique ?? false,\n ...(d.default !== undefined && { default: d.default }),\n ...(d.minLength !== undefined && { minLength: d.minLength }),\n ...(d.maxLength !== undefined && { maxLength: d.maxLength }),\n ...(d.min !== undefined && { min: d.min }),\n ...(d.max !== undefined && { max: d.max }),\n ...(d.enum !== undefined && { enum: d.enum }),\n };\n }\n }\n\n return normalized;\n}\n\nexport function validateDocument(\n data: Record<string, unknown>,\n schema: NormalizedSchema,\n isUpdate = false,\n): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n\n for (const [field, def] of Object.entries(schema)) {\n let value = data[field];\n\n // Apply default\n if (value === undefined && def.default !== undefined && !isUpdate) {\n value =\n typeof def.default === \"function\"\n ? (def.default as () => unknown)()\n : def.default;\n }\n\n // Required check (skip on partial updates)\n if (!isUpdate && def.required && (value === undefined || value === null)) {\n throw new ValidationError(field, \"field is required\");\n }\n\n // Skip unset fields on update\n if (value === undefined) continue;\n\n // Type check\n const typeErr = validateFieldType(value, def.type);\n if (typeErr) throw new ValidationError(field, typeErr);\n\n // String constraints\n if (def.type === \"string\" && typeof value === \"string\") {\n if (def.minLength !== undefined && value.length < def.minLength) {\n throw new ValidationError(\n field,\n `minimum length is ${def.minLength}, got ${value.length}`,\n );\n }\n if (def.maxLength !== undefined && value.length > def.maxLength) {\n throw new ValidationError(\n field,\n `maximum length is ${def.maxLength}, got ${value.length}`,\n );\n }\n }\n\n // Number constraints\n if (def.type === \"number\" && typeof value === \"number\") {\n if (def.min !== undefined && value < def.min) {\n throw new ValidationError(field, `minimum value is ${def.min}`);\n }\n if (def.max !== undefined && value > def.max) {\n throw new ValidationError(field, `maximum value is ${def.max}`);\n }\n }\n\n // Enum check\n if (def.enum && !def.enum.includes(value)) {\n throw new ValidationError(\n field,\n `value must be one of: ${def.enum.join(\", \")}`,\n );\n }\n\n result[field] = coerceFieldValue(value, def.type);\n }\n\n // On update, pass through non-schema fields that were provided\n // (for id, createdAt, updatedAt)\n if (isUpdate) {\n for (const [key, val] of Object.entries(data)) {\n if (!(key in schema) && val !== undefined) {\n result[key] = val;\n }\n }\n }\n\n return result;\n}\n","import type { Document, FilterQuery, FindOptions, SortOption } from \"../types.js\";\nimport { applyOperator, isOperatorObject } from \"./operators.js\";\n\nfunction matchesFilter(doc: Document, filter: FilterQuery): boolean {\n for (const [field, condition] of Object.entries(filter)) {\n const value = doc[field];\n\n if (isOperatorObject(condition)) {\n for (const [op, operand] of Object.entries(\n condition as Record<string, unknown>,\n )) {\n if (!applyOperator(op, value, operand)) return false;\n }\n } else {\n // Shorthand: { field: value } is equivalent to { field: { $eq: value } }\n if (value !== condition) return false;\n }\n }\n return true;\n}\n\nfunction sortDocuments(docs: Document[], sort: SortOption): Document[] {\n const entries = Object.entries(sort);\n return [...docs].sort((a, b) => {\n for (const [field, dir] of entries) {\n const av = a[field];\n const bv = b[field];\n if (av === bv) continue;\n if (av === undefined || av === null) return dir;\n if (bv === undefined || bv === null) return -dir;\n if (av < bv) return -dir;\n if (av > bv) return dir;\n }\n return 0;\n });\n}\n\nexport function applyFindOptions(\n docs: Document[],\n options: FindOptions,\n): Document[] {\n let result = docs;\n\n if (options.filter) {\n result = result.filter((doc) => matchesFilter(doc, options.filter!));\n }\n\n if (options.sort) {\n result = sortDocuments(result, options.sort);\n }\n\n if (options.offset) {\n result = result.slice(options.offset);\n }\n\n if (options.limit !== undefined) {\n result = result.slice(0, options.limit);\n }\n\n return result;\n}\n\nexport function countWithFilter(\n docs: Document[],\n filter?: FilterQuery,\n): number {\n if (!filter) return docs.length;\n return docs.filter((doc) => matchesFilter(doc, filter)).length;\n}\n\nexport { matchesFilter };\n","import * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport writeFileAtomic from \"write-file-atomic\";\nimport type { Document } from \"../../types.js\";\n\nexport interface FileData {\n [collection: string]: Document[];\n}\n\nexport class FileEngine {\n private filePath: string;\n private data: FileData = {};\n private writeQueue: Promise<void> = Promise.resolve();\n private dirty = false;\n\n constructor(filePath: string) {\n this.filePath = path.resolve(filePath);\n }\n\n async load(): Promise<void> {\n try {\n const raw = fs.readFileSync(this.filePath, \"utf-8\");\n this.data = JSON.parse(raw) as FileData;\n } catch (err: unknown) {\n if ((err as NodeJS.ErrnoException).code === \"ENOENT\") {\n this.data = {};\n await this.flush();\n } else {\n throw err;\n }\n }\n }\n\n getData(): FileData {\n return this.data;\n }\n\n getCollection(name: string): Document[] {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n return this.data[name];\n }\n\n hasCollection(name: string): boolean {\n return name in this.data;\n }\n\n createCollection(name: string): void {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n }\n\n dropCollection(name: string): void {\n delete this.data[name];\n }\n\n listCollections(): string[] {\n return Object.keys(this.data);\n }\n\n markDirty(): void {\n this.dirty = true;\n }\n\n async flush(): Promise<void> {\n this.writeQueue = this.writeQueue.then(async () => {\n const dir = path.dirname(this.filePath);\n if (!fs.existsSync(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n await writeFileAtomic(\n this.filePath,\n JSON.stringify(this.data, null, 2) + \"\\n\",\n );\n this.dirty = false;\n });\n return this.writeQueue;\n }\n\n async flushIfDirty(): Promise<void> {\n if (this.dirty) {\n await this.flush();\n }\n }\n}\n","import type { Document } from \"../../types.js\";\nimport { UniqueConstraintError } from \"../../errors.js\";\n\ninterface FieldIndex {\n field: string;\n unique: boolean;\n map: Map<unknown, Set<string>>; // value → set of doc IDs\n}\n\nexport class Indexer {\n private indexes = new Map<string, Map<string, FieldIndex>>(); // collection → field → index\n\n setupIndex(\n collection: string,\n field: string,\n unique: boolean,\n docs: Document[],\n ): void {\n if (!this.indexes.has(collection)) {\n this.indexes.set(collection, new Map());\n }\n const colIndexes = this.indexes.get(collection)!;\n\n const idx: FieldIndex = { field, unique, map: new Map() };\n\n for (const doc of docs) {\n const val = doc[field];\n if (val === undefined || val === null) continue;\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n\n colIndexes.set(field, idx);\n }\n\n onInsert(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val === undefined || val === null) continue;\n\n if (idx.unique && idx.map.has(val) && idx.map.get(val)!.size > 0) {\n throw new UniqueConstraintError(collection, idx.field, val);\n }\n\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n }\n\n onUpdate(\n collection: string,\n oldDoc: Document,\n newDoc: Document,\n ): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const oldVal = oldDoc[idx.field];\n const newVal = newDoc[idx.field];\n\n if (oldVal === newVal) continue;\n\n // Remove old\n if (oldVal !== undefined && oldVal !== null) {\n idx.map.get(oldVal)?.delete(oldDoc.id);\n }\n\n // Add new\n if (newVal !== undefined && newVal !== null) {\n if (\n idx.unique &&\n idx.map.has(newVal) &&\n idx.map.get(newVal)!.size > 0\n ) {\n throw new UniqueConstraintError(collection, idx.field, newVal);\n }\n if (!idx.map.has(newVal)) {\n idx.map.set(newVal, new Set());\n }\n idx.map.get(newVal)!.add(newDoc.id);\n }\n }\n }\n\n onDelete(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val !== undefined && val !== null) {\n idx.map.get(val)?.delete(doc.id);\n }\n }\n }\n\n findByValue(\n collection: string,\n field: string,\n value: unknown,\n ): Set<string> | undefined {\n return this.indexes.get(collection)?.get(field)?.map.get(value);\n }\n\n dropCollection(collection: string): void {\n this.indexes.delete(collection);\n }\n}\n","import type {\n Document,\n FilterQuery,\n FindOptions,\n NormalizedSchema,\n StorageAdapter,\n} from \"../../types.js\";\nimport { AdapterError, CollectionNotFoundError } from \"../../errors.js\";\nimport { applyFindOptions, countWithFilter } from \"../../query/filter.js\";\nimport { FileEngine } from \"./file-engine.js\";\nimport { Indexer } from \"./indexer.js\";\n\nexport class JsonAdapter implements StorageAdapter {\n private engine: FileEngine;\n private indexer = new Indexer();\n private schemas = new Map<string, NormalizedSchema>();\n\n constructor(filePath: string) {\n this.engine = new FileEngine(filePath);\n }\n\n async connect(): Promise<void> {\n await this.engine.load();\n }\n\n async disconnect(): Promise<void> {\n await this.engine.flushIfDirty();\n }\n\n async createCollection(\n collection: string,\n schema: NormalizedSchema,\n ): Promise<void> {\n this.engine.createCollection(collection);\n this.schemas.set(collection, schema);\n\n // Set up indexes\n for (const [field, def] of Object.entries(schema)) {\n if (def.index || def.unique) {\n this.indexer.setupIndex(\n collection,\n field,\n def.unique,\n this.engine.getCollection(collection),\n );\n }\n }\n\n await this.engine.flush();\n }\n\n async dropCollection(collection: string): Promise<void> {\n this.engine.dropCollection(collection);\n this.indexer.dropCollection(collection);\n this.schemas.delete(collection);\n await this.engine.flush();\n }\n\n async listCollections(): Promise<string[]> {\n return this.engine.listCollections();\n }\n\n async insert(collection: string, doc: Document): Promise<Document> {\n const docs = this.getCollectionOrThrow(collection);\n\n // Check unique constraints via indexer\n this.indexer.onInsert(collection, doc);\n\n docs.push(doc);\n this.engine.markDirty();\n await this.engine.flush();\n return doc;\n }\n\n async findById(\n collection: string,\n id: string,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n return docs.find((d) => d.id === id) ?? null;\n }\n\n async find(\n collection: string,\n options: FindOptions,\n ): Promise<Document[]> {\n const docs = this.getCollectionOrThrow(collection);\n return applyFindOptions(docs, options);\n }\n\n async count(collection: string, filter?: FilterQuery): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n return countWithFilter(docs, filter);\n }\n\n async update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return null;\n\n const oldDoc = docs[index]!;\n const newDoc = { ...oldDoc, ...data, id: oldDoc.id };\n\n // Check unique constraints\n this.indexer.onUpdate(collection, oldDoc, newDoc);\n\n docs[index] = newDoc;\n this.engine.markDirty();\n await this.engine.flush();\n return newDoc;\n }\n\n async delete(collection: string, id: string): Promise<boolean> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return false;\n\n this.indexer.onDelete(collection, docs[index]!);\n docs.splice(index, 1);\n this.engine.markDirty();\n await this.engine.flush();\n return true;\n }\n\n async deleteMany(\n collection: string,\n filter: FilterQuery,\n ): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n const matching = applyFindOptions(docs, { filter });\n\n for (const doc of matching) {\n this.indexer.onDelete(collection, doc);\n }\n\n const ids = new Set(matching.map((d) => d.id));\n const remaining = docs.filter((d) => !ids.has(d.id));\n const deleted = docs.length - remaining.length;\n\n // Replace array contents in-place\n docs.length = 0;\n docs.push(...remaining);\n\n if (deleted > 0) {\n this.engine.markDirty();\n await this.engine.flush();\n }\n\n return deleted;\n }\n\n private getCollectionOrThrow(collection: string): Document[] {\n if (!this.engine.hasCollection(collection)) {\n throw new CollectionNotFoundError(collection);\n }\n return this.engine.getCollection(collection);\n }\n}\n","import {\n AdapterType,\n type AdapterConfig,\n type ModelDefinition,\n type SeedORMConfig,\n type StorageAdapter,\n} from \"./types.js\";\nimport { SeedORMError } from \"./errors.js\";\nimport { Model } from \"./model/model.js\";\nimport { JsonAdapter } from \"./adapters/json/json-adapter.js\";\nimport * as path from \"node:path\";\n\nexport class SeedORM {\n private config: SeedORMConfig;\n private adapter: StorageAdapter | null = null;\n private models = new Map<string, Model>();\n private connected = false;\n\n constructor(config?: Partial<SeedORMConfig>) {\n this.config = {\n adapter: config?.adapter ?? { adapter: AdapterType.Json, path: \"./data\" },\n migrationsDir: config?.migrationsDir ?? \"./migrations\",\n };\n }\n\n private async createAdapter(adapterConfig: AdapterConfig): Promise<StorageAdapter> {\n switch (adapterConfig.adapter) {\n case AdapterType.Json: {\n const dbPath = path.resolve(\n adapterConfig.path ?? \"./data\",\n \"seedorm.json\",\n );\n return new JsonAdapter(dbPath);\n }\n case AdapterType.Postgres: {\n const { PostgresAdapter } = await import(\"./adapters/postgres/postgres-adapter.js\");\n return new PostgresAdapter(adapterConfig.url);\n }\n case AdapterType.MySQL:\n throw new SeedORMError(\n 'MySQL adapter requires the \"mysql2\" package. Install it with: npm install mysql2',\n );\n default:\n throw new SeedORMError(\n `Unknown adapter: ${(adapterConfig as { adapter: string }).adapter}`,\n );\n }\n }\n\n async connect(): Promise<void> {\n if (this.connected) return;\n this.adapter = await this.createAdapter(this.config.adapter);\n await this.adapter.connect();\n this.connected = true;\n\n // Re-init existing models\n for (const model of this.models.values()) {\n await model.init();\n }\n }\n\n async disconnect(): Promise<void> {\n if (!this.connected || !this.adapter) return;\n await this.adapter.disconnect();\n this.connected = false;\n this.adapter = null;\n }\n\n model(definition: ModelDefinition): Model {\n if (this.models.has(definition.name)) {\n return this.models.get(definition.name)!;\n }\n\n if (!this.adapter) {\n throw new SeedORMError(\n \"Not connected. Call db.connect() before defining models.\",\n );\n }\n\n const model = new Model(definition, this.adapter, this);\n this.models.set(definition.name, model);\n return model;\n }\n\n getModel(name: string): Model | undefined {\n return this.models.get(name);\n }\n\n getAdapter(): StorageAdapter {\n if (!this.adapter) {\n throw new SeedORMError(\"Not connected.\");\n }\n return this.adapter;\n }\n\n getConfig(): SeedORMConfig {\n return this.config;\n }\n}\n"],"mappings":"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","names":["path","PostgresAdapter"]}
|
|
1
|
+
{"version":3,"sources":["../src/model/model.ts","../src/model/field-types.ts","../src/model/schema.ts","../src/query/filter.ts","../src/adapters/json/file-engine.ts","../src/adapters/json/indexer.ts","../src/adapters/json/json-adapter.ts","../src/seedorm.ts"],"sourcesContent":["import { nanoid } from \"nanoid\";\nimport {\n RelationType,\n type Document,\n type FilterQuery,\n type FindOptions,\n type ModelDefinition,\n type NormalizedSchema,\n type RelationDefinition,\n type RelationsDefinition,\n type StorageAdapter,\n} from \"../types.js\";\nimport { DocumentNotFoundError, SeedORMError } from \"../errors.js\";\nimport { normalizeSchema, validateDocument } from \"./schema.js\";\n\ninterface SeedORMInstance {\n getModel(name: string): Model | undefined;\n getAdapter(): StorageAdapter;\n}\n\nexport class Model {\n public readonly name: string;\n public readonly collection: string;\n public readonly schema: NormalizedSchema;\n public readonly prefix: string;\n public readonly relations: RelationsDefinition;\n private adapter: StorageAdapter;\n private timestamps: boolean;\n private db: SeedORMInstance | null;\n\n constructor(definition: ModelDefinition, adapter: StorageAdapter, db?: SeedORMInstance) {\n this.name = definition.name;\n this.collection = definition.collection;\n this.schema = normalizeSchema(definition.schema);\n this.prefix = definition.prefix ?? definition.collection.slice(0, 3);\n this.adapter = adapter;\n this.timestamps = definition.timestamps !== false;\n this.relations = definition.relations ?? {};\n this.db = db ?? null;\n }\n\n async init(): Promise<void> {\n await this.adapter.createCollection(this.collection, this.schema);\n\n // Create join collections for manyToMany relations\n for (const rel of Object.values(this.relations)) {\n if (rel.type === RelationType.ManyToMany && rel.joinCollection) {\n await this.adapter.createCollection(rel.joinCollection, {});\n }\n }\n }\n\n private generateId(): string {\n return `${this.prefix}_${nanoid(12)}`;\n }\n\n private resolveRelation(relationName: string): { rel: RelationDefinition; relatedModel: Model } {\n const rel = this.relations[relationName];\n if (!rel) {\n throw new SeedORMError(`Unknown relation \"${relationName}\" on model \"${this.name}\"`);\n }\n if (!this.db) {\n throw new SeedORMError(\"Cannot resolve relations without a SeedORM instance\");\n }\n const relatedModel = this.db.getModel(rel.model);\n if (!relatedModel) {\n throw new SeedORMError(`Related model \"${rel.model}\" not found. Make sure it is defined before querying.`);\n }\n return { rel, relatedModel };\n }\n\n private async populate(docs: Document[], includeList: string[]): Promise<Document[]> {\n if (includeList.length === 0 || docs.length === 0) return docs;\n\n // Shallow-clone docs to avoid mutating the adapter's internal store\n docs = docs.map((d) => ({ ...d }));\n\n for (const relationName of includeList) {\n const { rel, relatedModel } = this.resolveRelation(relationName);\n\n switch (rel.type) {\n case RelationType.HasMany: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const grouped = new Map<string, Document[]>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!grouped.has(fk)) grouped.set(fk, []);\n grouped.get(fk)!.push(r);\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n\n case RelationType.HasOne: {\n const parentIds = docs.map((d) => d.id);\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n const fk = r[rel.foreignKey] as string;\n if (!map.has(fk)) map.set(fk, r);\n }\n for (const doc of docs) {\n doc[relationName] = map.get(doc.id) ?? null;\n }\n break;\n }\n\n case RelationType.BelongsTo: {\n const fkValues = [...new Set(docs.map((d) => d[rel.foreignKey] as string).filter(Boolean))];\n if (fkValues.length === 0) {\n for (const doc of docs) doc[relationName] = null;\n break;\n }\n const related = await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: fkValues } },\n });\n const map = new Map<string, Document>();\n for (const r of related) {\n map.set(r.id, r);\n }\n for (const doc of docs) {\n const fk = doc[rel.foreignKey] as string;\n doc[relationName] = map.get(fk) ?? null;\n }\n break;\n }\n\n case RelationType.ManyToMany: {\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const parentIds = docs.map((d) => d.id);\n const joinRows = await this.adapter.find(rel.joinCollection, {\n filter: { [rel.foreignKey]: { $in: parentIds } },\n });\n const relatedIds = [...new Set(joinRows.map((r) => r[rel.relatedKey!] as string))];\n const relatedDocs =\n relatedIds.length > 0\n ? await this.adapter.find(relatedModel.collection, {\n filter: { id: { $in: relatedIds } },\n })\n : [];\n const relatedMap = new Map<string, Document>();\n for (const r of relatedDocs) relatedMap.set(r.id, r);\n\n const grouped = new Map<string, Document[]>();\n for (const row of joinRows) {\n const parentId = row[rel.foreignKey] as string;\n const relatedId = row[rel.relatedKey!] as string;\n const relatedDoc = relatedMap.get(relatedId);\n if (relatedDoc) {\n if (!grouped.has(parentId)) grouped.set(parentId, []);\n grouped.get(parentId)!.push(relatedDoc);\n }\n }\n for (const doc of docs) {\n doc[relationName] = grouped.get(doc.id) ?? [];\n }\n break;\n }\n }\n }\n\n return docs;\n }\n\n async create(data: Record<string, unknown>): Promise<Document> {\n const validated = validateDocument(data, this.schema);\n const now = new Date().toISOString();\n const doc: Document = {\n ...validated,\n id: this.generateId(),\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(this.collection, doc);\n }\n\n async createMany(\n items: Record<string, unknown>[],\n ): Promise<Document[]> {\n const results: Document[] = [];\n for (const item of items) {\n results.push(await this.create(item));\n }\n return results;\n }\n\n async findById(id: string, options?: { include?: string[] }): Promise<Document | null> {\n const doc = await this.adapter.findById(this.collection, id);\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async findByIdOrThrow(id: string, options?: { include?: string[] }): Promise<Document> {\n const doc = await this.findById(id, options);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async findOne(filter: FilterQuery, options?: { include?: string[] }): Promise<Document | null> {\n const results = await this.adapter.find(this.collection, {\n filter,\n limit: 1,\n });\n const doc = results[0] ?? null;\n if (!doc || !options?.include?.length) return doc;\n const [populated] = await this.populate([doc], options.include);\n return populated ?? null;\n }\n\n async find(options: FindOptions = {}): Promise<Document[]> {\n const { include, ...adapterOptions } = options;\n const docs = await this.adapter.find(this.collection, adapterOptions);\n if (!include?.length) return docs;\n return this.populate(docs, include);\n }\n\n async findAll(): Promise<Document[]> {\n return this.adapter.find(this.collection, {});\n }\n\n async count(filter?: FilterQuery): Promise<number> {\n return this.adapter.count(this.collection, filter);\n }\n\n async update(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document | null> {\n const validated = validateDocument(data, this.schema, true);\n if (this.timestamps) {\n validated.updatedAt = new Date().toISOString();\n }\n return this.adapter.update(this.collection, id, validated);\n }\n\n async updateOrThrow(\n id: string,\n data: Record<string, unknown>,\n ): Promise<Document> {\n const doc = await this.update(id, data);\n if (!doc) throw new DocumentNotFoundError(this.collection, id);\n return doc;\n }\n\n async delete(id: string): Promise<boolean> {\n return this.adapter.delete(this.collection, id);\n }\n\n async deleteMany(filter: FilterQuery): Promise<number> {\n return this.adapter.deleteMany(this.collection, filter);\n }\n\n async associate(id: string, relationName: string, relatedId: string): Promise<Document> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`associate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n const now = new Date().toISOString();\n const joinDoc: Document = {\n id: `${this.prefix}rel_${nanoid(12)}`,\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n createdAt: now,\n updatedAt: now,\n };\n return this.adapter.insert(rel.joinCollection, joinDoc);\n }\n\n async dissociate(id: string, relationName: string, relatedId: string): Promise<number> {\n const { rel } = this.resolveRelation(relationName);\n if (rel.type !== RelationType.ManyToMany) {\n throw new SeedORMError(`dissociate() is only supported for manyToMany relations, got \"${rel.type}\"`);\n }\n if (!rel.joinCollection || !rel.relatedKey) {\n throw new SeedORMError(\n `manyToMany relation \"${relationName}\" requires joinCollection and relatedKey`,\n );\n }\n return this.adapter.deleteMany(rel.joinCollection, {\n [rel.foreignKey]: id,\n [rel.relatedKey]: relatedId,\n });\n }\n}\n","import { FieldType } from \"../types.js\";\n\nexport function validateFieldType(\n value: unknown,\n type: FieldType,\n): string | null {\n if (value === undefined || value === null) return null; // handled by required check\n\n switch (type) {\n case FieldType.String:\n if (typeof value !== \"string\") return `expected string, got ${typeof value}`;\n break;\n case FieldType.Number:\n if (typeof value !== \"number\" || Number.isNaN(value))\n return `expected number, got ${typeof value}`;\n break;\n case FieldType.Boolean:\n if (typeof value !== \"boolean\")\n return `expected boolean, got ${typeof value}`;\n break;\n case FieldType.Date:\n if (typeof value === \"string\") {\n if (Number.isNaN(Date.parse(value))) return `invalid date string`;\n } else if (!(value instanceof Date)) {\n return `expected date string or Date, got ${typeof value}`;\n }\n break;\n case FieldType.Json:\n // Any non-undefined value is valid JSON\n break;\n case FieldType.Array:\n if (!Array.isArray(value)) return `expected array, got ${typeof value}`;\n break;\n default:\n return `unknown type: ${type as string}`;\n }\n\n return null;\n}\n\nexport function coerceFieldValue(value: unknown, type: FieldType): unknown {\n if (value === undefined || value === null) return value;\n\n if (type === FieldType.Date && value instanceof Date) {\n return value.toISOString();\n }\n\n return value;\n}\n","import {\n FieldType,\n type FieldDefinition,\n type NormalizedField,\n type NormalizedSchema,\n type SchemaDefinition,\n} from \"../types.js\";\nimport { ValidationError } from \"../errors.js\";\nimport { coerceFieldValue, validateFieldType } from \"./field-types.js\";\n\nexport function normalizeSchema(schema: SchemaDefinition): NormalizedSchema {\n const normalized: NormalizedSchema = {};\n\n for (const [field, def] of Object.entries(schema)) {\n if (typeof def === \"string\") {\n normalized[field] = {\n type: def as FieldType,\n required: false,\n unique: false,\n index: false,\n };\n } else {\n const d = def as FieldDefinition;\n normalized[field] = {\n type: d.type,\n required: d.required ?? false,\n unique: d.unique ?? false,\n index: d.index ?? d.unique ?? false,\n ...(d.default !== undefined && { default: d.default }),\n ...(d.minLength !== undefined && { minLength: d.minLength }),\n ...(d.maxLength !== undefined && { maxLength: d.maxLength }),\n ...(d.min !== undefined && { min: d.min }),\n ...(d.max !== undefined && { max: d.max }),\n ...(d.enum !== undefined && { enum: d.enum }),\n };\n }\n }\n\n return normalized;\n}\n\nexport function validateDocument(\n data: Record<string, unknown>,\n schema: NormalizedSchema,\n isUpdate = false,\n): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n\n for (const [field, def] of Object.entries(schema)) {\n let value = data[field];\n\n // Apply default\n if (value === undefined && def.default !== undefined && !isUpdate) {\n value =\n typeof def.default === \"function\"\n ? (def.default as () => unknown)()\n : def.default;\n }\n\n // Required check (skip on partial updates)\n if (!isUpdate && def.required && (value === undefined || value === null)) {\n throw new ValidationError(field, \"field is required\");\n }\n\n // Skip unset fields on update\n if (value === undefined) continue;\n\n // Type check\n const typeErr = validateFieldType(value, def.type);\n if (typeErr) throw new ValidationError(field, typeErr);\n\n // String constraints\n if (def.type === \"string\" && typeof value === \"string\") {\n if (def.minLength !== undefined && value.length < def.minLength) {\n throw new ValidationError(\n field,\n `minimum length is ${def.minLength}, got ${value.length}`,\n );\n }\n if (def.maxLength !== undefined && value.length > def.maxLength) {\n throw new ValidationError(\n field,\n `maximum length is ${def.maxLength}, got ${value.length}`,\n );\n }\n }\n\n // Number constraints\n if (def.type === \"number\" && typeof value === \"number\") {\n if (def.min !== undefined && value < def.min) {\n throw new ValidationError(field, `minimum value is ${def.min}`);\n }\n if (def.max !== undefined && value > def.max) {\n throw new ValidationError(field, `maximum value is ${def.max}`);\n }\n }\n\n // Enum check\n if (def.enum && !def.enum.includes(value)) {\n throw new ValidationError(\n field,\n `value must be one of: ${def.enum.join(\", \")}`,\n );\n }\n\n result[field] = coerceFieldValue(value, def.type);\n }\n\n // On update, pass through non-schema fields that were provided\n // (for id, createdAt, updatedAt)\n if (isUpdate) {\n for (const [key, val] of Object.entries(data)) {\n if (!(key in schema) && val !== undefined) {\n result[key] = val;\n }\n }\n }\n\n return result;\n}\n","import type { Document, FilterQuery, FindOptions, SortOption } from \"../types.js\";\nimport { applyOperator, isOperatorObject } from \"./operators.js\";\n\nfunction matchesFilter(doc: Document, filter: FilterQuery): boolean {\n for (const [field, condition] of Object.entries(filter)) {\n const value = doc[field];\n\n if (isOperatorObject(condition)) {\n for (const [op, operand] of Object.entries(\n condition as Record<string, unknown>,\n )) {\n if (!applyOperator(op, value, operand)) return false;\n }\n } else {\n // Shorthand: { field: value } is equivalent to { field: { $eq: value } }\n if (value !== condition) return false;\n }\n }\n return true;\n}\n\nfunction sortDocuments(docs: Document[], sort: SortOption): Document[] {\n const entries = Object.entries(sort);\n return [...docs].sort((a, b) => {\n for (const [field, dir] of entries) {\n const av = a[field];\n const bv = b[field];\n if (av === bv) continue;\n if (av === undefined || av === null) return dir;\n if (bv === undefined || bv === null) return -dir;\n if (av < bv) return -dir;\n if (av > bv) return dir;\n }\n return 0;\n });\n}\n\nexport function applyFindOptions(\n docs: Document[],\n options: FindOptions,\n): Document[] {\n let result = docs;\n\n if (options.filter) {\n result = result.filter((doc) => matchesFilter(doc, options.filter!));\n }\n\n if (options.sort) {\n result = sortDocuments(result, options.sort);\n }\n\n if (options.offset) {\n result = result.slice(options.offset);\n }\n\n if (options.limit !== undefined) {\n result = result.slice(0, options.limit);\n }\n\n return result;\n}\n\nexport function countWithFilter(\n docs: Document[],\n filter?: FilterQuery,\n): number {\n if (!filter) return docs.length;\n return docs.filter((doc) => matchesFilter(doc, filter)).length;\n}\n\nexport { matchesFilter };\n","import * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport writeFileAtomic from \"write-file-atomic\";\nimport type { Document } from \"../../types.js\";\n\nexport interface FileData {\n [collection: string]: Document[];\n}\n\nexport class FileEngine {\n private filePath: string;\n private data: FileData = {};\n private writeQueue: Promise<void> = Promise.resolve();\n private dirty = false;\n\n constructor(filePath: string) {\n this.filePath = path.resolve(filePath);\n }\n\n async load(): Promise<void> {\n try {\n const raw = fs.readFileSync(this.filePath, \"utf-8\");\n this.data = JSON.parse(raw) as FileData;\n } catch (err: unknown) {\n if ((err as NodeJS.ErrnoException).code === \"ENOENT\") {\n this.data = {};\n await this.flush();\n } else {\n throw err;\n }\n }\n }\n\n getData(): FileData {\n return this.data;\n }\n\n getCollection(name: string): Document[] {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n return this.data[name];\n }\n\n hasCollection(name: string): boolean {\n return name in this.data;\n }\n\n createCollection(name: string): void {\n if (!this.data[name]) {\n this.data[name] = [];\n }\n }\n\n dropCollection(name: string): void {\n delete this.data[name];\n }\n\n listCollections(): string[] {\n return Object.keys(this.data);\n }\n\n markDirty(): void {\n this.dirty = true;\n }\n\n async flush(): Promise<void> {\n this.writeQueue = this.writeQueue.then(async () => {\n const dir = path.dirname(this.filePath);\n if (!fs.existsSync(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n await writeFileAtomic(\n this.filePath,\n JSON.stringify(this.data, null, 2) + \"\\n\",\n );\n this.dirty = false;\n });\n return this.writeQueue;\n }\n\n async flushIfDirty(): Promise<void> {\n if (this.dirty) {\n await this.flush();\n }\n }\n}\n","import type { Document } from \"../../types.js\";\nimport { UniqueConstraintError } from \"../../errors.js\";\n\ninterface FieldIndex {\n field: string;\n unique: boolean;\n map: Map<unknown, Set<string>>; // value → set of doc IDs\n}\n\nexport class Indexer {\n private indexes = new Map<string, Map<string, FieldIndex>>(); // collection → field → index\n\n setupIndex(\n collection: string,\n field: string,\n unique: boolean,\n docs: Document[],\n ): void {\n if (!this.indexes.has(collection)) {\n this.indexes.set(collection, new Map());\n }\n const colIndexes = this.indexes.get(collection)!;\n\n const idx: FieldIndex = { field, unique, map: new Map() };\n\n for (const doc of docs) {\n const val = doc[field];\n if (val === undefined || val === null) continue;\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n\n colIndexes.set(field, idx);\n }\n\n onInsert(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val === undefined || val === null) continue;\n\n if (idx.unique && idx.map.has(val) && idx.map.get(val)!.size > 0) {\n throw new UniqueConstraintError(collection, idx.field, val);\n }\n\n if (!idx.map.has(val)) {\n idx.map.set(val, new Set());\n }\n idx.map.get(val)!.add(doc.id);\n }\n }\n\n onUpdate(\n collection: string,\n oldDoc: Document,\n newDoc: Document,\n ): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const oldVal = oldDoc[idx.field];\n const newVal = newDoc[idx.field];\n\n if (oldVal === newVal) continue;\n\n // Remove old\n if (oldVal !== undefined && oldVal !== null) {\n idx.map.get(oldVal)?.delete(oldDoc.id);\n }\n\n // Add new\n if (newVal !== undefined && newVal !== null) {\n if (\n idx.unique &&\n idx.map.has(newVal) &&\n idx.map.get(newVal)!.size > 0\n ) {\n throw new UniqueConstraintError(collection, idx.field, newVal);\n }\n if (!idx.map.has(newVal)) {\n idx.map.set(newVal, new Set());\n }\n idx.map.get(newVal)!.add(newDoc.id);\n }\n }\n }\n\n onDelete(collection: string, doc: Document): void {\n const colIndexes = this.indexes.get(collection);\n if (!colIndexes) return;\n\n for (const [, idx] of colIndexes) {\n const val = doc[idx.field];\n if (val !== undefined && val !== null) {\n idx.map.get(val)?.delete(doc.id);\n }\n }\n }\n\n findByValue(\n collection: string,\n field: string,\n value: unknown,\n ): Set<string> | undefined {\n return this.indexes.get(collection)?.get(field)?.map.get(value);\n }\n\n dropCollection(collection: string): void {\n this.indexes.delete(collection);\n }\n}\n","import type {\n Document,\n FilterQuery,\n FindOptions,\n NormalizedSchema,\n StorageAdapter,\n} from \"../../types.js\";\nimport { AdapterError, CollectionNotFoundError } from \"../../errors.js\";\nimport { applyFindOptions, countWithFilter } from \"../../query/filter.js\";\nimport { FileEngine } from \"./file-engine.js\";\nimport { Indexer } from \"./indexer.js\";\n\nexport class JsonAdapter implements StorageAdapter {\n private engine: FileEngine;\n private indexer = new Indexer();\n private schemas = new Map<string, NormalizedSchema>();\n\n constructor(filePath: string) {\n this.engine = new FileEngine(filePath);\n }\n\n async connect(): Promise<void> {\n await this.engine.load();\n }\n\n async disconnect(): Promise<void> {\n await this.engine.flushIfDirty();\n }\n\n async createCollection(\n collection: string,\n schema: NormalizedSchema,\n ): Promise<void> {\n this.engine.createCollection(collection);\n this.schemas.set(collection, schema);\n\n // Set up indexes\n for (const [field, def] of Object.entries(schema)) {\n if (def.index || def.unique) {\n this.indexer.setupIndex(\n collection,\n field,\n def.unique,\n this.engine.getCollection(collection),\n );\n }\n }\n\n await this.engine.flush();\n }\n\n async dropCollection(collection: string): Promise<void> {\n this.engine.dropCollection(collection);\n this.indexer.dropCollection(collection);\n this.schemas.delete(collection);\n await this.engine.flush();\n }\n\n async listCollections(): Promise<string[]> {\n return this.engine.listCollections();\n }\n\n async insert(collection: string, doc: Document): Promise<Document> {\n const docs = this.getCollectionOrThrow(collection);\n\n // Check unique constraints via indexer\n this.indexer.onInsert(collection, doc);\n\n docs.push(doc);\n this.engine.markDirty();\n await this.engine.flush();\n return doc;\n }\n\n async findById(\n collection: string,\n id: string,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n return docs.find((d) => d.id === id) ?? null;\n }\n\n async find(\n collection: string,\n options: FindOptions,\n ): Promise<Document[]> {\n const docs = this.getCollectionOrThrow(collection);\n return applyFindOptions(docs, options);\n }\n\n async count(collection: string, filter?: FilterQuery): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n return countWithFilter(docs, filter);\n }\n\n async update(\n collection: string,\n id: string,\n data: Partial<Document>,\n ): Promise<Document | null> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return null;\n\n const oldDoc = docs[index]!;\n const newDoc = { ...oldDoc, ...data, id: oldDoc.id };\n\n // Check unique constraints\n this.indexer.onUpdate(collection, oldDoc, newDoc);\n\n docs[index] = newDoc;\n this.engine.markDirty();\n await this.engine.flush();\n return newDoc;\n }\n\n async delete(collection: string, id: string): Promise<boolean> {\n const docs = this.getCollectionOrThrow(collection);\n const index = docs.findIndex((d) => d.id === id);\n if (index === -1) return false;\n\n this.indexer.onDelete(collection, docs[index]!);\n docs.splice(index, 1);\n this.engine.markDirty();\n await this.engine.flush();\n return true;\n }\n\n async deleteMany(\n collection: string,\n filter: FilterQuery,\n ): Promise<number> {\n const docs = this.getCollectionOrThrow(collection);\n const matching = applyFindOptions(docs, { filter });\n\n for (const doc of matching) {\n this.indexer.onDelete(collection, doc);\n }\n\n const ids = new Set(matching.map((d) => d.id));\n const remaining = docs.filter((d) => !ids.has(d.id));\n const deleted = docs.length - remaining.length;\n\n // Replace array contents in-place\n docs.length = 0;\n docs.push(...remaining);\n\n if (deleted > 0) {\n this.engine.markDirty();\n await this.engine.flush();\n }\n\n return deleted;\n }\n\n private getCollectionOrThrow(collection: string): Document[] {\n if (!this.engine.hasCollection(collection)) {\n throw new CollectionNotFoundError(collection);\n }\n return this.engine.getCollection(collection);\n }\n}\n","import {\n AdapterType,\n type AdapterConfig,\n type ModelDefinition,\n type SeedORMConfig,\n type StorageAdapter,\n} from \"./types.js\";\nimport { SeedORMError } from \"./errors.js\";\nimport { Model } from \"./model/model.js\";\nimport { JsonAdapter } from \"./adapters/json/json-adapter.js\";\nimport * as path from \"node:path\";\n\nexport class SeedORM {\n private config: SeedORMConfig;\n private adapter: StorageAdapter | null = null;\n private models = new Map<string, Model>();\n private connected = false;\n\n constructor(config?: Partial<SeedORMConfig>) {\n this.config = {\n adapter: config?.adapter ?? { adapter: AdapterType.Json, path: \"./data\" },\n migrationsDir: config?.migrationsDir ?? \"./migrations\",\n };\n }\n\n private async createAdapter(adapterConfig: AdapterConfig): Promise<StorageAdapter> {\n switch (adapterConfig.adapter) {\n case AdapterType.Json: {\n const dbPath = path.resolve(\n adapterConfig.path ?? \"./data\",\n \"seedorm.json\",\n );\n return new JsonAdapter(dbPath);\n }\n case AdapterType.Postgres: {\n const { PostgresAdapter } = await import(\"./adapters/postgres/postgres-adapter.js\");\n return new PostgresAdapter(adapterConfig.url);\n }\n case AdapterType.MySQL:\n throw new SeedORMError(\n 'MySQL adapter requires the \"mysql2\" package. Install it with: npm install mysql2',\n );\n default:\n throw new SeedORMError(\n `Unknown adapter: ${(adapterConfig as { adapter: string }).adapter}`,\n );\n }\n }\n\n async connect(): Promise<void> {\n if (this.connected) return;\n this.adapter = await this.createAdapter(this.config.adapter);\n await this.adapter.connect();\n this.connected = true;\n\n // Re-init existing models\n for (const model of this.models.values()) {\n await model.init();\n }\n }\n\n async disconnect(): Promise<void> {\n if (!this.connected || !this.adapter) return;\n await this.adapter.disconnect();\n this.connected = false;\n this.adapter = null;\n }\n\n model(definition: ModelDefinition): Model {\n if (this.models.has(definition.name)) {\n return this.models.get(definition.name)!;\n }\n\n if (!this.adapter) {\n throw new SeedORMError(\n \"Not connected. Call db.connect() before defining models.\",\n );\n }\n\n const model = new Model(definition, this.adapter, this);\n this.models.set(definition.name, model);\n return model;\n }\n\n getModel(name: string): Model | undefined {\n return this.models.get(name);\n }\n\n getAdapter(): StorageAdapter {\n if (!this.adapter) {\n throw new SeedORMError(\"Not connected.\");\n }\n return this.adapter;\n }\n\n getConfig(): SeedORMConfig {\n return this.config;\n }\n}\n"],"mappings":"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","names":["path","PostgresAdapter"]}
|