@fragno-dev/db 0.2.2 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.turbo/turbo-build.log +202 -140
- package/CHANGELOG.md +35 -0
- package/README.md +30 -9
- package/dist/adapters/adapters.d.ts +23 -21
- package/dist/adapters/adapters.d.ts.map +1 -1
- package/dist/adapters/adapters.js.map +1 -1
- package/dist/adapters/generic-sql/driver-config.d.ts +16 -1
- package/dist/adapters/generic-sql/driver-config.d.ts.map +1 -1
- package/dist/adapters/generic-sql/driver-config.js +23 -1
- package/dist/adapters/generic-sql/driver-config.js.map +1 -1
- package/dist/adapters/generic-sql/generic-sql-adapter.d.ts +27 -9
- package/dist/adapters/generic-sql/generic-sql-adapter.d.ts.map +1 -1
- package/dist/adapters/generic-sql/generic-sql-adapter.js +55 -16
- package/dist/adapters/generic-sql/generic-sql-adapter.js.map +1 -1
- package/dist/adapters/generic-sql/generic-sql-uow-executor.js +129 -3
- package/dist/adapters/generic-sql/generic-sql-uow-executor.js.map +1 -1
- package/dist/adapters/generic-sql/migration/dialect/mysql.js +24 -5
- package/dist/adapters/generic-sql/migration/dialect/mysql.js.map +1 -1
- package/dist/adapters/generic-sql/migration/dialect/postgres.js +6 -5
- package/dist/adapters/generic-sql/migration/dialect/postgres.js.map +1 -1
- package/dist/adapters/generic-sql/migration/dialect/sqlite.js +21 -10
- package/dist/adapters/generic-sql/migration/dialect/sqlite.js.map +1 -1
- package/dist/adapters/generic-sql/migration/prepared-migrations.d.ts.map +1 -1
- package/dist/adapters/generic-sql/migration/prepared-migrations.js +8 -8
- package/dist/adapters/generic-sql/migration/prepared-migrations.js.map +1 -1
- package/dist/adapters/generic-sql/migration/sql-generator.js +74 -51
- package/dist/adapters/generic-sql/migration/sql-generator.js.map +1 -1
- package/dist/adapters/generic-sql/query/create-sql-query-compiler.js +6 -5
- package/dist/adapters/generic-sql/query/create-sql-query-compiler.js.map +1 -1
- package/dist/adapters/generic-sql/query/cursor-utils.js +42 -4
- package/dist/adapters/generic-sql/query/cursor-utils.js.map +1 -1
- package/dist/adapters/generic-sql/query/generic-sql-uow-operation-compiler.js +25 -17
- package/dist/adapters/generic-sql/query/generic-sql-uow-operation-compiler.js.map +1 -1
- package/dist/adapters/generic-sql/query/select-builder.js +5 -3
- package/dist/adapters/generic-sql/query/select-builder.js.map +1 -1
- package/dist/adapters/generic-sql/query/sql-query-compiler.js +15 -12
- package/dist/adapters/generic-sql/query/sql-query-compiler.js.map +1 -1
- package/dist/adapters/generic-sql/query/where-builder.js +39 -29
- package/dist/adapters/generic-sql/query/where-builder.js.map +1 -1
- package/dist/adapters/generic-sql/sqlite-storage.d.ts +13 -0
- package/dist/adapters/generic-sql/sqlite-storage.d.ts.map +1 -0
- package/dist/adapters/generic-sql/sqlite-storage.js +15 -0
- package/dist/adapters/generic-sql/sqlite-storage.js.map +1 -0
- package/dist/adapters/generic-sql/uow-decoder.js +7 -3
- package/dist/adapters/generic-sql/uow-decoder.js.map +1 -1
- package/dist/adapters/generic-sql/uow-encoder.js +28 -8
- package/dist/adapters/generic-sql/uow-encoder.js.map +1 -1
- package/dist/adapters/in-memory/condition-evaluator.js +131 -0
- package/dist/adapters/in-memory/condition-evaluator.js.map +1 -0
- package/dist/adapters/in-memory/errors.d.ts +13 -0
- package/dist/adapters/in-memory/errors.d.ts.map +1 -0
- package/dist/adapters/in-memory/errors.js +23 -0
- package/dist/adapters/in-memory/errors.js.map +1 -0
- package/dist/adapters/in-memory/in-memory-adapter.d.ts +27 -0
- package/dist/adapters/in-memory/in-memory-adapter.d.ts.map +1 -0
- package/dist/adapters/in-memory/in-memory-adapter.js +176 -0
- package/dist/adapters/in-memory/in-memory-adapter.js.map +1 -0
- package/dist/adapters/in-memory/in-memory-uow.js +648 -0
- package/dist/adapters/in-memory/in-memory-uow.js.map +1 -0
- package/dist/adapters/in-memory/index.d.ts +4 -0
- package/dist/adapters/in-memory/index.js +4 -0
- package/dist/adapters/in-memory/options.d.ts +28 -0
- package/dist/adapters/in-memory/options.d.ts.map +1 -0
- package/dist/adapters/in-memory/options.js +61 -0
- package/dist/adapters/in-memory/options.js.map +1 -0
- package/dist/adapters/in-memory/reference-resolution.js +26 -0
- package/dist/adapters/in-memory/reference-resolution.js.map +1 -0
- package/dist/adapters/in-memory/sorted-array-index.js +129 -0
- package/dist/adapters/in-memory/sorted-array-index.js.map +1 -0
- package/dist/adapters/in-memory/store.js +71 -0
- package/dist/adapters/in-memory/store.js.map +1 -0
- package/dist/adapters/in-memory/value-comparison.js +28 -0
- package/dist/adapters/in-memory/value-comparison.js.map +1 -0
- package/dist/adapters/shared/from-unit-of-work-compiler.js.map +1 -1
- package/dist/adapters/shared/uow-operation-compiler.js +11 -11
- package/dist/adapters/shared/uow-operation-compiler.js.map +1 -1
- package/dist/adapters/sql/index.d.ts +5 -0
- package/dist/adapters/sql/index.js +4 -0
- package/dist/db-fragment-definition-builder.d.ts +18 -7
- package/dist/db-fragment-definition-builder.d.ts.map +1 -1
- package/dist/db-fragment-definition-builder.js +116 -54
- package/dist/db-fragment-definition-builder.js.map +1 -1
- package/dist/dispatchers/cloudflare-do/index.d.ts +26 -0
- package/dist/dispatchers/cloudflare-do/index.d.ts.map +1 -0
- package/dist/dispatchers/cloudflare-do/index.js +63 -0
- package/dist/dispatchers/cloudflare-do/index.js.map +1 -0
- package/dist/dispatchers/node/index.d.ts +17 -0
- package/dist/dispatchers/node/index.d.ts.map +1 -0
- package/dist/dispatchers/node/index.js +59 -0
- package/dist/dispatchers/node/index.js.map +1 -0
- package/dist/fragments/internal-fragment.d.ts +79 -2
- package/dist/fragments/internal-fragment.d.ts.map +1 -1
- package/dist/fragments/internal-fragment.js +150 -32
- package/dist/fragments/internal-fragment.js.map +1 -1
- package/dist/fragments/internal-fragment.routes.js +29 -0
- package/dist/fragments/internal-fragment.routes.js.map +1 -0
- package/dist/fragments/internal-fragment.schema.d.ts +9 -0
- package/dist/fragments/internal-fragment.schema.d.ts.map +1 -0
- package/dist/fragments/internal-fragment.schema.js +22 -0
- package/dist/fragments/internal-fragment.schema.js.map +1 -0
- package/dist/hooks/durable-hooks-processor.d.ts +14 -0
- package/dist/hooks/durable-hooks-processor.d.ts.map +1 -0
- package/dist/hooks/durable-hooks-processor.js +32 -0
- package/dist/hooks/durable-hooks-processor.js.map +1 -0
- package/dist/hooks/hooks.d.ts +42 -1
- package/dist/hooks/hooks.d.ts.map +1 -1
- package/dist/hooks/hooks.js +72 -6
- package/dist/hooks/hooks.js.map +1 -1
- package/dist/migration-engine/auto-from-schema.js +14 -11
- package/dist/migration-engine/auto-from-schema.js.map +1 -1
- package/dist/migration-engine/generation-engine.d.ts +16 -10
- package/dist/migration-engine/generation-engine.d.ts.map +1 -1
- package/dist/migration-engine/generation-engine.js +72 -33
- package/dist/migration-engine/generation-engine.js.map +1 -1
- package/dist/migration-engine/shared.js.map +1 -1
- package/dist/mod.d.ts +15 -8
- package/dist/mod.d.ts.map +1 -1
- package/dist/mod.js +14 -8
- package/dist/mod.js.map +1 -1
- package/dist/naming/sql-naming.d.ts +19 -0
- package/dist/naming/sql-naming.d.ts.map +1 -0
- package/dist/naming/sql-naming.js +116 -0
- package/dist/naming/sql-naming.js.map +1 -0
- package/dist/node_modules/.pnpm/{rou3@0.7.10 → rou3@0.7.12}/node_modules/rou3/dist/index.js +8 -5
- package/dist/node_modules/.pnpm/rou3@0.7.12/node_modules/rou3/dist/index.js.map +1 -0
- package/dist/outbox/outbox-builder.js +156 -0
- package/dist/outbox/outbox-builder.js.map +1 -0
- package/dist/outbox/outbox.d.ts +52 -0
- package/dist/outbox/outbox.d.ts.map +1 -0
- package/dist/outbox/outbox.js +37 -0
- package/dist/outbox/outbox.js.map +1 -0
- package/dist/packages/fragno/dist/api/fragment-definition-builder.js +3 -2
- package/dist/packages/fragno/dist/api/fragment-definition-builder.js.map +1 -1
- package/dist/packages/fragno/dist/api/fragment-instantiator.js +164 -20
- package/dist/packages/fragno/dist/api/fragment-instantiator.js.map +1 -1
- package/dist/packages/fragno/dist/api/request-input-context.js +67 -0
- package/dist/packages/fragno/dist/api/request-input-context.js.map +1 -1
- package/dist/packages/fragno/dist/api/route.js +14 -1
- package/dist/packages/fragno/dist/api/route.js.map +1 -1
- package/dist/packages/fragno/dist/internal/trace-context.js +12 -0
- package/dist/packages/fragno/dist/internal/trace-context.js.map +1 -0
- package/dist/query/column-defaults.js +20 -4
- package/dist/query/column-defaults.js.map +1 -1
- package/dist/query/cursor.d.ts +3 -1
- package/dist/query/cursor.d.ts.map +1 -1
- package/dist/query/cursor.js +45 -14
- package/dist/query/cursor.js.map +1 -1
- package/dist/query/db-now.d.ts +8 -0
- package/dist/query/db-now.d.ts.map +1 -0
- package/dist/query/db-now.js +7 -0
- package/dist/query/db-now.js.map +1 -0
- package/dist/query/serialize/create-sql-serializer.js +3 -2
- package/dist/query/serialize/create-sql-serializer.js.map +1 -1
- package/dist/query/serialize/dialect/mysql-serializer.js +12 -6
- package/dist/query/serialize/dialect/mysql-serializer.js.map +1 -1
- package/dist/query/serialize/dialect/postgres-serializer.js +25 -7
- package/dist/query/serialize/dialect/postgres-serializer.js.map +1 -1
- package/dist/query/serialize/dialect/sqlite-serializer.js +55 -11
- package/dist/query/serialize/dialect/sqlite-serializer.js.map +1 -1
- package/dist/query/serialize/sql-serializer.js +2 -2
- package/dist/query/serialize/sql-serializer.js.map +1 -1
- package/dist/query/simple-query-interface.d.ts +6 -1
- package/dist/query/simple-query-interface.d.ts.map +1 -1
- package/dist/query/unit-of-work/execute-unit-of-work.d.ts.map +1 -1
- package/dist/query/unit-of-work/execute-unit-of-work.js +11 -6
- package/dist/query/unit-of-work/execute-unit-of-work.js.map +1 -1
- package/dist/query/unit-of-work/unit-of-work.d.ts +50 -14
- package/dist/query/unit-of-work/unit-of-work.d.ts.map +1 -1
- package/dist/query/unit-of-work/unit-of-work.js +86 -5
- package/dist/query/unit-of-work/unit-of-work.js.map +1 -1
- package/dist/query/value-decoding.js +9 -6
- package/dist/query/value-decoding.js.map +1 -1
- package/dist/query/value-encoding.js +29 -9
- package/dist/query/value-encoding.js.map +1 -1
- package/dist/schema/create.d.ts +38 -14
- package/dist/schema/create.d.ts.map +1 -1
- package/dist/schema/create.js +81 -42
- package/dist/schema/create.js.map +1 -1
- package/dist/schema/generate-id.js +2 -2
- package/dist/schema/generate-id.js.map +1 -1
- package/dist/schema/type-conversion/create-sql-type-mapper.js +3 -2
- package/dist/schema/type-conversion/create-sql-type-mapper.js.map +1 -1
- package/dist/schema/type-conversion/dialect/sqlite.js +9 -0
- package/dist/schema/type-conversion/dialect/sqlite.js.map +1 -1
- package/dist/schema/validator.d.ts +10 -0
- package/dist/schema/validator.d.ts.map +1 -0
- package/dist/schema/validator.js +123 -0
- package/dist/schema/validator.js.map +1 -0
- package/dist/schema-output/drizzle.d.ts +30 -0
- package/dist/schema-output/drizzle.d.ts.map +1 -0
- package/dist/{adapters/drizzle/generate.js → schema-output/drizzle.js} +82 -56
- package/dist/schema-output/drizzle.js.map +1 -0
- package/dist/schema-output/prisma.d.ts +17 -0
- package/dist/schema-output/prisma.d.ts.map +1 -0
- package/dist/schema-output/prisma.js +296 -0
- package/dist/schema-output/prisma.js.map +1 -0
- package/dist/util/default-database-adapter.js +61 -0
- package/dist/util/default-database-adapter.js.map +1 -0
- package/dist/with-database.d.ts +1 -1
- package/dist/with-database.d.ts.map +1 -1
- package/dist/with-database.js +12 -3
- package/dist/with-database.js.map +1 -1
- package/package.json +43 -28
- package/src/adapters/adapters.ts +30 -24
- package/src/adapters/drizzle/migrate-drizzle.test.ts +54 -33
- package/src/adapters/drizzle/migration-parity-drizzle-kit.test.ts +599 -0
- package/src/adapters/drizzle/test-utils.ts +12 -8
- package/src/adapters/generic-sql/driver-config.ts +38 -0
- package/src/adapters/generic-sql/generic-sql-adapter.test.ts +5 -5
- package/src/adapters/generic-sql/generic-sql-adapter.ts +110 -24
- package/src/adapters/generic-sql/generic-sql-uow-executor.test.ts +54 -0
- package/src/adapters/generic-sql/generic-sql-uow-executor.ts +231 -3
- package/src/adapters/generic-sql/migration/adapter-migration-parity.test.ts +118 -0
- package/src/adapters/generic-sql/migration/dialect/mysql.test.ts +26 -8
- package/src/adapters/generic-sql/migration/dialect/mysql.ts +46 -8
- package/src/adapters/generic-sql/migration/dialect/postgres.test.ts +25 -7
- package/src/adapters/generic-sql/migration/dialect/postgres.ts +8 -4
- package/src/adapters/generic-sql/migration/dialect/sqlite.test.ts +47 -8
- package/src/adapters/generic-sql/migration/dialect/sqlite.ts +27 -12
- package/src/adapters/generic-sql/migration/prepared-migrations.test.ts +128 -39
- package/src/adapters/generic-sql/migration/prepared-migrations.ts +15 -8
- package/src/adapters/generic-sql/migration/sql-generator.ts +142 -65
- package/src/adapters/generic-sql/query/create-sql-query-compiler.ts +9 -6
- package/src/adapters/generic-sql/query/cursor-utils.test.ts +271 -0
- package/src/adapters/generic-sql/query/cursor-utils.ts +41 -6
- package/src/adapters/generic-sql/query/generic-sql-uow-operation-compiler.test.ts +27 -27
- package/src/adapters/generic-sql/query/generic-sql-uow-operation-compiler.ts +38 -24
- package/src/adapters/generic-sql/query/select-builder.test.ts +15 -11
- package/src/adapters/generic-sql/query/select-builder.ts +6 -2
- package/src/adapters/generic-sql/query/sql-query-compiler.test.ts +52 -2
- package/src/adapters/generic-sql/query/sql-query-compiler.ts +50 -15
- package/src/adapters/generic-sql/query/where-builder.test.ts +91 -17
- package/src/adapters/generic-sql/query/where-builder.ts +90 -38
- package/src/adapters/{kysely/kysely-adapter-pglite.test.ts → generic-sql/sql-adapter-pglite-migrations.test.ts} +6 -6
- package/src/adapters/generic-sql/sql-adapter-pglite-pagination.test.ts +806 -0
- package/src/adapters/{drizzle/drizzle-adapter-pglite.test.ts → generic-sql/sql-adapter-pglite-queries.test.ts} +11 -11
- package/src/adapters/generic-sql/{test/generic-drizzle-adapter-sqlite3.test.ts → sql-adapter-sqlite3-driver.test.ts} +10 -10
- package/src/adapters/{drizzle/drizzle-adapter-sqlite3.test.ts → generic-sql/sql-adapter-sqlite3-uow.test.ts} +7 -7
- package/src/adapters/{kysely/kysely-adapter-sqlocal.test.ts → generic-sql/sql-adapter-sqlocal.test.ts} +6 -6
- package/src/adapters/generic-sql/sqlite-storage.ts +20 -0
- package/src/adapters/generic-sql/uow-decoder.test.ts +1 -1
- package/src/adapters/generic-sql/uow-decoder.ts +21 -3
- package/src/adapters/generic-sql/uow-encoder.test.ts +33 -2
- package/src/adapters/generic-sql/uow-encoder.ts +50 -11
- package/src/adapters/in-memory/condition-evaluator.test.ts +193 -0
- package/src/adapters/in-memory/condition-evaluator.ts +275 -0
- package/src/adapters/in-memory/errors.ts +20 -0
- package/src/adapters/in-memory/in-memory-adapter.ts +277 -0
- package/src/adapters/in-memory/in-memory-uow.mutations.test.ts +296 -0
- package/src/adapters/in-memory/in-memory-uow.retrieval.test.ts +100 -0
- package/src/adapters/in-memory/in-memory-uow.ts +1348 -0
- package/src/adapters/in-memory/index.ts +3 -0
- package/src/adapters/in-memory/options.test.ts +41 -0
- package/src/adapters/in-memory/options.ts +87 -0
- package/src/adapters/in-memory/reference-resolution.test.ts +50 -0
- package/src/adapters/in-memory/reference-resolution.ts +67 -0
- package/src/adapters/in-memory/sorted-array-index.test.ts +123 -0
- package/src/adapters/in-memory/sorted-array-index.ts +228 -0
- package/src/adapters/in-memory/store.test.ts +68 -0
- package/src/adapters/in-memory/store.ts +145 -0
- package/src/adapters/in-memory/value-comparison.ts +53 -0
- package/src/adapters/in-memory/value-normalization.test.ts +57 -0
- package/src/adapters/prisma/prisma-adapter-sqlite3.test.ts +1163 -0
- package/src/adapters/shared/from-unit-of-work-compiler.ts +3 -1
- package/src/adapters/shared/uow-operation-compiler.ts +26 -16
- package/src/adapters/sql/index.ts +12 -0
- package/src/db-fragment-definition-builder.test.ts +30 -12
- package/src/db-fragment-definition-builder.ts +142 -73
- package/src/db-fragment-instantiator.test.ts +105 -13
- package/src/db-fragment-integration.test.ts +9 -7
- package/src/dispatchers/cloudflare-do/index.test.ts +73 -0
- package/src/dispatchers/cloudflare-do/index.ts +104 -0
- package/src/dispatchers/node/index.test.ts +91 -0
- package/src/dispatchers/node/index.ts +87 -0
- package/src/fragments/internal-fragment.routes.ts +42 -0
- package/src/fragments/internal-fragment.schema.ts +51 -0
- package/src/fragments/internal-fragment.test.ts +458 -8
- package/src/fragments/internal-fragment.ts +322 -63
- package/src/hooks/durable-hooks-processor.test.ts +117 -0
- package/src/hooks/durable-hooks-processor.ts +67 -0
- package/src/hooks/hooks.test.ts +165 -5
- package/src/hooks/hooks.ts +197 -9
- package/src/migration-engine/auto-from-schema.test.ts +14 -14
- package/src/migration-engine/auto-from-schema.ts +5 -2
- package/src/migration-engine/create.test.ts +2 -2
- package/src/migration-engine/generation-engine.test.ts +229 -104
- package/src/migration-engine/generation-engine.ts +94 -64
- package/src/migration-engine/shared.ts +1 -0
- package/src/mod.ts +64 -26
- package/src/naming/sql-naming.ts +180 -0
- package/src/outbox/outbox-builder.ts +241 -0
- package/src/outbox/outbox.test.ts +253 -0
- package/src/outbox/outbox.ts +137 -0
- package/src/query/column-defaults.ts +41 -3
- package/src/query/condition-builder.test.ts +3 -3
- package/src/query/cursor.test.ts +116 -18
- package/src/query/cursor.ts +75 -26
- package/src/query/db-now.ts +6 -0
- package/src/query/query-type.test.ts +2 -2
- package/src/query/serialize/create-sql-serializer.ts +7 -2
- package/src/query/serialize/dialect/mysql-serializer.ts +12 -4
- package/src/query/serialize/dialect/postgres-serializer.ts +34 -4
- package/src/query/serialize/dialect/sqlite-serializer.test.ts +51 -1
- package/src/query/serialize/dialect/sqlite-serializer.ts +92 -9
- package/src/query/serialize/sql-serializer.ts +4 -4
- package/src/query/simple-query-interface.ts +5 -0
- package/src/query/unit-of-work/execute-unit-of-work.test.ts +25 -1
- package/src/query/unit-of-work/execute-unit-of-work.ts +25 -8
- package/src/query/unit-of-work/unit-of-work-coordinator.test.ts +12 -12
- package/src/query/unit-of-work/unit-of-work-types.test.ts +1 -1
- package/src/query/unit-of-work/unit-of-work.test.ts +168 -37
- package/src/query/unit-of-work/unit-of-work.ts +203 -18
- package/src/query/value-decoding.test.ts +13 -2
- package/src/query/value-decoding.ts +17 -4
- package/src/query/value-encoding.test.ts +85 -2
- package/src/query/value-encoding.ts +56 -6
- package/src/schema/create.test.ts +129 -42
- package/src/schema/create.ts +185 -47
- package/src/schema/generate-id.test.ts +2 -2
- package/src/schema/generate-id.ts +2 -2
- package/src/schema/serialize.test.ts +14 -2
- package/src/schema/type-conversion/create-sql-type-mapper.ts +7 -2
- package/src/schema/type-conversion/dialect/sqlite.ts +18 -0
- package/src/schema/type-conversion/type-mapping.test.ts +25 -1
- package/src/schema/validator.test.ts +197 -0
- package/src/schema/validator.ts +231 -0
- package/src/{adapters/drizzle/generate.test.ts → schema-output/drizzle.test.ts} +179 -129
- package/src/{adapters/drizzle/generate.ts → schema-output/drizzle.ts} +143 -93
- package/src/schema-output/prisma.test.ts +536 -0
- package/src/schema-output/prisma.ts +573 -0
- package/src/util/default-database-adapter.ts +106 -0
- package/src/with-database.ts +22 -3
- package/tsdown.config.ts +6 -4
- package/dist/adapters/drizzle/drizzle-adapter.d.ts +0 -20
- package/dist/adapters/drizzle/drizzle-adapter.d.ts.map +0 -1
- package/dist/adapters/drizzle/drizzle-adapter.js +0 -27
- package/dist/adapters/drizzle/drizzle-adapter.js.map +0 -1
- package/dist/adapters/drizzle/generate.d.ts +0 -30
- package/dist/adapters/drizzle/generate.d.ts.map +0 -1
- package/dist/adapters/drizzle/generate.js.map +0 -1
- package/dist/adapters/kysely/kysely-adapter.d.ts +0 -19
- package/dist/adapters/kysely/kysely-adapter.d.ts.map +0 -1
- package/dist/adapters/kysely/kysely-adapter.js +0 -17
- package/dist/adapters/kysely/kysely-adapter.js.map +0 -1
- package/dist/adapters/shared/table-name-mapper.d.ts +0 -12
- package/dist/adapters/shared/table-name-mapper.d.ts.map +0 -1
- package/dist/adapters/shared/table-name-mapper.js +0 -43
- package/dist/adapters/shared/table-name-mapper.js.map +0 -1
- package/dist/node_modules/.pnpm/rou3@0.7.10/node_modules/rou3/dist/index.js.map +0 -1
- package/dist/schema-generator/schema-generator.d.ts +0 -15
- package/dist/schema-generator/schema-generator.d.ts.map +0 -1
- package/src/adapters/drizzle/drizzle-adapter.ts +0 -39
- package/src/adapters/kysely/kysely-adapter.ts +0 -27
- package/src/adapters/shared/table-name-mapper.ts +0 -50
- package/src/schema-generator/schema-generator.ts +0 -12
|
@@ -5,6 +5,7 @@ import type {
|
|
|
5
5
|
UOWCompiler,
|
|
6
6
|
UOWDecoder,
|
|
7
7
|
UOWExecutor,
|
|
8
|
+
UOWInstrumentation,
|
|
8
9
|
ValidIndexName,
|
|
9
10
|
} from "../../query/unit-of-work/unit-of-work";
|
|
10
11
|
import { UnitOfWork } from "../../query/unit-of-work/unit-of-work";
|
|
@@ -25,6 +26,7 @@ export interface UnitOfWorkConfig {
|
|
|
25
26
|
* since those have to be manually executed.
|
|
26
27
|
*/
|
|
27
28
|
dryRun?: boolean;
|
|
29
|
+
instrumentation?: UOWInstrumentation;
|
|
28
30
|
}
|
|
29
31
|
|
|
30
32
|
/**
|
|
@@ -50,7 +52,7 @@ export interface UnitOfWorkFactory {
|
|
|
50
52
|
/**
|
|
51
53
|
* Optional WeakMap for schema-to-namespace lookups
|
|
52
54
|
*/
|
|
53
|
-
schemaNamespaceMap?: WeakMap<AnySchema, string>;
|
|
55
|
+
schemaNamespaceMap?: WeakMap<AnySchema, string | null>;
|
|
54
56
|
}
|
|
55
57
|
|
|
56
58
|
/**
|
|
@@ -8,7 +8,7 @@ import type {
|
|
|
8
8
|
} from "../../query/unit-of-work/unit-of-work";
|
|
9
9
|
import { Cursor } from "../../query/cursor";
|
|
10
10
|
import type { DriverConfig } from "../generic-sql/driver-config";
|
|
11
|
-
import {
|
|
11
|
+
import { createNamingResolver, type NamingResolver } from "../../naming/sql-naming";
|
|
12
12
|
|
|
13
13
|
/**
|
|
14
14
|
* Options for compiling a find operation with cursor pagination
|
|
@@ -55,24 +55,24 @@ export interface CursorConditionResult {
|
|
|
55
55
|
*/
|
|
56
56
|
export abstract class UOWOperationCompiler<TCompiledQuery> {
|
|
57
57
|
#driverConfig: DriverConfig;
|
|
58
|
-
#
|
|
58
|
+
#resolverFactory?: (schema: AnySchema, namespace: string | null) => NamingResolver;
|
|
59
59
|
|
|
60
60
|
constructor(
|
|
61
61
|
driverConfig: DriverConfig,
|
|
62
|
-
|
|
62
|
+
resolverFactory?: (schema: AnySchema, namespace: string | null) => NamingResolver,
|
|
63
63
|
) {
|
|
64
64
|
this.#driverConfig = driverConfig;
|
|
65
|
-
this.#
|
|
65
|
+
this.#resolverFactory = resolverFactory;
|
|
66
66
|
}
|
|
67
67
|
|
|
68
68
|
protected get driverConfig(): DriverConfig {
|
|
69
69
|
return this.#driverConfig;
|
|
70
70
|
}
|
|
71
71
|
|
|
72
|
-
protected get
|
|
73
|
-
| ((namespace: string |
|
|
72
|
+
protected get resolverFactory():
|
|
73
|
+
| ((schema: AnySchema, namespace: string | null) => NamingResolver)
|
|
74
74
|
| undefined {
|
|
75
|
-
return this.#
|
|
75
|
+
return this.#resolverFactory;
|
|
76
76
|
}
|
|
77
77
|
|
|
78
78
|
abstract compileCount(
|
|
@@ -105,12 +105,18 @@ export abstract class UOWOperationCompiler<TCompiledQuery> {
|
|
|
105
105
|
/**
|
|
106
106
|
* Get the mapper for a specific operation based on its namespace
|
|
107
107
|
*/
|
|
108
|
-
protected
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
108
|
+
protected getNamingResolver(
|
|
109
|
+
schema: AnySchema,
|
|
110
|
+
namespace: string | null | undefined,
|
|
111
|
+
): NamingResolver {
|
|
112
|
+
if (this.#resolverFactory) {
|
|
113
|
+
return this.#resolverFactory(schema, namespace ?? null);
|
|
114
|
+
}
|
|
115
|
+
return createNamingResolver(
|
|
116
|
+
schema,
|
|
117
|
+
namespace ?? null,
|
|
118
|
+
this.#driverConfig.defaultNamingStrategy,
|
|
119
|
+
);
|
|
114
120
|
}
|
|
115
121
|
|
|
116
122
|
/**
|
|
@@ -154,9 +160,13 @@ export abstract class UOWOperationCompiler<TCompiledQuery> {
|
|
|
154
160
|
/**
|
|
155
161
|
* Get the physical table name for an operation, applying namespace mapping if needed
|
|
156
162
|
*/
|
|
157
|
-
protected getPhysicalTableName(
|
|
158
|
-
|
|
159
|
-
|
|
163
|
+
protected getPhysicalTableName(
|
|
164
|
+
schema: AnySchema,
|
|
165
|
+
logicalName: string,
|
|
166
|
+
namespace: string | undefined,
|
|
167
|
+
): string {
|
|
168
|
+
const resolver = this.getNamingResolver(schema, namespace ?? null);
|
|
169
|
+
return resolver.getTableName(logicalName);
|
|
160
170
|
}
|
|
161
171
|
}
|
|
162
172
|
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export {
|
|
2
|
+
SqlAdapter,
|
|
3
|
+
type SqlAdapterOptions,
|
|
4
|
+
type UnitOfWorkConfig,
|
|
5
|
+
type OutboxConfig,
|
|
6
|
+
sqliteProfiles,
|
|
7
|
+
sqliteStorageDefault,
|
|
8
|
+
sqliteStoragePrisma,
|
|
9
|
+
type SQLiteStorageMode,
|
|
10
|
+
} from "../generic-sql/generic-sql-adapter";
|
|
11
|
+
|
|
12
|
+
export type { SQLiteProfile } from "../adapters";
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import fs from "node:fs";
|
|
2
|
+
import os from "node:os";
|
|
3
|
+
import path from "node:path";
|
|
1
4
|
import { describe, it, expect, vi, expectTypeOf } from "vitest";
|
|
2
5
|
import { defineFragment } from "@fragno-dev/core";
|
|
3
6
|
import {
|
|
@@ -9,9 +12,11 @@ import { schema, column, idColumn } from "./schema/create";
|
|
|
9
12
|
import type { SimpleQueryInterface } from "./query/simple-query-interface";
|
|
10
13
|
import type { DatabaseAdapter } from "./adapters/adapters";
|
|
11
14
|
import * as executeUnitOfWork from "./query/unit-of-work/execute-unit-of-work";
|
|
15
|
+
import { RequestContextStorage } from "@fragno-dev/core/internal/request-context-storage";
|
|
16
|
+
import { suffixNamingStrategy } from "./naming/sql-naming";
|
|
12
17
|
|
|
13
18
|
// Create a test schema
|
|
14
|
-
const testSchema = schema((s) => {
|
|
19
|
+
const testSchema = schema("test", (s) => {
|
|
15
20
|
return s.addTable("users", (t) => {
|
|
16
21
|
return t
|
|
17
22
|
.addColumn("id", idColumn())
|
|
@@ -29,13 +34,17 @@ function createMockAdapter(): DatabaseAdapter {
|
|
|
29
34
|
forSchema: vi.fn(),
|
|
30
35
|
executeRetrieve: vi.fn(),
|
|
31
36
|
executeMutations: vi.fn(),
|
|
37
|
+
registerSchema: vi.fn(),
|
|
38
|
+
reset: vi.fn(),
|
|
32
39
|
})),
|
|
33
40
|
} as unknown as SimpleQueryInterface<TestSchema>;
|
|
34
41
|
|
|
35
42
|
return {
|
|
36
43
|
createQueryEngine: vi.fn(() => mockdb),
|
|
37
|
-
|
|
44
|
+
getSchemaVersion: vi.fn(async () => undefined),
|
|
38
45
|
close: vi.fn(),
|
|
46
|
+
contextStorage: new RequestContextStorage(),
|
|
47
|
+
namingStrategy: suffixNamingStrategy,
|
|
39
48
|
} as unknown as DatabaseAdapter;
|
|
40
49
|
}
|
|
41
50
|
|
|
@@ -735,10 +744,7 @@ describe("DatabaseFragmentDefinitionBuilder", () => {
|
|
|
735
744
|
|
|
736
745
|
const mockAdapter = createMockAdapter();
|
|
737
746
|
|
|
738
|
-
const definition = withDatabase(
|
|
739
|
-
testSchema,
|
|
740
|
-
"my-namespace",
|
|
741
|
-
)(defineFragment<Config>("complex-db-frag"))
|
|
747
|
+
const definition = withDatabase(testSchema)(defineFragment<Config>("complex-db-frag"))
|
|
742
748
|
.withDependencies(({ config }) => ({
|
|
743
749
|
connectionString: config.dbConnectionString,
|
|
744
750
|
debug: config.debug,
|
|
@@ -806,17 +812,29 @@ describe("DatabaseFragmentDefinitionBuilder", () => {
|
|
|
806
812
|
});
|
|
807
813
|
});
|
|
808
814
|
|
|
809
|
-
describe("
|
|
810
|
-
it("should
|
|
815
|
+
describe("default adapter", () => {
|
|
816
|
+
it("should default to sqlite adapter when database adapter is missing", () => {
|
|
817
|
+
const previous = process.env["FRAGNO_DATA_DIR"];
|
|
818
|
+
const dataDir = fs.mkdtempSync(path.join(os.tmpdir(), "fragno-db-default-"));
|
|
819
|
+
process.env["FRAGNO_DATA_DIR"] = dataDir;
|
|
820
|
+
|
|
811
821
|
const definition = withDatabase(testSchema)(defineFragment("db-frag")).build();
|
|
812
822
|
|
|
813
|
-
|
|
814
|
-
definition.dependencies!({
|
|
823
|
+
try {
|
|
824
|
+
const deps = definition.dependencies!({
|
|
815
825
|
config: {},
|
|
816
|
-
// @ts-expect-error No databaseAdapter - intentionally invalid for runtime error test
|
|
817
826
|
options: {},
|
|
818
827
|
});
|
|
819
|
-
|
|
828
|
+
|
|
829
|
+
expect(deps.db).toBeDefined();
|
|
830
|
+
expect(deps.createUnitOfWork).toBeDefined();
|
|
831
|
+
} finally {
|
|
832
|
+
if (previous === undefined) {
|
|
833
|
+
delete process.env["FRAGNO_DATA_DIR"];
|
|
834
|
+
} else {
|
|
835
|
+
process.env["FRAGNO_DATA_DIR"] = previous;
|
|
836
|
+
}
|
|
837
|
+
}
|
|
820
838
|
});
|
|
821
839
|
});
|
|
822
840
|
|
|
@@ -21,20 +21,34 @@ import {
|
|
|
21
21
|
} from "./query/unit-of-work/execute-unit-of-work";
|
|
22
22
|
import {
|
|
23
23
|
prepareHookMutations,
|
|
24
|
-
processHooks,
|
|
25
24
|
type HooksMap,
|
|
26
25
|
type HookFn,
|
|
27
26
|
type HookContext,
|
|
27
|
+
type HookProcessorConfig,
|
|
28
|
+
type DurableHooksProcessingOptions,
|
|
29
|
+
createHookScheduler,
|
|
28
30
|
} from "./hooks/hooks";
|
|
29
31
|
import type { InternalFragmentInstance } from "./fragments/internal-fragment";
|
|
32
|
+
import { resolveDatabaseAdapter } from "./util/default-database-adapter";
|
|
33
|
+
import { sanitizeNamespace } from "./naming/sql-naming";
|
|
30
34
|
|
|
31
35
|
/**
|
|
32
|
-
* Extended FragnoPublicConfig
|
|
33
|
-
*
|
|
36
|
+
* Extended FragnoPublicConfig for database fragments.
|
|
37
|
+
* If databaseAdapter is omitted and better-sqlite3 is available, a default SQLite adapter is used.
|
|
34
38
|
*/
|
|
35
39
|
export type FragnoPublicConfigWithDatabase = FragnoPublicConfig & {
|
|
36
40
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
37
|
-
databaseAdapter
|
|
41
|
+
databaseAdapter?: DatabaseAdapter<any>;
|
|
42
|
+
/**
|
|
43
|
+
* Optional durable hooks processing configuration.
|
|
44
|
+
*/
|
|
45
|
+
durableHooks?: DurableHooksProcessingOptions;
|
|
46
|
+
/**
|
|
47
|
+
* Optional override for database namespace. If provided (including null), it is used as-is
|
|
48
|
+
* without sanitization — the caller is responsible for providing a valid namespace.
|
|
49
|
+
* When omitted, defaults to a sanitized version of schema.name.
|
|
50
|
+
*/
|
|
51
|
+
databaseNamespace?: string | null;
|
|
38
52
|
};
|
|
39
53
|
|
|
40
54
|
/**
|
|
@@ -44,6 +58,7 @@ export type FragnoPublicConfigWithDatabase = FragnoPublicConfig & {
|
|
|
44
58
|
export type ImplicitDatabaseDependencies<TSchema extends AnySchema> = {
|
|
45
59
|
/**
|
|
46
60
|
* Database query engine for the fragment's schema.
|
|
61
|
+
* @deprecated Prefer handlerTx/serviceTx instead of direct db usage.
|
|
47
62
|
*/
|
|
48
63
|
db: SimpleQueryInterface<TSchema>;
|
|
49
64
|
/**
|
|
@@ -53,7 +68,7 @@ export type ImplicitDatabaseDependencies<TSchema extends AnySchema> = {
|
|
|
53
68
|
/**
|
|
54
69
|
* The database namespace for this fragment.
|
|
55
70
|
*/
|
|
56
|
-
namespace: string;
|
|
71
|
+
namespace: string | null;
|
|
57
72
|
/**
|
|
58
73
|
* Create a new Unit of Work for database operations.
|
|
59
74
|
*/
|
|
@@ -145,21 +160,23 @@ export type DatabaseFragmentContext<TSchema extends AnySchema> = {
|
|
|
145
160
|
function createDatabaseContext<TSchema extends AnySchema>(
|
|
146
161
|
options: FragnoPublicConfigWithDatabase,
|
|
147
162
|
schema: TSchema,
|
|
148
|
-
namespace: string,
|
|
149
163
|
): DatabaseFragmentContext<TSchema> {
|
|
150
|
-
const databaseAdapter = options
|
|
151
|
-
|
|
152
|
-
if (!databaseAdapter) {
|
|
153
|
-
throw new Error(
|
|
154
|
-
"Database fragment requires a database adapter to be provided in options.databaseAdapter",
|
|
155
|
-
);
|
|
156
|
-
}
|
|
164
|
+
const databaseAdapter = resolveDatabaseAdapter(options, schema);
|
|
157
165
|
|
|
166
|
+
const namespace = resolveDatabaseNamespace(options, schema);
|
|
158
167
|
const db = databaseAdapter.createQueryEngine(schema, namespace);
|
|
159
168
|
|
|
160
169
|
return { databaseAdapter, db };
|
|
161
170
|
}
|
|
162
171
|
|
|
172
|
+
function resolveDatabaseNamespace<TSchema extends AnySchema>(
|
|
173
|
+
options: FragnoPublicConfigWithDatabase,
|
|
174
|
+
schema: TSchema,
|
|
175
|
+
): string | null {
|
|
176
|
+
const hasOverride = options.databaseNamespace !== undefined;
|
|
177
|
+
return hasOverride ? (options.databaseNamespace ?? null) : sanitizeNamespace(schema.name);
|
|
178
|
+
}
|
|
179
|
+
|
|
163
180
|
/**
|
|
164
181
|
* Storage type for database fragments - stores the Unit of Work.
|
|
165
182
|
*/
|
|
@@ -171,7 +188,7 @@ export type DatabaseRequestStorage = {
|
|
|
171
188
|
* Builder for database fragments that wraps the core fragment builder
|
|
172
189
|
* and provides database-specific functionality.
|
|
173
190
|
*
|
|
174
|
-
* Database fragments
|
|
191
|
+
* Database fragments use FragnoPublicConfigWithDatabase and default the adapter when possible.
|
|
175
192
|
*/
|
|
176
193
|
export class DatabaseFragmentDefinitionBuilder<
|
|
177
194
|
TSchema extends AnySchema,
|
|
@@ -201,7 +218,6 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
201
218
|
TLinkedFragments
|
|
202
219
|
>;
|
|
203
220
|
#schema: TSchema;
|
|
204
|
-
#namespace: string;
|
|
205
221
|
#hooksFactory?: (context: { config: TConfig; options: FragnoPublicConfigWithDatabase }) => THooks;
|
|
206
222
|
|
|
207
223
|
constructor(
|
|
@@ -219,7 +235,6 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
219
235
|
TLinkedFragments
|
|
220
236
|
>,
|
|
221
237
|
schema: TSchema,
|
|
222
|
-
namespace?: string,
|
|
223
238
|
hooksFactory?: (context: {
|
|
224
239
|
config: TConfig;
|
|
225
240
|
options: FragnoPublicConfigWithDatabase;
|
|
@@ -227,7 +242,6 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
227
242
|
) {
|
|
228
243
|
this.#baseBuilder = baseBuilder;
|
|
229
244
|
this.#schema = schema;
|
|
230
|
-
this.#namespace = namespace ?? baseBuilder.name;
|
|
231
245
|
this.#hooksFactory = hooksFactory;
|
|
232
246
|
}
|
|
233
247
|
|
|
@@ -257,7 +271,8 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
257
271
|
> {
|
|
258
272
|
// Wrap user function to inject DB context
|
|
259
273
|
const wrappedFn = (context: { config: TConfig; options: FragnoPublicConfigWithDatabase }) => {
|
|
260
|
-
const dbContext = createDatabaseContext(context.options, this.#schema
|
|
274
|
+
const dbContext = createDatabaseContext(context.options, this.#schema);
|
|
275
|
+
const namespace = resolveDatabaseNamespace(context.options, this.#schema);
|
|
261
276
|
|
|
262
277
|
// Call user function with enriched context
|
|
263
278
|
const userDeps = fn({
|
|
@@ -272,7 +287,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
272
287
|
const implicitDeps: ImplicitDatabaseDependencies<TSchema> = {
|
|
273
288
|
db: dbContext.db,
|
|
274
289
|
schema: this.#schema,
|
|
275
|
-
namespace
|
|
290
|
+
namespace,
|
|
276
291
|
createUnitOfWork: createUow,
|
|
277
292
|
};
|
|
278
293
|
|
|
@@ -285,12 +300,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
285
300
|
// Create new base builder with wrapped function
|
|
286
301
|
const newBaseBuilder = this.#baseBuilder.withDependencies(wrappedFn);
|
|
287
302
|
|
|
288
|
-
return new DatabaseFragmentDefinitionBuilder(
|
|
289
|
-
newBaseBuilder,
|
|
290
|
-
this.#schema,
|
|
291
|
-
this.#namespace,
|
|
292
|
-
this.#hooksFactory,
|
|
293
|
-
);
|
|
303
|
+
return new DatabaseFragmentDefinitionBuilder(newBaseBuilder, this.#schema, this.#hooksFactory);
|
|
294
304
|
}
|
|
295
305
|
|
|
296
306
|
providesBaseService<TNewService>(
|
|
@@ -318,12 +328,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
318
328
|
> {
|
|
319
329
|
const newBaseBuilder = this.#baseBuilder.providesBaseService<TNewService>(fn);
|
|
320
330
|
|
|
321
|
-
return new DatabaseFragmentDefinitionBuilder(
|
|
322
|
-
newBaseBuilder,
|
|
323
|
-
this.#schema,
|
|
324
|
-
this.#namespace,
|
|
325
|
-
this.#hooksFactory,
|
|
326
|
-
);
|
|
331
|
+
return new DatabaseFragmentDefinitionBuilder(newBaseBuilder, this.#schema, this.#hooksFactory);
|
|
327
332
|
}
|
|
328
333
|
|
|
329
334
|
providesService<TServiceName extends string, TService>(
|
|
@@ -355,12 +360,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
355
360
|
fn,
|
|
356
361
|
);
|
|
357
362
|
|
|
358
|
-
return new DatabaseFragmentDefinitionBuilder(
|
|
359
|
-
newBaseBuilder,
|
|
360
|
-
this.#schema,
|
|
361
|
-
this.#namespace,
|
|
362
|
-
this.#hooksFactory,
|
|
363
|
-
);
|
|
363
|
+
return new DatabaseFragmentDefinitionBuilder(newBaseBuilder, this.#schema, this.#hooksFactory);
|
|
364
364
|
}
|
|
365
365
|
|
|
366
366
|
/**
|
|
@@ -399,12 +399,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
399
399
|
fn,
|
|
400
400
|
);
|
|
401
401
|
|
|
402
|
-
return new DatabaseFragmentDefinitionBuilder(
|
|
403
|
-
newBaseBuilder,
|
|
404
|
-
this.#schema,
|
|
405
|
-
this.#namespace,
|
|
406
|
-
this.#hooksFactory,
|
|
407
|
-
);
|
|
402
|
+
return new DatabaseFragmentDefinitionBuilder(newBaseBuilder, this.#schema, this.#hooksFactory);
|
|
408
403
|
}
|
|
409
404
|
|
|
410
405
|
/**
|
|
@@ -468,7 +463,6 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
468
463
|
const newBuilder = new DatabaseFragmentDefinitionBuilder(
|
|
469
464
|
this.#baseBuilder,
|
|
470
465
|
this.#schema,
|
|
471
|
-
this.#namespace,
|
|
472
466
|
) as unknown as DatabaseFragmentDefinitionBuilder<
|
|
473
467
|
TSchema,
|
|
474
468
|
TConfig,
|
|
@@ -509,12 +503,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
509
503
|
> {
|
|
510
504
|
const newBaseBuilder = this.#baseBuilder.usesService<TServiceName, TService>(serviceName);
|
|
511
505
|
|
|
512
|
-
return new DatabaseFragmentDefinitionBuilder(
|
|
513
|
-
newBaseBuilder,
|
|
514
|
-
this.#schema,
|
|
515
|
-
this.#namespace,
|
|
516
|
-
this.#hooksFactory,
|
|
517
|
-
);
|
|
506
|
+
return new DatabaseFragmentDefinitionBuilder(newBaseBuilder, this.#schema, this.#hooksFactory);
|
|
518
507
|
}
|
|
519
508
|
|
|
520
509
|
/**
|
|
@@ -540,12 +529,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
540
529
|
serviceName,
|
|
541
530
|
);
|
|
542
531
|
|
|
543
|
-
return new DatabaseFragmentDefinitionBuilder(
|
|
544
|
-
newBaseBuilder,
|
|
545
|
-
this.#schema,
|
|
546
|
-
this.#namespace,
|
|
547
|
-
this.#hooksFactory,
|
|
548
|
-
);
|
|
532
|
+
return new DatabaseFragmentDefinitionBuilder(newBaseBuilder, this.#schema, this.#hooksFactory);
|
|
549
533
|
}
|
|
550
534
|
|
|
551
535
|
/**
|
|
@@ -594,12 +578,13 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
594
578
|
}
|
|
595
579
|
}
|
|
596
580
|
|
|
597
|
-
const { db } = createDatabaseContext(context.options, this.#schema
|
|
581
|
+
const { db } = createDatabaseContext(context.options, this.#schema);
|
|
582
|
+
const namespace = resolveDatabaseNamespace(context.options, this.#schema);
|
|
598
583
|
|
|
599
584
|
const implicitDeps: ImplicitDatabaseDependencies<TSchema> = {
|
|
600
585
|
db,
|
|
601
586
|
schema: this.#schema,
|
|
602
|
-
namespace
|
|
587
|
+
namespace,
|
|
603
588
|
createUnitOfWork: () => db.createUnitOfWork(),
|
|
604
589
|
};
|
|
605
590
|
|
|
@@ -612,7 +597,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
612
597
|
// Use the adapter's shared context storage (all fragments using the same adapter share this storage)
|
|
613
598
|
const builderWithExternalStorage = this.#baseBuilder.withExternalRequestStorage(
|
|
614
599
|
({ options }) => {
|
|
615
|
-
const dbContext = createDatabaseContext(options, this.#schema
|
|
600
|
+
const dbContext = createDatabaseContext(options, this.#schema);
|
|
616
601
|
return dbContext.databaseAdapter.contextStorage;
|
|
617
602
|
},
|
|
618
603
|
);
|
|
@@ -621,7 +606,7 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
621
606
|
const builderWithStorage = builderWithExternalStorage.withRequestStorage(
|
|
622
607
|
({ options }): DatabaseRequestStorage => {
|
|
623
608
|
// Create database context - needed here to create the UOW
|
|
624
|
-
const dbContextForStorage = createDatabaseContext(options, this.#schema
|
|
609
|
+
const dbContextForStorage = createDatabaseContext(options, this.#schema);
|
|
625
610
|
|
|
626
611
|
// Create a new Unit of Work for this request
|
|
627
612
|
const uow: IUnitOfWork = dbContextForStorage.db.createUnitOfWork();
|
|
@@ -637,18 +622,91 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
637
622
|
options: FragnoPublicConfigWithDatabase;
|
|
638
623
|
}) => InternalFragmentInstance;
|
|
639
624
|
|
|
625
|
+
// Cache per instantiated fragment (deps object is unique per instantiation).
|
|
626
|
+
const hooksConfigCache = new WeakMap<object, HookProcessorConfig<THooks>>();
|
|
627
|
+
|
|
628
|
+
const createHooksConfig = (context: {
|
|
629
|
+
config: TConfig;
|
|
630
|
+
options: FragnoPublicConfigWithDatabase;
|
|
631
|
+
deps: TDeps;
|
|
632
|
+
}) => {
|
|
633
|
+
if (!this.#hooksFactory) {
|
|
634
|
+
return undefined;
|
|
635
|
+
}
|
|
636
|
+
const depsKey =
|
|
637
|
+
typeof context.deps === "object" && context.deps !== null
|
|
638
|
+
? (context.deps as object)
|
|
639
|
+
: undefined;
|
|
640
|
+
const cachedHooksConfig = depsKey ? hooksConfigCache.get(depsKey) : undefined;
|
|
641
|
+
if (cachedHooksConfig) {
|
|
642
|
+
return cachedHooksConfig;
|
|
643
|
+
}
|
|
644
|
+
|
|
645
|
+
const namespace = resolveDatabaseNamespace(context.options, this.#schema);
|
|
646
|
+
const namespaceKey = namespace ?? this.#schema.name;
|
|
647
|
+
const durableHooksOptions = context.options.durableHooks;
|
|
648
|
+
const baseAdapter = resolveDatabaseAdapter(context.options, this.#schema);
|
|
649
|
+
const hookAdapter = baseAdapter.getHookProcessingAdapter?.() ?? baseAdapter;
|
|
650
|
+
const hookOptions =
|
|
651
|
+
hookAdapter === baseAdapter
|
|
652
|
+
? context.options
|
|
653
|
+
: { ...context.options, databaseAdapter: hookAdapter };
|
|
654
|
+
const dbContextForHooks = createDatabaseContext(hookOptions, this.#schema);
|
|
655
|
+
const hooksConfig: HookProcessorConfig<THooks> = {
|
|
656
|
+
hooks: this.#hooksFactory(context),
|
|
657
|
+
namespace: namespaceKey,
|
|
658
|
+
internalFragment: internalFragmentFactory({
|
|
659
|
+
config: context.config,
|
|
660
|
+
options: hookOptions,
|
|
661
|
+
}),
|
|
662
|
+
handlerTx: (execOptions?: Omit<ExecuteTxOptions, "createUnitOfWork">) => {
|
|
663
|
+
const userOnBeforeMutate = execOptions?.onBeforeMutate;
|
|
664
|
+
const userOnAfterMutate = execOptions?.onAfterMutate;
|
|
665
|
+
return createHandlerTxBuilder<THooks>({
|
|
666
|
+
...execOptions,
|
|
667
|
+
createUnitOfWork: () => {
|
|
668
|
+
const uow = dbContextForHooks.db.createUnitOfWork();
|
|
669
|
+
uow.registerSchema(
|
|
670
|
+
hooksConfig.internalFragment.$internal.deps.schema,
|
|
671
|
+
hooksConfig.internalFragment.$internal.deps.namespace,
|
|
672
|
+
);
|
|
673
|
+
return uow;
|
|
674
|
+
},
|
|
675
|
+
onBeforeMutate: (uow) => {
|
|
676
|
+
prepareHookMutations(uow, hooksConfig);
|
|
677
|
+
if (userOnBeforeMutate) {
|
|
678
|
+
userOnBeforeMutate(uow);
|
|
679
|
+
}
|
|
680
|
+
},
|
|
681
|
+
onAfterMutate: async (uow) => {
|
|
682
|
+
void hooksConfig.scheduler?.schedule().catch((error) => {
|
|
683
|
+
console.error("Durable hooks processing failed", error);
|
|
684
|
+
});
|
|
685
|
+
if (userOnAfterMutate) {
|
|
686
|
+
await userOnAfterMutate(uow);
|
|
687
|
+
}
|
|
688
|
+
},
|
|
689
|
+
});
|
|
690
|
+
},
|
|
691
|
+
stuckProcessingTimeoutMinutes: durableHooksOptions?.stuckProcessingTimeoutMinutes,
|
|
692
|
+
onStuckProcessingHooks: durableHooksOptions?.onStuckProcessingHooks,
|
|
693
|
+
};
|
|
694
|
+
hooksConfig.scheduler = createHookScheduler(hooksConfig);
|
|
695
|
+
if (depsKey) {
|
|
696
|
+
hooksConfigCache.set(depsKey, hooksConfig);
|
|
697
|
+
}
|
|
698
|
+
return hooksConfig;
|
|
699
|
+
};
|
|
700
|
+
|
|
640
701
|
const builderWithContext = builderWithStorage.withThisContext<
|
|
641
702
|
DatabaseServiceContext<THooks>,
|
|
642
703
|
DatabaseHandlerContext<THooks>
|
|
643
|
-
>(({ storage, config, options }) => {
|
|
704
|
+
>(({ storage, config, options, deps }) => {
|
|
644
705
|
// Create hooks config if hooks factory is defined
|
|
645
|
-
const hooksConfig =
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
internalFragment: internalFragmentFactory({ config, options }),
|
|
650
|
-
}
|
|
651
|
-
: undefined;
|
|
706
|
+
const hooksConfig = createHooksConfig({ config, options, deps });
|
|
707
|
+
const internalFragment =
|
|
708
|
+
hooksConfig?.internalFragment ??
|
|
709
|
+
(internalFragmentFactory ? internalFragmentFactory({ config, options }) : undefined);
|
|
652
710
|
|
|
653
711
|
// Builder API: serviceTx using createServiceTxBuilder
|
|
654
712
|
function serviceTx<TSchema extends AnySchema>(schema: TSchema) {
|
|
@@ -681,10 +739,10 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
681
739
|
...execOptions,
|
|
682
740
|
createUnitOfWork: () => {
|
|
683
741
|
currentStorage.uow.reset();
|
|
684
|
-
if (
|
|
742
|
+
if (internalFragment) {
|
|
685
743
|
currentStorage.uow.registerSchema(
|
|
686
|
-
|
|
687
|
-
|
|
744
|
+
internalFragment.$internal.deps.schema,
|
|
745
|
+
internalFragment.$internal.deps.namespace,
|
|
688
746
|
);
|
|
689
747
|
}
|
|
690
748
|
return currentStorage.uow;
|
|
@@ -698,8 +756,10 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
698
756
|
}
|
|
699
757
|
},
|
|
700
758
|
onAfterMutate: async (uow) => {
|
|
701
|
-
if (hooksConfig) {
|
|
702
|
-
|
|
759
|
+
if (hooksConfig?.scheduler) {
|
|
760
|
+
void hooksConfig.scheduler.schedule().catch((error) => {
|
|
761
|
+
console.error("Durable hooks processing failed", error);
|
|
762
|
+
});
|
|
703
763
|
}
|
|
704
764
|
if (userOnAfterMutate) {
|
|
705
765
|
await userOnAfterMutate(uow);
|
|
@@ -717,6 +777,15 @@ export class DatabaseFragmentDefinitionBuilder<
|
|
|
717
777
|
|
|
718
778
|
// Build the final definition
|
|
719
779
|
const finalDef = builderWithContext.build();
|
|
780
|
+
if (this.#hooksFactory) {
|
|
781
|
+
finalDef.internalDataFactory = ({ config, options, deps }) => ({
|
|
782
|
+
durableHooks: createHooksConfig({
|
|
783
|
+
config: config as TConfig,
|
|
784
|
+
options: options as FragnoPublicConfigWithDatabase,
|
|
785
|
+
deps: deps as TDeps,
|
|
786
|
+
}),
|
|
787
|
+
});
|
|
788
|
+
}
|
|
720
789
|
|
|
721
790
|
// Return the complete definition with proper typing and dependencies
|
|
722
791
|
return {
|