effect-qb 0.13.0 → 0.14.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.
Files changed (54) hide show
  1. package/README.md +6 -1431
  2. package/dist/mysql.js +1678 -355
  3. package/dist/postgres/metadata.js +2724 -0
  4. package/dist/postgres.js +7197 -5433
  5. package/package.json +8 -10
  6. package/src/internal/column-state.ts +84 -10
  7. package/src/internal/column.ts +556 -34
  8. package/src/internal/datatypes/define.ts +0 -30
  9. package/src/internal/executor.ts +45 -11
  10. package/src/internal/expression-ast.ts +4 -0
  11. package/src/internal/expression.ts +1 -1
  12. package/src/internal/implication-runtime.ts +171 -0
  13. package/src/internal/mysql-query.ts +7173 -0
  14. package/src/internal/mysql-renderer.ts +2 -2
  15. package/src/internal/plan.ts +14 -4
  16. package/src/internal/{query-factory.ts → postgres-query.ts} +619 -167
  17. package/src/internal/postgres-renderer.ts +2 -2
  18. package/src/internal/postgres-schema-model.ts +144 -0
  19. package/src/internal/predicate-analysis.ts +10 -0
  20. package/src/internal/predicate-context.ts +112 -36
  21. package/src/internal/predicate-formula.ts +31 -19
  22. package/src/internal/predicate-normalize.ts +177 -106
  23. package/src/internal/predicate-runtime.ts +676 -0
  24. package/src/internal/query.ts +455 -39
  25. package/src/internal/renderer.ts +2 -2
  26. package/src/internal/runtime-schema.ts +74 -20
  27. package/src/internal/schema-ddl.ts +55 -0
  28. package/src/internal/schema-derivation.ts +93 -21
  29. package/src/internal/schema-expression.ts +44 -0
  30. package/src/internal/sql-expression-renderer.ts +95 -31
  31. package/src/internal/table-options.ts +87 -7
  32. package/src/internal/table.ts +104 -41
  33. package/src/mysql/column.ts +1 -0
  34. package/src/mysql/datatypes/index.ts +17 -2
  35. package/src/mysql/function/core.ts +1 -0
  36. package/src/mysql/function/index.ts +1 -0
  37. package/src/mysql/private/query.ts +1 -13
  38. package/src/mysql/query.ts +5 -0
  39. package/src/postgres/cast.ts +31 -0
  40. package/src/postgres/column.ts +26 -0
  41. package/src/postgres/datatypes/index.ts +40 -5
  42. package/src/postgres/function/core.ts +12 -0
  43. package/src/postgres/function/index.ts +2 -1
  44. package/src/postgres/function/json.ts +499 -2
  45. package/src/postgres/metadata.ts +31 -0
  46. package/src/postgres/private/query.ts +1 -13
  47. package/src/postgres/query.ts +5 -2
  48. package/src/postgres/schema-expression.ts +16 -0
  49. package/src/postgres/schema-management.ts +204 -0
  50. package/src/postgres/schema.ts +35 -0
  51. package/src/postgres/table.ts +307 -41
  52. package/src/postgres/type.ts +4 -0
  53. package/src/postgres.ts +14 -0
  54. package/CHANGELOG.md +0 -134
package/package.json CHANGED
@@ -1,11 +1,10 @@
1
1
  {
2
2
  "name": "effect-qb",
3
- "version": "0.13.0",
3
+ "version": "0.14.0",
4
4
  "type": "module",
5
5
  "files": [
6
6
  "dist",
7
7
  "src",
8
- "CHANGELOG.md",
9
8
  "README.md"
10
9
  ],
11
10
  "exports": {
@@ -13,6 +12,10 @@
13
12
  "types": "./src/postgres.ts",
14
13
  "import": "./dist/postgres.js"
15
14
  },
15
+ "./postgres/metadata": {
16
+ "types": "./src/postgres/metadata.ts",
17
+ "import": "./dist/postgres/metadata.js"
18
+ },
16
19
  "./mysql": {
17
20
  "types": "./src/mysql.ts",
18
21
  "import": "./dist/mysql.js"
@@ -28,22 +31,17 @@
28
31
  "access": "public"
29
32
  },
30
33
  "scripts": {
31
- "build": "bun scripts/build-package.ts",
32
- "release": "bun scripts/release.ts",
33
- "test": "bun test",
34
- "test:types": "bunx tsgo -p tsconfig.type-tests.json",
35
- "test:integration": "bun scripts/test-integration.ts",
34
+ "build": "bun scripts/build.ts",
36
35
  "prepack": "bun run build"
37
36
  },
38
37
  "devDependencies": {
39
- "@effect/sql-mysql2": "0.48.0",
40
- "@effect/sql-pg": "0.48.0",
41
38
  "@types/bun": "latest",
42
39
  "@typescript/native-preview": "latest"
43
40
  },
44
41
  "dependencies": {
45
42
  "@effect/experimental": "^0.57.0",
46
43
  "@effect/sql": "^0.48.0",
47
- "effect": "^3.19.3"
44
+ "effect": "^3.19.3",
45
+ "pgsql-ast-parser": "^12.0.2"
48
46
  }
49
47
  }
@@ -1,8 +1,10 @@
1
+ import type * as Brand from "effect/Brand"
1
2
  import { pipeArguments, type Pipeable } from "effect/Pipeable"
2
3
  import * as Schema from "effect/Schema"
3
4
 
4
5
  import * as Expression from "./expression.js"
5
6
  import * as ExpressionAst from "./expression-ast.js"
7
+ import type * as SchemaExpression from "./schema-expression.js"
6
8
 
7
9
  /** Symbol used to attach column-definition metadata. */
8
10
  export const ColumnTypeId: unique symbol = Symbol.for("effect-qb/Column")
@@ -12,9 +14,34 @@ export const BoundColumnTypeId: unique symbol = Symbol.for("effect-qb/BoundColum
12
14
  export type ColumnTypeId = typeof ColumnTypeId
13
15
  export type BoundColumnTypeId = typeof BoundColumnTypeId
14
16
 
17
+ export type DdlExpression = Expression.Any | SchemaExpression.Any
18
+
15
19
  /** Lazy reference to another bound column. */
16
20
  export interface ColumnReference<Target = unknown> {
17
21
  readonly target: () => Target
22
+ readonly name?: string
23
+ readonly onUpdate?: "noAction" | "restrict" | "cascade" | "setNull" | "setDefault"
24
+ readonly onDelete?: "noAction" | "restrict" | "cascade" | "setNull" | "setDefault"
25
+ readonly deferrable?: boolean
26
+ readonly initiallyDeferred?: boolean
27
+ }
28
+
29
+ /** Inline single-column index metadata. */
30
+ export interface ColumnIndexOptions {
31
+ readonly name?: string
32
+ readonly method?: string
33
+ readonly include?: readonly string[]
34
+ readonly predicate?: DdlExpression
35
+ readonly order?: "asc" | "desc"
36
+ readonly nulls?: "first" | "last"
37
+ }
38
+
39
+ /** Inline single-column unique-constraint metadata. */
40
+ export interface ColumnUniqueOptions {
41
+ readonly name?: string
42
+ readonly nullsNotDistinct?: boolean
43
+ readonly deferrable?: boolean
44
+ readonly initiallyDeferred?: boolean
18
45
  }
19
46
 
20
47
  /** Complete static state tracked for a column definition. */
@@ -42,8 +69,20 @@ export interface ColumnState<
42
69
  readonly primaryKey: PrimaryKey
43
70
  readonly unique: Unique
44
71
  readonly references: Ref
45
- readonly defaultValue?: Expression.Any
46
- readonly generatedValue?: Expression.Any
72
+ readonly brand?: true
73
+ readonly index?: ColumnIndexOptions
74
+ readonly uniqueConstraint?: ColumnUniqueOptions
75
+ readonly defaultValue?: DdlExpression
76
+ readonly generatedValue?: DdlExpression
77
+ readonly ddlType?: string
78
+ readonly identity?: {
79
+ readonly generation: "always" | "byDefault"
80
+ }
81
+ readonly enum?: {
82
+ readonly name: string
83
+ readonly schemaName?: string
84
+ readonly values: readonly [string, ...string[]]
85
+ }
47
86
  readonly source: Source
48
87
  readonly dependencies: Dependencies
49
88
  }
@@ -95,8 +134,20 @@ export interface ColumnDefinition<
95
134
  readonly primaryKey: PrimaryKey
96
135
  readonly unique: Unique
97
136
  readonly references: Ref
98
- readonly defaultValue?: Expression.Any
99
- readonly generatedValue?: Expression.Any
137
+ readonly brand?: true
138
+ readonly index?: ColumnIndexOptions
139
+ readonly uniqueConstraint?: ColumnUniqueOptions
140
+ readonly defaultValue?: DdlExpression
141
+ readonly generatedValue?: DdlExpression
142
+ readonly ddlType?: string
143
+ readonly identity?: {
144
+ readonly generation: "always" | "byDefault"
145
+ }
146
+ readonly enum?: {
147
+ readonly name: string
148
+ readonly schemaName?: string
149
+ readonly values: readonly [string, ...string[]]
150
+ }
100
151
  }
101
152
  }
102
153
 
@@ -255,6 +306,9 @@ export const makeColumnDefinition = <
255
306
  references: metadata.references,
256
307
  defaultValue: metadata.defaultValue,
257
308
  generatedValue: metadata.generatedValue,
309
+ ddlType: metadata.ddlType,
310
+ identity: metadata.identity,
311
+ enum: metadata.enum,
258
312
  source: undefined as Source,
259
313
  dependencies: {} as Dependencies
260
314
  }
@@ -346,7 +400,10 @@ export const remapColumnDefinition = <
346
400
  unique: metadata.unique,
347
401
  references: metadata.references,
348
402
  defaultValue: metadata.defaultValue,
349
- generatedValue: metadata.generatedValue
403
+ generatedValue: metadata.generatedValue,
404
+ ddlType: metadata.ddlType,
405
+ identity: metadata.identity,
406
+ enum: metadata.enum
350
407
  }
351
408
  if (ExpressionAst.TypeId in column) {
352
409
  next[ExpressionAst.TypeId] = (column as unknown as {
@@ -380,13 +437,17 @@ export const bindColumn = <
380
437
  baseTableName: BaseTableName,
381
438
  schemaName?: SchemaName
382
439
  ): BoundColumnFrom<Column, TableName, ColumnName, BaseTableName> => {
440
+ const brandName = `${tableName}.${columnName}`
441
+ const schema = column.metadata.brand === true
442
+ ? Schema.brand(brandName)(column.schema)
443
+ : column.schema
383
444
  const bound = Object.create(ColumnProto)
384
- bound.schema = column.schema
445
+ bound.schema = schema
385
446
  bound.metadata = column.metadata
386
447
  bound[Expression.TypeId] = {
387
448
  runtime: undefined as SelectType<Column>,
388
449
  dbType: column.metadata.dbType,
389
- runtimeSchema: column.schema,
450
+ runtimeSchema: schema,
390
451
  nullability: (column.metadata.nullable ? "maybe" : "never") as IsNullable<Column> extends true ? "maybe" : "never",
391
452
  dialect: column.metadata.dbType.dialect,
392
453
  aggregation: "scalar",
@@ -438,6 +499,13 @@ export type ReferencesOf<Column extends AnyColumnDefinition> = ColumnStateOf<Col
438
499
  /** Extracts the non-null select type of a column. */
439
500
  export type BaseSelectType<Column extends AnyColumnDefinition> = NonNullable<SelectType<Column>>
440
501
 
502
+ type BrandedValue<
503
+ Value,
504
+ BrandName extends string
505
+ > = [Extract<Value, null | undefined>] extends [never]
506
+ ? Value & Brand.Brand<BrandName>
507
+ : Exclude<Value, null | undefined> & Brand.Brand<BrandName> | Extract<Value, null | undefined>
508
+
441
509
  /** Rebinds a generic column definition to a specific table and key. */
442
510
  export type BoundColumnFrom<
443
511
  Column extends AnyColumnDefinition,
@@ -445,9 +513,15 @@ export type BoundColumnFrom<
445
513
  ColumnName extends string,
446
514
  BaseTableName extends string = TableName
447
515
  > = BoundColumn<
448
- SelectType<Column>,
449
- InsertType<Column>,
450
- UpdateType<Column>,
516
+ Column["metadata"]["brand"] extends true
517
+ ? BrandedValue<SelectType<Column>, `${TableName}.${ColumnName}`>
518
+ : SelectType<Column>,
519
+ Column["metadata"]["brand"] extends true
520
+ ? BrandedValue<InsertType<Column>, `${TableName}.${ColumnName}`>
521
+ : InsertType<Column>,
522
+ Column["metadata"]["brand"] extends true
523
+ ? BrandedValue<UpdateType<Column>, `${TableName}.${ColumnName}`>
524
+ : UpdateType<Column>,
451
525
  ColumnStateOf<Column>["dbType"],
452
526
  IsNullable<Column>,
453
527
  HasDefault<Column>,