@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
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { FragnoId } from "../schema/create.js";
|
|
2
|
+
|
|
3
|
+
//#region src/outbox/outbox.d.ts
|
|
4
|
+
type OutboxConfig = {
|
|
5
|
+
enabled: boolean;
|
|
6
|
+
};
|
|
7
|
+
type OutboxPayload = {
|
|
8
|
+
version: 1;
|
|
9
|
+
mutations: OutboxMutation[];
|
|
10
|
+
};
|
|
11
|
+
type OutboxMutation = {
|
|
12
|
+
op: "create";
|
|
13
|
+
schema: string;
|
|
14
|
+
namespace?: string;
|
|
15
|
+
table: string;
|
|
16
|
+
externalId: string;
|
|
17
|
+
versionstamp: string;
|
|
18
|
+
values: Record<string, unknown>;
|
|
19
|
+
} | {
|
|
20
|
+
op: "update";
|
|
21
|
+
schema: string;
|
|
22
|
+
namespace?: string;
|
|
23
|
+
table: string;
|
|
24
|
+
externalId: string;
|
|
25
|
+
versionstamp: string;
|
|
26
|
+
set: Record<string, unknown>;
|
|
27
|
+
checkVersion?: number;
|
|
28
|
+
} | {
|
|
29
|
+
op: "delete";
|
|
30
|
+
schema: string;
|
|
31
|
+
namespace?: string;
|
|
32
|
+
table: string;
|
|
33
|
+
externalId: string;
|
|
34
|
+
versionstamp: string;
|
|
35
|
+
checkVersion?: number;
|
|
36
|
+
};
|
|
37
|
+
type OutboxRefMap = Record<string, string>;
|
|
38
|
+
type OutboxPayloadSerialized = {
|
|
39
|
+
json: unknown;
|
|
40
|
+
meta?: Record<string, unknown>;
|
|
41
|
+
};
|
|
42
|
+
type OutboxEntry = {
|
|
43
|
+
id: FragnoId;
|
|
44
|
+
versionstamp: string;
|
|
45
|
+
uowId: string;
|
|
46
|
+
payload: OutboxPayloadSerialized;
|
|
47
|
+
refMap?: OutboxRefMap;
|
|
48
|
+
createdAt: Date;
|
|
49
|
+
};
|
|
50
|
+
//#endregion
|
|
51
|
+
export { OutboxConfig, OutboxEntry, OutboxMutation, OutboxPayload, OutboxRefMap };
|
|
52
|
+
//# sourceMappingURL=outbox.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"outbox.d.ts","names":[],"sources":["../../src/outbox/outbox.ts"],"sourcesContent":[],"mappings":";;;KAEY,YAAA;;AAAZ,CAAA;AAcY,KALA,aAAA,GAKc;EA8Bd,OAAA,EAAA,CAAA;EAEA,SAAA,EAnCC,cAmCD,EAAuB;AAKnC,CAAA;AACM,KAtCM,cAAA,GAsCN;EAGK,EAAA,EAAA,QAAA;EACA,MAAA,EAAA,MAAA;EACE,SAAA,CAAA,EAAA,MAAA;EAAI,KAAA,EAAA,MAAA;;;UAnCH;;;;;;;;OASH;;;;;;;;;;;KAaC,YAAA,GAAe;KAEf,uBAAA;;SAEH;;KAGG,WAAA;MACN;;;WAGK;WACA;aACE"}
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
//#region src/outbox/outbox.ts
|
|
2
|
+
function encodeVersionstamp(transactionVersion, userVersion) {
|
|
3
|
+
if (userVersion < 0 || userVersion > 65535) throw new Error(`Invalid outbox user version: ${userVersion}`);
|
|
4
|
+
const txBytes = bigintToBytes(transactionVersion, 10);
|
|
5
|
+
const userBytes = new Uint8Array(2);
|
|
6
|
+
userBytes[0] = userVersion >> 8 & 255;
|
|
7
|
+
userBytes[1] = userVersion & 255;
|
|
8
|
+
const combined = new Uint8Array(12);
|
|
9
|
+
combined.set(txBytes, 0);
|
|
10
|
+
combined.set(userBytes, 10);
|
|
11
|
+
return combined;
|
|
12
|
+
}
|
|
13
|
+
function versionstampToHex(bytes) {
|
|
14
|
+
let hex = "";
|
|
15
|
+
for (const byte of bytes) hex += byte.toString(16).padStart(2, "0");
|
|
16
|
+
return hex;
|
|
17
|
+
}
|
|
18
|
+
function parseOutboxVersionValue(value) {
|
|
19
|
+
if (typeof value === "bigint") return value;
|
|
20
|
+
if (typeof value === "number") return BigInt(value);
|
|
21
|
+
if (typeof value === "string") return BigInt(value);
|
|
22
|
+
throw new Error(`Invalid outbox version value: ${String(value)}`);
|
|
23
|
+
}
|
|
24
|
+
function bigintToBytes(value, length) {
|
|
25
|
+
const bytes = new Uint8Array(length);
|
|
26
|
+
let remaining = value;
|
|
27
|
+
for (let i = length - 1; i >= 0; i -= 1) {
|
|
28
|
+
bytes[i] = Number(remaining & 255n);
|
|
29
|
+
remaining >>= 8n;
|
|
30
|
+
}
|
|
31
|
+
if (remaining !== 0n) throw new Error(`Outbox version ${value} exceeds ${length * 8} bits`);
|
|
32
|
+
return bytes;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
//#endregion
|
|
36
|
+
export { encodeVersionstamp, parseOutboxVersionValue, versionstampToHex };
|
|
37
|
+
//# sourceMappingURL=outbox.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"outbox.js","names":[],"sources":["../../src/outbox/outbox.ts"],"sourcesContent":["import type { AnyTable, FragnoId } from \"../schema/create\";\n\nexport type OutboxConfig = {\n enabled: boolean;\n};\n\nexport type OutboxVersionstampStrategy =\n | \"update-returning\"\n | \"insert-on-conflict-returning\"\n | \"insert-on-duplicate-last-insert-id\";\n\nexport type OutboxPayload = {\n version: 1;\n mutations: OutboxMutation[];\n};\n\nexport type OutboxMutation =\n | {\n op: \"create\";\n schema: string;\n namespace?: string;\n table: string;\n externalId: string;\n versionstamp: string;\n values: Record<string, unknown>;\n }\n | {\n op: \"update\";\n schema: string;\n namespace?: string;\n table: string;\n externalId: string;\n versionstamp: string;\n set: Record<string, unknown>;\n checkVersion?: number;\n }\n | {\n op: \"delete\";\n schema: string;\n namespace?: string;\n table: string;\n externalId: string;\n versionstamp: string;\n checkVersion?: number;\n };\n\nexport type OutboxRefMap = Record<string, string>;\n\nexport type OutboxPayloadSerialized = {\n json: unknown;\n meta?: Record<string, unknown>;\n};\n\nexport type OutboxEntry = {\n id: FragnoId;\n versionstamp: string;\n uowId: string;\n payload: OutboxPayloadSerialized;\n refMap?: OutboxRefMap;\n createdAt: Date;\n};\n\nexport type OutboxRefLookup = {\n key: string;\n internalId: bigint | number;\n table: AnyTable;\n namespace?: string;\n};\n\nexport function encodeVersionstamp(transactionVersion: bigint, userVersion: number): Uint8Array {\n if (userVersion < 0 || userVersion > 0xffff) {\n throw new Error(`Invalid outbox user version: ${userVersion}`);\n }\n\n const txBytes = bigintToBytes(transactionVersion, 10);\n const userBytes = new Uint8Array(2);\n userBytes[0] = (userVersion >> 8) & 0xff;\n userBytes[1] = userVersion & 0xff;\n\n const combined = new Uint8Array(12);\n combined.set(txBytes, 0);\n combined.set(userBytes, 10);\n\n return combined;\n}\n\nexport function versionstampToHex(bytes: Uint8Array): string {\n let hex = \"\";\n for (const byte of bytes) {\n hex += byte.toString(16).padStart(2, \"0\");\n }\n return hex;\n}\n\nexport function hexToVersionstamp(hex: string): Uint8Array {\n if (hex.length % 2 !== 0) {\n throw new Error(`Invalid versionstamp hex length: ${hex.length}`);\n }\n\n const bytes = new Uint8Array(hex.length / 2);\n for (let i = 0; i < hex.length; i += 2) {\n bytes[i / 2] = Number.parseInt(hex.slice(i, i + 2), 16);\n }\n return bytes;\n}\n\nexport function parseOutboxVersionValue(value: unknown): bigint {\n if (typeof value === \"bigint\") {\n return value;\n }\n\n if (typeof value === \"number\") {\n return BigInt(value);\n }\n\n if (typeof value === \"string\") {\n return BigInt(value);\n }\n\n throw new Error(`Invalid outbox version value: ${String(value)}`);\n}\n\nfunction bigintToBytes(value: bigint, length: number): Uint8Array {\n const bytes = new Uint8Array(length);\n let remaining = value;\n\n for (let i = length - 1; i >= 0; i -= 1) {\n bytes[i] = Number(remaining & 0xffn);\n remaining >>= 8n;\n }\n\n if (remaining !== 0n) {\n throw new Error(`Outbox version ${value} exceeds ${length * 8} bits`);\n }\n\n return bytes;\n}\n"],"mappings":";AAqEA,SAAgB,mBAAmB,oBAA4B,aAAiC;AAC9F,KAAI,cAAc,KAAK,cAAc,MACnC,OAAM,IAAI,MAAM,gCAAgC,cAAc;CAGhE,MAAM,UAAU,cAAc,oBAAoB,GAAG;CACrD,MAAM,YAAY,IAAI,WAAW,EAAE;AACnC,WAAU,KAAM,eAAe,IAAK;AACpC,WAAU,KAAK,cAAc;CAE7B,MAAM,WAAW,IAAI,WAAW,GAAG;AACnC,UAAS,IAAI,SAAS,EAAE;AACxB,UAAS,IAAI,WAAW,GAAG;AAE3B,QAAO;;AAGT,SAAgB,kBAAkB,OAA2B;CAC3D,IAAI,MAAM;AACV,MAAK,MAAM,QAAQ,MACjB,QAAO,KAAK,SAAS,GAAG,CAAC,SAAS,GAAG,IAAI;AAE3C,QAAO;;AAeT,SAAgB,wBAAwB,OAAwB;AAC9D,KAAI,OAAO,UAAU,SACnB,QAAO;AAGT,KAAI,OAAO,UAAU,SACnB,QAAO,OAAO,MAAM;AAGtB,KAAI,OAAO,UAAU,SACnB,QAAO,OAAO,MAAM;AAGtB,OAAM,IAAI,MAAM,iCAAiC,OAAO,MAAM,GAAG;;AAGnE,SAAS,cAAc,OAAe,QAA4B;CAChE,MAAM,QAAQ,IAAI,WAAW,OAAO;CACpC,IAAI,YAAY;AAEhB,MAAK,IAAI,IAAI,SAAS,GAAG,KAAK,GAAG,KAAK,GAAG;AACvC,QAAM,KAAK,OAAO,YAAY,KAAM;AACpC,gBAAc;;AAGhB,KAAI,cAAc,GAChB,OAAM,IAAI,MAAM,kBAAkB,MAAM,WAAW,SAAS,EAAE,OAAO;AAGvE,QAAO"}
|
|
@@ -269,8 +269,9 @@ var FragmentDefinitionBuilder = class FragmentDefinitionBuilder$1 {
|
|
|
269
269
|
}
|
|
270
270
|
/**
|
|
271
271
|
* Register a linked fragment that will be automatically instantiated.
|
|
272
|
-
* Linked fragments
|
|
273
|
-
*
|
|
272
|
+
* Linked fragments share the same config/options as the parent and their services
|
|
273
|
+
* are exposed as private services. Routes are not exposed by default, but the
|
|
274
|
+
* instantiator may mount internal linked fragment routes under an internal prefix.
|
|
274
275
|
*/
|
|
275
276
|
withLinkedFragment(name, callback) {
|
|
276
277
|
const newLinkedFragments = {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fragment-definition-builder.js","names":["FragmentDefinitionBuilder","#name","#dependencies","#baseServices","#namedServices","#privateServices","#serviceDependencies","#createRequestStorage","#createThisContext","#getExternalStorage","#linkedFragments"],"sources":["../../../../../../fragno/dist/api/fragment-definition-builder.js"],"sourcesContent":["//#region src/api/fragment-definition-builder.ts\n/**\n* Builder class for creating fragment definitions.\n* This provides a fluent API for defining fragments with type safety.\n*/\nvar FragmentDefinitionBuilder = class FragmentDefinitionBuilder {\n\t#name;\n\t#dependencies;\n\t#baseServices;\n\t#namedServices;\n\t#privateServices;\n\t#serviceDependencies;\n\t#createRequestStorage;\n\t#createThisContext;\n\t#getExternalStorage;\n\t#linkedFragments;\n\tconstructor(name, state) {\n\t\tthis.#name = name;\n\t\tif (state) {\n\t\t\tthis.#dependencies = state.dependencies;\n\t\t\tthis.#baseServices = state.baseServices;\n\t\t\tthis.#namedServices = state.namedServices;\n\t\t\tthis.#privateServices = state.privateServices;\n\t\t\tthis.#serviceDependencies = state.serviceDependencies;\n\t\t\tthis.#createRequestStorage = state.createRequestStorage;\n\t\t\tthis.#createThisContext = state.createThisContext;\n\t\t\tthis.#getExternalStorage = state.getExternalStorage;\n\t\t\tthis.#linkedFragments = state.linkedFragments;\n\t\t}\n\t}\n\tget name() {\n\t\treturn this.#name;\n\t}\n\t/**\n\t* Define dependencies for this fragment.\n\t* Dependencies are available to services and handlers.\n\t*\n\t* **IMPORTANT**: This method resets all services, storage, and context configurations.\n\t* Always call `withDependencies` early in the builder chain, before defining services\n\t* or request storage/context.\n\t*\n\t* @example\n\t* ```typescript\n\t* // ✅ GOOD: Dependencies set first\n\t* defineFragment(\"my-fragment\")\n\t* .withDependencies(() => ({ apiKey: \"...\" }))\n\t* .withRequestStorage(({ deps }) => ({ userId: deps.apiKey }))\n\t* .providesService(\"myService\", ...)\n\t*\n\t* // ❌ BAD: Dependencies set late (erases storage setup)\n\t* defineFragment(\"my-fragment\")\n\t* .withRequestStorage(() => ({ userId: \"...\" })) // This gets erased!\n\t* .withDependencies(() => ({ apiKey: \"...\" }))\n\t* ```\n\t*/\n\twithDependencies(fn) {\n\t\tif (this.#baseServices || this.#namedServices || this.#privateServices || this.#createRequestStorage || this.#createThisContext || this.#getExternalStorage) console.warn(`[Fragno] Warning: withDependencies() on fragment \"${this.#name}\" is resetting previously configured services, request storage, or request context. To avoid this, call withDependencies() earlier in the builder chain, before configuring services or storage.`);\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: fn,\n\t\t\tbaseServices: void 0,\n\t\t\tnamedServices: void 0,\n\t\t\tprivateServices: void 0,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: void 0,\n\t\t\tcreateThisContext: void 0,\n\t\t\tgetExternalStorage: void 0,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Define base (unnamed) services for this fragment.\n\t* Base services are accessible directly on the fragment instance.\n\t*/\n\tprovidesBaseService(fn) {\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: fn,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Provide a named service that other fragments or users can use.\n\t* Named services are accessible as fragment.serviceName.method()\n\t*/\n\tprovidesService(serviceName, fn) {\n\t\tconst newNamedServices = {\n\t\t\t...this.#namedServices,\n\t\t\t[serviceName]: fn\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: newNamedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Provide a private service that is only accessible to the fragment author.\n\t* Private services are NOT exposed on the fragment instance, but can be used\n\t* when defining other services (baseServices, namedServices, and other privateServices).\n\t* Private services are instantiated in order, so earlier private services are available\n\t* to later ones.\n\t*/\n\tprovidesPrivateService(serviceName, fn) {\n\t\tconst newPrivateServices = {\n\t\t\t...this.#privateServices,\n\t\t\t[serviceName]: fn\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: newPrivateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Declare that this fragment uses a required service provided by the runtime.\n\t*/\n\tusesService(serviceName) {\n\t\tconst newServiceDependencies = {\n\t\t\t...this.#serviceDependencies,\n\t\t\t[serviceName]: {\n\t\t\t\tname: serviceName,\n\t\t\t\trequired: true\n\t\t\t}\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: newServiceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Declare that this fragment uses an optional service provided by the runtime.\n\t*/\n\tusesOptionalService(serviceName) {\n\t\tconst newServiceDependencies = {\n\t\t\t...this.#serviceDependencies,\n\t\t\t[serviceName]: {\n\t\t\t\tname: serviceName,\n\t\t\t\trequired: false\n\t\t\t}\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: newServiceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Define the type and initial data stored in AsyncLocalStorage for per-request isolation.\n\t* This should be called before withThisContext if you need to store request-specific data.\n\t*\n\t* @param initializer Function that returns the initial storage data for each request\n\t*\n\t* @example\n\t* ```typescript\n\t* .withRequestStorage(({ config, options, deps }) => ({\n\t* counter: 0,\n\t* userId: deps.currentUserId\n\t* }))\n\t* .withThisContext(({ storage }) => ({\n\t* serviceContext: {\n\t* get counter() { return storage.getStore()!.counter; }\n\t* },\n\t* handlerContext: {\n\t* get counter() { return storage.getStore()!.counter; }\n\t* }\n\t* }))\n\t* ```\n\t*/\n\twithRequestStorage(initializer) {\n\t\tconst preservedExternalStorage = this.#getExternalStorage ? this.#getExternalStorage : void 0;\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: initializer,\n\t\t\tcreateThisContext: void 0,\n\t\t\tgetExternalStorage: preservedExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Use an externally-provided RequestContextStorage instance.\n\t* This allows multiple fragments to share the same storage instance.\n\t* Useful when fragments need to coordinate (e.g., database fragments sharing adapter storage).\n\t* Note: You must still call withRequestStorage to provide the initial storage data.\n\t*\n\t* @example\n\t* ```typescript\n\t* .withExternalRequestStorage(({ options }) =>\n\t* options.databaseAdapter.contextStorage\n\t* )\n\t* .withRequestStorage(({ options }) => ({\n\t* uow: options.databaseAdapter.db.createUnitOfWork()\n\t* }))\n\t* ```\n\t*/\n\twithExternalRequestStorage(getStorage) {\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: void 0,\n\t\t\tcreateThisContext: void 0,\n\t\t\tgetExternalStorage: getStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Set the this contexts for services and handlers in this fragment.\n\t* Both contexts should contain only methods or getters that read from storage.\n\t* This ensures proper per-request isolation via AsyncLocalStorage.\n\t*\n\t* @example\n\t* ```ts\n\t* .withThisContext(({ storage }) => ({\n\t* serviceContext: {\n\t* get myNumber() { return storage.getStore()?.myNumber ?? 0; }\n\t* },\n\t* handlerContext: {\n\t* get myNumber() { return storage.getStore()?.myNumber ?? 0; }\n\t* }\n\t* }))\n\t* ```\n\t*/\n\twithThisContext(fn) {\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: fn,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Register a linked fragment that will be automatically instantiated.\n\t* Linked fragments are service-only (no routes) and share the same config/options as the parent.\n\t* All services from the linked fragment will be available as private services.\n\t*/\n\twithLinkedFragment(name, callback) {\n\t\tconst newLinkedFragments = {\n\t\t\t...this.#linkedFragments,\n\t\t\t[name]: callback\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: newLinkedFragments\n\t\t});\n\t}\n\t/**\n\t* Extend this builder with a transformation function.\n\t* This enables fluent API extensions like `.extend(withDatabase(schema))`.\n\t*/\n\textend(transformer) {\n\t\treturn transformer(this);\n\t}\n\t/**\n\t* Build the final fragment definition\n\t*/\n\tbuild() {\n\t\treturn {\n\t\t\tname: this.#name,\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t};\n\t}\n};\n/**\n* Create a new fragment definition builder\n*/\nfunction defineFragment(name) {\n\treturn new FragmentDefinitionBuilder(name);\n}\n\n//#endregion\nexport { FragmentDefinitionBuilder, defineFragment };\n//# sourceMappingURL=fragment-definition-builder.js.map"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"fragment-definition-builder.js","names":["FragmentDefinitionBuilder","#name","#dependencies","#baseServices","#namedServices","#privateServices","#serviceDependencies","#createRequestStorage","#createThisContext","#getExternalStorage","#linkedFragments"],"sources":["../../../../../../fragno/dist/api/fragment-definition-builder.js"],"sourcesContent":["//#region src/api/fragment-definition-builder.ts\n/**\n* Builder class for creating fragment definitions.\n* This provides a fluent API for defining fragments with type safety.\n*/\nvar FragmentDefinitionBuilder = class FragmentDefinitionBuilder {\n\t#name;\n\t#dependencies;\n\t#baseServices;\n\t#namedServices;\n\t#privateServices;\n\t#serviceDependencies;\n\t#createRequestStorage;\n\t#createThisContext;\n\t#getExternalStorage;\n\t#linkedFragments;\n\tconstructor(name, state) {\n\t\tthis.#name = name;\n\t\tif (state) {\n\t\t\tthis.#dependencies = state.dependencies;\n\t\t\tthis.#baseServices = state.baseServices;\n\t\t\tthis.#namedServices = state.namedServices;\n\t\t\tthis.#privateServices = state.privateServices;\n\t\t\tthis.#serviceDependencies = state.serviceDependencies;\n\t\t\tthis.#createRequestStorage = state.createRequestStorage;\n\t\t\tthis.#createThisContext = state.createThisContext;\n\t\t\tthis.#getExternalStorage = state.getExternalStorage;\n\t\t\tthis.#linkedFragments = state.linkedFragments;\n\t\t}\n\t}\n\tget name() {\n\t\treturn this.#name;\n\t}\n\t/**\n\t* Define dependencies for this fragment.\n\t* Dependencies are available to services and handlers.\n\t*\n\t* **IMPORTANT**: This method resets all services, storage, and context configurations.\n\t* Always call `withDependencies` early in the builder chain, before defining services\n\t* or request storage/context.\n\t*\n\t* @example\n\t* ```typescript\n\t* // ✅ GOOD: Dependencies set first\n\t* defineFragment(\"my-fragment\")\n\t* .withDependencies(() => ({ apiKey: \"...\" }))\n\t* .withRequestStorage(({ deps }) => ({ userId: deps.apiKey }))\n\t* .providesService(\"myService\", ...)\n\t*\n\t* // ❌ BAD: Dependencies set late (erases storage setup)\n\t* defineFragment(\"my-fragment\")\n\t* .withRequestStorage(() => ({ userId: \"...\" })) // This gets erased!\n\t* .withDependencies(() => ({ apiKey: \"...\" }))\n\t* ```\n\t*/\n\twithDependencies(fn) {\n\t\tif (this.#baseServices || this.#namedServices || this.#privateServices || this.#createRequestStorage || this.#createThisContext || this.#getExternalStorage) console.warn(`[Fragno] Warning: withDependencies() on fragment \"${this.#name}\" is resetting previously configured services, request storage, or request context. To avoid this, call withDependencies() earlier in the builder chain, before configuring services or storage.`);\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: fn,\n\t\t\tbaseServices: void 0,\n\t\t\tnamedServices: void 0,\n\t\t\tprivateServices: void 0,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: void 0,\n\t\t\tcreateThisContext: void 0,\n\t\t\tgetExternalStorage: void 0,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Define base (unnamed) services for this fragment.\n\t* Base services are accessible directly on the fragment instance.\n\t*/\n\tprovidesBaseService(fn) {\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: fn,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Provide a named service that other fragments or users can use.\n\t* Named services are accessible as fragment.serviceName.method()\n\t*/\n\tprovidesService(serviceName, fn) {\n\t\tconst newNamedServices = {\n\t\t\t...this.#namedServices,\n\t\t\t[serviceName]: fn\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: newNamedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Provide a private service that is only accessible to the fragment author.\n\t* Private services are NOT exposed on the fragment instance, but can be used\n\t* when defining other services (baseServices, namedServices, and other privateServices).\n\t* Private services are instantiated in order, so earlier private services are available\n\t* to later ones.\n\t*/\n\tprovidesPrivateService(serviceName, fn) {\n\t\tconst newPrivateServices = {\n\t\t\t...this.#privateServices,\n\t\t\t[serviceName]: fn\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: newPrivateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Declare that this fragment uses a required service provided by the runtime.\n\t*/\n\tusesService(serviceName) {\n\t\tconst newServiceDependencies = {\n\t\t\t...this.#serviceDependencies,\n\t\t\t[serviceName]: {\n\t\t\t\tname: serviceName,\n\t\t\t\trequired: true\n\t\t\t}\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: newServiceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Declare that this fragment uses an optional service provided by the runtime.\n\t*/\n\tusesOptionalService(serviceName) {\n\t\tconst newServiceDependencies = {\n\t\t\t...this.#serviceDependencies,\n\t\t\t[serviceName]: {\n\t\t\t\tname: serviceName,\n\t\t\t\trequired: false\n\t\t\t}\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: newServiceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Define the type and initial data stored in AsyncLocalStorage for per-request isolation.\n\t* This should be called before withThisContext if you need to store request-specific data.\n\t*\n\t* @param initializer Function that returns the initial storage data for each request\n\t*\n\t* @example\n\t* ```typescript\n\t* .withRequestStorage(({ config, options, deps }) => ({\n\t* counter: 0,\n\t* userId: deps.currentUserId\n\t* }))\n\t* .withThisContext(({ storage }) => ({\n\t* serviceContext: {\n\t* get counter() { return storage.getStore()!.counter; }\n\t* },\n\t* handlerContext: {\n\t* get counter() { return storage.getStore()!.counter; }\n\t* }\n\t* }))\n\t* ```\n\t*/\n\twithRequestStorage(initializer) {\n\t\tconst preservedExternalStorage = this.#getExternalStorage ? this.#getExternalStorage : void 0;\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: initializer,\n\t\t\tcreateThisContext: void 0,\n\t\t\tgetExternalStorage: preservedExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Use an externally-provided RequestContextStorage instance.\n\t* This allows multiple fragments to share the same storage instance.\n\t* Useful when fragments need to coordinate (e.g., database fragments sharing adapter storage).\n\t* Note: You must still call withRequestStorage to provide the initial storage data.\n\t*\n\t* @example\n\t* ```typescript\n\t* .withExternalRequestStorage(({ options }) =>\n\t* options.databaseAdapter.contextStorage\n\t* )\n\t* .withRequestStorage(({ options }) => ({\n\t* uow: options.databaseAdapter.db.createUnitOfWork()\n\t* }))\n\t* ```\n\t*/\n\twithExternalRequestStorage(getStorage) {\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: void 0,\n\t\t\tcreateThisContext: void 0,\n\t\t\tgetExternalStorage: getStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Set the this contexts for services and handlers in this fragment.\n\t* Both contexts should contain only methods or getters that read from storage.\n\t* This ensures proper per-request isolation via AsyncLocalStorage.\n\t*\n\t* @example\n\t* ```ts\n\t* .withThisContext(({ storage }) => ({\n\t* serviceContext: {\n\t* get myNumber() { return storage.getStore()?.myNumber ?? 0; }\n\t* },\n\t* handlerContext: {\n\t* get myNumber() { return storage.getStore()?.myNumber ?? 0; }\n\t* }\n\t* }))\n\t* ```\n\t*/\n\twithThisContext(fn) {\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: fn,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t});\n\t}\n\t/**\n\t* Register a linked fragment that will be automatically instantiated.\n\t* Linked fragments share the same config/options as the parent and their services\n\t* are exposed as private services. Routes are not exposed by default, but the\n\t* instantiator may mount internal linked fragment routes under an internal prefix.\n\t*/\n\twithLinkedFragment(name, callback) {\n\t\tconst newLinkedFragments = {\n\t\t\t...this.#linkedFragments,\n\t\t\t[name]: callback\n\t\t};\n\t\treturn new FragmentDefinitionBuilder(this.#name, {\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: newLinkedFragments\n\t\t});\n\t}\n\t/**\n\t* Extend this builder with a transformation function.\n\t* This enables fluent API extensions like `.extend(withDatabase(schema))`.\n\t*/\n\textend(transformer) {\n\t\treturn transformer(this);\n\t}\n\t/**\n\t* Build the final fragment definition\n\t*/\n\tbuild() {\n\t\treturn {\n\t\t\tname: this.#name,\n\t\t\tdependencies: this.#dependencies,\n\t\t\tbaseServices: this.#baseServices,\n\t\t\tnamedServices: this.#namedServices,\n\t\t\tprivateServices: this.#privateServices,\n\t\t\tserviceDependencies: this.#serviceDependencies,\n\t\t\tcreateRequestStorage: this.#createRequestStorage,\n\t\t\tcreateThisContext: this.#createThisContext,\n\t\t\tgetExternalStorage: this.#getExternalStorage,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t};\n\t}\n};\n/**\n* Create a new fragment definition builder\n*/\nfunction defineFragment(name) {\n\treturn new FragmentDefinitionBuilder(name);\n}\n\n//#endregion\nexport { FragmentDefinitionBuilder, defineFragment };\n//# sourceMappingURL=fragment-definition-builder.js.map"],"mappings":"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"}
|
|
@@ -9,14 +9,66 @@ import { RequestMiddlewareInputContext, RequestMiddlewareOutputContext } from ".
|
|
|
9
9
|
import { parseFragnoResponse } from "./fragno-response.js";
|
|
10
10
|
import { RequestContextStorage } from "./request-context-storage.js";
|
|
11
11
|
import { bindServicesToContext } from "./bind-services.js";
|
|
12
|
-
import {
|
|
12
|
+
import { recordTraceEvent } from "../internal/trace-context.js";
|
|
13
|
+
import { addRoute, createRouter, findRoute } from "../../../../node_modules/.pnpm/rou3@0.7.12/node_modules/rou3/dist/index.js";
|
|
13
14
|
|
|
14
15
|
//#region ../fragno/dist/api/fragment-instantiator.js
|
|
16
|
+
const serializeHeadersForTrace = (headers) => Array.from(headers.entries()).sort(([a], [b]) => a.localeCompare(b));
|
|
17
|
+
const serializeQueryForTrace = (query) => Array.from(query.entries()).sort(([a], [b]) => a.localeCompare(b));
|
|
18
|
+
const serializeBodyForTrace = (body) => {
|
|
19
|
+
if (body instanceof FormData) return {
|
|
20
|
+
type: "form-data",
|
|
21
|
+
entries: Array.from(body.entries()).map(([key, value]) => {
|
|
22
|
+
if (value instanceof Blob) return [key, {
|
|
23
|
+
type: "blob",
|
|
24
|
+
size: value.size,
|
|
25
|
+
mime: value.type
|
|
26
|
+
}];
|
|
27
|
+
return [key, value];
|
|
28
|
+
})
|
|
29
|
+
};
|
|
30
|
+
if (body instanceof Blob) return {
|
|
31
|
+
type: "blob",
|
|
32
|
+
size: body.size,
|
|
33
|
+
mime: body.type
|
|
34
|
+
};
|
|
35
|
+
if (body instanceof ReadableStream) return { type: "stream" };
|
|
36
|
+
return body;
|
|
37
|
+
};
|
|
38
|
+
const INTERNAL_LINKED_FRAGMENT_NAME = "_fragno_internal";
|
|
39
|
+
const INTERNAL_ROUTE_PREFIX = "/_internal";
|
|
40
|
+
function normalizeRoutePrefix(prefix) {
|
|
41
|
+
if (!prefix.startsWith("/")) prefix = `/${prefix}`;
|
|
42
|
+
return prefix.endsWith("/") && prefix.length > 1 ? prefix.slice(0, -1) : prefix;
|
|
43
|
+
}
|
|
44
|
+
function joinRoutePath(prefix, path) {
|
|
45
|
+
const normalizedPrefix = normalizeRoutePrefix(prefix);
|
|
46
|
+
if (!path || path === "/") return normalizedPrefix;
|
|
47
|
+
return `${normalizedPrefix}${path.startsWith("/") ? path : `/${path}`}`;
|
|
48
|
+
}
|
|
49
|
+
function collectLinkedFragmentRoutes(linkedFragments) {
|
|
50
|
+
const linkedRoutes = [];
|
|
51
|
+
for (const [name, fragment] of Object.entries(linkedFragments)) {
|
|
52
|
+
if (name !== INTERNAL_LINKED_FRAGMENT_NAME) continue;
|
|
53
|
+
const internalRoutes = fragment.routes ?? [];
|
|
54
|
+
if (internalRoutes.length === 0) continue;
|
|
55
|
+
for (const route of internalRoutes) linkedRoutes.push({
|
|
56
|
+
...route,
|
|
57
|
+
path: joinRoutePath(INTERNAL_ROUTE_PREFIX, route.path),
|
|
58
|
+
__internal: {
|
|
59
|
+
fragment,
|
|
60
|
+
originalPath: route.path,
|
|
61
|
+
routes: internalRoutes
|
|
62
|
+
}
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
return linkedRoutes;
|
|
66
|
+
}
|
|
15
67
|
/**
|
|
16
68
|
* Instantiated fragment class with encapsulated state.
|
|
17
69
|
* Provides the same public API as the old FragnoInstantiatedFragment but with better encapsulation.
|
|
18
70
|
*/
|
|
19
|
-
var FragnoInstantiatedFragment = class {
|
|
71
|
+
var FragnoInstantiatedFragment = class FragnoInstantiatedFragment$1 {
|
|
20
72
|
[instantiatedFragmentFakeSymbol] = instantiatedFragmentFakeSymbol;
|
|
21
73
|
#name;
|
|
22
74
|
#routes;
|
|
@@ -31,6 +83,7 @@ var FragnoInstantiatedFragment = class {
|
|
|
31
83
|
#createRequestStorage;
|
|
32
84
|
#options;
|
|
33
85
|
#linkedFragments;
|
|
86
|
+
#internalData;
|
|
34
87
|
constructor(params) {
|
|
35
88
|
this.#name = params.name;
|
|
36
89
|
this.#routes = params.routes;
|
|
@@ -43,6 +96,7 @@ var FragnoInstantiatedFragment = class {
|
|
|
43
96
|
this.#createRequestStorage = params.createRequestStorage;
|
|
44
97
|
this.#options = params.options;
|
|
45
98
|
this.#linkedFragments = params.linkedFragments ?? {};
|
|
99
|
+
this.#internalData = params.internalData ?? {};
|
|
46
100
|
this.#router = createRouter();
|
|
47
101
|
for (const routeConfig of this.#routes) addRoute(this.#router, routeConfig.method.toUpperCase(), routeConfig.path, routeConfig);
|
|
48
102
|
this.handler = this.handler.bind(this);
|
|
@@ -66,7 +120,8 @@ var FragnoInstantiatedFragment = class {
|
|
|
66
120
|
return {
|
|
67
121
|
deps: this.#deps,
|
|
68
122
|
options: this.#options,
|
|
69
|
-
linkedFragments: this.#linkedFragments
|
|
123
|
+
linkedFragments: this.#linkedFragments,
|
|
124
|
+
...this.#internalData
|
|
70
125
|
};
|
|
71
126
|
}
|
|
72
127
|
/**
|
|
@@ -160,26 +215,65 @@ var FragnoInstantiatedFragment = class {
|
|
|
160
215
|
error: `Fragno: Route for '${this.#name}' not found`,
|
|
161
216
|
code: "ROUTE_NOT_FOUND"
|
|
162
217
|
}, { status: 404 });
|
|
218
|
+
const routeConfig = route.data;
|
|
219
|
+
const expectedContentType = routeConfig.contentType ?? "application/json";
|
|
163
220
|
let requestBody = void 0;
|
|
164
221
|
let rawBody = void 0;
|
|
165
222
|
if (req.body instanceof ReadableStream) {
|
|
166
|
-
|
|
167
|
-
if (
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
223
|
+
const requestContentType = (req.headers.get("content-type") ?? "").toLowerCase();
|
|
224
|
+
if (expectedContentType === "multipart/form-data") {
|
|
225
|
+
if (!requestContentType.includes("multipart/form-data")) return Response.json({
|
|
226
|
+
error: `This endpoint expects multipart/form-data, but received: ${requestContentType || "no content-type"}`,
|
|
227
|
+
code: "UNSUPPORTED_MEDIA_TYPE"
|
|
228
|
+
}, { status: 415 });
|
|
229
|
+
try {
|
|
230
|
+
requestBody = await req.formData();
|
|
231
|
+
} catch {
|
|
232
|
+
return Response.json({
|
|
233
|
+
error: "Failed to parse multipart form data",
|
|
234
|
+
code: "INVALID_REQUEST_BODY"
|
|
235
|
+
}, { status: 400 });
|
|
236
|
+
}
|
|
237
|
+
} else if (expectedContentType === "application/octet-stream") {
|
|
238
|
+
if (!requestContentType.includes("application/octet-stream")) return Response.json({
|
|
239
|
+
error: `This endpoint expects application/octet-stream, but received: ${requestContentType || "no content-type"}`,
|
|
240
|
+
code: "UNSUPPORTED_MEDIA_TYPE"
|
|
241
|
+
}, { status: 415 });
|
|
242
|
+
requestBody = req.body ?? new ReadableStream();
|
|
243
|
+
} else {
|
|
244
|
+
if (requestContentType.includes("multipart/form-data")) return Response.json({
|
|
245
|
+
error: `This endpoint expects JSON, but received multipart/form-data. Use a route with contentType: "multipart/form-data" for file uploads.`,
|
|
246
|
+
code: "UNSUPPORTED_MEDIA_TYPE"
|
|
247
|
+
}, { status: 415 });
|
|
248
|
+
rawBody = await req.clone().text();
|
|
249
|
+
if (rawBody) try {
|
|
250
|
+
requestBody = JSON.parse(rawBody);
|
|
251
|
+
} catch {
|
|
252
|
+
requestBody = void 0;
|
|
253
|
+
}
|
|
171
254
|
}
|
|
172
255
|
}
|
|
256
|
+
const decodedRouteParams = {};
|
|
257
|
+
for (const [key, value] of Object.entries(route.params ?? {})) decodedRouteParams[key] = decodeURIComponent(value);
|
|
173
258
|
const requestState = new MutableRequestState({
|
|
174
|
-
pathParams:
|
|
259
|
+
pathParams: decodedRouteParams,
|
|
175
260
|
searchParams: url.searchParams,
|
|
176
261
|
body: requestBody,
|
|
177
262
|
headers: new Headers(req.headers)
|
|
178
263
|
});
|
|
179
264
|
const executeRequest = async () => {
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
265
|
+
const middlewareResult = await this.#executeMiddleware(req, route, requestState);
|
|
266
|
+
if (middlewareResult !== void 0) return middlewareResult;
|
|
267
|
+
const internalMeta = routeConfig.__internal;
|
|
268
|
+
if (internalMeta) {
|
|
269
|
+
const internalResult = await FragnoInstantiatedFragment$1.#runMiddlewareForFragment(internalMeta.fragment, {
|
|
270
|
+
req,
|
|
271
|
+
method: routeConfig.method,
|
|
272
|
+
path: internalMeta.originalPath,
|
|
273
|
+
requestState,
|
|
274
|
+
routes: internalMeta.routes
|
|
275
|
+
});
|
|
276
|
+
if (internalResult !== void 0) return internalResult;
|
|
183
277
|
}
|
|
184
278
|
return this.#executeHandler(req, route, requestState, rawBody);
|
|
185
279
|
};
|
|
@@ -215,6 +309,15 @@ var FragnoInstantiatedFragment = class {
|
|
|
215
309
|
inputSchema: route.inputSchema,
|
|
216
310
|
shouldValidateInput: true
|
|
217
311
|
});
|
|
312
|
+
recordTraceEvent({
|
|
313
|
+
type: "route-input",
|
|
314
|
+
method: route.method,
|
|
315
|
+
path: route.path,
|
|
316
|
+
pathParams: pathParams ?? {},
|
|
317
|
+
queryParams: serializeQueryForTrace(searchParams),
|
|
318
|
+
headers: serializeHeadersForTrace(requestHeaders),
|
|
319
|
+
body: serializeBodyForTrace(body)
|
|
320
|
+
});
|
|
218
321
|
const outputContext = new RequestOutputContext(route.outputSchema);
|
|
219
322
|
const executeHandler = async () => {
|
|
220
323
|
try {
|
|
@@ -236,20 +339,43 @@ var FragnoInstantiatedFragment = class {
|
|
|
236
339
|
* Returns undefined if middleware allows the request to continue to the handler.
|
|
237
340
|
*/
|
|
238
341
|
async #executeMiddleware(req, route, requestState) {
|
|
239
|
-
if (!
|
|
342
|
+
if (!route) return;
|
|
240
343
|
const { path } = route.data;
|
|
241
|
-
|
|
344
|
+
return FragnoInstantiatedFragment$1.#runMiddlewareForFragment(this, {
|
|
345
|
+
req,
|
|
242
346
|
method: req.method,
|
|
243
347
|
path,
|
|
244
|
-
|
|
245
|
-
|
|
348
|
+
requestState
|
|
349
|
+
});
|
|
350
|
+
}
|
|
351
|
+
static async #runMiddlewareForFragment(fragment, options) {
|
|
352
|
+
if (!fragment.#middlewareHandler) return;
|
|
353
|
+
const middlewareInputContext = new RequestMiddlewareInputContext(options.routes ?? fragment.#routes, {
|
|
354
|
+
method: options.method,
|
|
355
|
+
path: options.path,
|
|
356
|
+
request: options.req,
|
|
357
|
+
state: options.requestState
|
|
246
358
|
});
|
|
247
|
-
const middlewareOutputContext = new RequestMiddlewareOutputContext(
|
|
359
|
+
const middlewareOutputContext = new RequestMiddlewareOutputContext(fragment.#deps, fragment.#services);
|
|
248
360
|
try {
|
|
249
|
-
const middlewareResult = await
|
|
361
|
+
const middlewareResult = await fragment.#middlewareHandler(middlewareInputContext, middlewareOutputContext);
|
|
362
|
+
recordTraceEvent({
|
|
363
|
+
type: "middleware-decision",
|
|
364
|
+
method: options.method,
|
|
365
|
+
path: options.path,
|
|
366
|
+
outcome: middlewareResult ? "deny" : "allow",
|
|
367
|
+
status: middlewareResult?.status
|
|
368
|
+
});
|
|
250
369
|
if (middlewareResult !== void 0) return middlewareResult;
|
|
251
370
|
} catch (error) {
|
|
252
371
|
console.error("Error in middleware", error);
|
|
372
|
+
recordTraceEvent({
|
|
373
|
+
type: "middleware-decision",
|
|
374
|
+
method: options.method,
|
|
375
|
+
path: options.path,
|
|
376
|
+
outcome: "deny",
|
|
377
|
+
status: error instanceof FragnoApiError ? error.status : 500
|
|
378
|
+
});
|
|
253
379
|
if (error instanceof FragnoApiError) return error.toResponse();
|
|
254
380
|
return Response.json({
|
|
255
381
|
error: "Internal server error",
|
|
@@ -275,6 +401,15 @@ var FragnoInstantiatedFragment = class {
|
|
|
275
401
|
state: requestState,
|
|
276
402
|
rawBody
|
|
277
403
|
});
|
|
404
|
+
recordTraceEvent({
|
|
405
|
+
type: "route-input",
|
|
406
|
+
method: req.method,
|
|
407
|
+
path,
|
|
408
|
+
pathParams: inputContext.pathParams,
|
|
409
|
+
queryParams: serializeQueryForTrace(requestState.searchParams),
|
|
410
|
+
headers: serializeHeadersForTrace(requestState.headers),
|
|
411
|
+
body: serializeBodyForTrace(requestState.body)
|
|
412
|
+
});
|
|
278
413
|
const outputContext = new RequestOutputContext(outputSchema);
|
|
279
414
|
try {
|
|
280
415
|
const contextForHandler = this.#handlerThisContext ?? {};
|
|
@@ -397,6 +532,12 @@ function instantiateFragment(definition, config, routesOrFactories, options, ser
|
|
|
397
532
|
});
|
|
398
533
|
const serviceContext = contexts?.serviceContext;
|
|
399
534
|
const handlerContext = contexts?.handlerContext;
|
|
535
|
+
const internalData = definition.internalDataFactory?.({
|
|
536
|
+
config,
|
|
537
|
+
options,
|
|
538
|
+
deps,
|
|
539
|
+
linkedFragments: linkedFragmentInstances
|
|
540
|
+
}) ?? {};
|
|
400
541
|
const boundServices = serviceContext ? bindServicesToContext(services, serviceContext) : services;
|
|
401
542
|
const routes = resolveRouteFactories({
|
|
402
543
|
config,
|
|
@@ -404,6 +545,8 @@ function instantiateFragment(definition, config, routesOrFactories, options, ser
|
|
|
404
545
|
services: boundServices,
|
|
405
546
|
serviceDeps: serviceImplementations ?? {}
|
|
406
547
|
}, routesOrFactories);
|
|
548
|
+
const linkedRoutes = collectLinkedFragmentRoutes(linkedFragmentInstances);
|
|
549
|
+
const finalRoutes = linkedRoutes.length > 0 ? [...routes, ...linkedRoutes] : routes;
|
|
407
550
|
const mountRoute = getMountRoute({
|
|
408
551
|
name: definition.name,
|
|
409
552
|
mountRoute: options.mountRoute
|
|
@@ -415,7 +558,7 @@ function instantiateFragment(definition, config, routesOrFactories, options, ser
|
|
|
415
558
|
}) : void 0;
|
|
416
559
|
return new FragnoInstantiatedFragment({
|
|
417
560
|
name: definition.name,
|
|
418
|
-
routes,
|
|
561
|
+
routes: finalRoutes,
|
|
419
562
|
deps,
|
|
420
563
|
services: boundServices,
|
|
421
564
|
mountRoute,
|
|
@@ -424,7 +567,8 @@ function instantiateFragment(definition, config, routesOrFactories, options, ser
|
|
|
424
567
|
storage,
|
|
425
568
|
createRequestStorage: createRequestStorageWithContext,
|
|
426
569
|
options,
|
|
427
|
-
linkedFragments: linkedFragmentInstances
|
|
570
|
+
linkedFragments: linkedFragmentInstances,
|
|
571
|
+
internalData
|
|
428
572
|
});
|
|
429
573
|
}
|
|
430
574
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fragment-instantiator.js","names":["#name","#routes","#deps","#services","#mountRoute","#serviceThisContext","#handlerThisContext","#contextStorage","#createRequestStorage","#options","#linkedFragments","#router","#middlewareHandler","#withRequestStorage","#executeMiddleware","#executeHandler","FragmentInstantiationBuilder","#definition","#config"],"sources":["../../../../../../fragno/dist/api/fragment-instantiator.js"],"sourcesContent":["import { instantiatedFragmentFakeSymbol } from \"../internal/symbols.js\";\nimport { resolveRouteFactories } from \"./route.js\";\nimport { FragnoApiError } from \"./error.js\";\nimport { getMountRoute } from \"./internal/route.js\";\nimport { RequestInputContext } from \"./request-input-context.js\";\nimport { RequestOutputContext } from \"./request-output-context.js\";\nimport { MutableRequestState } from \"./mutable-request-state.js\";\nimport { RequestMiddlewareInputContext, RequestMiddlewareOutputContext } from \"./request-middleware.js\";\nimport { parseFragnoResponse } from \"./fragno-response.js\";\nimport { RequestContextStorage } from \"./request-context-storage.js\";\nimport { bindServicesToContext } from \"./bind-services.js\";\nimport { addRoute, createRouter, findRoute } from \"rou3\";\n\n//#region src/api/fragment-instantiator.ts\n/**\n* Instantiated fragment class with encapsulated state.\n* Provides the same public API as the old FragnoInstantiatedFragment but with better encapsulation.\n*/\nvar FragnoInstantiatedFragment = class {\n\t[instantiatedFragmentFakeSymbol] = instantiatedFragmentFakeSymbol;\n\t#name;\n\t#routes;\n\t#deps;\n\t#services;\n\t#mountRoute;\n\t#router;\n\t#middlewareHandler;\n\t#serviceThisContext;\n\t#handlerThisContext;\n\t#contextStorage;\n\t#createRequestStorage;\n\t#options;\n\t#linkedFragments;\n\tconstructor(params) {\n\t\tthis.#name = params.name;\n\t\tthis.#routes = params.routes;\n\t\tthis.#deps = params.deps;\n\t\tthis.#services = params.services;\n\t\tthis.#mountRoute = params.mountRoute;\n\t\tthis.#serviceThisContext = params.serviceThisContext;\n\t\tthis.#handlerThisContext = params.handlerThisContext;\n\t\tthis.#contextStorage = params.storage;\n\t\tthis.#createRequestStorage = params.createRequestStorage;\n\t\tthis.#options = params.options;\n\t\tthis.#linkedFragments = params.linkedFragments ?? {};\n\t\tthis.#router = createRouter();\n\t\tfor (const routeConfig of this.#routes) addRoute(this.#router, routeConfig.method.toUpperCase(), routeConfig.path, routeConfig);\n\t\tthis.handler = this.handler.bind(this);\n\t}\n\tget name() {\n\t\treturn this.#name;\n\t}\n\tget routes() {\n\t\treturn this.#routes;\n\t}\n\tget services() {\n\t\treturn this.#services;\n\t}\n\tget mountRoute() {\n\t\treturn this.#mountRoute;\n\t}\n\t/**\n\t* @internal\n\t*/\n\tget $internal() {\n\t\treturn {\n\t\t\tdeps: this.#deps,\n\t\t\toptions: this.#options,\n\t\t\tlinkedFragments: this.#linkedFragments\n\t\t};\n\t}\n\t/**\n\t* Add middleware to this fragment.\n\t* Middleware can inspect and modify requests before they reach handlers.\n\t*/\n\twithMiddleware(handler) {\n\t\tif (this.#middlewareHandler) throw new Error(\"Middleware already set\");\n\t\tthis.#middlewareHandler = handler;\n\t\treturn this;\n\t}\n\t#withRequestStorage(callback) {\n\t\tif (!this.#serviceThisContext && !this.#handlerThisContext) return callback();\n\t\tconst storageData = this.#createRequestStorage ? this.#createRequestStorage() : {};\n\t\treturn this.#contextStorage.run(storageData, callback);\n\t}\n\tinContext(callback) {\n\t\tif (this.#handlerThisContext) {\n\t\t\tconst boundCallback = callback.bind(this.#handlerThisContext);\n\t\t\treturn this.#withRequestStorage(boundCallback);\n\t\t}\n\t\treturn this.#withRequestStorage(callback);\n\t}\n\t/**\n\t* Get framework-specific handlers for this fragment.\n\t* Use this to integrate the fragment with different fullstack frameworks.\n\t*/\n\thandlersFor(framework) {\n\t\tconst handler = this.handler.bind(this);\n\t\tif (framework === \"h3\" || framework === \"nuxt\") throw new Error(`To get handlers for h3, use the 'fromWebHandler' utility function:\n import { fromWebHandler } from \"h3\";\n export default fromWebHandler(myFragment().handler);`);\n\t\treturn {\n\t\t\tastro: { ALL: handler },\n\t\t\t\"react-router\": {\n\t\t\t\tloader: ({ request }) => handler(request),\n\t\t\t\taction: ({ request }) => handler(request)\n\t\t\t},\n\t\t\t\"next-js\": {\n\t\t\t\tGET: handler,\n\t\t\t\tPOST: handler,\n\t\t\t\tPUT: handler,\n\t\t\t\tDELETE: handler,\n\t\t\t\tPATCH: handler,\n\t\t\t\tHEAD: handler,\n\t\t\t\tOPTIONS: handler\n\t\t\t},\n\t\t\t\"svelte-kit\": {\n\t\t\t\tGET: handler,\n\t\t\t\tPOST: handler,\n\t\t\t\tPUT: handler,\n\t\t\t\tDELETE: handler,\n\t\t\t\tPATCH: handler,\n\t\t\t\tHEAD: handler,\n\t\t\t\tOPTIONS: handler\n\t\t\t},\n\t\t\t\"solid-start\": {\n\t\t\t\tGET: ({ request }) => handler(request),\n\t\t\t\tPOST: ({ request }) => handler(request),\n\t\t\t\tPUT: ({ request }) => handler(request),\n\t\t\t\tDELETE: ({ request }) => handler(request),\n\t\t\t\tPATCH: ({ request }) => handler(request),\n\t\t\t\tHEAD: ({ request }) => handler(request),\n\t\t\t\tOPTIONS: ({ request }) => handler(request)\n\t\t\t},\n\t\t\t\"tanstack-start\": {\n\t\t\t\tGET: ({ request }) => handler(request),\n\t\t\t\tPOST: ({ request }) => handler(request),\n\t\t\t\tPUT: ({ request }) => handler(request),\n\t\t\t\tDELETE: ({ request }) => handler(request),\n\t\t\t\tPATCH: ({ request }) => handler(request),\n\t\t\t\tHEAD: ({ request }) => handler(request),\n\t\t\t\tOPTIONS: ({ request }) => handler(request)\n\t\t\t}\n\t\t}[framework];\n\t}\n\t/**\n\t* Main request handler for this fragment.\n\t* Handles routing, middleware, and error handling.\n\t*/\n\tasync handler(req) {\n\t\tconst url = new URL(req.url);\n\t\tconst pathname = url.pathname;\n\t\tconst matchRoute = pathname.startsWith(this.#mountRoute) ? pathname.slice(this.#mountRoute.length) : null;\n\t\tif (matchRoute === null) return Response.json({\n\t\t\terror: `Fragno: Route for '${this.#name}' not found. Is the fragment mounted on the right route? Expecting: '${this.#mountRoute}'.`,\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst route = findRoute(this.#router, req.method, matchRoute);\n\t\tif (!route) return Response.json({\n\t\t\terror: `Fragno: Route for '${this.#name}' not found`,\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tlet requestBody = void 0;\n\t\tlet rawBody = void 0;\n\t\tif (req.body instanceof ReadableStream) {\n\t\t\trawBody = await req.clone().text();\n\t\t\tif (rawBody) try {\n\t\t\t\trequestBody = JSON.parse(rawBody);\n\t\t\t} catch {\n\t\t\t\trequestBody = void 0;\n\t\t\t}\n\t\t}\n\t\tconst requestState = new MutableRequestState({\n\t\t\tpathParams: route.params ?? {},\n\t\t\tsearchParams: url.searchParams,\n\t\t\tbody: requestBody,\n\t\t\theaders: new Headers(req.headers)\n\t\t});\n\t\tconst executeRequest = async () => {\n\t\t\tif (this.#middlewareHandler) {\n\t\t\t\tconst middlewareResult = await this.#executeMiddleware(req, route, requestState);\n\t\t\t\tif (middlewareResult !== void 0) return middlewareResult;\n\t\t\t}\n\t\t\treturn this.#executeHandler(req, route, requestState, rawBody);\n\t\t};\n\t\treturn this.#withRequestStorage(executeRequest);\n\t}\n\t/**\n\t* Call a route directly with typed inputs and outputs.\n\t* Useful for testing and server-side route calls.\n\t*/\n\tasync callRoute(method, path, inputOptions) {\n\t\treturn parseFragnoResponse(await this.callRouteRaw(method, path, inputOptions));\n\t}\n\t/**\n\t* Call a route directly and get the raw Response object.\n\t* Useful for testing and server-side route calls.\n\t*/\n\tasync callRouteRaw(method, path, inputOptions) {\n\t\tconst route = this.#routes.find((r) => r.method === method && r.path === path);\n\t\tif (!route) return Response.json({\n\t\t\terror: `Route ${method} ${path} not found`,\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst { pathParams = {}, body, query, headers } = inputOptions || {};\n\t\tconst searchParams = query instanceof URLSearchParams ? query : query ? new URLSearchParams(query) : new URLSearchParams();\n\t\tconst requestHeaders = headers instanceof Headers ? headers : headers ? new Headers(headers) : new Headers();\n\t\tconst inputContext = new RequestInputContext({\n\t\t\tpath: route.path,\n\t\t\tmethod: route.method,\n\t\t\tpathParams,\n\t\t\tsearchParams,\n\t\t\theaders: requestHeaders,\n\t\t\tparsedBody: body,\n\t\t\tinputSchema: route.inputSchema,\n\t\t\tshouldValidateInput: true\n\t\t});\n\t\tconst outputContext = new RequestOutputContext(route.outputSchema);\n\t\tconst executeHandler = async () => {\n\t\t\ttry {\n\t\t\t\tconst thisContext = this.#handlerThisContext ?? {};\n\t\t\t\treturn await route.handler.call(thisContext, inputContext, outputContext);\n\t\t\t} catch (error) {\n\t\t\t\tconsole.error(\"Error in callRoute handler\", error);\n\t\t\t\tif (error instanceof FragnoApiError) return error.toResponse();\n\t\t\t\treturn Response.json({\n\t\t\t\t\terror: \"Internal server error\",\n\t\t\t\t\tcode: \"INTERNAL_SERVER_ERROR\"\n\t\t\t\t}, { status: 500 });\n\t\t\t}\n\t\t};\n\t\treturn this.#withRequestStorage(executeHandler);\n\t}\n\t/**\n\t* Execute middleware for a request.\n\t* Returns undefined if middleware allows the request to continue to the handler.\n\t*/\n\tasync #executeMiddleware(req, route, requestState) {\n\t\tif (!this.#middlewareHandler || !route) return;\n\t\tconst { path } = route.data;\n\t\tconst middlewareInputContext = new RequestMiddlewareInputContext(this.#routes, {\n\t\t\tmethod: req.method,\n\t\t\tpath,\n\t\t\trequest: req,\n\t\t\tstate: requestState\n\t\t});\n\t\tconst middlewareOutputContext = new RequestMiddlewareOutputContext(this.#deps, this.#services);\n\t\ttry {\n\t\t\tconst middlewareResult = await this.#middlewareHandler(middlewareInputContext, middlewareOutputContext);\n\t\t\tif (middlewareResult !== void 0) return middlewareResult;\n\t\t} catch (error) {\n\t\t\tconsole.error(\"Error in middleware\", error);\n\t\t\tif (error instanceof FragnoApiError) return error.toResponse();\n\t\t\treturn Response.json({\n\t\t\t\terror: \"Internal server error\",\n\t\t\t\tcode: \"INTERNAL_SERVER_ERROR\"\n\t\t\t}, { status: 500 });\n\t\t}\n\t}\n\t/**\n\t* Execute a route handler with proper error handling.\n\t*/\n\tasync #executeHandler(req, route, requestState, rawBody) {\n\t\tif (!route) return Response.json({\n\t\t\terror: \"Route not found\",\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst { handler, inputSchema, outputSchema, path } = route.data;\n\t\tconst inputContext = await RequestInputContext.fromRequest({\n\t\t\trequest: req,\n\t\t\tmethod: req.method,\n\t\t\tpath,\n\t\t\tpathParams: route.params ?? {},\n\t\t\tinputSchema,\n\t\t\tstate: requestState,\n\t\t\trawBody\n\t\t});\n\t\tconst outputContext = new RequestOutputContext(outputSchema);\n\t\ttry {\n\t\t\tconst contextForHandler = this.#handlerThisContext ?? {};\n\t\t\treturn await handler.call(contextForHandler, inputContext, outputContext);\n\t\t} catch (error) {\n\t\t\tconsole.error(\"Error in handler\", error);\n\t\t\tif (error instanceof FragnoApiError) return error.toResponse();\n\t\t\treturn Response.json({\n\t\t\t\terror: \"Internal server error\",\n\t\t\t\tcode: \"INTERNAL_SERVER_ERROR\"\n\t\t\t}, { status: 500 });\n\t\t}\n\t}\n};\n/**\n* Core instantiation function that creates a fragment instance from a definition.\n* This function validates dependencies, calls all callbacks, and wires everything together.\n*/\nfunction instantiateFragment(definition, config, routesOrFactories, options, serviceImplementations, instantiationOptions) {\n\tconst { dryRun = false } = instantiationOptions ?? {};\n\tconst serviceDependencies = definition.serviceDependencies;\n\tif (serviceDependencies) for (const [serviceName, meta] of Object.entries(serviceDependencies)) {\n\t\tconst metadata = meta;\n\t\tconst implementation = serviceImplementations?.[serviceName];\n\t\tif (metadata.required && !implementation) throw new Error(`Fragment '${definition.name}' requires service '${metadata.name}' but it was not provided`);\n\t}\n\tlet deps;\n\ttry {\n\t\tdeps = definition.dependencies?.({\n\t\t\tconfig,\n\t\t\toptions\n\t\t}) ?? {};\n\t} catch (error) {\n\t\tif (dryRun) {\n\t\t\tconsole.warn(\"Warning: Failed to initialize dependencies in dry run mode:\", error instanceof Error ? error.message : String(error));\n\t\t\tdeps = {};\n\t\t} else throw error;\n\t}\n\tconst linkedFragmentInstances = {};\n\tconst linkedFragmentServices = {};\n\tif (definition.linkedFragments) for (const [name, callback] of Object.entries(definition.linkedFragments)) {\n\t\tconst linkedFragment = callback({\n\t\t\tconfig,\n\t\t\toptions,\n\t\t\tserviceDependencies: serviceImplementations\n\t\t});\n\t\tlinkedFragmentInstances[name] = linkedFragment;\n\t\tconst services$1 = linkedFragment.services;\n\t\tfor (const [serviceName, service] of Object.entries(services$1)) linkedFragmentServices[serviceName] = service;\n\t}\n\tconst defineService = (services$1) => services$1;\n\tconst privateServices = { ...linkedFragmentServices };\n\tif (definition.privateServices) for (const [serviceName, factory] of Object.entries(definition.privateServices)) {\n\t\tconst serviceFactory = factory;\n\t\ttry {\n\t\t\tprivateServices[serviceName] = serviceFactory({\n\t\t\t\tconfig,\n\t\t\t\toptions,\n\t\t\t\tdeps,\n\t\t\t\tserviceDeps: serviceImplementations ?? {},\n\t\t\t\tprivateServices,\n\t\t\t\tdefineService\n\t\t\t});\n\t\t} catch (error) {\n\t\t\tif (dryRun) {\n\t\t\t\tconsole.warn(`Warning: Failed to initialize private service '${serviceName}' in dry run mode:`, error instanceof Error ? error.message : String(error));\n\t\t\t\tprivateServices[serviceName] = {};\n\t\t\t} else throw error;\n\t\t}\n\t}\n\tlet baseServices;\n\ttry {\n\t\tbaseServices = definition.baseServices?.({\n\t\t\tconfig,\n\t\t\toptions,\n\t\t\tdeps,\n\t\t\tserviceDeps: serviceImplementations ?? {},\n\t\t\tprivateServices,\n\t\t\tdefineService\n\t\t}) ?? {};\n\t} catch (error) {\n\t\tif (dryRun) {\n\t\t\tconsole.warn(\"Warning: Failed to initialize base services in dry run mode:\", error instanceof Error ? error.message : String(error));\n\t\t\tbaseServices = {};\n\t\t} else throw error;\n\t}\n\tconst namedServices = {};\n\tif (definition.namedServices) for (const [serviceName, factory] of Object.entries(definition.namedServices)) {\n\t\tconst serviceFactory = factory;\n\t\ttry {\n\t\t\tnamedServices[serviceName] = serviceFactory({\n\t\t\t\tconfig,\n\t\t\t\toptions,\n\t\t\t\tdeps,\n\t\t\t\tserviceDeps: serviceImplementations ?? {},\n\t\t\t\tprivateServices,\n\t\t\t\tdefineService\n\t\t\t});\n\t\t} catch (error) {\n\t\t\tif (dryRun) {\n\t\t\t\tconsole.warn(`Warning: Failed to initialize service '${serviceName}' in dry run mode:`, error instanceof Error ? error.message : String(error));\n\t\t\t\tnamedServices[serviceName] = {};\n\t\t\t} else throw error;\n\t\t}\n\t}\n\tconst services = {\n\t\t...baseServices,\n\t\t...namedServices\n\t};\n\tconst storage = definition.getExternalStorage ? definition.getExternalStorage({\n\t\tconfig,\n\t\toptions,\n\t\tdeps\n\t}) : new RequestContextStorage();\n\tconst contexts = definition.createThisContext?.({\n\t\tconfig,\n\t\toptions,\n\t\tdeps,\n\t\tstorage\n\t});\n\tconst serviceContext = contexts?.serviceContext;\n\tconst handlerContext = contexts?.handlerContext;\n\tconst boundServices = serviceContext ? bindServicesToContext(services, serviceContext) : services;\n\tconst routes = resolveRouteFactories({\n\t\tconfig,\n\t\tdeps,\n\t\tservices: boundServices,\n\t\tserviceDeps: serviceImplementations ?? {}\n\t}, routesOrFactories);\n\tconst mountRoute = getMountRoute({\n\t\tname: definition.name,\n\t\tmountRoute: options.mountRoute\n\t});\n\tconst createRequestStorageWithContext = definition.createRequestStorage ? () => definition.createRequestStorage({\n\t\tconfig,\n\t\toptions,\n\t\tdeps\n\t}) : void 0;\n\treturn new FragnoInstantiatedFragment({\n\t\tname: definition.name,\n\t\troutes,\n\t\tdeps,\n\t\tservices: boundServices,\n\t\tmountRoute,\n\t\tserviceThisContext: serviceContext,\n\t\thandlerThisContext: handlerContext,\n\t\tstorage,\n\t\tcreateRequestStorage: createRequestStorageWithContext,\n\t\toptions,\n\t\tlinkedFragments: linkedFragmentInstances\n\t});\n}\n/**\n* Fluent builder for instantiating fragments.\n* Provides a type-safe API for configuring and building fragment instances.\n*/\nvar FragmentInstantiationBuilder = class FragmentInstantiationBuilder {\n\t#definition;\n\t#config;\n\t#routes;\n\t#options;\n\t#services;\n\tconstructor(definition, routes) {\n\t\tthis.#definition = definition;\n\t\tthis.#routes = routes;\n\t}\n\t/**\n\t* Get the fragment definition\n\t*/\n\tget definition() {\n\t\treturn this.#definition;\n\t}\n\t/**\n\t* Get the configured routes\n\t*/\n\tget routes() {\n\t\treturn this.#routes ?? [];\n\t}\n\t/**\n\t* Get the configuration\n\t*/\n\tget config() {\n\t\treturn this.#config;\n\t}\n\t/**\n\t* Get the options\n\t*/\n\tget options() {\n\t\treturn this.#options;\n\t}\n\t/**\n\t* Set the configuration for the fragment\n\t*/\n\twithConfig(config) {\n\t\tthis.#config = config;\n\t\treturn this;\n\t}\n\t/**\n\t* Set the routes for the fragment\n\t*/\n\twithRoutes(routes) {\n\t\tconst newBuilder = new FragmentInstantiationBuilder(this.#definition, routes);\n\t\tnewBuilder.#config = this.#config;\n\t\tnewBuilder.#options = this.#options;\n\t\tnewBuilder.#services = this.#services;\n\t\treturn newBuilder;\n\t}\n\t/**\n\t* Set the options for the fragment (e.g., mountRoute, databaseAdapter)\n\t*/\n\twithOptions(options) {\n\t\tthis.#options = options;\n\t\treturn this;\n\t}\n\t/**\n\t* Provide implementations for services that this fragment uses\n\t*/\n\twithServices(services) {\n\t\tthis.#services = services;\n\t\treturn this;\n\t}\n\t/**\n\t* Build and return the instantiated fragment\n\t*/\n\tbuild() {\n\t\tconst dryRun = process.env[\"FRAGNO_INIT_DRY_RUN\"] === \"true\";\n\t\treturn instantiateFragment(this.#definition, this.#config ?? {}, this.#routes ?? [], this.#options ?? {}, this.#services, { dryRun });\n\t}\n};\n/**\n* Create a fluent builder for instantiating a fragment.\n*\n* @example\n* ```ts\n* const fragment = instantiate(myFragmentDefinition)\n* .withConfig({ apiKey: \"key\" })\n* .withRoutes([route1, route2])\n* .withOptions({ mountRoute: \"/api\" })\n* .build();\n* ```\n*/\nfunction instantiate(definition) {\n\treturn new FragmentInstantiationBuilder(definition);\n}\n\n//#endregion\nexport { FragmentInstantiationBuilder, FragnoInstantiatedFragment, instantiate, instantiateFragment };\n//# sourceMappingURL=fragment-instantiator.js.map"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"fragment-instantiator.js","names":["FragnoInstantiatedFragment","#name","#routes","#deps","#services","#mountRoute","#serviceThisContext","#handlerThisContext","#contextStorage","#createRequestStorage","#options","#linkedFragments","#internalData","#router","#middlewareHandler","#withRequestStorage","#executeMiddleware","#runMiddlewareForFragment","#executeHandler","FragmentInstantiationBuilder","#definition","#config"],"sources":["../../../../../../fragno/dist/api/fragment-instantiator.js"],"sourcesContent":["import { instantiatedFragmentFakeSymbol } from \"../internal/symbols.js\";\nimport { resolveRouteFactories } from \"./route.js\";\nimport { FragnoApiError } from \"./error.js\";\nimport { getMountRoute } from \"./internal/route.js\";\nimport { RequestInputContext } from \"./request-input-context.js\";\nimport { RequestOutputContext } from \"./request-output-context.js\";\nimport { MutableRequestState } from \"./mutable-request-state.js\";\nimport { RequestMiddlewareInputContext, RequestMiddlewareOutputContext } from \"./request-middleware.js\";\nimport { parseFragnoResponse } from \"./fragno-response.js\";\nimport { RequestContextStorage } from \"./request-context-storage.js\";\nimport { bindServicesToContext } from \"./bind-services.js\";\nimport { recordTraceEvent } from \"../internal/trace-context.js\";\nimport { addRoute, createRouter, findRoute } from \"rou3\";\n\n//#region src/api/fragment-instantiator.ts\nconst serializeHeadersForTrace = (headers) => Array.from(headers.entries()).sort(([a], [b]) => a.localeCompare(b));\nconst serializeQueryForTrace = (query) => Array.from(query.entries()).sort(([a], [b]) => a.localeCompare(b));\nconst serializeBodyForTrace = (body) => {\n\tif (body instanceof FormData) return {\n\t\ttype: \"form-data\",\n\t\tentries: Array.from(body.entries()).map(([key, value]) => {\n\t\t\tif (value instanceof Blob) return [key, {\n\t\t\t\ttype: \"blob\",\n\t\t\t\tsize: value.size,\n\t\t\t\tmime: value.type\n\t\t\t}];\n\t\t\treturn [key, value];\n\t\t})\n\t};\n\tif (body instanceof Blob) return {\n\t\ttype: \"blob\",\n\t\tsize: body.size,\n\t\tmime: body.type\n\t};\n\tif (body instanceof ReadableStream) return { type: \"stream\" };\n\treturn body;\n};\nconst INTERNAL_LINKED_FRAGMENT_NAME = \"_fragno_internal\";\nconst INTERNAL_ROUTE_PREFIX = \"/_internal\";\nfunction normalizeRoutePrefix(prefix) {\n\tif (!prefix.startsWith(\"/\")) prefix = `/${prefix}`;\n\treturn prefix.endsWith(\"/\") && prefix.length > 1 ? prefix.slice(0, -1) : prefix;\n}\nfunction joinRoutePath(prefix, path) {\n\tconst normalizedPrefix = normalizeRoutePrefix(prefix);\n\tif (!path || path === \"/\") return normalizedPrefix;\n\treturn `${normalizedPrefix}${path.startsWith(\"/\") ? path : `/${path}`}`;\n}\nfunction collectLinkedFragmentRoutes(linkedFragments) {\n\tconst linkedRoutes = [];\n\tfor (const [name, fragment] of Object.entries(linkedFragments)) {\n\t\tif (name !== INTERNAL_LINKED_FRAGMENT_NAME) continue;\n\t\tconst internalRoutes = fragment.routes ?? [];\n\t\tif (internalRoutes.length === 0) continue;\n\t\tfor (const route of internalRoutes) linkedRoutes.push({\n\t\t\t...route,\n\t\t\tpath: joinRoutePath(INTERNAL_ROUTE_PREFIX, route.path),\n\t\t\t__internal: {\n\t\t\t\tfragment,\n\t\t\t\toriginalPath: route.path,\n\t\t\t\troutes: internalRoutes\n\t\t\t}\n\t\t});\n\t}\n\treturn linkedRoutes;\n}\n/**\n* Instantiated fragment class with encapsulated state.\n* Provides the same public API as the old FragnoInstantiatedFragment but with better encapsulation.\n*/\nvar FragnoInstantiatedFragment = class FragnoInstantiatedFragment {\n\t[instantiatedFragmentFakeSymbol] = instantiatedFragmentFakeSymbol;\n\t#name;\n\t#routes;\n\t#deps;\n\t#services;\n\t#mountRoute;\n\t#router;\n\t#middlewareHandler;\n\t#serviceThisContext;\n\t#handlerThisContext;\n\t#contextStorage;\n\t#createRequestStorage;\n\t#options;\n\t#linkedFragments;\n\t#internalData;\n\tconstructor(params) {\n\t\tthis.#name = params.name;\n\t\tthis.#routes = params.routes;\n\t\tthis.#deps = params.deps;\n\t\tthis.#services = params.services;\n\t\tthis.#mountRoute = params.mountRoute;\n\t\tthis.#serviceThisContext = params.serviceThisContext;\n\t\tthis.#handlerThisContext = params.handlerThisContext;\n\t\tthis.#contextStorage = params.storage;\n\t\tthis.#createRequestStorage = params.createRequestStorage;\n\t\tthis.#options = params.options;\n\t\tthis.#linkedFragments = params.linkedFragments ?? {};\n\t\tthis.#internalData = params.internalData ?? {};\n\t\tthis.#router = createRouter();\n\t\tfor (const routeConfig of this.#routes) addRoute(this.#router, routeConfig.method.toUpperCase(), routeConfig.path, routeConfig);\n\t\tthis.handler = this.handler.bind(this);\n\t}\n\tget name() {\n\t\treturn this.#name;\n\t}\n\tget routes() {\n\t\treturn this.#routes;\n\t}\n\tget services() {\n\t\treturn this.#services;\n\t}\n\tget mountRoute() {\n\t\treturn this.#mountRoute;\n\t}\n\t/**\n\t* @internal\n\t*/\n\tget $internal() {\n\t\treturn {\n\t\t\tdeps: this.#deps,\n\t\t\toptions: this.#options,\n\t\t\tlinkedFragments: this.#linkedFragments,\n\t\t\t...this.#internalData\n\t\t};\n\t}\n\t/**\n\t* Add middleware to this fragment.\n\t* Middleware can inspect and modify requests before they reach handlers.\n\t*/\n\twithMiddleware(handler) {\n\t\tif (this.#middlewareHandler) throw new Error(\"Middleware already set\");\n\t\tthis.#middlewareHandler = handler;\n\t\treturn this;\n\t}\n\t#withRequestStorage(callback) {\n\t\tif (!this.#serviceThisContext && !this.#handlerThisContext) return callback();\n\t\tconst storageData = this.#createRequestStorage ? this.#createRequestStorage() : {};\n\t\treturn this.#contextStorage.run(storageData, callback);\n\t}\n\tinContext(callback) {\n\t\tif (this.#handlerThisContext) {\n\t\t\tconst boundCallback = callback.bind(this.#handlerThisContext);\n\t\t\treturn this.#withRequestStorage(boundCallback);\n\t\t}\n\t\treturn this.#withRequestStorage(callback);\n\t}\n\t/**\n\t* Get framework-specific handlers for this fragment.\n\t* Use this to integrate the fragment with different fullstack frameworks.\n\t*/\n\thandlersFor(framework) {\n\t\tconst handler = this.handler.bind(this);\n\t\tif (framework === \"h3\" || framework === \"nuxt\") throw new Error(`To get handlers for h3, use the 'fromWebHandler' utility function:\n import { fromWebHandler } from \"h3\";\n export default fromWebHandler(myFragment().handler);`);\n\t\treturn {\n\t\t\tastro: { ALL: handler },\n\t\t\t\"react-router\": {\n\t\t\t\tloader: ({ request }) => handler(request),\n\t\t\t\taction: ({ request }) => handler(request)\n\t\t\t},\n\t\t\t\"next-js\": {\n\t\t\t\tGET: handler,\n\t\t\t\tPOST: handler,\n\t\t\t\tPUT: handler,\n\t\t\t\tDELETE: handler,\n\t\t\t\tPATCH: handler,\n\t\t\t\tHEAD: handler,\n\t\t\t\tOPTIONS: handler\n\t\t\t},\n\t\t\t\"svelte-kit\": {\n\t\t\t\tGET: handler,\n\t\t\t\tPOST: handler,\n\t\t\t\tPUT: handler,\n\t\t\t\tDELETE: handler,\n\t\t\t\tPATCH: handler,\n\t\t\t\tHEAD: handler,\n\t\t\t\tOPTIONS: handler\n\t\t\t},\n\t\t\t\"solid-start\": {\n\t\t\t\tGET: ({ request }) => handler(request),\n\t\t\t\tPOST: ({ request }) => handler(request),\n\t\t\t\tPUT: ({ request }) => handler(request),\n\t\t\t\tDELETE: ({ request }) => handler(request),\n\t\t\t\tPATCH: ({ request }) => handler(request),\n\t\t\t\tHEAD: ({ request }) => handler(request),\n\t\t\t\tOPTIONS: ({ request }) => handler(request)\n\t\t\t},\n\t\t\t\"tanstack-start\": {\n\t\t\t\tGET: ({ request }) => handler(request),\n\t\t\t\tPOST: ({ request }) => handler(request),\n\t\t\t\tPUT: ({ request }) => handler(request),\n\t\t\t\tDELETE: ({ request }) => handler(request),\n\t\t\t\tPATCH: ({ request }) => handler(request),\n\t\t\t\tHEAD: ({ request }) => handler(request),\n\t\t\t\tOPTIONS: ({ request }) => handler(request)\n\t\t\t}\n\t\t}[framework];\n\t}\n\t/**\n\t* Main request handler for this fragment.\n\t* Handles routing, middleware, and error handling.\n\t*/\n\tasync handler(req) {\n\t\tconst url = new URL(req.url);\n\t\tconst pathname = url.pathname;\n\t\tconst matchRoute = pathname.startsWith(this.#mountRoute) ? pathname.slice(this.#mountRoute.length) : null;\n\t\tif (matchRoute === null) return Response.json({\n\t\t\terror: `Fragno: Route for '${this.#name}' not found. Is the fragment mounted on the right route? Expecting: '${this.#mountRoute}'.`,\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst route = findRoute(this.#router, req.method, matchRoute);\n\t\tif (!route) return Response.json({\n\t\t\terror: `Fragno: Route for '${this.#name}' not found`,\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst routeConfig = route.data;\n\t\tconst expectedContentType = routeConfig.contentType ?? \"application/json\";\n\t\tlet requestBody = void 0;\n\t\tlet rawBody = void 0;\n\t\tif (req.body instanceof ReadableStream) {\n\t\t\tconst requestContentType = (req.headers.get(\"content-type\") ?? \"\").toLowerCase();\n\t\t\tif (expectedContentType === \"multipart/form-data\") {\n\t\t\t\tif (!requestContentType.includes(\"multipart/form-data\")) return Response.json({\n\t\t\t\t\terror: `This endpoint expects multipart/form-data, but received: ${requestContentType || \"no content-type\"}`,\n\t\t\t\t\tcode: \"UNSUPPORTED_MEDIA_TYPE\"\n\t\t\t\t}, { status: 415 });\n\t\t\t\ttry {\n\t\t\t\t\trequestBody = await req.formData();\n\t\t\t\t} catch {\n\t\t\t\t\treturn Response.json({\n\t\t\t\t\t\terror: \"Failed to parse multipart form data\",\n\t\t\t\t\t\tcode: \"INVALID_REQUEST_BODY\"\n\t\t\t\t\t}, { status: 400 });\n\t\t\t\t}\n\t\t\t} else if (expectedContentType === \"application/octet-stream\") {\n\t\t\t\tif (!requestContentType.includes(\"application/octet-stream\")) return Response.json({\n\t\t\t\t\terror: `This endpoint expects application/octet-stream, but received: ${requestContentType || \"no content-type\"}`,\n\t\t\t\t\tcode: \"UNSUPPORTED_MEDIA_TYPE\"\n\t\t\t\t}, { status: 415 });\n\t\t\t\trequestBody = req.body ?? new ReadableStream();\n\t\t\t} else {\n\t\t\t\tif (requestContentType.includes(\"multipart/form-data\")) return Response.json({\n\t\t\t\t\terror: `This endpoint expects JSON, but received multipart/form-data. Use a route with contentType: \"multipart/form-data\" for file uploads.`,\n\t\t\t\t\tcode: \"UNSUPPORTED_MEDIA_TYPE\"\n\t\t\t\t}, { status: 415 });\n\t\t\t\trawBody = await req.clone().text();\n\t\t\t\tif (rawBody) try {\n\t\t\t\t\trequestBody = JSON.parse(rawBody);\n\t\t\t\t} catch {\n\t\t\t\t\trequestBody = void 0;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tconst decodedRouteParams = {};\n\t\tfor (const [key, value] of Object.entries(route.params ?? {})) decodedRouteParams[key] = decodeURIComponent(value);\n\t\tconst requestState = new MutableRequestState({\n\t\t\tpathParams: decodedRouteParams,\n\t\t\tsearchParams: url.searchParams,\n\t\t\tbody: requestBody,\n\t\t\theaders: new Headers(req.headers)\n\t\t});\n\t\tconst executeRequest = async () => {\n\t\t\tconst middlewareResult = await this.#executeMiddleware(req, route, requestState);\n\t\t\tif (middlewareResult !== void 0) return middlewareResult;\n\t\t\tconst internalMeta = routeConfig.__internal;\n\t\t\tif (internalMeta) {\n\t\t\t\tconst internalResult = await FragnoInstantiatedFragment.#runMiddlewareForFragment(internalMeta.fragment, {\n\t\t\t\t\treq,\n\t\t\t\t\tmethod: routeConfig.method,\n\t\t\t\t\tpath: internalMeta.originalPath,\n\t\t\t\t\trequestState,\n\t\t\t\t\troutes: internalMeta.routes\n\t\t\t\t});\n\t\t\t\tif (internalResult !== void 0) return internalResult;\n\t\t\t}\n\t\t\treturn this.#executeHandler(req, route, requestState, rawBody);\n\t\t};\n\t\treturn this.#withRequestStorage(executeRequest);\n\t}\n\t/**\n\t* Call a route directly with typed inputs and outputs.\n\t* Useful for testing and server-side route calls.\n\t*/\n\tasync callRoute(method, path, inputOptions) {\n\t\treturn parseFragnoResponse(await this.callRouteRaw(method, path, inputOptions));\n\t}\n\t/**\n\t* Call a route directly and get the raw Response object.\n\t* Useful for testing and server-side route calls.\n\t*/\n\tasync callRouteRaw(method, path, inputOptions) {\n\t\tconst route = this.#routes.find((r) => r.method === method && r.path === path);\n\t\tif (!route) return Response.json({\n\t\t\terror: `Route ${method} ${path} not found`,\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst { pathParams = {}, body, query, headers } = inputOptions || {};\n\t\tconst searchParams = query instanceof URLSearchParams ? query : query ? new URLSearchParams(query) : new URLSearchParams();\n\t\tconst requestHeaders = headers instanceof Headers ? headers : headers ? new Headers(headers) : new Headers();\n\t\tconst inputContext = new RequestInputContext({\n\t\t\tpath: route.path,\n\t\t\tmethod: route.method,\n\t\t\tpathParams,\n\t\t\tsearchParams,\n\t\t\theaders: requestHeaders,\n\t\t\tparsedBody: body,\n\t\t\tinputSchema: route.inputSchema,\n\t\t\tshouldValidateInput: true\n\t\t});\n\t\trecordTraceEvent({\n\t\t\ttype: \"route-input\",\n\t\t\tmethod: route.method,\n\t\t\tpath: route.path,\n\t\t\tpathParams: pathParams ?? {},\n\t\t\tqueryParams: serializeQueryForTrace(searchParams),\n\t\t\theaders: serializeHeadersForTrace(requestHeaders),\n\t\t\tbody: serializeBodyForTrace(body)\n\t\t});\n\t\tconst outputContext = new RequestOutputContext(route.outputSchema);\n\t\tconst executeHandler = async () => {\n\t\t\ttry {\n\t\t\t\tconst thisContext = this.#handlerThisContext ?? {};\n\t\t\t\treturn await route.handler.call(thisContext, inputContext, outputContext);\n\t\t\t} catch (error) {\n\t\t\t\tconsole.error(\"Error in callRoute handler\", error);\n\t\t\t\tif (error instanceof FragnoApiError) return error.toResponse();\n\t\t\t\treturn Response.json({\n\t\t\t\t\terror: \"Internal server error\",\n\t\t\t\t\tcode: \"INTERNAL_SERVER_ERROR\"\n\t\t\t\t}, { status: 500 });\n\t\t\t}\n\t\t};\n\t\treturn this.#withRequestStorage(executeHandler);\n\t}\n\t/**\n\t* Execute middleware for a request.\n\t* Returns undefined if middleware allows the request to continue to the handler.\n\t*/\n\tasync #executeMiddleware(req, route, requestState) {\n\t\tif (!route) return;\n\t\tconst { path } = route.data;\n\t\treturn FragnoInstantiatedFragment.#runMiddlewareForFragment(this, {\n\t\t\treq,\n\t\t\tmethod: req.method,\n\t\t\tpath,\n\t\t\trequestState\n\t\t});\n\t}\n\tstatic async #runMiddlewareForFragment(fragment, options) {\n\t\tif (!fragment.#middlewareHandler) return;\n\t\tconst middlewareInputContext = new RequestMiddlewareInputContext(options.routes ?? fragment.#routes, {\n\t\t\tmethod: options.method,\n\t\t\tpath: options.path,\n\t\t\trequest: options.req,\n\t\t\tstate: options.requestState\n\t\t});\n\t\tconst middlewareOutputContext = new RequestMiddlewareOutputContext(fragment.#deps, fragment.#services);\n\t\ttry {\n\t\t\tconst middlewareResult = await fragment.#middlewareHandler(middlewareInputContext, middlewareOutputContext);\n\t\t\trecordTraceEvent({\n\t\t\t\ttype: \"middleware-decision\",\n\t\t\t\tmethod: options.method,\n\t\t\t\tpath: options.path,\n\t\t\t\toutcome: middlewareResult ? \"deny\" : \"allow\",\n\t\t\t\tstatus: middlewareResult?.status\n\t\t\t});\n\t\t\tif (middlewareResult !== void 0) return middlewareResult;\n\t\t} catch (error) {\n\t\t\tconsole.error(\"Error in middleware\", error);\n\t\t\trecordTraceEvent({\n\t\t\t\ttype: \"middleware-decision\",\n\t\t\t\tmethod: options.method,\n\t\t\t\tpath: options.path,\n\t\t\t\toutcome: \"deny\",\n\t\t\t\tstatus: error instanceof FragnoApiError ? error.status : 500\n\t\t\t});\n\t\t\tif (error instanceof FragnoApiError) return error.toResponse();\n\t\t\treturn Response.json({\n\t\t\t\terror: \"Internal server error\",\n\t\t\t\tcode: \"INTERNAL_SERVER_ERROR\"\n\t\t\t}, { status: 500 });\n\t\t}\n\t}\n\t/**\n\t* Execute a route handler with proper error handling.\n\t*/\n\tasync #executeHandler(req, route, requestState, rawBody) {\n\t\tif (!route) return Response.json({\n\t\t\terror: \"Route not found\",\n\t\t\tcode: \"ROUTE_NOT_FOUND\"\n\t\t}, { status: 404 });\n\t\tconst { handler, inputSchema, outputSchema, path } = route.data;\n\t\tconst inputContext = await RequestInputContext.fromRequest({\n\t\t\trequest: req,\n\t\t\tmethod: req.method,\n\t\t\tpath,\n\t\t\tpathParams: route.params ?? {},\n\t\t\tinputSchema,\n\t\t\tstate: requestState,\n\t\t\trawBody\n\t\t});\n\t\trecordTraceEvent({\n\t\t\ttype: \"route-input\",\n\t\t\tmethod: req.method,\n\t\t\tpath,\n\t\t\tpathParams: inputContext.pathParams,\n\t\t\tqueryParams: serializeQueryForTrace(requestState.searchParams),\n\t\t\theaders: serializeHeadersForTrace(requestState.headers),\n\t\t\tbody: serializeBodyForTrace(requestState.body)\n\t\t});\n\t\tconst outputContext = new RequestOutputContext(outputSchema);\n\t\ttry {\n\t\t\tconst contextForHandler = this.#handlerThisContext ?? {};\n\t\t\treturn await handler.call(contextForHandler, inputContext, outputContext);\n\t\t} catch (error) {\n\t\t\tconsole.error(\"Error in handler\", error);\n\t\t\tif (error instanceof FragnoApiError) return error.toResponse();\n\t\t\treturn Response.json({\n\t\t\t\terror: \"Internal server error\",\n\t\t\t\tcode: \"INTERNAL_SERVER_ERROR\"\n\t\t\t}, { status: 500 });\n\t\t}\n\t}\n};\n/**\n* Core instantiation function that creates a fragment instance from a definition.\n* This function validates dependencies, calls all callbacks, and wires everything together.\n*/\nfunction instantiateFragment(definition, config, routesOrFactories, options, serviceImplementations, instantiationOptions) {\n\tconst { dryRun = false } = instantiationOptions ?? {};\n\tconst serviceDependencies = definition.serviceDependencies;\n\tif (serviceDependencies) for (const [serviceName, meta] of Object.entries(serviceDependencies)) {\n\t\tconst metadata = meta;\n\t\tconst implementation = serviceImplementations?.[serviceName];\n\t\tif (metadata.required && !implementation) throw new Error(`Fragment '${definition.name}' requires service '${metadata.name}' but it was not provided`);\n\t}\n\tlet deps;\n\ttry {\n\t\tdeps = definition.dependencies?.({\n\t\t\tconfig,\n\t\t\toptions\n\t\t}) ?? {};\n\t} catch (error) {\n\t\tif (dryRun) {\n\t\t\tconsole.warn(\"Warning: Failed to initialize dependencies in dry run mode:\", error instanceof Error ? error.message : String(error));\n\t\t\tdeps = {};\n\t\t} else throw error;\n\t}\n\tconst linkedFragmentInstances = {};\n\tconst linkedFragmentServices = {};\n\tif (definition.linkedFragments) for (const [name, callback] of Object.entries(definition.linkedFragments)) {\n\t\tconst linkedFragment = callback({\n\t\t\tconfig,\n\t\t\toptions,\n\t\t\tserviceDependencies: serviceImplementations\n\t\t});\n\t\tlinkedFragmentInstances[name] = linkedFragment;\n\t\tconst services$1 = linkedFragment.services;\n\t\tfor (const [serviceName, service] of Object.entries(services$1)) linkedFragmentServices[serviceName] = service;\n\t}\n\tconst defineService = (services$1) => services$1;\n\tconst privateServices = { ...linkedFragmentServices };\n\tif (definition.privateServices) for (const [serviceName, factory] of Object.entries(definition.privateServices)) {\n\t\tconst serviceFactory = factory;\n\t\ttry {\n\t\t\tprivateServices[serviceName] = serviceFactory({\n\t\t\t\tconfig,\n\t\t\t\toptions,\n\t\t\t\tdeps,\n\t\t\t\tserviceDeps: serviceImplementations ?? {},\n\t\t\t\tprivateServices,\n\t\t\t\tdefineService\n\t\t\t});\n\t\t} catch (error) {\n\t\t\tif (dryRun) {\n\t\t\t\tconsole.warn(`Warning: Failed to initialize private service '${serviceName}' in dry run mode:`, error instanceof Error ? error.message : String(error));\n\t\t\t\tprivateServices[serviceName] = {};\n\t\t\t} else throw error;\n\t\t}\n\t}\n\tlet baseServices;\n\ttry {\n\t\tbaseServices = definition.baseServices?.({\n\t\t\tconfig,\n\t\t\toptions,\n\t\t\tdeps,\n\t\t\tserviceDeps: serviceImplementations ?? {},\n\t\t\tprivateServices,\n\t\t\tdefineService\n\t\t}) ?? {};\n\t} catch (error) {\n\t\tif (dryRun) {\n\t\t\tconsole.warn(\"Warning: Failed to initialize base services in dry run mode:\", error instanceof Error ? error.message : String(error));\n\t\t\tbaseServices = {};\n\t\t} else throw error;\n\t}\n\tconst namedServices = {};\n\tif (definition.namedServices) for (const [serviceName, factory] of Object.entries(definition.namedServices)) {\n\t\tconst serviceFactory = factory;\n\t\ttry {\n\t\t\tnamedServices[serviceName] = serviceFactory({\n\t\t\t\tconfig,\n\t\t\t\toptions,\n\t\t\t\tdeps,\n\t\t\t\tserviceDeps: serviceImplementations ?? {},\n\t\t\t\tprivateServices,\n\t\t\t\tdefineService\n\t\t\t});\n\t\t} catch (error) {\n\t\t\tif (dryRun) {\n\t\t\t\tconsole.warn(`Warning: Failed to initialize service '${serviceName}' in dry run mode:`, error instanceof Error ? error.message : String(error));\n\t\t\t\tnamedServices[serviceName] = {};\n\t\t\t} else throw error;\n\t\t}\n\t}\n\tconst services = {\n\t\t...baseServices,\n\t\t...namedServices\n\t};\n\tconst storage = definition.getExternalStorage ? definition.getExternalStorage({\n\t\tconfig,\n\t\toptions,\n\t\tdeps\n\t}) : new RequestContextStorage();\n\tconst contexts = definition.createThisContext?.({\n\t\tconfig,\n\t\toptions,\n\t\tdeps,\n\t\tstorage\n\t});\n\tconst serviceContext = contexts?.serviceContext;\n\tconst handlerContext = contexts?.handlerContext;\n\tconst internalData = definition.internalDataFactory?.({\n\t\tconfig,\n\t\toptions,\n\t\tdeps,\n\t\tlinkedFragments: linkedFragmentInstances\n\t}) ?? {};\n\tconst boundServices = serviceContext ? bindServicesToContext(services, serviceContext) : services;\n\tconst routes = resolveRouteFactories({\n\t\tconfig,\n\t\tdeps,\n\t\tservices: boundServices,\n\t\tserviceDeps: serviceImplementations ?? {}\n\t}, routesOrFactories);\n\tconst linkedRoutes = collectLinkedFragmentRoutes(linkedFragmentInstances);\n\tconst finalRoutes = linkedRoutes.length > 0 ? [...routes, ...linkedRoutes] : routes;\n\tconst mountRoute = getMountRoute({\n\t\tname: definition.name,\n\t\tmountRoute: options.mountRoute\n\t});\n\tconst createRequestStorageWithContext = definition.createRequestStorage ? () => definition.createRequestStorage({\n\t\tconfig,\n\t\toptions,\n\t\tdeps\n\t}) : void 0;\n\treturn new FragnoInstantiatedFragment({\n\t\tname: definition.name,\n\t\troutes: finalRoutes,\n\t\tdeps,\n\t\tservices: boundServices,\n\t\tmountRoute,\n\t\tserviceThisContext: serviceContext,\n\t\thandlerThisContext: handlerContext,\n\t\tstorage,\n\t\tcreateRequestStorage: createRequestStorageWithContext,\n\t\toptions,\n\t\tlinkedFragments: linkedFragmentInstances,\n\t\tinternalData\n\t});\n}\n/**\n* Fluent builder for instantiating fragments.\n* Provides a type-safe API for configuring and building fragment instances.\n*/\nvar FragmentInstantiationBuilder = class FragmentInstantiationBuilder {\n\t#definition;\n\t#config;\n\t#routes;\n\t#options;\n\t#services;\n\tconstructor(definition, routes) {\n\t\tthis.#definition = definition;\n\t\tthis.#routes = routes;\n\t}\n\t/**\n\t* Get the fragment definition\n\t*/\n\tget definition() {\n\t\treturn this.#definition;\n\t}\n\t/**\n\t* Get the configured routes\n\t*/\n\tget routes() {\n\t\treturn this.#routes ?? [];\n\t}\n\t/**\n\t* Get the configuration\n\t*/\n\tget config() {\n\t\treturn this.#config;\n\t}\n\t/**\n\t* Get the options\n\t*/\n\tget options() {\n\t\treturn this.#options;\n\t}\n\t/**\n\t* Set the configuration for the fragment\n\t*/\n\twithConfig(config) {\n\t\tthis.#config = config;\n\t\treturn this;\n\t}\n\t/**\n\t* Set the routes for the fragment\n\t*/\n\twithRoutes(routes) {\n\t\tconst newBuilder = new FragmentInstantiationBuilder(this.#definition, routes);\n\t\tnewBuilder.#config = this.#config;\n\t\tnewBuilder.#options = this.#options;\n\t\tnewBuilder.#services = this.#services;\n\t\treturn newBuilder;\n\t}\n\t/**\n\t* Set the options for the fragment (e.g., mountRoute, databaseAdapter)\n\t*/\n\twithOptions(options) {\n\t\tthis.#options = options;\n\t\treturn this;\n\t}\n\t/**\n\t* Provide implementations for services that this fragment uses\n\t*/\n\twithServices(services) {\n\t\tthis.#services = services;\n\t\treturn this;\n\t}\n\t/**\n\t* Build and return the instantiated fragment\n\t*/\n\tbuild() {\n\t\tconst dryRun = process.env[\"FRAGNO_INIT_DRY_RUN\"] === \"true\";\n\t\treturn instantiateFragment(this.#definition, this.#config ?? {}, this.#routes ?? [], this.#options ?? {}, this.#services, { dryRun });\n\t}\n};\n/**\n* Create a fluent builder for instantiating a fragment.\n*\n* @example\n* ```ts\n* const fragment = instantiate(myFragmentDefinition)\n* .withConfig({ apiKey: \"key\" })\n* .withRoutes([route1, route2])\n* .withOptions({ mountRoute: \"/api\" })\n* .build();\n* ```\n*/\nfunction instantiate(definition) {\n\treturn new FragmentInstantiationBuilder(definition);\n}\n\n//#endregion\nexport { FragmentInstantiationBuilder, FragnoInstantiatedFragment, instantiate, instantiateFragment };\n//# sourceMappingURL=fragment-instantiator.js.map"],"mappings":"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"}
|