You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
feat: warn on Effect 3 syntax in @customType; docs + cleanup
The cascade of "GeneratedSchema not assignable to Schema.Top" errors a
consumer hit was NOT a helper-type defect — it was a version-resolution
trap ('prisma-effect-kysely': '*' resolves to the stable 5.x line, not the
6.0.0-next prerelease, because npm/pnpm exclude prereleases from ranges) plus
v3-syntax @customType annotations passed through verbatim. The helper types
were correct as published in 6.0.0-next.1.
Generator-side response (warn-only, never rewrite — transforming arbitrary
user TS is unsafe):
- detectLegacyEffectV3Syntax() in src/utils/annotations.ts: matches known
v3 @customType patterns (filters now under .check(Schema.is*); variadic
Union/Tuple/multi-Literal now take arrays; removed Schema.UUID/DateFromSelf;
optionalWith). The orchestrator scans every field's @customType at generate
time and prints field-level v4 upgrade hints to stderr.
- README: v3->v4 @customType table + the '*'-resolves-to-stable gotcha (pin
exact 6.0.0-next.x or use overrides/resolutions).
Docs accuracy: DB interface is Schema.Schema.Type<typeof Model> (not
Selectable<Model>); Json maps to recursive JsonValue (not Schema.Unknown);
Type-safety note scopes the load-bearing helper casts vs cast-free output.
Cleanup: remove dead internal type aliases (MutableInsert/MutableUpdate ==
CustomInsertable/CustomUpdateable; ExtractInsertBaseType == ExtractInsertType).
Bump dev/test effect pin to 4.0.0-beta.70.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Copy file name to clipboardExpand all lines: CLAUDE.md
+26-23Lines changed: 26 additions & 23 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -50,7 +50,7 @@ Three files in the configured output directory:
50
50
-**types.ts** — direct exports (no underscore prefix, no wrapper functions):
51
51
- Branded ID schema + type per model
52
52
- Model `Schema.Struct` + type alias
53
-
-`DB` interface using `Selectable<Model>` per table (respects `@@map`)
53
+
-`DB` interface using `Schema.Schema.Type<typeof Model>` per table (preserves the `__select__/__insert__/__update__` brands Kysely needs; respects `@@map`)
54
54
-**index.ts** — re-exports
55
55
56
56
## Generated shape
@@ -67,7 +67,7 @@ export const User = Schema.Struct({
67
67
exporttypeUser=typeofUser;
68
68
69
69
exportinterfaceDB {
70
-
User:Selectable<User>;
70
+
User:Schema.Schema.Type<typeofUser>;
71
71
}
72
72
```
73
73
@@ -97,36 +97,37 @@ Prisma stores `A`/`B` columns; we emit semantic snake_case fields on the struct,
- Zero coercion in DMMF→type mapping — exact DMMF types, no string parsing of types
117
+
- The runtime `Selectable`/`Insertable`/`Updateable` helpers use `as unknown as` casts (load-bearing: a dynamically-rebuilt `Schema.Struct` has no statically-checkable shape — see the note above the Schema Functions section in `helpers.ts`); generated OUTPUT contains no casts
@@ -150,6 +151,8 @@ can `Effect.catchTag` cleanly.
150
151
- Generator must be rebuilt before `prisma generate` picks up changes
151
152
- Test fixtures: `src/__tests__/fixtures/test.prisma`
152
153
- Generated headers include timestamp + edit warning
153
-
- Direct exports only — never reintroduce underscore prefixes or wrapper functions in generated code (`getSchemas` remains in runtime API, not in output)
154
+
- Direct exports only — generated code exports schemas directly (`export const User = Schema.Struct(...)`); never reintroduce underscore prefixes or wrapper functions in the output
154
155
- Run `bun run test:emit` after touching any generator emit string — it generates against the fixture and type-checks the emitted code against the installed Effect (unit tests only string-match, they don't compile output)
155
-
-`effect` targets **4.x (beta)**, peer dep `^4.0.0-beta`, dev pin `4.0.0-beta.68`. `src/kysely/helpers.ts` uses the public `Schema.Struct.fields` API (not `effect/SchemaAST` internals — those were reworked in v4). Key v4 names: `Schema.Codec` (was `Schema.Schema`), `Schema.Top` (was `Schema.Schema.All`), `Schema.revealCodec` (was `asSchema`), `.annotate()` (was `.annotations()`), `Schema.Date` (was `DateFromSelf`), `Schema.Union([...])` (was variadic), `Schema.encodeKeys` (was `propertySignature(...).pipe(fromKey(...))`).
156
+
-`effect` targets **4.x (beta)**, peer dep `^4.0.0-beta`, dev pin `4.0.0-beta.70`. `src/kysely/helpers.ts` uses the public `Schema.Struct.fields` API (not `effect/SchemaAST` internals — those were reworked in v4). Key v4 names: `Schema.Codec` (was `Schema.Schema`), `Schema.Top` (was `Schema.Schema.All`), `Schema.revealCodec` (was `asSchema`), `.annotate()` (was `.annotations()`), `Schema.Date` (was `DateFromSelf`), `Schema.Union([...])` (was variadic), `Schema.encodeKeys` (was `propertySignature(...).pipe(fromKey(...))`).
157
+
-`@customType(...)` strings are emitted verbatim and must be valid Effect 4 syntax. `detectLegacyEffectV3Syntax()` in `src/utils/annotations.ts` warns (never rewrites) on known v3 patterns at generate time. v3 filters → `.check(Schema.is*)`; variadic `Union`/`Tuple`/multi-`Literal` → array form.
158
+
- Consumers must pin the exact `6.0.0-next.x` version — a `"*"` range resolves to the stable `5.x` line (npm/pnpm exclude prereleases from ranges), which silently pulls the v3 types.
0 commit comments