@proseql/core 0.1.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/LICENSE +21 -0
- package/dist/errors/crud-errors.d.ts +98 -0
- package/dist/errors/crud-errors.d.ts.map +1 -0
- package/dist/errors/crud-errors.js +23 -0
- package/dist/errors/crud-errors.js.map +1 -0
- package/dist/errors/index.d.ts +16 -0
- package/dist/errors/index.d.ts.map +1 -0
- package/dist/errors/index.js +12 -0
- package/dist/errors/index.js.map +1 -0
- package/dist/errors/migration-errors.d.ts +22 -0
- package/dist/errors/migration-errors.d.ts.map +1 -0
- package/dist/errors/migration-errors.js +14 -0
- package/dist/errors/migration-errors.js.map +1 -0
- package/dist/errors/plugin-errors.d.ts +15 -0
- package/dist/errors/plugin-errors.d.ts.map +1 -0
- package/dist/errors/plugin-errors.js +11 -0
- package/dist/errors/plugin-errors.js.map +1 -0
- package/dist/errors/query-errors.d.ts +31 -0
- package/dist/errors/query-errors.d.ts.map +1 -0
- package/dist/errors/query-errors.js +11 -0
- package/dist/errors/query-errors.js.map +1 -0
- package/dist/errors/storage-errors.d.ts +30 -0
- package/dist/errors/storage-errors.d.ts.map +1 -0
- package/dist/errors/storage-errors.js +11 -0
- package/dist/errors/storage-errors.js.map +1 -0
- package/dist/factories/crud-factory-with-relationships.d.ts +28 -0
- package/dist/factories/crud-factory-with-relationships.d.ts.map +1 -0
- package/dist/factories/crud-factory-with-relationships.js +8 -0
- package/dist/factories/crud-factory-with-relationships.js.map +1 -0
- package/dist/factories/crud-factory.d.ts +25 -0
- package/dist/factories/crud-factory.d.ts.map +1 -0
- package/dist/factories/crud-factory.js +8 -0
- package/dist/factories/crud-factory.js.map +1 -0
- package/dist/factories/database-effect.d.ts +241 -0
- package/dist/factories/database-effect.d.ts.map +1 -0
- package/dist/factories/database-effect.js +859 -0
- package/dist/factories/database-effect.js.map +1 -0
- package/dist/hooks/hook-runner.d.ts +60 -0
- package/dist/hooks/hook-runner.d.ts.map +1 -0
- package/dist/hooks/hook-runner.js +107 -0
- package/dist/hooks/hook-runner.js.map +1 -0
- package/dist/index.d.ts +84 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +110 -0
- package/dist/index.js.map +1 -0
- package/dist/indexes/index-lookup.d.ts +33 -0
- package/dist/indexes/index-lookup.d.ts.map +1 -0
- package/dist/indexes/index-lookup.js +180 -0
- package/dist/indexes/index-lookup.js.map +1 -0
- package/dist/indexes/index-manager.d.ts +118 -0
- package/dist/indexes/index-manager.d.ts.map +1 -0
- package/dist/indexes/index-manager.js +345 -0
- package/dist/indexes/index-manager.js.map +1 -0
- package/dist/indexes/search-index.d.ts +179 -0
- package/dist/indexes/search-index.d.ts.map +1 -0
- package/dist/indexes/search-index.js +405 -0
- package/dist/indexes/search-index.js.map +1 -0
- package/dist/migrations/migration-runner.d.ts +70 -0
- package/dist/migrations/migration-runner.d.ts.map +1 -0
- package/dist/migrations/migration-runner.js +271 -0
- package/dist/migrations/migration-runner.js.map +1 -0
- package/dist/migrations/migration-types.d.ts +63 -0
- package/dist/migrations/migration-types.d.ts.map +1 -0
- package/dist/migrations/migration-types.js +5 -0
- package/dist/migrations/migration-types.js.map +1 -0
- package/dist/operations/crud/create-with-relationships.d.ts +44 -0
- package/dist/operations/crud/create-with-relationships.d.ts.map +1 -0
- package/dist/operations/crud/create-with-relationships.js +483 -0
- package/dist/operations/crud/create-with-relationships.js.map +1 -0
- package/dist/operations/crud/create.d.ts +48 -0
- package/dist/operations/crud/create.d.ts.map +1 -0
- package/dist/operations/crud/create.js +333 -0
- package/dist/operations/crud/create.js.map +1 -0
- package/dist/operations/crud/delete-with-relationships.d.ts +63 -0
- package/dist/operations/crud/delete-with-relationships.d.ts.map +1 -0
- package/dist/operations/crud/delete-with-relationships.js +395 -0
- package/dist/operations/crud/delete-with-relationships.js.map +1 -0
- package/dist/operations/crud/delete.d.ts +58 -0
- package/dist/operations/crud/delete.d.ts.map +1 -0
- package/dist/operations/crud/delete.js +267 -0
- package/dist/operations/crud/delete.js.map +1 -0
- package/dist/operations/crud/unique-check.d.ts +114 -0
- package/dist/operations/crud/unique-check.d.ts.map +1 -0
- package/dist/operations/crud/unique-check.js +383 -0
- package/dist/operations/crud/unique-check.js.map +1 -0
- package/dist/operations/crud/update-with-relationships.d.ts +45 -0
- package/dist/operations/crud/update-with-relationships.d.ts.map +1 -0
- package/dist/operations/crud/update-with-relationships.js +516 -0
- package/dist/operations/crud/update-with-relationships.js.map +1 -0
- package/dist/operations/crud/update.d.ts +91 -0
- package/dist/operations/crud/update.d.ts.map +1 -0
- package/dist/operations/crud/update.js +505 -0
- package/dist/operations/crud/update.js.map +1 -0
- package/dist/operations/crud/upsert.d.ts +52 -0
- package/dist/operations/crud/upsert.d.ts.map +1 -0
- package/dist/operations/crud/upsert.js +386 -0
- package/dist/operations/crud/upsert.js.map +1 -0
- package/dist/operations/query/aggregate.d.ts +30 -0
- package/dist/operations/query/aggregate.d.ts.map +1 -0
- package/dist/operations/query/aggregate.js +227 -0
- package/dist/operations/query/aggregate.js.map +1 -0
- package/dist/operations/query/cursor-stream.d.ts +18 -0
- package/dist/operations/query/cursor-stream.d.ts.map +1 -0
- package/dist/operations/query/cursor-stream.js +199 -0
- package/dist/operations/query/cursor-stream.js.map +1 -0
- package/dist/operations/query/filter-stream.d.ts +12 -0
- package/dist/operations/query/filter-stream.d.ts.map +1 -0
- package/dist/operations/query/filter-stream.js +167 -0
- package/dist/operations/query/filter-stream.js.map +1 -0
- package/dist/operations/query/filter.d.ts +13 -0
- package/dist/operations/query/filter.d.ts.map +1 -0
- package/dist/operations/query/filter.js +267 -0
- package/dist/operations/query/filter.js.map +1 -0
- package/dist/operations/query/paginate-stream.d.ts +11 -0
- package/dist/operations/query/paginate-stream.d.ts.map +1 -0
- package/dist/operations/query/paginate-stream.js +22 -0
- package/dist/operations/query/paginate-stream.js.map +1 -0
- package/dist/operations/query/query-helpers.d.ts +14 -0
- package/dist/operations/query/query-helpers.d.ts.map +1 -0
- package/dist/operations/query/query-helpers.js +22 -0
- package/dist/operations/query/query-helpers.js.map +1 -0
- package/dist/operations/query/resolve-computed.d.ts +142 -0
- package/dist/operations/query/resolve-computed.d.ts.map +1 -0
- package/dist/operations/query/resolve-computed.js +197 -0
- package/dist/operations/query/resolve-computed.js.map +1 -0
- package/dist/operations/query/search.d.ts +110 -0
- package/dist/operations/query/search.d.ts.map +1 -0
- package/dist/operations/query/search.js +188 -0
- package/dist/operations/query/search.js.map +1 -0
- package/dist/operations/query/select-stream.d.ts +27 -0
- package/dist/operations/query/select-stream.d.ts.map +1 -0
- package/dist/operations/query/select-stream.js +88 -0
- package/dist/operations/query/select-stream.js.map +1 -0
- package/dist/operations/query/select.d.ts +54 -0
- package/dist/operations/query/select.d.ts.map +1 -0
- package/dist/operations/query/select.js +159 -0
- package/dist/operations/query/select.js.map +1 -0
- package/dist/operations/query/sort-stream.d.ts +46 -0
- package/dist/operations/query/sort-stream.d.ts.map +1 -0
- package/dist/operations/query/sort-stream.js +158 -0
- package/dist/operations/query/sort-stream.js.map +1 -0
- package/dist/operations/query/sort.d.ts +9 -0
- package/dist/operations/query/sort.d.ts.map +1 -0
- package/dist/operations/query/sort.js +58 -0
- package/dist/operations/query/sort.js.map +1 -0
- package/dist/operations/relationships/populate-stream.d.ts +29 -0
- package/dist/operations/relationships/populate-stream.d.ts.map +1 -0
- package/dist/operations/relationships/populate-stream.js +159 -0
- package/dist/operations/relationships/populate-stream.js.map +1 -0
- package/dist/operations/relationships/populate.d.ts +15 -0
- package/dist/operations/relationships/populate.d.ts.map +1 -0
- package/dist/operations/relationships/populate.js +228 -0
- package/dist/operations/relationships/populate.js.map +1 -0
- package/dist/plugins/plugin-hooks.d.ts +25 -0
- package/dist/plugins/plugin-hooks.d.ts.map +1 -0
- package/dist/plugins/plugin-hooks.js +64 -0
- package/dist/plugins/plugin-hooks.js.map +1 -0
- package/dist/plugins/plugin-registry.d.ts +26 -0
- package/dist/plugins/plugin-registry.d.ts.map +1 -0
- package/dist/plugins/plugin-registry.js +150 -0
- package/dist/plugins/plugin-registry.js.map +1 -0
- package/dist/plugins/plugin-types.d.ts +95 -0
- package/dist/plugins/plugin-types.d.ts.map +1 -0
- package/dist/plugins/plugin-types.js +6 -0
- package/dist/plugins/plugin-types.js.map +1 -0
- package/dist/plugins/plugin-validation.d.ts +49 -0
- package/dist/plugins/plugin-validation.d.ts.map +1 -0
- package/dist/plugins/plugin-validation.js +295 -0
- package/dist/plugins/plugin-validation.js.map +1 -0
- package/dist/reactive/change-event.d.ts +44 -0
- package/dist/reactive/change-event.d.ts.map +1 -0
- package/dist/reactive/change-event.js +49 -0
- package/dist/reactive/change-event.js.map +1 -0
- package/dist/reactive/change-pubsub.d.ts +32 -0
- package/dist/reactive/change-pubsub.d.ts.map +1 -0
- package/dist/reactive/change-pubsub.js +31 -0
- package/dist/reactive/change-pubsub.js.map +1 -0
- package/dist/reactive/evaluate-query.d.ts +62 -0
- package/dist/reactive/evaluate-query.d.ts.map +1 -0
- package/dist/reactive/evaluate-query.js +57 -0
- package/dist/reactive/evaluate-query.js.map +1 -0
- package/dist/reactive/watch-by-id.d.ts +53 -0
- package/dist/reactive/watch-by-id.d.ts.map +1 -0
- package/dist/reactive/watch-by-id.js +55 -0
- package/dist/reactive/watch-by-id.js.map +1 -0
- package/dist/reactive/watch.d.ts +78 -0
- package/dist/reactive/watch.d.ts.map +1 -0
- package/dist/reactive/watch.js +133 -0
- package/dist/reactive/watch.js.map +1 -0
- package/dist/serializers/codecs/hjson.d.ts +33 -0
- package/dist/serializers/codecs/hjson.d.ts.map +1 -0
- package/dist/serializers/codecs/hjson.js +40 -0
- package/dist/serializers/codecs/hjson.js.map +1 -0
- package/dist/serializers/codecs/json.d.ts +22 -0
- package/dist/serializers/codecs/json.d.ts.map +1 -0
- package/dist/serializers/codecs/json.js +28 -0
- package/dist/serializers/codecs/json.js.map +1 -0
- package/dist/serializers/codecs/json5.d.ts +26 -0
- package/dist/serializers/codecs/json5.d.ts.map +1 -0
- package/dist/serializers/codecs/json5.js +33 -0
- package/dist/serializers/codecs/json5.js.map +1 -0
- package/dist/serializers/codecs/jsonc.d.ts +29 -0
- package/dist/serializers/codecs/jsonc.d.ts.map +1 -0
- package/dist/serializers/codecs/jsonc.js +38 -0
- package/dist/serializers/codecs/jsonc.js.map +1 -0
- package/dist/serializers/codecs/jsonl.d.ts +17 -0
- package/dist/serializers/codecs/jsonl.d.ts.map +1 -0
- package/dist/serializers/codecs/jsonl.js +31 -0
- package/dist/serializers/codecs/jsonl.js.map +1 -0
- package/dist/serializers/codecs/prose.d.ts +419 -0
- package/dist/serializers/codecs/prose.d.ts.map +1 -0
- package/dist/serializers/codecs/prose.js +1060 -0
- package/dist/serializers/codecs/prose.js.map +1 -0
- package/dist/serializers/codecs/toml.d.ts +23 -0
- package/dist/serializers/codecs/toml.d.ts.map +1 -0
- package/dist/serializers/codecs/toml.js +66 -0
- package/dist/serializers/codecs/toml.js.map +1 -0
- package/dist/serializers/codecs/toon.d.ts +20 -0
- package/dist/serializers/codecs/toon.d.ts.map +1 -0
- package/dist/serializers/codecs/toon.js +33 -0
- package/dist/serializers/codecs/toon.js.map +1 -0
- package/dist/serializers/codecs/yaml.d.ts +24 -0
- package/dist/serializers/codecs/yaml.d.ts.map +1 -0
- package/dist/serializers/codecs/yaml.js +31 -0
- package/dist/serializers/codecs/yaml.js.map +1 -0
- package/dist/serializers/format-codec.d.ts +53 -0
- package/dist/serializers/format-codec.d.ts.map +1 -0
- package/dist/serializers/format-codec.js +148 -0
- package/dist/serializers/format-codec.js.map +1 -0
- package/dist/serializers/presets.d.ts +48 -0
- package/dist/serializers/presets.d.ts.map +1 -0
- package/dist/serializers/presets.js +72 -0
- package/dist/serializers/presets.js.map +1 -0
- package/dist/serializers/serializer-service.d.ts +11 -0
- package/dist/serializers/serializer-service.d.ts.map +1 -0
- package/dist/serializers/serializer-service.js +4 -0
- package/dist/serializers/serializer-service.js.map +1 -0
- package/dist/state/collection-state.d.ts +19 -0
- package/dist/state/collection-state.d.ts.map +1 -0
- package/dist/state/collection-state.js +15 -0
- package/dist/state/collection-state.js.map +1 -0
- package/dist/state/state-operations.d.ts +38 -0
- package/dist/state/state-operations.d.ts.map +1 -0
- package/dist/state/state-operations.js +65 -0
- package/dist/state/state-operations.js.map +1 -0
- package/dist/storage/in-memory-adapter-layer.d.ts +16 -0
- package/dist/storage/in-memory-adapter-layer.d.ts.map +1 -0
- package/dist/storage/in-memory-adapter-layer.js +81 -0
- package/dist/storage/in-memory-adapter-layer.js.map +1 -0
- package/dist/storage/persistence-effect.d.ts +244 -0
- package/dist/storage/persistence-effect.d.ts.map +1 -0
- package/dist/storage/persistence-effect.js +551 -0
- package/dist/storage/persistence-effect.js.map +1 -0
- package/dist/storage/storage-service.d.ts +22 -0
- package/dist/storage/storage-service.d.ts.map +1 -0
- package/dist/storage/storage-service.js +4 -0
- package/dist/storage/storage-service.js.map +1 -0
- package/dist/storage/transforms.d.ts +183 -0
- package/dist/storage/transforms.d.ts.map +1 -0
- package/dist/storage/transforms.js +263 -0
- package/dist/storage/transforms.js.map +1 -0
- package/dist/transactions/transaction.d.ts +87 -0
- package/dist/transactions/transaction.d.ts.map +1 -0
- package/dist/transactions/transaction.js +240 -0
- package/dist/transactions/transaction.js.map +1 -0
- package/dist/types/aggregate-types.d.ts +73 -0
- package/dist/types/aggregate-types.d.ts.map +1 -0
- package/dist/types/aggregate-types.js +14 -0
- package/dist/types/aggregate-types.js.map +1 -0
- package/dist/types/computed-types.d.ts +71 -0
- package/dist/types/computed-types.d.ts.map +1 -0
- package/dist/types/computed-types.js +8 -0
- package/dist/types/computed-types.js.map +1 -0
- package/dist/types/crud-relationship-types.d.ts +180 -0
- package/dist/types/crud-relationship-types.d.ts.map +1 -0
- package/dist/types/crud-relationship-types.js +17 -0
- package/dist/types/crud-relationship-types.js.map +1 -0
- package/dist/types/crud-types.d.ts +343 -0
- package/dist/types/crud-types.d.ts.map +1 -0
- package/dist/types/crud-types.js +43 -0
- package/dist/types/crud-types.js.map +1 -0
- package/dist/types/cursor-types.d.ts +52 -0
- package/dist/types/cursor-types.d.ts.map +1 -0
- package/dist/types/cursor-types.js +2 -0
- package/dist/types/cursor-types.js.map +1 -0
- package/dist/types/database-config-types.d.ts +196 -0
- package/dist/types/database-config-types.d.ts.map +1 -0
- package/dist/types/database-config-types.js +11 -0
- package/dist/types/database-config-types.js.map +1 -0
- package/dist/types/hook-types.d.ts +158 -0
- package/dist/types/hook-types.d.ts.map +1 -0
- package/dist/types/hook-types.js +6 -0
- package/dist/types/hook-types.js.map +1 -0
- package/dist/types/index-types.d.ts +42 -0
- package/dist/types/index-types.d.ts.map +1 -0
- package/dist/types/index-types.js +8 -0
- package/dist/types/index-types.js.map +1 -0
- package/dist/types/operators.d.ts +5 -0
- package/dist/types/operators.d.ts.map +1 -0
- package/dist/types/operators.js +297 -0
- package/dist/types/operators.js.map +1 -0
- package/dist/types/query-overloads.d.ts +54 -0
- package/dist/types/query-overloads.d.ts.map +1 -0
- package/dist/types/query-overloads.js +3 -0
- package/dist/types/query-overloads.js.map +1 -0
- package/dist/types/reactive-types.d.ts +75 -0
- package/dist/types/reactive-types.d.ts.map +1 -0
- package/dist/types/reactive-types.js +7 -0
- package/dist/types/reactive-types.js.map +1 -0
- package/dist/types/schema-types.d.ts +56 -0
- package/dist/types/schema-types.d.ts.map +1 -0
- package/dist/types/schema-types.js +8 -0
- package/dist/types/schema-types.js.map +1 -0
- package/dist/types/search-types.d.ts +82 -0
- package/dist/types/search-types.d.ts.map +1 -0
- package/dist/types/search-types.js +110 -0
- package/dist/types/search-types.js.map +1 -0
- package/dist/types/types.d.ts +286 -0
- package/dist/types/types.d.ts.map +1 -0
- package/dist/types/types.js +2 -0
- package/dist/types/types.js.map +1 -0
- package/dist/utils/id-generator.d.ts +97 -0
- package/dist/utils/id-generator.d.ts.map +1 -0
- package/dist/utils/id-generator.js +247 -0
- package/dist/utils/id-generator.js.map +1 -0
- package/dist/utils/nested-path.d.ts +56 -0
- package/dist/utils/nested-path.d.ts.map +1 -0
- package/dist/utils/nested-path.js +119 -0
- package/dist/utils/nested-path.js.map +1 -0
- package/dist/utils/path.d.ts +16 -0
- package/dist/utils/path.d.ts.map +1 -0
- package/dist/utils/path.js +24 -0
- package/dist/utils/path.js.map +1 -0
- package/dist/validators/foreign-key.d.ts +49 -0
- package/dist/validators/foreign-key.d.ts.map +1 -0
- package/dist/validators/foreign-key.js +153 -0
- package/dist/validators/foreign-key.js.map +1 -0
- package/dist/validators/schema-validator.d.ts +19 -0
- package/dist/validators/schema-validator.d.ts.map +1 -0
- package/dist/validators/schema-validator.js +34 -0
- package/dist/validators/schema-validator.js.map +1 -0
- package/package.json +57 -0
|
@@ -0,0 +1,483 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Effect-based create operations with relationship support.
|
|
3
|
+
*
|
|
4
|
+
* Uses Ref<ReadonlyMap> for atomic state mutation, Effect Schema for validation,
|
|
5
|
+
* and typed errors. Supports $connect, $create, and $connectOrCreate operations
|
|
6
|
+
* for both ref (single) and inverse (many) relationship types.
|
|
7
|
+
*/
|
|
8
|
+
import { Effect, PubSub, Ref } from "effect";
|
|
9
|
+
import { ForeignKeyError, ValidationError, } from "../../errors/crud-errors.js";
|
|
10
|
+
import { isRelationshipOperation } from "../../types/crud-relationship-types.js";
|
|
11
|
+
import { generateId } from "../../utils/id-generator.js";
|
|
12
|
+
import { validateForeignKeysEffect } from "../../validators/foreign-key.js";
|
|
13
|
+
import { validateEntity } from "../../validators/schema-validator.js";
|
|
14
|
+
// ============================================================================
|
|
15
|
+
// Helpers
|
|
16
|
+
// ============================================================================
|
|
17
|
+
const getTargetCollection = (rel) => rel.target || rel.__targetCollection;
|
|
18
|
+
/**
|
|
19
|
+
* Resolve a connect input to a target entity's ID by looking up the Ref state.
|
|
20
|
+
*/
|
|
21
|
+
const resolveConnectInput = (input, targetCollection, stateRefs) => Effect.gen(function* () {
|
|
22
|
+
const targetRef = stateRefs[targetCollection];
|
|
23
|
+
if (targetRef === undefined) {
|
|
24
|
+
return yield* Effect.fail(new ForeignKeyError({
|
|
25
|
+
collection: targetCollection,
|
|
26
|
+
field: "",
|
|
27
|
+
value: "",
|
|
28
|
+
targetCollection,
|
|
29
|
+
message: `Target collection '${targetCollection}' not found`,
|
|
30
|
+
}));
|
|
31
|
+
}
|
|
32
|
+
const targetMap = yield* Ref.get(targetRef);
|
|
33
|
+
// If input has id, use it directly
|
|
34
|
+
if ("id" in input &&
|
|
35
|
+
typeof input.id === "string") {
|
|
36
|
+
const id = input.id;
|
|
37
|
+
if (targetMap.has(id)) {
|
|
38
|
+
return id;
|
|
39
|
+
}
|
|
40
|
+
return yield* Effect.fail(new ForeignKeyError({
|
|
41
|
+
collection: targetCollection,
|
|
42
|
+
field: "id",
|
|
43
|
+
value: id,
|
|
44
|
+
targetCollection,
|
|
45
|
+
message: `Entity with ID '${id}' not found in '${targetCollection}'`,
|
|
46
|
+
}));
|
|
47
|
+
}
|
|
48
|
+
// Otherwise, find by matching fields
|
|
49
|
+
const inputEntries = Object.entries(input);
|
|
50
|
+
for (const [id, entity] of targetMap) {
|
|
51
|
+
const entityRecord = entity;
|
|
52
|
+
const matches = inputEntries.every(([key, value]) => entityRecord[key] === value);
|
|
53
|
+
if (matches) {
|
|
54
|
+
return id;
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
return yield* Effect.fail(new ForeignKeyError({
|
|
58
|
+
collection: targetCollection,
|
|
59
|
+
field: "",
|
|
60
|
+
value: JSON.stringify(input),
|
|
61
|
+
targetCollection,
|
|
62
|
+
message: `No matching entity found in '${targetCollection}'`,
|
|
63
|
+
}));
|
|
64
|
+
});
|
|
65
|
+
/**
|
|
66
|
+
* Find the inverse relationship field name in the target collection
|
|
67
|
+
* that points back to the source collection.
|
|
68
|
+
*/
|
|
69
|
+
const findInverseRelationship = (sourceCollection, targetRelationships) => {
|
|
70
|
+
for (const [field, rel] of Object.entries(targetRelationships)) {
|
|
71
|
+
const target = getTargetCollection(rel);
|
|
72
|
+
if (target === sourceCollection) {
|
|
73
|
+
return field;
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
return null;
|
|
77
|
+
};
|
|
78
|
+
// ============================================================================
|
|
79
|
+
// Relationship Processing
|
|
80
|
+
// ============================================================================
|
|
81
|
+
/**
|
|
82
|
+
* Process a single (ref) relationship input into connect/create/connectOrCreate ops.
|
|
83
|
+
*/
|
|
84
|
+
const processSingleRelationship = (field, value, targetCollection) => {
|
|
85
|
+
const connect = [];
|
|
86
|
+
const create = [];
|
|
87
|
+
const connectOrCreate = [];
|
|
88
|
+
// Direct connect (shorthand syntax — not a relationship operation object)
|
|
89
|
+
if (!isRelationshipOperation(value)) {
|
|
90
|
+
connect.push({ field, targetId: "__pending__", targetCollection });
|
|
91
|
+
return { connect, create, connectOrCreate };
|
|
92
|
+
}
|
|
93
|
+
const ops = value;
|
|
94
|
+
if (ops.$connect) {
|
|
95
|
+
connect.push({ field, targetId: "__pending__", targetCollection });
|
|
96
|
+
}
|
|
97
|
+
if (ops.$create) {
|
|
98
|
+
create.push({ field, data: ops.$create, targetCollection });
|
|
99
|
+
}
|
|
100
|
+
if (ops.$connectOrCreate) {
|
|
101
|
+
connectOrCreate.push({
|
|
102
|
+
field,
|
|
103
|
+
where: ops.$connectOrCreate.where,
|
|
104
|
+
create: ops.$connectOrCreate.create,
|
|
105
|
+
targetCollection,
|
|
106
|
+
});
|
|
107
|
+
}
|
|
108
|
+
return { connect, create, connectOrCreate };
|
|
109
|
+
};
|
|
110
|
+
/**
|
|
111
|
+
* Process a many (inverse) relationship input into connect/create/connectOrCreate ops.
|
|
112
|
+
*/
|
|
113
|
+
const processManyRelationship = (field, value, targetCollection) => {
|
|
114
|
+
const connect = [];
|
|
115
|
+
const create = [];
|
|
116
|
+
const connectOrCreate = [];
|
|
117
|
+
if (value.$connect) {
|
|
118
|
+
const connects = Array.isArray(value.$connect)
|
|
119
|
+
? value.$connect
|
|
120
|
+
: [value.$connect];
|
|
121
|
+
for (const _ of connects) {
|
|
122
|
+
connect.push({ field, targetId: "__pending__", targetCollection });
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
if (value.$create) {
|
|
126
|
+
const creates = Array.isArray(value.$create)
|
|
127
|
+
? value.$create
|
|
128
|
+
: [value.$create];
|
|
129
|
+
for (const c of creates) {
|
|
130
|
+
create.push({ field, data: c, targetCollection });
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
if (value.$createMany) {
|
|
134
|
+
for (const c of value.$createMany) {
|
|
135
|
+
create.push({ field, data: c, targetCollection });
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
if (value.$connectOrCreate) {
|
|
139
|
+
const items = Array.isArray(value.$connectOrCreate)
|
|
140
|
+
? value.$connectOrCreate
|
|
141
|
+
: [value.$connectOrCreate];
|
|
142
|
+
for (const item of items) {
|
|
143
|
+
connectOrCreate.push({
|
|
144
|
+
field,
|
|
145
|
+
where: item.where,
|
|
146
|
+
create: item.create,
|
|
147
|
+
targetCollection,
|
|
148
|
+
});
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
return { connect, create, connectOrCreate };
|
|
152
|
+
};
|
|
153
|
+
/**
|
|
154
|
+
* Extract the original connect inputs from the raw input for later resolution.
|
|
155
|
+
*/
|
|
156
|
+
const extractConnectInputs = (input, relationships) => {
|
|
157
|
+
const result = {};
|
|
158
|
+
for (const [field, value] of Object.entries(input)) {
|
|
159
|
+
const rel = relationships[field];
|
|
160
|
+
if (!rel || value === undefined || value === null)
|
|
161
|
+
continue;
|
|
162
|
+
if (rel.type === "ref") {
|
|
163
|
+
if (!isRelationshipOperation(value)) {
|
|
164
|
+
result[field] = [value];
|
|
165
|
+
}
|
|
166
|
+
else {
|
|
167
|
+
const ops = value;
|
|
168
|
+
if (ops.$connect) {
|
|
169
|
+
result[field] = [ops.$connect];
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
else {
|
|
174
|
+
const ops = value;
|
|
175
|
+
if (ops.$connect) {
|
|
176
|
+
const connects = Array.isArray(ops.$connect)
|
|
177
|
+
? ops.$connect
|
|
178
|
+
: [ops.$connect];
|
|
179
|
+
result[field] = connects;
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
return result;
|
|
184
|
+
};
|
|
185
|
+
/**
|
|
186
|
+
* Process all relationship operations from the input.
|
|
187
|
+
*/
|
|
188
|
+
const processRelationshipOperations = (input, relationships) => {
|
|
189
|
+
const allConnect = [];
|
|
190
|
+
const allCreate = [];
|
|
191
|
+
const allConnectOrCreate = [];
|
|
192
|
+
for (const [field, value] of Object.entries(input)) {
|
|
193
|
+
const rel = relationships[field];
|
|
194
|
+
if (!rel || value === undefined || value === null)
|
|
195
|
+
continue;
|
|
196
|
+
const targetCollection = getTargetCollection(rel);
|
|
197
|
+
if (!targetCollection)
|
|
198
|
+
continue;
|
|
199
|
+
let processed;
|
|
200
|
+
if (rel.type === "ref") {
|
|
201
|
+
processed = processSingleRelationship(field, value, targetCollection);
|
|
202
|
+
}
|
|
203
|
+
else {
|
|
204
|
+
processed = processManyRelationship(field, value, targetCollection);
|
|
205
|
+
}
|
|
206
|
+
allConnect.push(...processed.connect);
|
|
207
|
+
allCreate.push(...processed.create);
|
|
208
|
+
allConnectOrCreate.push(...processed.connectOrCreate);
|
|
209
|
+
}
|
|
210
|
+
return {
|
|
211
|
+
connect: allConnect,
|
|
212
|
+
create: allCreate,
|
|
213
|
+
connectOrCreate: allConnectOrCreate,
|
|
214
|
+
};
|
|
215
|
+
};
|
|
216
|
+
// ============================================================================
|
|
217
|
+
// Computed Field Stripping
|
|
218
|
+
// ============================================================================
|
|
219
|
+
/**
|
|
220
|
+
* Strip computed field keys from an input object.
|
|
221
|
+
* Used to remove computed field names from create input before schema validation.
|
|
222
|
+
*
|
|
223
|
+
* @param input - The input object (possibly with computed field keys)
|
|
224
|
+
* @param computed - The computed fields configuration that defines which keys to strip
|
|
225
|
+
* @returns A new object with computed field keys removed
|
|
226
|
+
*/
|
|
227
|
+
const stripComputedFromInput = (input, computed) => {
|
|
228
|
+
if (computed === undefined || Object.keys(computed).length === 0) {
|
|
229
|
+
return input;
|
|
230
|
+
}
|
|
231
|
+
const computedKeys = new Set(Object.keys(computed));
|
|
232
|
+
const result = {};
|
|
233
|
+
for (const key of Object.keys(input)) {
|
|
234
|
+
if (!computedKeys.has(key)) {
|
|
235
|
+
result[key] = input[key];
|
|
236
|
+
}
|
|
237
|
+
}
|
|
238
|
+
return result;
|
|
239
|
+
};
|
|
240
|
+
// ============================================================================
|
|
241
|
+
// Create with Relationships
|
|
242
|
+
// ============================================================================
|
|
243
|
+
/**
|
|
244
|
+
* Create a single entity with relationship support.
|
|
245
|
+
*
|
|
246
|
+
* Steps:
|
|
247
|
+
* 1. Strip computed field keys from input (they are derived, not stored)
|
|
248
|
+
* 2. Parse relationship operations from input
|
|
249
|
+
* 3. Generate parent ID early for use in inverse relationships
|
|
250
|
+
* 4. Process $create: create nested entities in target collections
|
|
251
|
+
* 5. Process $connectOrCreate: find or create target entities
|
|
252
|
+
* 6. Process $connect: resolve target entity IDs
|
|
253
|
+
* 7. Set foreign keys from resolved relationships
|
|
254
|
+
* 8. Validate and create the parent entity
|
|
255
|
+
* 9. Update inverse relationship foreign keys on connected entities
|
|
256
|
+
*/
|
|
257
|
+
export const createWithRelationships = (collectionName, schema, relationships, ref, stateRefs, dbConfig, computed, changePubSub) => (input) => Effect.gen(function* () {
|
|
258
|
+
// 1. Strip computed field keys from input (they are derived, not stored)
|
|
259
|
+
const sanitizedInput = stripComputedFromInput(input, computed);
|
|
260
|
+
// 2. Process relationship operations
|
|
261
|
+
const relationshipOps = processRelationshipOperations(sanitizedInput, relationships);
|
|
262
|
+
// Extract connect inputs for later resolution
|
|
263
|
+
const connectInputMap = extractConnectInputs(sanitizedInput, relationships);
|
|
264
|
+
// Make a mutable copy for tracking which have been consumed
|
|
265
|
+
const pendingConnects = {};
|
|
266
|
+
for (const [k, v] of Object.entries(connectInputMap)) {
|
|
267
|
+
pendingConnects[k] = [...v];
|
|
268
|
+
}
|
|
269
|
+
// 3. Extract base entity data (non-relationship fields)
|
|
270
|
+
const baseInput = {};
|
|
271
|
+
for (const [key, value] of Object.entries(sanitizedInput)) {
|
|
272
|
+
if (!(key in relationships)) {
|
|
273
|
+
baseInput[key] = value;
|
|
274
|
+
}
|
|
275
|
+
}
|
|
276
|
+
// Generate parent ID early
|
|
277
|
+
const parentId = baseInput.id || generateId();
|
|
278
|
+
const now = new Date().toISOString();
|
|
279
|
+
// 4. Process $create: create nested entities
|
|
280
|
+
for (const nestedCreate of relationshipOps.create) {
|
|
281
|
+
const targetConfig = dbConfig[nestedCreate.targetCollection];
|
|
282
|
+
if (!targetConfig)
|
|
283
|
+
continue;
|
|
284
|
+
const targetRef = stateRefs[nestedCreate.targetCollection];
|
|
285
|
+
if (!targetRef)
|
|
286
|
+
continue;
|
|
287
|
+
const id = generateId();
|
|
288
|
+
const relationship = relationships[nestedCreate.field];
|
|
289
|
+
let entityData = nestedCreate.data;
|
|
290
|
+
if (typeof entityData !== "object" || entityData === null) {
|
|
291
|
+
entityData = {};
|
|
292
|
+
}
|
|
293
|
+
entityData = { ...entityData };
|
|
294
|
+
// For inverse relationships, set the foreign key on the nested entity
|
|
295
|
+
if (relationship && relationship.type === "inverse") {
|
|
296
|
+
const targetRels = targetConfig.relationships;
|
|
297
|
+
const inverseField = findInverseRelationship(collectionName, targetRels);
|
|
298
|
+
if (inverseField) {
|
|
299
|
+
const inverseRel = targetRels[inverseField];
|
|
300
|
+
if (inverseRel) {
|
|
301
|
+
const foreignKey = inverseRel.foreignKey || `${inverseField}Id`;
|
|
302
|
+
entityData[foreignKey] = parentId;
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
const entity = {
|
|
307
|
+
...entityData,
|
|
308
|
+
id,
|
|
309
|
+
createdAt: now,
|
|
310
|
+
updatedAt: now,
|
|
311
|
+
};
|
|
312
|
+
// Validate nested entity
|
|
313
|
+
const validated = yield* validateEntity(targetConfig.schema, entity).pipe(Effect.mapError((ve) => new ValidationError({
|
|
314
|
+
message: `Nested create in '${nestedCreate.targetCollection}' failed: ${ve.message}`,
|
|
315
|
+
issues: ve.issues,
|
|
316
|
+
})));
|
|
317
|
+
// Add to target collection Ref
|
|
318
|
+
yield* Ref.update(targetRef, (map) => {
|
|
319
|
+
const next = new Map(map);
|
|
320
|
+
next.set(id, validated);
|
|
321
|
+
return next;
|
|
322
|
+
});
|
|
323
|
+
// For ref relationships, set the foreign key on the parent
|
|
324
|
+
if (relationship && relationship.type === "ref") {
|
|
325
|
+
const foreignKey = relationship.foreignKey || `${nestedCreate.field}Id`;
|
|
326
|
+
baseInput[foreignKey] = id;
|
|
327
|
+
}
|
|
328
|
+
}
|
|
329
|
+
// 5. Process $connectOrCreate operations
|
|
330
|
+
for (const op of relationshipOps.connectOrCreate) {
|
|
331
|
+
const targetRef = stateRefs[op.targetCollection];
|
|
332
|
+
if (!targetRef)
|
|
333
|
+
continue;
|
|
334
|
+
const targetConfig = dbConfig[op.targetCollection];
|
|
335
|
+
// Try to resolve existing entity
|
|
336
|
+
const existingResult = yield* resolveConnectInput(op.where, op.targetCollection, stateRefs).pipe(Effect.map((id) => ({ found: true, id })), Effect.catchTag("ForeignKeyError", () => Effect.succeed({ found: false, id: "" })));
|
|
337
|
+
let resolvedId;
|
|
338
|
+
if (existingResult.found) {
|
|
339
|
+
resolvedId = existingResult.id;
|
|
340
|
+
}
|
|
341
|
+
else {
|
|
342
|
+
// Create new entity
|
|
343
|
+
if (!targetConfig)
|
|
344
|
+
continue;
|
|
345
|
+
const id = generateId();
|
|
346
|
+
const createData = { ...op.create };
|
|
347
|
+
// For inverse relationships, set the foreign key on the created entity
|
|
348
|
+
const relForCOC = relationships[op.field];
|
|
349
|
+
if (relForCOC && relForCOC.type === "inverse") {
|
|
350
|
+
const targetRels = targetConfig.relationships;
|
|
351
|
+
const inverseField = findInverseRelationship(collectionName, targetRels);
|
|
352
|
+
if (inverseField) {
|
|
353
|
+
const inverseRel = targetRels[inverseField];
|
|
354
|
+
if (inverseRel) {
|
|
355
|
+
const foreignKey = inverseRel.foreignKey || `${inverseField}Id`;
|
|
356
|
+
createData[foreignKey] = parentId;
|
|
357
|
+
}
|
|
358
|
+
}
|
|
359
|
+
}
|
|
360
|
+
const entity = {
|
|
361
|
+
...createData,
|
|
362
|
+
id,
|
|
363
|
+
createdAt: now,
|
|
364
|
+
updatedAt: now,
|
|
365
|
+
};
|
|
366
|
+
const validated = yield* validateEntity(targetConfig.schema, entity).pipe(Effect.mapError((ve) => new ValidationError({
|
|
367
|
+
message: `ConnectOrCreate in '${op.targetCollection}' failed: ${ve.message}`,
|
|
368
|
+
issues: ve.issues,
|
|
369
|
+
})));
|
|
370
|
+
yield* Ref.update(targetRef, (map) => {
|
|
371
|
+
const next = new Map(map);
|
|
372
|
+
next.set(id, validated);
|
|
373
|
+
return next;
|
|
374
|
+
});
|
|
375
|
+
resolvedId = id;
|
|
376
|
+
}
|
|
377
|
+
// Set the foreign key on the parent for ref relationships
|
|
378
|
+
const relationship = relationships[op.field];
|
|
379
|
+
if (relationship && relationship.type === "ref") {
|
|
380
|
+
const foreignKey = relationship.foreignKey || `${op.field}Id`;
|
|
381
|
+
baseInput[foreignKey] = resolvedId;
|
|
382
|
+
}
|
|
383
|
+
}
|
|
384
|
+
// 6. Process $connect operations — resolve target IDs
|
|
385
|
+
const resolvedConnects = [];
|
|
386
|
+
// Deduplicate connect ops by field — each field's pending inputs are consumed once
|
|
387
|
+
const seenFields = new Set();
|
|
388
|
+
for (const conn of relationshipOps.connect) {
|
|
389
|
+
if (seenFields.has(conn.field))
|
|
390
|
+
continue;
|
|
391
|
+
seenFields.add(conn.field);
|
|
392
|
+
const fieldInputs = pendingConnects[conn.field];
|
|
393
|
+
if (!fieldInputs || fieldInputs.length === 0)
|
|
394
|
+
continue;
|
|
395
|
+
for (const connectInput of fieldInputs) {
|
|
396
|
+
const targetId = yield* resolveConnectInput(connectInput, conn.targetCollection, stateRefs);
|
|
397
|
+
resolvedConnects.push({
|
|
398
|
+
field: conn.field,
|
|
399
|
+
targetId,
|
|
400
|
+
targetCollection: conn.targetCollection,
|
|
401
|
+
});
|
|
402
|
+
}
|
|
403
|
+
}
|
|
404
|
+
// 7. Set foreign keys from connect operations (ref relationships)
|
|
405
|
+
for (const connect of resolvedConnects) {
|
|
406
|
+
const relationship = relationships[connect.field];
|
|
407
|
+
if (relationship && relationship.type === "ref") {
|
|
408
|
+
const foreignKey = relationship.foreignKey || `${connect.field}Id`;
|
|
409
|
+
baseInput[foreignKey] = connect.targetId;
|
|
410
|
+
}
|
|
411
|
+
}
|
|
412
|
+
// 8. Construct, validate, and create the parent entity
|
|
413
|
+
const rawEntity = {
|
|
414
|
+
...baseInput,
|
|
415
|
+
id: parentId,
|
|
416
|
+
createdAt: now,
|
|
417
|
+
updatedAt: now,
|
|
418
|
+
};
|
|
419
|
+
const validated = yield* validateEntity(schema, rawEntity);
|
|
420
|
+
// Check for duplicate ID
|
|
421
|
+
const currentMap = yield* Ref.get(ref);
|
|
422
|
+
if (currentMap.has(parentId)) {
|
|
423
|
+
return yield* Effect.fail(new ValidationError({
|
|
424
|
+
message: `Entity with ID '${parentId}' already exists in '${collectionName}'`,
|
|
425
|
+
issues: [
|
|
426
|
+
{
|
|
427
|
+
field: "id",
|
|
428
|
+
message: `Entity with ID ${parentId} already exists`,
|
|
429
|
+
value: parentId,
|
|
430
|
+
},
|
|
431
|
+
],
|
|
432
|
+
}));
|
|
433
|
+
}
|
|
434
|
+
// Validate foreign keys
|
|
435
|
+
yield* validateForeignKeysEffect(validated, collectionName, relationships, stateRefs);
|
|
436
|
+
// Add to collection
|
|
437
|
+
yield* Ref.update(ref, (map) => {
|
|
438
|
+
const next = new Map(map);
|
|
439
|
+
next.set(parentId, validated);
|
|
440
|
+
return next;
|
|
441
|
+
});
|
|
442
|
+
// 9. Update inverse relationship foreign keys on connected entities
|
|
443
|
+
for (const connect of resolvedConnects) {
|
|
444
|
+
const relationship = relationships[connect.field];
|
|
445
|
+
if (relationship && relationship.type === "inverse") {
|
|
446
|
+
const targetConfig = dbConfig[connect.targetCollection];
|
|
447
|
+
if (!targetConfig)
|
|
448
|
+
continue;
|
|
449
|
+
const inverseField = findInverseRelationship(collectionName, targetConfig.relationships);
|
|
450
|
+
if (inverseField) {
|
|
451
|
+
const inverseRel = targetConfig.relationships[inverseField];
|
|
452
|
+
if (!inverseRel)
|
|
453
|
+
continue;
|
|
454
|
+
const foreignKey = inverseRel.foreignKey || `${inverseField}Id`;
|
|
455
|
+
const targetRef = stateRefs[connect.targetCollection];
|
|
456
|
+
if (!targetRef)
|
|
457
|
+
continue;
|
|
458
|
+
yield* Ref.update(targetRef, (map) => {
|
|
459
|
+
const existing = map.get(connect.targetId);
|
|
460
|
+
if (!existing)
|
|
461
|
+
return map;
|
|
462
|
+
const updated = {
|
|
463
|
+
...existing,
|
|
464
|
+
[foreignKey]: parentId,
|
|
465
|
+
updatedAt: now,
|
|
466
|
+
};
|
|
467
|
+
const next = new Map(map);
|
|
468
|
+
next.set(connect.targetId, updated);
|
|
469
|
+
return next;
|
|
470
|
+
});
|
|
471
|
+
}
|
|
472
|
+
}
|
|
473
|
+
}
|
|
474
|
+
// Publish change event for reactive query subscribers
|
|
475
|
+
if (changePubSub) {
|
|
476
|
+
yield* PubSub.publish(changePubSub, {
|
|
477
|
+
collection: collectionName,
|
|
478
|
+
operation: "create",
|
|
479
|
+
});
|
|
480
|
+
}
|
|
481
|
+
return validated;
|
|
482
|
+
});
|
|
483
|
+
//# sourceMappingURL=create-with-relationships.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"create-with-relationships.js","sourceRoot":"","sources":["../../../src/operations/crud/create-with-relationships.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Effect-based create operations for entities.
|
|
3
|
+
*
|
|
4
|
+
* Uses Ref<ReadonlyMap> for atomic state mutation, Effect Schema for validation,
|
|
5
|
+
* and typed errors (ValidationError, DuplicateKeyError, ForeignKeyError).
|
|
6
|
+
*/
|
|
7
|
+
import { Effect, PubSub, Ref, type Schema } from "effect";
|
|
8
|
+
import { DuplicateKeyError, type ForeignKeyError, type HookError, type UniqueConstraintError, type ValidationError } from "../../errors/crud-errors.js";
|
|
9
|
+
import type { CustomIdGenerator } from "../../plugins/plugin-types.js";
|
|
10
|
+
import type { ComputedFieldsConfig } from "../../types/computed-types.js";
|
|
11
|
+
import type { CreateInput, CreateManyOptions, CreateManyResult } from "../../types/crud-types.js";
|
|
12
|
+
import type { HooksConfig } from "../../types/hook-types.js";
|
|
13
|
+
import type { CollectionIndexes } from "../../types/index-types.js";
|
|
14
|
+
import type { ChangeEvent } from "../../types/reactive-types.js";
|
|
15
|
+
import type { SearchIndexMap } from "../../types/search-types.js";
|
|
16
|
+
import { type NormalizedConstraints } from "./unique-check.js";
|
|
17
|
+
type HasId = {
|
|
18
|
+
readonly id: string;
|
|
19
|
+
};
|
|
20
|
+
type RelationshipConfig = {
|
|
21
|
+
readonly type: "ref" | "inverse";
|
|
22
|
+
readonly target: string;
|
|
23
|
+
readonly foreignKey?: string;
|
|
24
|
+
};
|
|
25
|
+
/**
|
|
26
|
+
* Create a single entity with validation, hooks, and foreign key checks.
|
|
27
|
+
*
|
|
28
|
+
* Steps:
|
|
29
|
+
* 1. Strip computed field keys from input (they are derived, not stored)
|
|
30
|
+
* 2. Generate ID if not provided, add timestamps
|
|
31
|
+
* 3. Validate through Effect Schema
|
|
32
|
+
* 4. Run beforeCreate hooks (can transform entity)
|
|
33
|
+
* 5. Check for duplicate ID in Ref state
|
|
34
|
+
* 6. Validate foreign key constraints
|
|
35
|
+
* 7. Atomically add to Ref state
|
|
36
|
+
* 8. Update indexes if provided
|
|
37
|
+
*/
|
|
38
|
+
export declare const create: <T extends HasId, I = T>(collectionName: string, schema: Schema.Schema<T, I>, relationships: Record<string, RelationshipConfig>, ref: Ref.Ref<ReadonlyMap<string, T>>, stateRefs: Record<string, Ref.Ref<ReadonlyMap<string, HasId>>>, indexes?: CollectionIndexes, hooks?: HooksConfig<T>, uniqueFields?: NormalizedConstraints, computed?: ComputedFieldsConfig<unknown>, searchIndexRef?: Ref.Ref<SearchIndexMap>, searchIndexFields?: ReadonlyArray<string>, idGeneratorName?: string, idGeneratorMap?: Map<string, CustomIdGenerator>, changePubSub?: PubSub.PubSub<ChangeEvent>) => (input: CreateInput<T>) => Effect.Effect<T, ValidationError | DuplicateKeyError | ForeignKeyError | HookError | UniqueConstraintError>;
|
|
39
|
+
/**
|
|
40
|
+
* Create multiple entities with batch validation, hooks, and optional duplicate skipping.
|
|
41
|
+
*
|
|
42
|
+
* When `skipDuplicates` is true, entities that fail validation, have duplicate IDs,
|
|
43
|
+
* or have a HookError are skipped and reported in the result. Otherwise, the first error
|
|
44
|
+
* stops the operation.
|
|
45
|
+
*/
|
|
46
|
+
export declare const createMany: <T extends HasId, I = T>(collectionName: string, schema: Schema.Schema<T, I>, relationships: Record<string, RelationshipConfig>, ref: Ref.Ref<ReadonlyMap<string, T>>, stateRefs: Record<string, Ref.Ref<ReadonlyMap<string, HasId>>>, indexes?: CollectionIndexes, hooks?: HooksConfig<T>, uniqueFields?: NormalizedConstraints, computed?: ComputedFieldsConfig<unknown>, searchIndexRef?: Ref.Ref<SearchIndexMap>, searchIndexFields?: ReadonlyArray<string>, idGeneratorName?: string, idGeneratorMap?: Map<string, CustomIdGenerator>, changePubSub?: PubSub.PubSub<ChangeEvent>) => (inputs: ReadonlyArray<CreateInput<T>>, options?: CreateManyOptions) => Effect.Effect<CreateManyResult<T>, ValidationError | DuplicateKeyError | ForeignKeyError | HookError | UniqueConstraintError>;
|
|
47
|
+
export {};
|
|
48
|
+
//# sourceMappingURL=create.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"create.d.ts","sourceRoot":"","sources":["../../../src/operations/crud/create.ts"],"names":[],"mappings":"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"}
|