@aventara/prisma7-adapter 1.0.0-rc.1 → 1.0.0-rc.10
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/CHANGELOG.md +418 -0
- package/README.md +101 -24
- package/dist/discovery/artifact.loader.d.ts +8 -3
- package/dist/discovery/artifact.loader.js +6 -1
- package/dist/discovery/capability.deriver.d.ts +7 -7
- package/dist/discovery/capability.deriver.js +51 -8
- package/dist/discovery/client-shape.verifier.d.ts +0 -5
- package/dist/discovery/client-shape.verifier.js +1 -1
- package/dist/discovery/discovery-artifact.interface.d.ts +16 -4
- package/dist/discovery/discovery-artifact.interface.js +1 -1
- package/dist/discovery/enum.mapper.d.ts +4 -3
- package/dist/discovery/field.mapper.d.ts +8 -10
- package/dist/discovery/identifier.mapper.d.ts +3 -2
- package/dist/discovery/installed-client.locator.d.ts +14 -0
- package/dist/discovery/installed-client.locator.js +43 -0
- package/dist/discovery/model.discoverer.d.ts +6 -2
- package/dist/discovery/model.discoverer.js +22 -2
- package/dist/discovery/operations.deriver.d.ts +1 -1
- package/dist/discovery/scalar.mapper.d.ts +3 -2
- package/dist/discovery/schema-facts.interface.d.ts +10 -0
- package/dist/discovery/schema.reader.d.ts +2 -1
- package/dist/discovery/schema.reader.js +37 -5
- package/dist/discovery/vocabulary.dictionary.d.ts +6 -5
- package/dist/errors/back-reference.locator.d.ts +25 -0
- package/dist/errors/back-reference.locator.js +100 -0
- package/dist/errors/bigint-binding.locator.d.ts +7 -0
- package/dist/errors/bigint-binding.locator.js +27 -0
- package/dist/errors/error.normalizer.d.ts +42 -5
- package/dist/errors/error.normalizer.js +77 -2
- package/dist/errors/held-link.locator.d.ts +7 -0
- package/dist/errors/held-link.locator.js +66 -0
- package/dist/errors/prisma-error.reader.d.ts +4 -0
- package/dist/errors/prisma-error.reader.js +2 -0
- package/dist/execution/first-variant.emulator.d.ts +2 -1
- package/dist/execution/operation.executor.d.ts +9 -2
- package/dist/execution/operation.executor.js +40 -11
- package/dist/execution/result.shaper.d.ts +0 -6
- package/dist/execution/result.shaper.js +0 -5
- package/dist/execution/scoped-cursor.resolver.d.ts +11 -0
- package/dist/execution/scoped-cursor.resolver.js +47 -0
- package/dist/execution/transaction.executor.d.ts +7 -2
- package/dist/execution/transaction.executor.js +2 -0
- package/dist/generate/artifact.emitter.d.ts +12 -1
- package/dist/generate/artifact.emitter.js +56 -2
- package/dist/generate/computed-fields.import.d.ts +5 -0
- package/dist/generate/computed-fields.import.js +52 -0
- package/dist/generate/declared-support.reader.d.ts +3 -2
- package/dist/generate/discovery.cli.d.ts +3 -1
- package/dist/generate/discovery.cli.js +16 -4
- package/dist/generate/existence.gate.d.ts +2 -1
- package/dist/generate/index.d.ts +6 -0
- package/dist/generate/index.js +2 -0
- package/dist/generate/prisma-cli.resolver.d.ts +2 -1
- package/dist/generate/prisma.generate.d.ts +9 -0
- package/dist/generate/prisma.generate.js +91 -7
- package/dist/generate/reader-crosscheck.d.ts +5 -4
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/prisma-adapter.description.d.ts +42 -0
- package/dist/prisma-adapter.description.js +36 -0
- package/dist/prisma-client.interface.d.ts +2 -1
- package/dist/prisma.adapter.d.ts +6 -5
- package/dist/prisma.adapter.js +43 -28
- package/dist/provider/provider-profile.d.ts +21 -4
- package/dist/provider/provider-profile.js +21 -0
- package/dist/translation/identifier.addressing.d.ts +5 -4
- package/dist/translation/json-null.sentinel.d.ts +7 -0
- package/dist/translation/json-null.sentinel.js +17 -0
- package/dist/translation/mutation.translator.d.ts +4 -3
- package/dist/translation/mutation.translator.js +23 -4
- package/dist/translation/operation.translator.d.ts +15 -3
- package/dist/translation/operation.translator.js +54 -8
- package/dist/translation/order-pagination.translator.d.ts +23 -3
- package/dist/translation/order-pagination.translator.js +15 -0
- package/dist/translation/scalar.conversion.d.ts +0 -2
- package/dist/translation/where.translator.d.ts +3 -2
- package/dist/translation/where.translator.js +160 -18
- package/package.json +16 -16
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,423 @@
|
|
|
1
1
|
# @aventara/prisma7-adapter
|
|
2
2
|
|
|
3
|
+
## 1.0.0-rc.10
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- 04bb39a: `engines.node` is now `^22.23.4 || >=24.22.1`, the Node security releases of 2026-10-20 (CVE-2026-105481,
|
|
8
|
+
CVE-2026-105482, CVE-2026-105483, CVE-2026-106069, CVE-2026-106072, CVE-2026-106073, CVE-2026-106074,
|
|
9
|
+
CVE-2026-111497). The bins refuse an older Node in one sentence naming that range.
|
|
10
|
+
- 827ccb6: A listed update (`afterChecks`) no longer refuses an unchanged row on PostgreSQL. The compare-and-swap that holds the
|
|
11
|
+
write to the rows as they were read compares each field by `equals`, and the adapter's `equals` now matches every row
|
|
12
|
+
that reads as the value:
|
|
13
|
+
|
|
14
|
+
- a scalar list a create left out, which Prisma stores as `NULL` and reads as `[]`: an operator object that holds for
|
|
15
|
+
`[]` (`equals: []`, `isEmpty: true`, `hasEvery: []`) holds for that row too, in every filter;
|
|
16
|
+
- a timestamp finer than a millisecond (a `@db.Timestamptz(6)` the database writes), which Prisma reads truncated:
|
|
17
|
+
equality with an instant also holds the instants inside its millisecond.
|
|
18
|
+
|
|
19
|
+
On a `Bytes[]` column, `equals`, `hasEvery` and `hasSome` are no longer offered: Prisma 7.10.1 binds their operand's
|
|
20
|
+
members as base64 text, so they matched other rows than they named. `has` and `isEmpty` remain. Such a column is not
|
|
21
|
+
part of the compare-and-swap.
|
|
22
|
+
|
|
23
|
+
The compare-and-swap takes its fields from what the adapter compares, so an exemption that hides `equals` from callers
|
|
24
|
+
no longer takes a field out of it.
|
|
25
|
+
- 4f0fd29: The Prisma 7 adapter's peer floor is now `^7.10.1` (`prisma`, `@prisma/client`, `@prisma/adapter-pg`,
|
|
26
|
+
`@prisma/adapter-better-sqlite3`). `prisma` 7.10.0 pins `mysql2` 3.15.3 (GHSA-3f6p-5ww8-9rcr, GHSA-rgwj-5xj2-c3m3)
|
|
27
|
+
and, through `@prisma/config`, `deepmerge-ts` 7.1.5 (GHSA-ggr8-5vv4-36mx); 7.10.1 pins `mysql2` 3.24.4 and
|
|
28
|
+
`deepmerge-ts` 8.0.2. `aventara new` and `aventara init` install Prisma at the floor, so new projects get 7.10.1, and
|
|
29
|
+
`aventara init` refuses a project whose Prisma is below it.
|
|
30
|
+
- f52c499: The generate step reads multiSchema's `@@schema("auth")`: a model states its PostgreSQL schema in the discovery
|
|
31
|
+
artifact (`schema`), and the Core Contract carries it. Until now `@@schema` stopped the build. On an enum it is read and
|
|
32
|
+
dropped. A model whose table another service owns is marked `managedElsewhere: true` in the Aventara configuration and
|
|
33
|
+
listed in `prisma.config.ts` as an external table (`experimental.externalTables`, `tables.external`), so neither
|
|
34
|
+
Aventara writes it nor `prisma migrate` changes it.
|
|
35
|
+
- 10341d5: Policy checks, tightened:
|
|
36
|
+
|
|
37
|
+
- Writing a reference field itself (`authorId: "u2"`) is held to the target's read scope, as `$connect` is: the row it
|
|
38
|
+
names must be one the caller may read, or the write is refused (`A4002`). Creates, updates, both branches of an
|
|
39
|
+
upsert and the records of nested writes are all checked. The reference is handed to the adapter as a `$connect` that
|
|
40
|
+
carries the read scope, so the write itself refuses a row outside it, with no extra query; a row that is not there is
|
|
41
|
+
refused the same way. Where Prisma's input takes no relation (`createMany`, `updateMany`, a to-many nested
|
|
42
|
+
`$update`), and where a create writes a reference `null` (left out, the column's default would fill it), one count
|
|
43
|
+
per target Resource asks before the write whether every row named is there and readable. Nothing is asked where that
|
|
44
|
+
Resource is read by everyone, and a `null` reference is not asked about. A record written this way writes its other
|
|
45
|
+
references as links too, so a missing row there answers `A2003` rather than `A2008`.
|
|
46
|
+
- A row a write names to link that is not there is refused (`A4002`) like a row the caller cannot read, wherever the
|
|
47
|
+
target has a scope: a reference field, and a `$connect`, `$set` or `$disconnect` selector. Before, a missing row
|
|
48
|
+
answered the store's `A2008` or `A2003`, which told a caller which rows it cannot read exist. Without a scope, the
|
|
49
|
+
codes are unchanged.
|
|
50
|
+
- An update the engine lists in `afterChecks` now holds a to-one nested `$update` to its row as it was read. A row a
|
|
51
|
+
concurrent write changed in between refuses the write (`A4002`) and rolls it back, with no extra query.
|
|
52
|
+
- A listed `update.many` or `update.count` that changes fewer rows than it read (a concurrent write changed one in
|
|
53
|
+
between) is refused (`A4002`) and rolled back, rather than answering a partial success.
|
|
54
|
+
- The client and agent Contracts leave out an enum that only a Resource managed elsewhere uses. The ClientContract hash
|
|
55
|
+
of an app with such an enum changes.
|
|
56
|
+
- Seven public types write their members out in an editor's hover instead of naming a type no entry exports (`ctx.$sql`,
|
|
57
|
+
a compute stage's context, a pipe's return, `defineResource`'s overlays, a family's variants, the `access` and
|
|
58
|
+
`policy` check, `AvConfigComputedFields.agentExtends`).
|
|
59
|
+
|
|
60
|
+
- 88263a1: On PostgreSQL, a scalar list Prisma stored as `NULL` (a create left it out; it reads as `[]`) now answers every list
|
|
61
|
+
filter as `[]` does, negated ones included: `NOT { tags: { has: "a" } }` (and `hasSome`, `hasEvery`, `isEmpty: false`,
|
|
62
|
+
`equals: [x]`) holds for that row. Inside a relation's `every`, a related row whose list was never written fails
|
|
63
|
+
`every: { tags: { has: "a" } }` as an empty list does, so its parent is no longer kept.
|
|
64
|
+
- Updated dependencies [587dd01]
|
|
65
|
+
- Updated dependencies [d7e7369]
|
|
66
|
+
- Updated dependencies [7ee547b]
|
|
67
|
+
- Updated dependencies [f52c499]
|
|
68
|
+
- Updated dependencies [2907484]
|
|
69
|
+
- Updated dependencies [a6bbdf0]
|
|
70
|
+
- Updated dependencies [3e26549]
|
|
71
|
+
- Updated dependencies [a6bbdf0]
|
|
72
|
+
- Updated dependencies [6f3f6f6]
|
|
73
|
+
- Updated dependencies [04bb39a]
|
|
74
|
+
- Updated dependencies [3fb3333]
|
|
75
|
+
- Updated dependencies [827ccb6]
|
|
76
|
+
- Updated dependencies [7f5abc3]
|
|
77
|
+
- Updated dependencies [88263a1]
|
|
78
|
+
- Updated dependencies [10341d5]
|
|
79
|
+
- Updated dependencies [8129844]
|
|
80
|
+
- Updated dependencies [88263a1]
|
|
81
|
+
- Updated dependencies [3020b5c]
|
|
82
|
+
- Updated dependencies [88263a1]
|
|
83
|
+
- Updated dependencies [88263a1]
|
|
84
|
+
- @aventara/core@1.0.0-rc.10
|
|
85
|
+
|
|
86
|
+
## 1.0.0-rc.9
|
|
87
|
+
|
|
88
|
+
### Patch Changes
|
|
89
|
+
|
|
90
|
+
- Updated dependencies [205a379]
|
|
91
|
+
- Updated dependencies [a0bb05e]
|
|
92
|
+
- Updated dependencies [86ab319]
|
|
93
|
+
- Updated dependencies [fdf52e6]
|
|
94
|
+
- @aventara/core@1.0.0-rc.9
|
|
95
|
+
|
|
96
|
+
## 1.0.0-rc.8
|
|
97
|
+
|
|
98
|
+
1.0.0-rc.5, rc.6 and rc.7 were tagged but never published; 1.0.0-rc.8 contains everything listed under them and the changes below.
|
|
99
|
+
|
|
100
|
+
### Patch Changes
|
|
101
|
+
|
|
102
|
+
- 1c8e4ee: The discovery artifact's referential actions say `referenceFields` where they said `references`: in
|
|
103
|
+
`referentialActions.<Resource>.owningEdges[]`, the fields of the Resource itself that hold the reference
|
|
104
|
+
(`@relation(fields: [...])`). The model's relation fields already use `references` for the target's fields
|
|
105
|
+
(`@relation(references: [...])`) and `referenceFields` for these, so the same word meant two different lists in one
|
|
106
|
+
file. The generated `discovery.artifact.ts` changes on the next `aventara:prepare` (it runs on install, build and
|
|
107
|
+
start), and only in those keys: `modelHash` is unchanged, since the referential actions are outside it, and so is the
|
|
108
|
+
prebuilt Contracts file `aventara-build` writes. Code that read `owningEdges[i].references` reads
|
|
109
|
+
`owningEdges[i].referenceFields`.
|
|
110
|
+
- Updated dependencies [1c8e4ee]
|
|
111
|
+
- @aventara/core@1.0.0-rc.8
|
|
112
|
+
|
|
113
|
+
## 1.0.0-rc.7
|
|
114
|
+
|
|
115
|
+
1.0.0-rc.5 and 1.0.0-rc.6 were tagged but never published; 1.0.0-rc.7 contains everything listed under them and the changes below.
|
|
116
|
+
|
|
117
|
+
### Patch Changes
|
|
118
|
+
|
|
119
|
+
- Updated dependencies [f917c1c]
|
|
120
|
+
- @aventara/core@1.0.0-rc.7
|
|
121
|
+
|
|
122
|
+
## 1.0.0-rc.6
|
|
123
|
+
|
|
124
|
+
1.0.0-rc.5 was tagged but never published. 1.0.0-rc.6 contains everything listed under 1.0.0-rc.5 and the fix below.
|
|
125
|
+
|
|
126
|
+
### Patch Changes
|
|
127
|
+
|
|
128
|
+
- Updated dependencies [1cf72e0]
|
|
129
|
+
- @aventara/core@1.0.0-rc.6
|
|
130
|
+
|
|
131
|
+
## 1.0.0-rc.5
|
|
132
|
+
|
|
133
|
+
### Patch Changes
|
|
134
|
+
|
|
135
|
+
- 4795ff1: Two additions for policy engines. A Framework without a policy, and every Contract a caller is served, are unchanged.
|
|
136
|
+
|
|
137
|
+
- A policy engine can check a create whose row reaches another Resource through a relation. Discovery now states, on the end of a relation that holds the reference, which of the target's fields its reference fields name, pair by pair (`Note.campaign`: `referenceFields: ["campaignId"]`, `references: ["id"]`). An engine reads them from the model it is built from (a Prisma discovery artifact's `model`) or from `framework.contracts.core`, and asks one `exists` about the row they name: "a player creates a note only in a campaign they play in". Only the adapter's model and the Core Contract carry them. The Application, Client and Agent Contracts, `/_contract`, the MCP tools and every ClientContract hash are unchanged. The discovery artifact's model hash, and so a prebuilt Contracts file's fingerprint, change: regenerate the artifact and rebuild the prebuilt file.
|
|
138
|
+
- `fieldsOf({ access: "write" })` also names the action that writes the record, `action: "create" | "update"` (an upsert's branches each their own, a nested record its directive's), so an engine can lock a field on update and still let a create write it. A read question names none. An engine that ignores it keeps working.
|
|
139
|
+
|
|
140
|
+
- 9e178ca: Fixes for applications that check requests with a policy engine. A Framework without a policy behaves as before.
|
|
141
|
+
|
|
142
|
+
- A cursor on a row the caller cannot read is answered exactly as a cursor on a row that does not exist, at the root and in a to-many relation, whatever values the caller sends beside the identifier. Before, the page started at the hidden row, so it told that the row exists and where its values sort. The Prisma adapter reads the cursor's row under the read scope first: one statement more for a cursor on a readable row, and only that read for one on a row the caller cannot read.
|
|
143
|
+
- A unique update with a nested write (`$create`, `$connect`, …) on a row the caller can read but not change answers `A4002`, as the same update without one does. It answered `A2003`. A row the caller cannot read still answers `A2003`.
|
|
144
|
+
- The `exists` questions a policy asks select the Resource's primary identifier, never another unique field such as a governed `email`.
|
|
145
|
+
- `policy.principal` may answer with a promise. A synchronous principal works as before; a rejection answers `A3000`, as a throw does.
|
|
146
|
+
- `AvConstructionError.message` names the first problem and how many more there are, for example `Aventara framework configuration validation failed: CONFIG_INVALID_TYPE at adapter.execute: adapter.execute must be a function (+2 more)`. `stage` and `diagnostics` are unchanged.
|
|
147
|
+
|
|
148
|
+
## 1.0.0-rc.4
|
|
149
|
+
|
|
150
|
+
### Patch Changes
|
|
151
|
+
|
|
152
|
+
- 7c3b65f: Build-time Contracts for serverless and edge cold starts.
|
|
153
|
+
|
|
154
|
+
- New package `@aventara/build`, bin `aventara-build`, a development dependency. It runs `src/aventara.config.ts` and
|
|
155
|
+
`src/aventara.adapter.ts` without a database client, compiles the Contracts with the project's `@aventara/core` and
|
|
156
|
+
writes `src/generated/aventara/contracts.generated.ts` (`aventaraContracts`), which a serverless or edge entry passes
|
|
157
|
+
to `createFramework` as `prebuilt`. A configuration that startup would refuse fails the build with the same
|
|
158
|
+
`CONFIG_…`/`COMPILER_…` diagnostics. `aventara-build --check` writes nothing and exits 1 when the file is missing or
|
|
159
|
+
stale, naming the Resources that changed.
|
|
160
|
+
- `@aventara/prisma7-adapter`: `describePrismaAdapter({ discovery, provider, driver })` states the adapter's passive
|
|
161
|
+
facts (the model, the driver's transaction capability, the referential actions, the computed fields) with no client.
|
|
162
|
+
`createPrismaAdapter({ ...description, client })` builds the adapter from the same facts, and still checks the client
|
|
163
|
+
against the discovery artifact.
|
|
164
|
+
- `@aventara/cli`: the scaffold's `src/aventara.config.ts` exports the configuration as a plain value
|
|
165
|
+
(`export const aventaraConfig = { … } as const`) with no `adapter`. A new `src/aventara.adapter.ts` default-exports
|
|
166
|
+
`describePrismaAdapter(…)`, and `app.module.ts` joins the two:
|
|
167
|
+
`config: { ...aventaraConfig, adapter: await createPrismaAdapter({ ...adapter, client: prisma }) }`. The Nest server
|
|
168
|
+
still compiles its Contracts at startup and passes no `prebuilt`. `aventara:prepare` ends with `&& aventara-build`,
|
|
169
|
+
and `@aventara/build` is an exact development dependency.
|
|
170
|
+
|
|
171
|
+
- 2b1b17e: `aventara-build`'s files no longer land inside a Prisma client generated into `src/generated`.
|
|
172
|
+
|
|
173
|
+
When `aventara init` reuses a project whose Prisma client is generated into `src/generated`, it already puts the
|
|
174
|
+
discovery artifact in `src/aventara/`, because `prisma generate` deletes every file in its output directory that it did
|
|
175
|
+
not write. `aventara-build` still wrote its three files to `src/generated/aventara/`, so each `prisma generate` deleted
|
|
176
|
+
them and the project stopped compiling until the next `aventara:prepare`. Now all of Aventara's generated files are
|
|
177
|
+
in one place.
|
|
178
|
+
|
|
179
|
+
- `@aventara/build`: `aventara-build` writes `resources.generated.ts`, `computed-fields.generated.ts` and
|
|
180
|
+
`contracts.generated.ts` to the directory the configuration imports `aventaraResources` from, so the tree is always
|
|
181
|
+
written where the configuration reads it. A configuration that imports no tree keeps `src/generated/aventara/`.
|
|
182
|
+
The files of a project whose client is generated anywhere else are the same bytes, in the same place.
|
|
183
|
+
- `@aventara/prisma7-adapter`: with `--config`, the artifact imports the computed fields from its sibling,
|
|
184
|
+
`./computed-fields.generated`, wherever `--out` puts it. `--config` is still required for that import and the step
|
|
185
|
+
still checks that the file exists, but the step no longer uses its location. A scaffold's artifact is unchanged.
|
|
186
|
+
- `@aventara/cli`: in that project, `src/aventara.config.ts` imports the tree from `./aventara/resources.generated`,
|
|
187
|
+
and `.gitignore` gets the one `/src/aventara/` line that covers all four files (no separate
|
|
188
|
+
`/src/generated/aventara/contracts.generated.ts` line). The agent skill says where the generated files are in
|
|
189
|
+
both cases.
|
|
190
|
+
|
|
191
|
+
- 3a0dfca: A write the policy checks costs fewer database round trips. What each check decides and refuses is unchanged.
|
|
192
|
+
|
|
193
|
+
- A single-row update or delete carries the caller's scopes inside its own `where` and runs as one statement, with no
|
|
194
|
+
read of its row before it. One that matches nothing still answers `A4002` when the caller can read the row and
|
|
195
|
+
`A2003` when it cannot, with one lookup on that miss only. The Prisma adapter sends it as
|
|
196
|
+
`update({ where: { id, AND: [scope] } })`.
|
|
197
|
+
- A create asks `can({ action: "create", row })` and its `exists` lookups before the insert, without a transaction. A
|
|
198
|
+
transaction around them never closed the race between the lookup and the insert at the database's default
|
|
199
|
+
isolation, and cost a BEGIN and a COMMIT.
|
|
200
|
+
- A transaction opens only when a check after the write may roll it back: an update's after check or move-out, a
|
|
201
|
+
created row held to a write grant, a nested write, or returned rows checked by `exists`. A plain checked create or
|
|
202
|
+
delete is one statement, its interceptors and hooks outside any transaction.
|
|
203
|
+
- The after check asks `can` about the row the update returned, so it reads nothing again. Only a move-out reads the
|
|
204
|
+
changed rows again. An `update.count` runs as the returning `update.many` when the Contract offers it.
|
|
205
|
+
|
|
206
|
+
Round trips per request on PostgreSQL: `create.one` 3 → 1, `delete.unique` 4 → 1, `update.unique` 5 → 3,
|
|
207
|
+
`update.many` 4 → 3, `update.count` 5 → 3. Reads, and a Framework without a policy, are unchanged.
|
|
208
|
+
|
|
209
|
+
- 3813207: The Resource tree and the computed fields come from `aventara-build`.
|
|
210
|
+
|
|
211
|
+
- `@aventara/build`: before it compiles the Contracts, `aventara-build` writes two more files under
|
|
212
|
+
`src/generated/aventara/`. `resources.generated.ts` exports `aventaraResources`: every `defineResource(…)` result
|
|
213
|
+
that the files `src/resources/**/*.resource.ts` export, found by its type (never run), one `resources` tree per
|
|
214
|
+
layer, written as the plain spreads you wrote by hand (`root` always, `application`, `client` and `agent` when some
|
|
215
|
+
Resource has a block for them). Two definitions of one Resource stop the build, naming both. Imports are spelled as
|
|
216
|
+
the project spells its own. `computed-fields.generated.ts` exports `computedFields` and its type `AvComputedFields`:
|
|
217
|
+
which fields the configuration's write compute fills, read off its type after the tree exists, so a fresh install is
|
|
218
|
+
typed right on its first `aventara:prepare`. `--check` covers all three files. `typescript` (`>=5.7.0 <7`) is now a
|
|
219
|
+
peer dependency.
|
|
220
|
+
- `@aventara/prisma7-adapter`: the generate step no longer reads the configuration. With `--config`, the discovery
|
|
221
|
+
artifact imports `computedFields` and `AvComputedFields` from the file `aventara-build` writes beside the
|
|
222
|
+
configuration (`generated/aventara/computed-fields.generated.ts`); a `--config` file that does not exist is still
|
|
223
|
+
refused. `readConfigComputedFields`, `AvPrismaConfigReaderError` and `ConfigComputedFieldsReading` are removed from
|
|
224
|
+
`@aventara/prisma7-adapter/generate`, as are `PrismaGenerateToolchain.readComputedFields` and
|
|
225
|
+
`PrismaGenerateResult.computedFields`.
|
|
226
|
+
- `@aventara/cli`: the scaffold's `src/aventara.config.ts` takes its Resources from the tree,
|
|
227
|
+
`resources: aventaraResources.root`, so a new Resource file needs no configuration edit; the agent skill says so.
|
|
228
|
+
|
|
229
|
+
- Updated dependencies [e3d03a7]
|
|
230
|
+
- Updated dependencies [d10639a]
|
|
231
|
+
- Updated dependencies [f67e68c]
|
|
232
|
+
- Updated dependencies [708556c]
|
|
233
|
+
- Updated dependencies [3a0dfca]
|
|
234
|
+
- Updated dependencies [99169d2]
|
|
235
|
+
- Updated dependencies [0fd2608]
|
|
236
|
+
- Updated dependencies [154e440]
|
|
237
|
+
- Updated dependencies [2fcffdb]
|
|
238
|
+
- @aventara/core@1.0.0-rc.4
|
|
239
|
+
|
|
240
|
+
## 1.0.0-rc.3
|
|
241
|
+
|
|
242
|
+
### Patch Changes
|
|
243
|
+
|
|
244
|
+
- b38034d: `aventara-prisma7-generate` refuses a `--provider` that the schema's `datasource` block contradicts, or a block naming
|
|
245
|
+
a provider the adapter does not support, before `prisma generate` runs, so neither the Prisma client nor the artifact
|
|
246
|
+
is written:
|
|
247
|
+
|
|
248
|
+
```text
|
|
249
|
+
aventara-prisma7-generate: --provider postgresql contradicts the schema's datasource `db` (prisma/schema.prisma:12), which names provider "sqlite"; pass --provider sqlite.
|
|
250
|
+
```
|
|
251
|
+
|
|
252
|
+
PSL's `postgres` spelling counts as `postgresql`, and a provider that is not a string literal is not compared.
|
|
253
|
+
Before, the flag was taken on trust, and a wrong one wrote the wrong provider into the artifact and the wrong filter
|
|
254
|
+
modes into the Contract.
|
|
255
|
+
|
|
256
|
+
When the file system refuses the artifact file (`--out`), the step says so in one sentence naming the file and why,
|
|
257
|
+
such as
|
|
258
|
+
`the artifact file /app/src/generated/aventara/discovery.artifact.ts (--out) cannot be written: permission denied (EACCES).`,
|
|
259
|
+
and leaves no staged file behind. Before, every such failure except a directory printed a stack trace.
|
|
260
|
+
|
|
261
|
+
- b38034d: On PostgreSQL, a `@unique` value too long for its index (an index row past the B-tree's limit of about 2704 bytes, SQLSTATE
|
|
262
|
+
`54000`) is answered `422 A2004`, not `500 A3001`: one `V1004` issue at `["arguments"]`, as a value too long for its
|
|
263
|
+
column already was. The adapter reads the SQLSTATE, never the message. The issue's message for a value too long now
|
|
264
|
+
reads `The database refused this value: it is longer than the database can hold for its column.`
|
|
265
|
+
(it said `longer than its column can hold`, which an index refusal is not).
|
|
266
|
+
- Updated dependencies [b38034d]
|
|
267
|
+
- Updated dependencies [b38034d]
|
|
268
|
+
- Updated dependencies [b38034d]
|
|
269
|
+
- Updated dependencies [b38034d]
|
|
270
|
+
- Updated dependencies [b38034d]
|
|
271
|
+
- Updated dependencies [b38034d]
|
|
272
|
+
- @aventara/core@1.0.0-rc.3
|
|
273
|
+
|
|
274
|
+
## 1.0.0-rc.2
|
|
275
|
+
|
|
276
|
+
### Patch Changes
|
|
277
|
+
|
|
278
|
+
- On Cloudflare D1, a `BigInt` value beyond ±(2^53 − 1) is answered `A2004`, not `A3001`. `@prisma/adapter-d1`
|
|
279
|
+
binds a bigint as a JavaScript number and refuses one beyond that range before the statement runs, written,
|
|
280
|
+
compared in a filter or used in an `$increment`, and Prisma reports it as a database error (`P2039`). The adapter
|
|
281
|
+
answers that refusal as a value the database refused: `422 A2004` with one `V1004` issue, `The database refused
|
|
282
|
+
this value: it is outside the range its column can hold.`, at the value in the arguments (for example
|
|
283
|
+
`["arguments", "where", "views", "gt"]`). Nothing is written by the refused statement. It reads the arguments only
|
|
284
|
+
after the driver refused them, and only for the D1 driver; every other D1 database error stays `A3001`, and so does
|
|
285
|
+
a raw `ctx.$sql` statement binding such a value. Within ±(2^53 − 1) a bigint round-trips exactly on D1.
|
|
286
|
+
In rc.1 the refusal answered `500 A3001`. Measured on 7.10.0 through Miniflare's D1 binding.
|
|
287
|
+
- The README's D1 notes are corrected: D1 is measured in process through Miniflare, where Prisma's client refuses
|
|
288
|
+
an interactive `$transaction` and the D1 driver runs Prisma's implicit transaction for a nested write as single
|
|
289
|
+
statements, so a nested write is not atomic on D1.
|
|
290
|
+
- The optional `typescript` peer range is `>=5.7.0 <7` (it was `>=5.5.0 <7`). Under TypeScript 5.5 and 5.6 a
|
|
291
|
+
variant's stages written inline in `createFramework` are told `unknown` arguments, so `ctx.$args.data` and the
|
|
292
|
+
documented spread pipe `(args) => ({ ...args, data: { ...args.data, title: "t" } })` do not compile; TypeScript 5.7
|
|
293
|
+
and later type them. A project on TypeScript 5.5 or 5.6 upgrades to 5.7 or later.
|
|
294
|
+
- `createPrismaAdapter` checks the installed `@prisma/client`'s major against the discovery artifact's, as the
|
|
295
|
+
README says. It reads the version from `@prisma/client/package.json`, resolved from the adapter's own location and
|
|
296
|
+
then from the working directory, and refuses an artifact generated against another major with
|
|
297
|
+
`AvPrismaDiscoveryArtifactError`. In rc.1 the artifact's version stood in for the installed one when no
|
|
298
|
+
`installedPrismaVersion` was passed, which a scaffolded project never does, so the check compared the artifact with
|
|
299
|
+
itself. Where the version cannot be read (a runtime without Node's module loader, a bundle deployed without
|
|
300
|
+
`@prisma/client`), the adapter starts and emits a warning, code `AVENTARA_PRISMA_VERSION_UNCHECKED`, saying the
|
|
301
|
+
majors were not compared. `installedPrismaVersion` still overrides the version read.
|
|
302
|
+
- `aventara-prisma7-generate` refuses an `--out` inside `--client`, before `prisma generate` runs: exit 1 and one
|
|
303
|
+
sentence naming both paths. Prisma's next `prisma generate` clears the client's directory, so an artifact written
|
|
304
|
+
there was deleted. In rc.1 the step wrote it and exited 0. The same refusal applies to
|
|
305
|
+
`generatePrismaDiscoveryArtifact` and `runPrismaGenerateStep`.
|
|
306
|
+
- `aventara-prisma7-generate` refuses an `--out` that names a directory in one sentence (exit 1), before
|
|
307
|
+
`prisma generate` runs. In rc.1 it ran Prisma and then failed with an `EISDIR` stack trace.
|
|
308
|
+
- A nested write that writes its relation back is answered `A2004`, not `A3001`. Prisma writes a record reached
|
|
309
|
+
through a relation without that relation's other end, so it refuses a post created in `author.posts` that names
|
|
310
|
+
`author` or `authorId`, and a category created in a post's `category` that nests `posts`. The discovery artifact
|
|
311
|
+
now states each relation's other end (`inverse`, paired from the schema by relation name) and no relation writable
|
|
312
|
+
at the `"loopback"` position, so `@aventara/core` refuses such a write before any guard or SQL: `A2004`, `V1012` at
|
|
313
|
+
the field written back. It holds for `$create`, `$connectOrCreate`, `$update` and `$upsert`, to-one and to-many,
|
|
314
|
+
self-relations and one-to-ones. Where a layer hides the relation's other end, its Contract states no pairing and
|
|
315
|
+
Prisma's client is the one that refuses: the adapter answers that refusal as the caller's too, `A2004` with a
|
|
316
|
+
`V1012` issue at the field and the message `The data source refused this nested write: a record written through a
|
|
317
|
+
relation cannot write that relation or its reference fields back.` It reads the arguments only after Prisma
|
|
318
|
+
refused them; every other refusal of Prisma's client stays `A3001`. In rc.1 every case answered `500 A3001`.
|
|
319
|
+
Measured on 7.10.0, SQLite and PostgreSQL. Run `npm run aventara:prepare` to regenerate the artifact: the model's
|
|
320
|
+
hash and every Contract's hash change.
|
|
321
|
+
- The discovery artifact states each relation's reference fields (`referenceFields`, read from the schema's
|
|
322
|
+
`@relation(fields: …)`), on optional and required relations alike, and none on the end that holds no reference.
|
|
323
|
+
So the types leave `categoryId` out of a post created in `Category.posts`, as `@aventara/core` refuses it. Run
|
|
324
|
+
`npm run aventara:prepare` to regenerate the artifact: the model's hash and every Contract's hash change.
|
|
325
|
+
- A `$divide` by zero is answered `A2004`, not `A3001`. It reaches the database as given: PostgreSQL refuses the
|
|
326
|
+
division (`P2039`, `22012`) and the adapter answers `V1004` `The database refused this value: it divides by zero.`;
|
|
327
|
+
SQLite computes NULL and the `NOT NULL` column refuses it (`P2011`), answered `V1004` `The database refused this
|
|
328
|
+
value: the write computes no value for a column that requires one, as a division by zero does.` Both at
|
|
329
|
+
`["arguments"]`, nothing written. `P2011` reaches the adapter only this way: core refuses a `null` for a required
|
|
330
|
+
field and a missing one, and so does Prisma's client before the query. In rc.1 both answered `500 A3001`. Measured
|
|
331
|
+
on 7.10.0 for `Int`, `BigInt`, `Float` and `Decimal`, in `update` and `updateMany`.
|
|
332
|
+
- `null` on a nullable `Json` field is the database NULL, as on every other nullable field. A write of `null`
|
|
333
|
+
(create, update, upsert, bulk, nested, a plan step) is sent as Prisma's `DbNull`; `{ meta: null }` and
|
|
334
|
+
`{ meta: { equals: null } }` are sent as Prisma's `AnyNull` and match every row that reads back `null` (a database
|
|
335
|
+
NULL or a JSON `null` stored by other means), and `{ meta: { not: null } }` matches the other rows. A JSON `null`
|
|
336
|
+
inside a value is sent as written, and so is a `null` beside a `path`: Prisma matches the documents whose value at
|
|
337
|
+
that path is a JSON `null`. In rc.1 a write of `null` stored a JSON `null`, `equals: null` matched only the stored
|
|
338
|
+
JSON nulls, and `{ meta: null }` failed with `500 A3001`. Reads are unchanged. Measured on 7.10.0, SQLite and
|
|
339
|
+
PostgreSQL.
|
|
340
|
+
- A to-one relation filter is sent under Prisma's `is`. `{ category: {} }` matches the rows that have a related row and
|
|
341
|
+
`{ NOT: { category: {} } }` the rows that have none. In rc.1 the empty predicate was sent unwrapped, which Prisma
|
|
342
|
+
reads as no condition: both matched every row, and `Post.delete.count({ where: { NOT: { author: {} } } })` deleted
|
|
343
|
+
every post although each has its required author. A non-empty nested `where` and `null` match what they did.
|
|
344
|
+
- A value the database refuses is answered `A2004`, not `A3001`. Text-match operands and written values reach Prisma
|
|
345
|
+
as given (`%` and `_` are what the engine's `LIKE` makes of them, a column rounds or keeps what it does); when
|
|
346
|
+
PostgreSQL refuses a caller's value, the adapter answers `A2004` with one issue at `["arguments"]` (Prisma's error
|
|
347
|
+
names no column): `V1004` for a value too long for its column (`P2000`), out of its column's range (`P2020`: a
|
|
348
|
+
`Decimal` past its precision, `Number.MAX_VALUE` in a `Float`, an `Int` `$increment` past 2^31) or a `DateTime`
|
|
349
|
+
outside PostgreSQL's range (`P2039`, `22009`); `V1001` for U+0000 in text or `json` (`P2039`, `22021` and `22P05`),
|
|
350
|
+
a lone surrogate in `json` (`P2007`) and a `LIKE` pattern ending in `\` (`P2039`, `22025`). The issue's message
|
|
351
|
+
says which of these the database refused, in core's words and none of the database's (`The database refused this
|
|
352
|
+
value: it is longer than its column can hold.`), not the code's generic text. Inside a plan the
|
|
353
|
+
issue stands at the step (`["operations", i, "args"]`) and the plan rolls back. Every other database failure stays
|
|
354
|
+
`A3001`. In rc.1 each of these answered `500 A3001`. Measured on 7.10.0, SQLite and PostgreSQL; SQLite refused none
|
|
355
|
+
of these values.
|
|
356
|
+
- A field's `not` holding an operator object now means the negation of the whole object, on every field type, on
|
|
357
|
+
both engines, in reads and in bulk writes. `{ f: { not: X } }` matches exactly the rows `{ NOT: { f: X } }` matches:
|
|
358
|
+
a row where `X` is neither true nor false (the column is `NULL`, a `json` `path` is not in the document, a `json`
|
|
359
|
+
value is not the kind the operator reads) matches neither `X` nor `not: X`, as SQL's `NOT` reads it. The adapter
|
|
360
|
+
sends it to Prisma as `NOT` of the field's filter, ANDed with the rest of the `where`, because Prisma's own
|
|
361
|
+
field-level `not` says less (measured on 7.10.0, SQLite and PostgreSQL):
|
|
362
|
+
|
|
363
|
+
- In rc.1, a `json` field's `not` holding operators matched every row on both engines, because Prisma reads that
|
|
364
|
+
`not` as a JSON value to compare the document with. That covers `{ meta: { not: { path: ["label"],
|
|
365
|
+
stringContains: "x" } } }`, `{ meta: { not: { equals: { a: 1 } } } }` and every other operator under it, and an
|
|
366
|
+
`update.many`, `update.count`, `delete.count` or `delete.first` under such a filter wrote or deleted every row
|
|
367
|
+
the rest of the filter allowed.
|
|
368
|
+
- In rc.1, two or more operators under `not` were negated one at a time and ANDed, so
|
|
369
|
+
`{ views: { not: { gt: 2, lte: 5 } } }` matched no row. It now matches the rows outside that range.
|
|
370
|
+
- In rc.1 on PostgreSQL, a `mode` inside `not` (`{ title: { not: { contains: "x", mode: "insensitive" } } }`)
|
|
371
|
+
failed with `A3001`, because Prisma's filter under `not` has no `mode`. It now matches the titles that do not
|
|
372
|
+
contain `x` in any case.
|
|
373
|
+
|
|
374
|
+
The object under `not` is its own level: nothing from the object around it reaches into it. In rc.1 on
|
|
375
|
+
PostgreSQL, `{ title: { mode: "insensitive", not: { contains: "x" } } }` excluded `X` as well as `x`, because Prisma
|
|
376
|
+
applied the outer `mode` inside its own `not`. Core now refuses that filter (`A2004`, `V1001` at the `mode`); write
|
|
377
|
+
`{ title: { not: { contains: "x", mode: "insensitive" } } }`. A plain value under `not` (`{ not: "x" }`,
|
|
378
|
+
`{ not: null }`) is equality negated and is sent as before.
|
|
379
|
+
|
|
380
|
+
- A `json` field's bare value in a filter is equality on both engines: `{ meta: "x" }` and `{ meta: [1, 2] }` are sent
|
|
381
|
+
to Prisma as `{ equals: … }`. In rc.1 they failed with `A3001`, because Prisma's Json filter takes no bare value.
|
|
382
|
+
- Filter modes, measured on each engine. PostgreSQL offers `"default"`, `"sensitive"` and `"insensitive"` on a string
|
|
383
|
+
column and on a `json` value at a `path`; on a whole `json` document it offers `"default"` and `"sensitive"`, because
|
|
384
|
+
Prisma accepts an insensitive `stringContains` there and PostgreSQL then fails (`42883 function lower(jsonb) does not
|
|
385
|
+
exist`, answered `A3001`). That filter is now refused before any query (`A2004`, `V1006` at the `mode`). SQLite, and
|
|
386
|
+
so D1, offers `"default"` only: its `LIKE` folds ASCII case and nothing else, and `equals` folds none, so neither
|
|
387
|
+
promise holds. Every string field with a text operator now offers `mode` (on SQLite with `"default"` alone), and
|
|
388
|
+
`"default"` and `"sensitive"` are sent to Prisma as no `mode` at all. Regenerate the discovery artifact
|
|
389
|
+
(`aventara:prepare`).
|
|
390
|
+
- 9366e16: The discovery artifact names the model's type: it exports `AvModel`, and `model` is declared with it
|
|
391
|
+
(`typeof model` is `AvModel`). A project that emits declarations (Nest's `declaration: true`) now writes that
|
|
392
|
+
name wherever an exported declaration holds the model, instead of the whole model. Over 50 models the scaffold's
|
|
393
|
+
`aventara.config.d.ts` goes from 485 KB to 0.4 KB, and a `buildFramework` / `AppFramework` module from 931 KB to
|
|
394
|
+
0.6 KB (1.2 MB to 0.6 KB, and 2.4 MB to 22 KB for exported configurations holding typed stages, in the consumer-build
|
|
395
|
+
gate). Regenerate the artifact (`aventara:prepare`, which runs on install, build and start) to get it; Contract bytes
|
|
396
|
+
and hashes are unchanged.
|
|
397
|
+
- New: `aventara-prisma7-generate --config <file>`, optional. Given your Aventara configuration module
|
|
398
|
+
(`src/aventara.config.ts` in a project set up by `aventara`; its `aventaraConfig` export, a function or a value, or
|
|
399
|
+
its default export), the artifact states which fields it computes on create and on update, per layer. They are read
|
|
400
|
+
off the configuration's TypeScript type, never by running it, so nothing connects to a database and no environment
|
|
401
|
+
is needed. The artifact exports them as `computedFields` (type `AvComputedFields`), carries them on `AvModel` so a
|
|
402
|
+
variant's guards, pipes and filters may leave exactly those fields out of a create, and hands them to the framework
|
|
403
|
+
through `discovery.computedFields`, which it compares with the configuration at startup. A configuration that is
|
|
404
|
+
not a literal where a compute stage is written (one annotated with the wide `AvConfig`, a conditional spread) is not
|
|
405
|
+
read: the step prints where, and the artifact states nothing, so those stages may leave any create field out. A
|
|
406
|
+
`--config` file that does not exist, or exports neither `aventaraConfig` nor a default, stops the step.
|
|
407
|
+
`generatePrismaDiscoveryArtifact` and `runPrismaGenerateStep` take the same `config`, and
|
|
408
|
+
`readConfigComputedFields` is exported from `@aventara/prisma7-adapter/generate`.
|
|
409
|
+
- The discovery artifact's format is now 4 (`computedFields` is new): an artifact written before it is refused with
|
|
410
|
+
the regeneration instruction. `aventara:prepare` regenerates it on install, build and start.
|
|
411
|
+
- A transaction that expired (or was closed) under a step is answered `A3002`, as when the COMMIT finds it expired:
|
|
412
|
+
Prisma's `P2028`, raised by the step's own call, is the transaction's failure, at that step (`cause.operation`),
|
|
413
|
+
and the plan rolls back. In rc.1 it was unclassified and answered `500 A3001`, an adapter failure. Measured on
|
|
414
|
+
7.10.0, SQLite and PostgreSQL.
|
|
415
|
+
- Updated dependencies [9366e16]
|
|
416
|
+
- Updated dependencies [9366e16]
|
|
417
|
+
- Updated dependencies [9366e16]
|
|
418
|
+
- Updated dependencies [9366e16]
|
|
419
|
+
- @aventara/core@1.0.0-rc.2
|
|
420
|
+
|
|
3
421
|
## 1.0.0-rc.1
|
|
4
422
|
|
|
5
423
|
### Patch Changes
|