effect-qb 0.16.0 → 0.19.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 (128) hide show
  1. package/README.md +4 -0
  2. package/dist/index.js +8065 -0
  3. package/dist/mysql.js +4036 -2418
  4. package/dist/postgres/metadata.js +2536 -625
  5. package/dist/postgres.js +8248 -7857
  6. package/dist/sqlite.js +8854 -0
  7. package/dist/standard.js +8019 -0
  8. package/package.json +15 -3
  9. package/src/casing.ts +71 -0
  10. package/src/index.ts +2 -0
  11. package/src/internal/casing.ts +89 -0
  12. package/src/internal/column-state.ts +11 -6
  13. package/src/internal/column.ts +44 -7
  14. package/src/internal/datatypes/define.ts +2 -1
  15. package/src/internal/datatypes/enrich.ts +23 -0
  16. package/src/internal/datatypes/lookup.ts +14 -7
  17. package/src/internal/derived-table.ts +7 -13
  18. package/src/internal/dialect-renderers/mysql.ts +2046 -0
  19. package/src/{postgres/internal/sql-expression-renderer.ts → internal/dialect-renderers/postgres.ts} +867 -283
  20. package/src/{mysql/internal/sql-expression-renderer.ts → internal/dialect-renderers/sqlite.ts} +834 -358
  21. package/src/internal/dialect.ts +37 -0
  22. package/src/internal/dsl-mutation-runtime.ts +29 -10
  23. package/src/internal/dsl-plan-runtime.ts +41 -24
  24. package/src/internal/dsl-query-runtime.ts +11 -31
  25. package/src/internal/dsl-transaction-ddl-runtime.ts +61 -15
  26. package/src/internal/executor.ts +57 -15
  27. package/src/internal/expression-ast.ts +3 -2
  28. package/src/internal/grouping-key.ts +216 -9
  29. package/src/internal/implication-runtime.ts +3 -2
  30. package/src/internal/json/types.ts +155 -40
  31. package/src/internal/predicate/context.ts +14 -1
  32. package/src/internal/predicate/key.ts +19 -2
  33. package/src/internal/predicate/runtime.ts +30 -3
  34. package/src/internal/query.d.ts +38 -11
  35. package/src/internal/query.ts +315 -54
  36. package/src/internal/renderer.ts +51 -6
  37. package/src/internal/runtime/driver-value-mapping.ts +58 -0
  38. package/src/internal/runtime/normalize.ts +74 -43
  39. package/src/internal/runtime/schema.ts +5 -3
  40. package/src/internal/runtime/value.ts +153 -30
  41. package/src/internal/scalar.ts +6 -1
  42. package/src/internal/schema-derivation.d.ts +12 -61
  43. package/src/internal/schema-derivation.ts +90 -38
  44. package/src/internal/schema-expression.ts +2 -2
  45. package/src/internal/sql-expression-renderer.ts +19 -0
  46. package/src/internal/standard-dsl.ts +6885 -0
  47. package/src/internal/table-options.ts +229 -62
  48. package/src/internal/table.d.ts +33 -32
  49. package/src/internal/table.ts +469 -160
  50. package/src/mysql/column-extension.ts +3 -0
  51. package/src/mysql/column.ts +27 -12
  52. package/src/mysql/datatypes/index.ts +24 -2
  53. package/src/mysql/errors/catalog.ts +5 -5
  54. package/src/mysql/errors/normalize.ts +2 -2
  55. package/src/mysql/executor.ts +7 -5
  56. package/src/mysql/internal/dialect.ts +9 -4
  57. package/src/mysql/internal/dsl.ts +906 -324
  58. package/src/mysql/internal/renderer.ts +7 -2
  59. package/src/mysql/json.ts +37 -0
  60. package/src/mysql/query-extension.ts +16 -0
  61. package/src/mysql/query.ts +9 -2
  62. package/src/mysql/renderer.ts +31 -4
  63. package/src/mysql.ts +4 -12
  64. package/src/postgres/column-extension.ts +28 -0
  65. package/src/postgres/column.ts +9 -13
  66. package/src/postgres/datatypes/index.d.ts +2 -1
  67. package/src/postgres/datatypes/index.ts +3 -2
  68. package/src/postgres/errors/normalize.ts +2 -2
  69. package/src/postgres/executor.ts +55 -10
  70. package/src/postgres/function/core.ts +20 -4
  71. package/src/postgres/function/index.ts +1 -17
  72. package/src/postgres/internal/dialect.ts +9 -4
  73. package/src/postgres/internal/dsl.ts +850 -359
  74. package/src/postgres/internal/renderer.ts +7 -2
  75. package/src/postgres/internal/schema-ddl.ts +22 -9
  76. package/src/postgres/internal/schema-model.ts +244 -10
  77. package/src/postgres/json.ts +100 -24
  78. package/src/postgres/jsonb.ts +38 -0
  79. package/src/postgres/query-extension.ts +2 -0
  80. package/src/postgres/query.ts +9 -2
  81. package/src/postgres/renderer.ts +31 -4
  82. package/src/postgres/schema-management.ts +108 -16
  83. package/src/postgres/schema.ts +98 -15
  84. package/src/postgres/table.ts +203 -398
  85. package/src/postgres/type.ts +8 -7
  86. package/src/postgres.ts +9 -11
  87. package/src/sqlite/column-extension.ts +3 -0
  88. package/src/sqlite/column.ts +127 -0
  89. package/src/sqlite/datatypes/index.ts +80 -0
  90. package/src/sqlite/datatypes/spec.ts +98 -0
  91. package/src/sqlite/errors/catalog.ts +103 -0
  92. package/src/sqlite/errors/fields.ts +19 -0
  93. package/src/sqlite/errors/index.ts +19 -0
  94. package/src/sqlite/errors/normalize.ts +229 -0
  95. package/src/sqlite/errors/requirements.ts +71 -0
  96. package/src/sqlite/errors/types.ts +29 -0
  97. package/src/sqlite/executor.ts +229 -0
  98. package/src/sqlite/function/aggregate.ts +2 -0
  99. package/src/sqlite/function/core.ts +2 -0
  100. package/src/sqlite/function/index.ts +19 -0
  101. package/src/sqlite/function/string.ts +2 -0
  102. package/src/sqlite/function/temporal.ts +100 -0
  103. package/src/sqlite/function/window.ts +2 -0
  104. package/src/sqlite/internal/dialect.ts +42 -0
  105. package/src/sqlite/internal/dsl.ts +6979 -0
  106. package/src/sqlite/internal/renderer.ts +51 -0
  107. package/src/sqlite/json.ts +39 -0
  108. package/src/sqlite/query-extension.ts +2 -0
  109. package/src/sqlite/query.ts +196 -0
  110. package/src/sqlite/renderer.ts +51 -0
  111. package/src/sqlite.ts +14 -0
  112. package/src/standard/column.ts +163 -0
  113. package/src/standard/datatypes/index.ts +83 -0
  114. package/src/standard/datatypes/spec.ts +98 -0
  115. package/src/standard/dialect.ts +40 -0
  116. package/src/standard/function/aggregate.ts +2 -0
  117. package/src/standard/function/core.ts +2 -0
  118. package/src/standard/function/index.ts +18 -0
  119. package/src/standard/function/string.ts +2 -0
  120. package/src/standard/function/temporal.ts +78 -0
  121. package/src/standard/function/window.ts +2 -0
  122. package/src/standard/internal/renderer.ts +45 -0
  123. package/src/standard/query.ts +152 -0
  124. package/src/standard/renderer.ts +21 -0
  125. package/src/standard/table.ts +147 -0
  126. package/src/standard.ts +18 -0
  127. package/src/internal/aggregation-validation.ts +0 -57
  128. package/src/mysql/table.ts +0 -157
@@ -1,4 +1,4 @@
1
- import { pipeArguments } from "effect/Pipeable"
1
+ import { pipeArguments, type Pipeable } from "effect/Pipeable"
2
2
  import * as Schema from "effect/Schema"
3
3
 
4
4
  import { mysqlDatatypes } from "../datatypes/index.js"
@@ -6,9 +6,16 @@ import { mysqlDatatypes } from "../datatypes/index.js"
6
6
  import * as Expression from "../../internal/scalar.js"
7
7
  import * as Plan from "../../internal/row-set.js"
8
8
  import * as Table from "../../internal/table.js"
9
+ import type {
10
+ LiteralStringInput,
11
+ NonEmptyStringInput,
12
+ SafeSqlIdentifierInput,
13
+ SafeSqlIdentifierPathInput
14
+ } from "../../internal/table-options.js"
9
15
  import type { CastTargetError, OperandCompatibilityError } from "../../internal/coercion/errors.js"
10
16
  import type { RuntimeOfDbType } from "../../internal/coercion/analysis.js"
11
17
  import type { CanCastDbType, CanCompareDbTypes, CanContainDbTypes, CanTextuallyCoerceDbType } from "../../internal/coercion/rules.js"
18
+ import { normalizeDbValue } from "../../internal/runtime/normalize.js"
12
19
  import {
13
20
  currentRequiredList,
14
21
  extractRequiredRuntime,
@@ -30,11 +37,15 @@ import {
30
37
  type AssumptionsOfPlan,
31
38
  type AvailableOfPlan,
32
39
  type CapabilitiesOfPlan,
40
+ type CommonSetFacts,
33
41
  type DialectCompatibleNestedPlan,
34
42
  type DependenciesOf,
35
43
  type DependencyRecord,
36
44
  type DialectOf,
37
45
  type DerivedSelectionOf,
46
+ type DerivedTableCompatiblePlan,
47
+ type LateralSourceCompatiblePlan,
48
+ type DerivedSourceCompatiblePlan,
38
49
  type DerivedSource,
39
50
  type CompletePlan,
40
51
  type ExpressionInput,
@@ -66,6 +77,7 @@ import {
66
77
  type ScopedNamesOfPlan,
67
78
  type SelectionOfPlan,
68
79
  type SelectionShape,
80
+ type SelectionProjectionAliasCollisionConstraint,
69
81
  type SetCompatiblePlan,
70
82
  type SetCompatibleRightPlan,
71
83
  type SchemaTableLike,
@@ -75,10 +87,8 @@ import {
75
87
  type TableDialectOf,
76
88
  type StatementOfPlan,
77
89
  type MutationInputOf,
78
- type MutationTargetLike,
79
90
  type MutationTargetOfPlan,
80
91
  type MergeCapabilities,
81
- type MutationTargetInput,
82
92
  type MutationValuesInput,
83
93
  type SourceDialectOf,
84
94
  type SourceLike,
@@ -95,7 +105,6 @@ import {
95
105
  type TableLike,
96
106
  type UpdateInputOfTarget,
97
107
  type MutationTargetNamesOf,
98
- type MutationTargetTuple,
99
108
  type TupleDependencies,
100
109
  type TupleDialect,
101
110
  type ResultRow
@@ -133,6 +142,10 @@ import * as ProjectionAlias from "../../internal/projection-alias.js"
133
142
  import * as QueryAst from "../../internal/query-ast.js"
134
143
  import { normalizeColumnList } from "../../internal/table-options.js"
135
144
 
145
+ type MutationTargetLike = Table.AnyTable<Dialect | "standard">
146
+ type MutationTargetTuple = readonly [MutationTargetLike, MutationTargetLike, ...MutationTargetLike[]]
147
+ type MutationTargetInput = MutationTargetLike | MutationTargetTuple
148
+
136
149
  /**
137
150
  * Dialect-specific DB type profile used to specialize the shared query
138
151
  * operator surface.
@@ -217,6 +230,13 @@ type DialectAsExpression<
217
230
  ? Value
218
231
  : DialectLiteralExpression<Extract<Value, LiteralValue>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
219
232
 
233
+ type ProjectionAliasedExpression<
234
+ Value extends Expression.Any,
235
+ Alias extends string
236
+ > = Value & {
237
+ readonly [ProjectionAlias.TypeId]: ProjectionAlias.State<Alias>
238
+ }
239
+
220
240
  /** Normalizes a generic string-capable input into the expression form used internally. */
221
241
  type DialectAsStringExpression<
222
242
  Value extends ExpressionInput,
@@ -690,6 +710,21 @@ type DialectOfDialectNumericInput<
690
710
  NullDb extends Expression.DbType.Any
691
711
  > = DialectOf<DialectAsNumericExpression<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>>
692
712
 
713
+ type NumericExpressionDialectInput<
714
+ Value extends NumericExpressionInput,
715
+ Dialect extends string,
716
+ TextDb extends Expression.DbType.Any,
717
+ NumericDb extends Expression.DbType.Any,
718
+ BoolDb extends Expression.DbType.Any,
719
+ TimestampDb extends Expression.DbType.Any,
720
+ NullDb extends Expression.DbType.Any
721
+ > = Exclude<DialectOfDialectNumericInput<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>, Dialect | "standard"> extends never
722
+ ? unknown
723
+ : {
724
+ readonly __effect_qb_error__: "effect-qb: numeric expressions cannot mix dialects"
725
+ readonly __effect_qb_dialect__: DialectOfDialectNumericInput<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
726
+ }
727
+
693
728
  /** Dependency map carried by a numeric-clause input after coercion. */
694
729
  type DependenciesOfDialectNumericInput<
695
730
  Value extends NumericExpressionInput,
@@ -776,6 +811,35 @@ type DialectExpressionArray<
776
811
  ? Tuple
777
812
  : never
778
813
 
814
+ type ExtractFunctionFieldInput<
815
+ Value extends ExpressionInput
816
+ > = Value extends string
817
+ ? SafeSqlIdentifierInput<Value>
818
+ : Value extends { readonly [ExpressionAst.TypeId]: ExpressionAst.LiteralNode<infer Field extends string> }
819
+ ? SafeSqlIdentifierInput<Field> extends never ? never : Value
820
+ : never
821
+
822
+ type GenericFunctionNameInput<Name extends string> =
823
+ Name extends "current_date" | "extract" ? never : SafeSqlIdentifierPathInput<Name>
824
+
825
+ type FunctionCallApi = {
826
+ (name: "current_date"): Expression.Any
827
+ <Field extends string, Source extends ExpressionInput>(
828
+ name: "extract",
829
+ field: SafeSqlIdentifierInput<Field>,
830
+ source: Source
831
+ ): Expression.Any
832
+ <Field extends Expression.Any, Source extends ExpressionInput>(
833
+ name: "extract",
834
+ field: Field & ExtractFunctionFieldInput<Field>,
835
+ source: Source
836
+ ): Expression.Any
837
+ <Name extends string, Args extends readonly ExpressionInput[]>(
838
+ name: GenericFunctionNameInput<Name>,
839
+ ...args: Args
840
+ ): Expression.Any
841
+ }
842
+
779
843
  /** Normalized expression tuple for generic string operator inputs. */
780
844
  type DialectStringExpressionTuple<
781
845
  Values extends readonly ExpressionInput[],
@@ -1042,6 +1106,9 @@ type JsonPathInput = JsonPath.Path<any> | JsonPath.CanonicalSegment
1042
1106
 
1043
1107
  type JsonQueryInput = JsonPath.Path<any> | StringExpressionInput
1044
1108
 
1109
+ type JsonQueryValue<Query extends JsonQueryInput> =
1110
+ Query extends string ? LiteralStringInput<Query> : Query
1111
+
1045
1112
  type JsonPathOutputOf<
1046
1113
  Root,
1047
1114
  Target extends JsonPathInput,
@@ -1073,6 +1140,16 @@ type JsonSetOutputOf<
1073
1140
  ? JsonSetAtPath<Root, JsonPath.Path<[Target]>, Next, Operation>
1074
1141
  : never
1075
1142
 
1143
+ type JsonSetOutputWithCreateMissing<
1144
+ Root,
1145
+ Target extends JsonPathInput,
1146
+ Next,
1147
+ Operation extends string,
1148
+ CreateMissing extends boolean
1149
+ > = false extends CreateMissing
1150
+ ? Root | JsonSetOutputOf<Root, Target, Next, Operation>
1151
+ : JsonSetOutputOf<Root, Target, Next, Operation>
1152
+
1076
1153
  type JsonInsertOutputOf<
1077
1154
  Root,
1078
1155
  Target extends JsonPathInput,
@@ -1085,6 +1162,27 @@ type JsonInsertOutputOf<
1085
1162
  ? JsonInsertAtPath<Root, JsonPath.Path<[Target]>, Next, InsertAfter, Operation>
1086
1163
  : never
1087
1164
 
1165
+ type MySqlJsonLengthResult<Value> =
1166
+ JsonLengthResult<Value> extends null ? number : JsonLengthResult<Value>
1167
+
1168
+ type MySqlJsonTypeName<Value> =
1169
+ JsonTypeName<Value> extends "object" ? "OBJECT" :
1170
+ JsonTypeName<Value> extends "array" ? "ARRAY" :
1171
+ JsonTypeName<Value> extends "string" ? "STRING" :
1172
+ JsonTypeName<Value> extends "number" ? "INTEGER" | "DOUBLE" | "DECIMAL" :
1173
+ JsonTypeName<Value> extends "boolean" ? "BOOLEAN" :
1174
+ JsonTypeName<Value> extends "null" ? "NULL" :
1175
+ JsonTypeName<Value>
1176
+
1177
+ type MySqlUnsupportedJsonFeatureUsageError<Feature extends string> = {
1178
+ readonly __effect_qb_error__: "effect-qb: unsupported mysql json feature"
1179
+ readonly __effect_qb_json_feature__: Feature
1180
+ }
1181
+
1182
+ type MySqlUnsupportedJsonFeature<Feature extends string> = (
1183
+ feature: MySqlUnsupportedJsonFeatureUsageError<Feature>
1184
+ ) => never
1185
+
1088
1186
  type JsonPathGuard<
1089
1187
  Root,
1090
1188
  Target extends JsonPathInput,
@@ -1468,7 +1566,7 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1468
1566
  type: mysqlDatatypes
1469
1567
  }
1470
1568
  const ValuesInputProto = {
1471
- pipe(this: unknown) {
1569
+ pipe(this: Pipeable) {
1472
1570
  return pipeArguments(this, arguments)
1473
1571
  }
1474
1572
  }
@@ -1479,7 +1577,7 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1479
1577
  if (value === null || value instanceof Date) {
1480
1578
  return undefined
1481
1579
  }
1482
- return Schema.Literal(value) as unknown as Schema.Schema.Any
1580
+ return Schema.Literal(value) as Schema.Schema.Any
1483
1581
  }
1484
1582
 
1485
1583
  const literal = <const Value extends LiteralValue>(
@@ -1566,7 +1664,7 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1566
1664
  value: Expression.Any,
1567
1665
  target: Expression.Any
1568
1666
  ): Expression.Any => {
1569
- const ast = (value as unknown as { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1667
+ const ast = (value as Expression.Any & { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1570
1668
  if (ast.kind !== "literal") {
1571
1669
  return value
1572
1670
  }
@@ -1587,8 +1685,8 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1587
1685
  left: Expression.Any,
1588
1686
  right: Expression.Any
1589
1687
  ): readonly [Expression.Any, Expression.Any] => {
1590
- const leftAst = (left as unknown as { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1591
- const rightAst = (right as unknown as { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1688
+ const leftAst = (left as Expression.Any & { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1689
+ const rightAst = (right as Expression.Any & { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1592
1690
  if (leftAst.kind === "literal" && rightAst.kind !== "literal") {
1593
1691
  return [retargetLiteralExpression(left, right), right]
1594
1692
  }
@@ -1621,7 +1719,7 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1621
1719
  ): readonly Expression.Any[] => {
1622
1720
  const flattened: Array<Expression.Any> = []
1623
1721
  for (const value of values) {
1624
- const ast = (value as unknown as { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1722
+ const ast = (value as Expression.Any & { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
1625
1723
  if (ast.kind === kind) {
1626
1724
  flattened.push(...ast.values)
1627
1725
  } else {
@@ -1667,7 +1765,33 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1667
1765
  if (operations.every((operation) => typeof operation === "function")) {
1668
1766
  return pipeArguments(this, arguments)
1669
1767
  }
1670
- throw new TypeError(`Cannot mix query expressions and pipe functions inside ${kind}(...).pipe(...)`)
1768
+ const valuesForMixedPipe = (value: unknown): readonly Expression.Any[] => {
1769
+ if (typeof value !== "object" || value === null || !(Expression.TypeId in value)) {
1770
+ return []
1771
+ }
1772
+ const expression = value as Expression.Any & {
1773
+ readonly [ExpressionAst.TypeId]: ExpressionAst.Any
1774
+ }
1775
+ const ast = expression[ExpressionAst.TypeId]
1776
+ if (ast.kind === kind) {
1777
+ return (ast as {
1778
+ readonly values: readonly Expression.Any[]
1779
+ }).values
1780
+ }
1781
+ return [expression]
1782
+ }
1783
+ let current: unknown = this
1784
+ for (const operation of operations) {
1785
+ if (typeof operation === "function") {
1786
+ current = (operation as (value: unknown) => unknown)(current)
1787
+ continue
1788
+ }
1789
+ current = makeVariadicBooleanExpression(
1790
+ kind,
1791
+ [...valuesForMixedPipe(current), toDialectExpression(operation as ExpressionInput)] as const
1792
+ )
1793
+ }
1794
+ return current
1671
1795
  }
1672
1796
  })
1673
1797
 
@@ -1686,10 +1810,13 @@ const profile: QueryDialectProfile<Dialect, TextDb, NumericDb, BoolDb, Timestamp
1686
1810
  spec: WindowSpecInput<PartitionBy, OrderBy> | OrderedWindowSpecInput<PartitionBy, Extract<OrderBy, NonEmptyWindowOrderTerms>> | undefined
1687
1811
  ) => {
1688
1812
  const partitionBy = [...(spec?.partitionBy ?? [])] as unknown as PartitionBy
1689
- const orderBy = (spec?.orderBy ?? []).map((term) => ({
1690
- value: term.value,
1691
- direction: term.direction ?? "asc"
1692
- })) as {
1813
+ const orderBy = (spec?.orderBy ?? []).map((term) => {
1814
+ const direction = term.direction ?? "asc"
1815
+ return {
1816
+ value: term.value,
1817
+ direction
1818
+ }
1819
+ }) as {
1693
1820
  readonly [K in keyof OrderBy]: OrderBy[K] extends WindowOrderTermInput<infer Value extends WindowOrderInput>
1694
1821
  ? { readonly value: Value; readonly direction: OrderDirection }
1695
1822
  : never
@@ -1825,7 +1952,8 @@ type BinaryPredicateExpression<
1825
1952
  >(
1826
1953
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "eq">
1827
1954
  ): BinaryPredicateExpression<Left, Right, "eq"> => {
1828
- const [left, right] = args as unknown as [Left, Right]
1955
+ const left = args[0] as Left
1956
+ const right = args[1] as Right
1829
1957
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "eq")
1830
1958
  }
1831
1959
 
@@ -1835,7 +1963,8 @@ type BinaryPredicateExpression<
1835
1963
  >(
1836
1964
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "neq">
1837
1965
  ): BinaryPredicateExpression<Left, Right, "neq"> => {
1838
- const [left, right] = args as unknown as [Left, Right]
1966
+ const left = args[0] as Left
1967
+ const right = args[1] as Right
1839
1968
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "neq")
1840
1969
  }
1841
1970
 
@@ -1845,7 +1974,8 @@ type BinaryPredicateExpression<
1845
1974
  >(
1846
1975
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "lt">
1847
1976
  ): BinaryPredicateExpression<Left, Right, "lt"> => {
1848
- const [left, right] = args as unknown as [Left, Right]
1977
+ const left = args[0] as Left
1978
+ const right = args[1] as Right
1849
1979
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "lt")
1850
1980
  }
1851
1981
 
@@ -1855,7 +1985,8 @@ type BinaryPredicateExpression<
1855
1985
  >(
1856
1986
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "lte">
1857
1987
  ): BinaryPredicateExpression<Left, Right, "lte"> => {
1858
- const [left, right] = args as unknown as [Left, Right]
1988
+ const left = args[0] as Left
1989
+ const right = args[1] as Right
1859
1990
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "lte")
1860
1991
  }
1861
1992
 
@@ -1865,7 +1996,8 @@ type BinaryPredicateExpression<
1865
1996
  >(
1866
1997
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "gt">
1867
1998
  ): BinaryPredicateExpression<Left, Right, "gt"> => {
1868
- const [left, right] = args as unknown as [Left, Right]
1999
+ const left = args[0] as Left
2000
+ const right = args[1] as Right
1869
2001
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "gt")
1870
2002
  }
1871
2003
 
@@ -1875,7 +2007,8 @@ type BinaryPredicateExpression<
1875
2007
  >(
1876
2008
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "gte">
1877
2009
  ): BinaryPredicateExpression<Left, Right, "gte"> => {
1878
- const [left, right] = args as unknown as [Left, Right]
2010
+ const left = args[0] as Left
2011
+ const right = args[1] as Right
1879
2012
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "gte")
1880
2013
  }
1881
2014
 
@@ -1885,7 +2018,8 @@ type BinaryPredicateExpression<
1885
2018
  >(
1886
2019
  ...args: TextArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "like">
1887
2020
  ): BinaryPredicateExpression<Left, Right, "like"> => {
1888
- const [left, right] = args as unknown as [Left, Right]
2021
+ const left = args[0] as Left
2022
+ const right = args[1] as Right
1889
2023
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "like")
1890
2024
  }
1891
2025
 
@@ -1895,7 +2029,8 @@ type BinaryPredicateExpression<
1895
2029
  >(
1896
2030
  ...args: TextArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "ilike">
1897
2031
  ): BinaryPredicateExpression<Left, Right, "ilike"> => {
1898
- const [left, right] = args as unknown as [Left, Right]
2032
+ const left = args[0] as Left
2033
+ const right = args[1] as Right
1899
2034
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "ilike")
1900
2035
  }
1901
2036
 
@@ -1905,7 +2040,8 @@ type BinaryPredicateExpression<
1905
2040
  >(
1906
2041
  ...args: TextArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "regexMatch">
1907
2042
  ): BinaryPredicateExpression<Left, Right, "regexMatch"> => {
1908
- const [left, right] = args as unknown as [Left, Right]
2043
+ const left = args[0] as Left
2044
+ const right = args[1] as Right
1909
2045
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "regexMatch")
1910
2046
  }
1911
2047
 
@@ -1915,7 +2051,8 @@ type BinaryPredicateExpression<
1915
2051
  >(
1916
2052
  ...args: TextArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "regexIMatch">
1917
2053
  ): BinaryPredicateExpression<Left, Right, "regexIMatch"> => {
1918
- const [left, right] = args as unknown as [Left, Right]
2054
+ const left = args[0] as Left
2055
+ const right = args[1] as Right
1919
2056
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "regexIMatch")
1920
2057
  }
1921
2058
 
@@ -1925,7 +2062,8 @@ type BinaryPredicateExpression<
1925
2062
  >(
1926
2063
  ...args: TextArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "regexNotMatch">
1927
2064
  ): BinaryPredicateExpression<Left, Right, "regexNotMatch"> => {
1928
- const [left, right] = args as unknown as [Left, Right]
2065
+ const left = args[0] as Left
2066
+ const right = args[1] as Right
1929
2067
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "regexNotMatch")
1930
2068
  }
1931
2069
 
@@ -1935,7 +2073,8 @@ type BinaryPredicateExpression<
1935
2073
  >(
1936
2074
  ...args: TextArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "regexNotIMatch">
1937
2075
  ): BinaryPredicateExpression<Left, Right, "regexNotIMatch"> => {
1938
- const [left, right] = args as unknown as [Left, Right]
2076
+ const left = args[0] as Left
2077
+ const right = args[1] as Right
1939
2078
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "regexNotIMatch")
1940
2079
  }
1941
2080
 
@@ -1945,7 +2084,8 @@ type BinaryPredicateExpression<
1945
2084
  >(
1946
2085
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "isDistinctFrom">
1947
2086
  ): BinaryPredicateExpression<Left, Right, "isDistinctFrom", "never"> => {
1948
- const [left, right] = args as unknown as [Left, Right]
2087
+ const left = args[0] as Left
2088
+ const right = args[1] as Right
1949
2089
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "isDistinctFrom", "never")
1950
2090
  }
1951
2091
 
@@ -1955,7 +2095,8 @@ type BinaryPredicateExpression<
1955
2095
  >(
1956
2096
  ...args: ComparableArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "isNotDistinctFrom">
1957
2097
  ): BinaryPredicateExpression<Left, Right, "isNotDistinctFrom", "never"> => {
1958
- const [left, right] = args as unknown as [Left, Right]
2098
+ const left = args[0] as Left
2099
+ const right = args[1] as Right
1959
2100
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "isNotDistinctFrom", "never")
1960
2101
  }
1961
2102
 
@@ -2106,62 +2247,62 @@ type BinaryPredicateExpression<
2106
2247
  })
2107
2248
 
2108
2249
  const range = <Kind extends string, Subtype extends Expression.DbType.Any>(
2109
- kind: Kind,
2250
+ kind: NonEmptyStringInput<Kind>,
2110
2251
  subtype: Subtype
2111
2252
  ): Expression.DbType.Range<Dialect, Subtype, Kind> => ({
2112
2253
  dialect: profile.dialect,
2113
- kind,
2254
+ kind: kind as Kind,
2114
2255
  subtype
2115
2256
  })
2116
2257
 
2117
2258
  const multirange = <Kind extends string, Subtype extends Expression.DbType.Any>(
2118
- kind: Kind,
2259
+ kind: NonEmptyStringInput<Kind>,
2119
2260
  subtype: Subtype
2120
2261
  ): Expression.DbType.Multirange<Dialect, Subtype, Kind> => ({
2121
2262
  dialect: profile.dialect,
2122
- kind,
2263
+ kind: kind as Kind,
2123
2264
  subtype
2124
2265
  })
2125
2266
 
2126
2267
  const record = <Kind extends string, Fields extends Record<string, Expression.DbType.Any>>(
2127
- kind: Kind,
2268
+ kind: NonEmptyStringInput<Kind>,
2128
2269
  fields: Fields
2129
2270
  ): Expression.DbType.Composite<Dialect, Fields, Kind> => ({
2130
2271
  dialect: profile.dialect,
2131
- kind,
2272
+ kind: kind as Kind,
2132
2273
  fields
2133
2274
  })
2134
2275
 
2135
2276
  const domain = <Kind extends string, Base extends Expression.DbType.Any>(
2136
- kind: Kind,
2277
+ kind: NonEmptyStringInput<Kind>,
2137
2278
  base: Base
2138
2279
  ): Expression.DbType.Domain<Dialect, Base, Kind> => ({
2139
2280
  dialect: profile.dialect,
2140
- kind,
2281
+ kind: kind as Kind,
2141
2282
  base
2142
2283
  })
2143
2284
 
2144
2285
  const enum_ = <Kind extends string>(
2145
- kind: Kind
2286
+ kind: NonEmptyStringInput<Kind>
2146
2287
  ): Expression.DbType.Enum<Dialect, Kind> => ({
2147
2288
  dialect: profile.dialect,
2148
- kind,
2289
+ kind: kind as Kind,
2149
2290
  variant: "enum"
2150
2291
  })
2151
2292
 
2152
2293
  const set = <Kind extends string>(
2153
- kind: Kind
2294
+ kind: NonEmptyStringInput<Kind>
2154
2295
  ): Expression.DbType.Set<Dialect, Kind> => ({
2155
2296
  dialect: profile.dialect,
2156
- kind,
2297
+ kind: kind as Kind,
2157
2298
  variant: "set"
2158
2299
  })
2159
2300
 
2160
2301
  const custom = <Kind extends string>(
2161
- kind: Kind
2302
+ kind: NonEmptyStringInput<Kind>
2162
2303
  ): Expression.DbType.Base<Dialect, Kind> => ({
2163
2304
  dialect: profile.dialect,
2164
- kind
2305
+ kind: kind as Kind
2165
2306
  })
2166
2307
 
2167
2308
  const driverValueMapping = <Db extends Expression.DbType.Any>(
@@ -2655,18 +2796,19 @@ type BinaryPredicateExpression<
2655
2796
  const jsonSet = <
2656
2797
  Base extends JsonExpressionLike<any>,
2657
2798
  Target extends JsonPathInput,
2658
- Next extends JsonValueInput
2799
+ Next extends JsonValueInput,
2800
+ CreateMissing extends boolean = true
2659
2801
  >(
2660
2802
  base: Base,
2661
- target: Target & JsonSetGuard<Expression.RuntimeOf<Base>, Target, Next, "json.set">,
2803
+ target: Target & JsonSetGuard<Expression.RuntimeOf<Base>, Target, NoInfer<Next>, "json.set">,
2662
2804
  next: Next,
2663
2805
  options: {
2664
- readonly createMissing?: boolean
2806
+ readonly createMissing?: CreateMissing
2665
2807
  } = {}
2666
2808
  ): JsonExpression<
2667
- JsonSetOutputOf<Expression.RuntimeOf<Base>, Target, Next, "json.set">,
2809
+ JsonSetOutputWithCreateMissing<Expression.RuntimeOf<Base>, Target, Next, "json.set", CreateMissing>,
2668
2810
  JsonDbOfExpression<Base>,
2669
- JsonNullabilityOf<JsonSetOutputOf<Expression.RuntimeOf<Base>, Target, Next, "json.set">>,
2811
+ JsonNullabilityOf<JsonSetOutputWithCreateMissing<Expression.RuntimeOf<Base>, Target, Next, "json.set", CreateMissing>>,
2670
2812
  DialectOf<Base>,
2671
2813
  KindOf<Base>,
2672
2814
  DependenciesOf<Base>,
@@ -2677,9 +2819,9 @@ type BinaryPredicateExpression<
2677
2819
  return buildJsonNodeExpression(
2678
2820
  [base, newValue],
2679
2821
  {
2680
- runtime: undefined as unknown as JsonSetOutputOf<Expression.RuntimeOf<Base>, Target, Next, "json.set">,
2822
+ runtime: undefined as unknown as JsonSetOutputWithCreateMissing<Expression.RuntimeOf<Base>, Target, Next, "json.set", CreateMissing>,
2681
2823
  dbType: jsonDbTypeOf(base),
2682
- nullability: undefined as unknown as JsonNullabilityOf<JsonSetOutputOf<Expression.RuntimeOf<Base>, Target, Next, "json.set">>
2824
+ nullability: undefined as unknown as JsonNullabilityOf<JsonSetOutputWithCreateMissing<Expression.RuntimeOf<Base>, Target, Next, "json.set", CreateMissing>>
2683
2825
  },
2684
2826
  {
2685
2827
  kind: "jsonSet",
@@ -2689,9 +2831,9 @@ type BinaryPredicateExpression<
2689
2831
  createMissing: options.createMissing ?? true
2690
2832
  }
2691
2833
  ) as JsonExpression<
2692
- JsonSetOutputOf<Expression.RuntimeOf<Base>, Target, Next, "json.set">,
2834
+ JsonSetOutputWithCreateMissing<Expression.RuntimeOf<Base>, Target, Next, "json.set", CreateMissing>,
2693
2835
  JsonDbOfExpression<Base>,
2694
- JsonNullabilityOf<JsonSetOutputOf<Expression.RuntimeOf<Base>, Target, Next, "json.set">>,
2836
+ JsonNullabilityOf<JsonSetOutputWithCreateMissing<Expression.RuntimeOf<Base>, Target, Next, "json.set", CreateMissing>>,
2695
2837
  DialectOf<Base>,
2696
2838
  KindOf<Base>,
2697
2839
  DependenciesOf<Base>,
@@ -2706,7 +2848,7 @@ type BinaryPredicateExpression<
2706
2848
  InsertAfter extends boolean = false
2707
2849
  >(
2708
2850
  base: Base,
2709
- target: Target & JsonInsertGuard<Expression.RuntimeOf<Base>, Target, Next, InsertAfter, "json.insert">,
2851
+ target: Target & JsonInsertGuard<Expression.RuntimeOf<Base>, Target, NoInfer<Next>, NoInfer<InsertAfter>, "json.insert">,
2710
2852
  next: Next,
2711
2853
  options: {
2712
2854
  readonly insertAfter?: InsertAfter
@@ -2928,7 +3070,7 @@ type BinaryPredicateExpression<
2928
3070
  ) => buildJsonNodeExpression(
2929
3071
  [base],
2930
3072
  {
2931
- runtime: undefined as unknown as JsonTypeName<Expression.RuntimeOf<Base>>,
3073
+ runtime: undefined as unknown as MySqlJsonTypeName<Expression.RuntimeOf<Base>>,
2932
3074
  dbType: profile.textDb as TextDb,
2933
3075
  nullability: base[Expression.TypeId].nullability
2934
3076
  },
@@ -2943,9 +3085,9 @@ type BinaryPredicateExpression<
2943
3085
  ) => buildJsonNodeExpression(
2944
3086
  [base],
2945
3087
  {
2946
- runtime: undefined as unknown as JsonLengthResult<Expression.RuntimeOf<Base>>,
3088
+ runtime: undefined as unknown as MySqlJsonLengthResult<Expression.RuntimeOf<Base>>,
2947
3089
  dbType: profile.numericDb as NumericDb,
2948
- nullability: undefined as unknown as JsonNullabilityOf<JsonLengthResult<Expression.RuntimeOf<Base>>>
3090
+ nullability: undefined as unknown as JsonNullabilityOf<MySqlJsonLengthResult<Expression.RuntimeOf<Base>>>
2949
3091
  },
2950
3092
  {
2951
3093
  kind: "jsonLength",
@@ -2968,9 +3110,12 @@ type BinaryPredicateExpression<
2968
3110
  }
2969
3111
  )
2970
3112
 
2971
- const jsonPathExists = <Base extends JsonExpressionLike<any>>(
3113
+ const jsonPathExists = <
3114
+ Base extends JsonExpressionLike<any>,
3115
+ Query extends JsonQueryInput
3116
+ >(
2972
3117
  base: Base,
2973
- query: JsonQueryInput
3118
+ query: JsonQueryValue<Query>
2974
3119
  ) => {
2975
3120
  if (isJsonPathValue(query)) {
2976
3121
  return buildJsonNodeExpression(
@@ -3018,9 +3163,12 @@ type BinaryPredicateExpression<
3018
3163
  }
3019
3164
  )
3020
3165
 
3021
- const jsonPathMatch = <Base extends JsonExpressionLike<any>>(
3166
+ const jsonPathMatch = <
3167
+ Base extends JsonExpressionLike<any>,
3168
+ Query extends JsonQueryInput
3169
+ >(
3022
3170
  base: Base,
3023
- query: JsonQueryInput
3171
+ query: JsonQueryValue<Query>
3024
3172
  ) => {
3025
3173
  if (isJsonPathValue(query)) {
3026
3174
  return buildJsonNodeExpression(
@@ -3085,9 +3233,9 @@ type BinaryPredicateExpression<
3085
3233
  typeOf: jsonTypeOf,
3086
3234
  length: jsonLength,
3087
3235
  keys: jsonKeys,
3088
- stripNulls: jsonStripNulls,
3236
+ stripNulls: jsonStripNulls as unknown as MySqlUnsupportedJsonFeature<"json.stripNulls">,
3089
3237
  pathExists: jsonPathExists,
3090
- pathMatch: jsonPathMatch
3238
+ pathMatch: jsonPathMatch as unknown as MySqlUnsupportedJsonFeature<"json.pathMatch">
3091
3239
  }
3092
3240
 
3093
3241
  const jsonb = {
@@ -3247,7 +3395,8 @@ type BinaryPredicateExpression<
3247
3395
  >(
3248
3396
  ...args: ContainmentArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "contains">
3249
3397
  ): BinaryPredicateExpression<Left, Right, "contains"> => {
3250
- const [left, right] = args as unknown as [Left, Right]
3398
+ const left = args[0] as Left
3399
+ const right = args[1] as Right
3251
3400
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "contains")
3252
3401
  }
3253
3402
 
@@ -3257,7 +3406,8 @@ type BinaryPredicateExpression<
3257
3406
  >(
3258
3407
  ...args: ContainmentArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "containedBy">
3259
3408
  ): BinaryPredicateExpression<Left, Right, "containedBy"> => {
3260
- const [left, right] = args as unknown as [Left, Right]
3409
+ const left = args[0] as Left
3410
+ const right = args[1] as Right
3261
3411
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "containedBy")
3262
3412
  }
3263
3413
 
@@ -3267,7 +3417,8 @@ type BinaryPredicateExpression<
3267
3417
  >(
3268
3418
  ...args: ContainmentArgs<Left, Right, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb, "overlaps">
3269
3419
  ): BinaryPredicateExpression<Left, Right, "overlaps"> => {
3270
- const [left, right] = args as unknown as [Left, Right]
3420
+ const left = args[0] as Left
3421
+ const right = args[1] as Right
3271
3422
  return buildBinaryPredicate(left as ExpressionInput, right as ExpressionInput, "overlaps")
3272
3423
  }
3273
3424
 
@@ -3694,12 +3845,9 @@ type BinaryPredicateExpression<
3694
3845
  >
3695
3846
  }
3696
3847
 
3697
- const call = <
3698
- Name extends string,
3699
- Args extends readonly ExpressionInput[]
3700
- >(
3701
- name: Name,
3702
- ...args: Args
3848
+ const call: FunctionCallApi = (
3849
+ name: string,
3850
+ ...args: readonly ExpressionInput[]
3703
3851
  ): Expression.Any => {
3704
3852
  const expressions = args.map((value) => toDialectExpression(value)) as readonly Expression.Any[]
3705
3853
  return makeExpression({
@@ -3920,7 +4068,9 @@ type BinaryPredicateExpression<
3920
4068
  string,
3921
4069
  "scalar",
3922
4070
  Expression.BindingId
3923
- >
4071
+ > & {
4072
+ readonly [ExpressionAst.TypeId]: ExpressionAst.ColumnNode<any, string>
4073
+ }
3924
4074
  >(
3925
4075
  value: Value
3926
4076
  ): AstBackedExpression<
@@ -3933,9 +4083,6 @@ type BinaryPredicateExpression<
3933
4083
  ExpressionAst.ExcludedNode<AstOf<Value> extends ExpressionAst.ColumnNode<any, infer ColumnName extends string> ? ColumnName : string>
3934
4084
  > => {
3935
4085
  const ast = ((value as unknown) as Expression.Any & { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
3936
- if (ast.kind !== "column") {
3937
- throw new Error("excluded(...) only accepts bound table columns")
3938
- }
3939
4086
  return makeExpression({
3940
4087
  runtime: undefined as Expression.RuntimeOf<Value>,
3941
4088
  dbType: value[Expression.TypeId].dbType as Expression.DbTypeOf<Value>,
@@ -3948,7 +4095,7 @@ type BinaryPredicateExpression<
3948
4095
  dependencies: {}
3949
4096
  }, {
3950
4097
  kind: "excluded",
3951
- columnName: ast.columnName
4098
+ columnName: (ast as ExpressionAst.ColumnNode<any, string>).columnName
3952
4099
  }) as unknown as AstBackedExpression<
3953
4100
  Expression.RuntimeOf<Value>,
3954
4101
  Expression.DbTypeOf<Value>,
@@ -3964,22 +4111,56 @@ type BinaryPredicateExpression<
3964
4111
  value: Value,
3965
4112
  column: Expression.Any
3966
4113
  ): Expression.Any => {
4114
+ const columnState = column[Expression.TypeId]
4115
+ const normalizeMutationValue = (candidate: unknown): unknown => {
4116
+ if (candidate === null && columnState.nullability !== "never") {
4117
+ return null
4118
+ }
4119
+ const runtimeSchemaAccepts = columnState.runtimeSchema !== undefined &&
4120
+ (Schema.is(columnState.runtimeSchema) as (input: unknown) => boolean)(candidate)
4121
+ if (runtimeSchemaAccepts) {
4122
+ return candidate
4123
+ }
4124
+ const normalized = normalizeDbValue(columnState.dbType, candidate)
4125
+ return columnState.runtimeSchema === undefined
4126
+ ? normalized
4127
+ : (Schema.decodeUnknownSync as any)(columnState.runtimeSchema)(normalized)
4128
+ }
3967
4129
  if (value !== null && typeof value === "object" && Expression.TypeId in value) {
4130
+ const expression = value as unknown as Expression.Any
4131
+ const ast = (expression as Expression.Any & { readonly [ExpressionAst.TypeId]: ExpressionAst.Any })[ExpressionAst.TypeId]
4132
+ if (ast.kind === "literal") {
4133
+ const normalizedValue = normalizeMutationValue(ast.value)
4134
+ return makeExpression({
4135
+ runtime: normalizedValue,
4136
+ dbType: columnState.dbType,
4137
+ runtimeSchema: columnState.runtimeSchema,
4138
+ driverValueMapping: columnState.driverValueMapping,
4139
+ nullability: normalizedValue === null ? "always" : "never",
4140
+ dialect: columnState.dialect,
4141
+ kind: "scalar",
4142
+ dependencies: {}
4143
+ }, {
4144
+ kind: "literal",
4145
+ value: normalizedValue
4146
+ })
4147
+ }
3968
4148
  return retargetLiteralExpression(value as unknown as Expression.Any, column)
3969
4149
  }
4150
+ const normalizedValue = normalizeMutationValue(value)
3970
4151
  return makeExpression({
3971
- runtime: value as Value,
3972
- dbType: column[Expression.TypeId].dbType,
3973
- runtimeSchema: column[Expression.TypeId].runtimeSchema,
3974
- driverValueMapping: column[Expression.TypeId].driverValueMapping,
3975
- nullability: value === null ? "always" : "never",
3976
- dialect: column[Expression.TypeId].dialect,
4152
+ runtime: normalizedValue as Value,
4153
+ dbType: columnState.dbType,
4154
+ runtimeSchema: columnState.runtimeSchema,
4155
+ driverValueMapping: columnState.driverValueMapping,
4156
+ nullability: normalizedValue === null ? "always" : "never",
4157
+ dialect: columnState.dialect,
3977
4158
  kind: "scalar",
3978
4159
 
3979
4160
  dependencies: {}
3980
4161
  }, {
3981
4162
  kind: "literal",
3982
- value
4163
+ value: normalizedValue
3983
4164
  })
3984
4165
  }
3985
4166
 
@@ -4016,8 +4197,8 @@ type BinaryPredicateExpression<
4016
4197
  : ">="
4017
4198
 
4018
4199
  const targetSourceDetails = (table: MutationTargetLike | SchemaTableLike) => {
4019
- const sourceName = (table as unknown as TableLike)[Table.TypeId].name
4020
- const sourceBaseName = (table as unknown as TableLike)[Table.TypeId].baseName
4200
+ const sourceName = (table as TableLike)[Table.TypeId].name
4201
+ const sourceBaseName = (table as TableLike)[Table.TypeId].baseName
4021
4202
  return {
4022
4203
  sourceName,
4023
4204
  sourceBaseName
@@ -4067,16 +4248,16 @@ type BinaryPredicateExpression<
4067
4248
  Alias extends string
4068
4249
  >(
4069
4250
  rows: readonly [Record<string, Expression.Any>, ...Record<string, Expression.Any>[]],
4070
- selection: ValuesOutputShape<Rows[0], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4251
+ selection: ValuesOutputShape<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4071
4252
  alias: Alias
4072
4253
  ): ValuesSource<
4073
4254
  Rows,
4074
- ValuesOutputShape<Rows[0], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4255
+ ValuesOutputShape<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4075
4256
  Alias,
4076
4257
  Dialect
4077
4258
  > => {
4078
4259
  const columns = makeColumnReferenceSelection(alias, selection as Record<string, Expression.Any>) as unknown as ValuesOutputShape<
4079
- Rows[0],
4260
+ Rows,
4080
4261
  Dialect,
4081
4262
  TextDb,
4082
4263
  NumericDb,
@@ -4094,7 +4275,7 @@ type BinaryPredicateExpression<
4094
4275
  }
4095
4276
  return Object.assign(source, columns) as unknown as ValuesSource<
4096
4277
  Rows,
4097
- ValuesOutputShape<Rows[0], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4278
+ ValuesOutputShape<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4098
4279
  Alias,
4099
4280
  Dialect
4100
4281
  >
@@ -4150,6 +4331,11 @@ type BinaryPredicateExpression<
4150
4331
  })
4151
4332
  ) as unknown as AddAvailableMany<{}, MutationTargetNamesOf<Target>, Mode>
4152
4333
 
4334
+ const getMutationColumn = (
4335
+ columns: Record<string, unknown>,
4336
+ columnName: string
4337
+ ): Expression.Any => columns[columnName] as Expression.Any
4338
+
4153
4339
  const buildMutationAssignments = <Target extends MutationTargetInput, Values>(
4154
4340
  target: Target,
4155
4341
  values: Values
@@ -4159,18 +4345,18 @@ type BinaryPredicateExpression<
4159
4345
  const columns = target as unknown as Record<string, Expression.Any>
4160
4346
  return Object.entries(values as Record<string, unknown>).map(([columnName, value]) => ({
4161
4347
  columnName,
4162
- value: toMutationValueExpression(value, columns[columnName]!)
4348
+ value: toMutationValueExpression(value, getMutationColumn(columns, columnName))
4163
4349
  }))
4164
4350
  }
4165
4351
  const valueMap = values as Record<string, Record<string, unknown> | undefined>
4166
4352
  return targets.flatMap((table) => {
4167
- const targetName = (table as unknown as TableLike)[Table.TypeId].name
4353
+ const targetName = (table as TableLike)[Table.TypeId].name
4168
4354
  const scopedValues = valueMap[targetName] ?? {}
4169
4355
  const columns = table as unknown as Record<string, Expression.Any>
4170
4356
  return Object.entries(scopedValues).map(([columnName, value]) => ({
4171
4357
  tableName: targetName,
4172
4358
  columnName,
4173
- value: toMutationValueExpression(value, columns[columnName]!)
4359
+ value: toMutationValueExpression(value, getMutationColumn(columns, columnName))
4174
4360
  }))
4175
4361
  })
4176
4362
  }
@@ -4185,20 +4371,17 @@ type BinaryPredicateExpression<
4185
4371
  } => {
4186
4372
  const firstRow = rows[0]
4187
4373
  const firstColumns = Object.keys(firstRow)
4188
- if (firstColumns.length === 0) {
4189
- throw new Error("values(...) rows must specify at least one column; use insert(target) for default-only inserts instead")
4190
- }
4191
4374
  const columns = firstColumns as [string, ...string[]]
4192
- const normalizedRows = rows.map((row) => {
4193
- const rowKeys = Object.keys(row)
4194
- if (rowKeys.length !== columns.length || columns.some((column) => !(column in row))) {
4195
- throw new Error("All values(...) rows must project the same columns in the same shape")
4196
- }
4375
+ const normalizeRow = (row: InsertRowInput<Target>) => {
4197
4376
  const assignments = buildMutationAssignments(target, row) as readonly QueryAst.AssignmentClause[]
4198
4377
  return {
4199
4378
  values: columns.map((columnName) => assignments.find((assignment) => assignment.columnName === columnName)!)
4200
4379
  } satisfies QueryAst.InsertValuesRowClause
4201
- }) as unknown as [QueryAst.InsertValuesRowClause, ...QueryAst.InsertValuesRowClause[]]
4380
+ }
4381
+ const normalizedRows: readonly [QueryAst.InsertValuesRowClause, ...QueryAst.InsertValuesRowClause[]] = [
4382
+ normalizeRow(rows[0]),
4383
+ ...rows.slice(1).map(normalizeRow)
4384
+ ]
4202
4385
  const required = normalizedRows.flatMap((row) =>
4203
4386
  row.values.flatMap((entry) => Object.keys(entry.value[Expression.TypeId].dependencies))
4204
4387
  )
@@ -4213,9 +4396,6 @@ type BinaryPredicateExpression<
4213
4396
  selection: Record<string, Expression.Any>
4214
4397
  ): readonly [string, ...string[]] => {
4215
4398
  const columns = Object.keys(selection)
4216
- if (columns.length === 0) {
4217
- throw new Error("insert(...).pipe(from(subquery)) requires at least one projected column")
4218
- }
4219
4399
  return columns as [string, ...string[]]
4220
4400
  }
4221
4401
 
@@ -4230,41 +4410,33 @@ type BinaryPredicateExpression<
4230
4410
  }[]
4231
4411
  } => {
4232
4412
  const entries = Object.entries(values)
4233
- if (entries.length === 0) {
4234
- throw new Error("unnest(...) requires at least one column array")
4235
- }
4236
4413
  const columns = entries.map(([columnName]) => columnName) as [string, ...string[]]
4237
- const normalized = entries.map(([columnName, items]) => {
4238
- if (!Array.isArray(items)) {
4239
- throw new Error("unnest(...) expects every value to be an array")
4240
- }
4241
- return {
4242
- columnName,
4243
- values: items
4244
- }
4245
- })
4246
- const expectedLength = normalized[0]!.values.length
4247
- if (normalized.some((entry) => entry.values.length !== expectedLength)) {
4248
- throw new Error("unnest(...) expects every column array to have the same length")
4249
- }
4250
- const knownColumns = new Set(Object.keys(target[Table.TypeId].fields))
4251
- if (columns.some((columnName) => !knownColumns.has(columnName))) {
4252
- throw new Error("unnest(...) received a column that does not exist on the target table")
4253
- }
4414
+ const normalized = entries.map(([columnName, items]) => ({
4415
+ columnName,
4416
+ values: items
4417
+ }))
4254
4418
  return {
4255
4419
  columns,
4256
4420
  values: normalized
4257
4421
  }
4258
4422
  }
4259
4423
 
4424
+ const normalizeConflictColumns = <Target extends MutationTargetLike>(
4425
+ target: Target,
4426
+ columnsInput: string | readonly string[]
4427
+ ): readonly [string, ...string[]] => {
4428
+ const columns = normalizeColumnList(columnsInput) as readonly [string, ...string[]]
4429
+ return columns
4430
+ }
4431
+
4260
4432
  const buildConflictTarget = <Target extends MutationTargetLike>(
4261
4433
  target: Target,
4262
- input: readonly string[] | { readonly columns: readonly string[]; readonly where?: PredicateInput } | { readonly constraint: string }
4434
+ input: string | readonly string[] | { readonly columns: string | readonly string[]; readonly where?: PredicateInput } | { readonly constraint: string }
4263
4435
  ): QueryAst.ConflictTargetClause => {
4264
- if (Array.isArray(input)) {
4436
+ if (typeof input === "string" || Array.isArray(input)) {
4265
4437
  return {
4266
4438
  kind: "columns",
4267
- columns: normalizeColumnList(input) as readonly [string, ...string[]]
4439
+ columns: normalizeConflictColumns(target, input)
4268
4440
  }
4269
4441
  }
4270
4442
  if (!Array.isArray(input) && "constraint" in input) {
@@ -4274,12 +4446,12 @@ type BinaryPredicateExpression<
4274
4446
  }
4275
4447
  }
4276
4448
  const columnTarget = input as {
4277
- readonly columns: readonly string[]
4449
+ readonly columns: string | readonly string[]
4278
4450
  readonly where?: PredicateInput
4279
4451
  }
4280
4452
  return {
4281
4453
  kind: "columns",
4282
- columns: normalizeColumnList(columnTarget.columns) as readonly [string, ...string[]],
4454
+ columns: normalizeConflictColumns(target, columnTarget.columns),
4283
4455
  where: columnTarget.where === undefined ? undefined : toDialectExpression(columnTarget.where)
4284
4456
  }
4285
4457
  }
@@ -4317,20 +4489,30 @@ type ValidateDdlColumns<
4317
4489
  Columns extends readonly string[]
4318
4490
  > = Exclude<Columns[number], SchemaColumnNames<Target>> extends never ? Columns : never
4319
4491
 
4492
+ type ValidateDdlColumnInput<
4493
+ Target extends SchemaTableLike,
4494
+ Columns extends DdlColumnInput
4495
+ > = ValidateDdlColumns<Target, NormalizeDdlColumns<Columns>> extends never ? never : Columns
4496
+
4320
4497
  type ValidateTargetColumns<
4321
4498
  Target extends MutationTargetLike,
4322
4499
  Columns extends readonly string[]
4323
4500
  > = Exclude<Columns[number], Extract<keyof Target[typeof Table.TypeId]["fields"], string>> extends never ? Columns : never
4324
4501
 
4325
- type CreateIndexOptions = {
4326
- readonly name?: string
4502
+ type ValidateTargetColumnInput<
4503
+ Target extends MutationTargetLike,
4504
+ Columns extends DdlColumnInput
4505
+ > = ValidateTargetColumns<Target, NormalizeDdlColumns<Columns>> extends never ? never : Columns
4506
+
4507
+ type CreateIndexOptions<Name extends string = string> = {
4508
+ readonly name?: NonEmptyStringInput<Name>
4327
4509
  readonly unique?: boolean
4328
- readonly ifNotExists?: boolean
4510
+ readonly ifNotExists?: never
4329
4511
  }
4330
4512
 
4331
- type DropIndexOptions = {
4332
- readonly name?: string
4333
- readonly ifExists?: boolean
4513
+ type DropIndexOptions<Name extends string = string> = {
4514
+ readonly name?: NonEmptyStringInput<Name>
4515
+ readonly ifExists?: never
4334
4516
  }
4335
4517
 
4336
4518
  type CreateTableOptions = {
@@ -4342,8 +4524,8 @@ type DropTableOptions = {
4342
4524
  }
4343
4525
 
4344
4526
  type TruncateOptions = {
4345
- readonly restartIdentity?: boolean
4346
- readonly cascade?: boolean
4527
+ readonly restartIdentity?: never
4528
+ readonly cascade?: never
4347
4529
  }
4348
4530
 
4349
4531
  type TransactionOptions = {
@@ -4351,10 +4533,15 @@ type TransactionOptions = {
4351
4533
  readonly readOnly?: boolean
4352
4534
  }
4353
4535
 
4354
- type LockOptions = {
4355
- readonly nowait?: boolean
4356
- readonly skipLocked?: boolean
4357
- }
4536
+ type LockOptions =
4537
+ | {
4538
+ readonly nowait?: boolean
4539
+ readonly skipLocked?: false
4540
+ }
4541
+ | {
4542
+ readonly nowait?: false
4543
+ readonly skipLocked?: boolean
4544
+ }
4358
4545
 
4359
4546
  type UpsertConflictOptions = {
4360
4547
  readonly update?: Record<string, unknown>
@@ -4369,14 +4556,133 @@ type InsertRowInput<Target extends MutationTargetLike> = MutationInputOf<Table.I
4369
4556
  type ValuesRowInput = Record<string, ExpressionInput>
4370
4557
  type ValuesRowsInput = readonly [ValuesRowInput, ...ValuesRowInput[]]
4371
4558
 
4559
+ type ValuesColumnInput<Row, Key extends PropertyKey> =
4560
+ Row extends ValuesRowInput
4561
+ ? Key extends keyof Row ? Row[Key] : never
4562
+ : never
4563
+
4564
+ type ValuesRowShapeMismatch<
4565
+ First extends ValuesRowInput,
4566
+ Row extends ValuesRowInput
4567
+ > =
4568
+ | Exclude<Extract<keyof Row, string>, Extract<keyof First, string>>
4569
+ | Exclude<Extract<keyof First, string>, Extract<keyof Row, string>>
4570
+
4571
+ type ValuesRowsShapeMismatchesFor<
4572
+ First extends ValuesRowInput,
4573
+ Row
4574
+ > = Row extends ValuesRowInput ? ValuesRowShapeMismatch<First, Row> : never
4575
+
4576
+ type ValuesRowsShapeMismatches<Rows extends ValuesRowsInput> =
4577
+ Rows extends readonly [infer First extends ValuesRowInput, ...infer Rest extends ValuesRowInput[]]
4578
+ ? ValuesRowsShapeMismatchesFor<First, Rest[number]>
4579
+ : never
4580
+
4581
+ type ValuesRowsColumnKeys<Rows extends ValuesRowsInput> =
4582
+ Rows extends readonly [infer First extends ValuesRowInput, ...ValuesRowInput[]]
4583
+ ? Extract<keyof First, string>
4584
+ : never
4585
+
4586
+ type ValuesRowsShapeInput<Rows extends ValuesRowsInput> =
4587
+ [ValuesRowsColumnKeys<Rows>] extends [never]
4588
+ ? {
4589
+ readonly __effect_qb_error__: "effect-qb: values rows must project at least one column"
4590
+ }
4591
+ : [ValuesRowsShapeMismatches<Rows>] extends [never]
4592
+ ? unknown
4593
+ : {
4594
+ readonly __effect_qb_error__: "effect-qb: values rows must project the same columns"
4595
+ readonly __effect_qb_mismatched_columns__: ValuesRowsShapeMismatches<Rows>
4596
+ }
4597
+
4598
+ type ValuesRowsDialect<
4599
+ Rows extends ValuesRowsInput,
4600
+ Dialect extends string,
4601
+ TextDb extends Expression.DbType.Any,
4602
+ NumericDb extends Expression.DbType.Any,
4603
+ BoolDb extends Expression.DbType.Any,
4604
+ TimestampDb extends Expression.DbType.Any,
4605
+ NullDb extends Expression.DbType.Any
4606
+ > = Rows[number][keyof Rows[number]] extends infer Value extends ExpressionInput
4607
+ ? DialectOfDialectInput<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4608
+ : never
4609
+
4610
+ type ValuesRowsDialectInput<
4611
+ Rows extends ValuesRowsInput,
4612
+ Dialect extends string,
4613
+ TextDb extends Expression.DbType.Any,
4614
+ NumericDb extends Expression.DbType.Any,
4615
+ BoolDb extends Expression.DbType.Any,
4616
+ TimestampDb extends Expression.DbType.Any,
4617
+ NullDb extends Expression.DbType.Any
4618
+ > = Exclude<ValuesRowsDialect<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>, Dialect | "standard"> extends never
4619
+ ? unknown
4620
+ : {
4621
+ readonly __effect_qb_error__: "effect-qb: values rows cannot mix dialects"
4622
+ readonly __effect_qb_dialect__: ValuesRowsDialect<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4623
+ }
4624
+
4372
4625
  type UnnestColumnsInput = Record<string, readonly [ExpressionInput, ...ExpressionInput[]]>
4373
4626
 
4627
+ type IsNever<Value> = [Value] extends [never] ? true : false
4628
+
4629
+ type IsUnion<Value, All = Value> = Value extends any
4630
+ ? ([All] extends [Value] ? false : true)
4631
+ : never
4632
+
4633
+ type UnnestColumnKeys<Columns extends UnnestColumnsInput> =
4634
+ Extract<keyof Columns, string>
4635
+
4636
+ type UnnestColumnLengths<Columns extends UnnestColumnsInput> =
4637
+ Columns[UnnestColumnKeys<Columns>]["length"]
4638
+
4639
+ type UnnestColumnsShapeInput<Columns extends UnnestColumnsInput> =
4640
+ IsNever<UnnestColumnKeys<Columns>> extends true
4641
+ ? {
4642
+ readonly __effect_qb_error__: "effect-qb: unnest requires at least one column array"
4643
+ }
4644
+ : number extends UnnestColumnLengths<Columns>
4645
+ ? unknown
4646
+ : IsUnion<UnnestColumnLengths<Columns>> extends true
4647
+ ? {
4648
+ readonly __effect_qb_error__: "effect-qb: unnest column arrays must have the same length"
4649
+ readonly __effect_qb_column_lengths__: UnnestColumnLengths<Columns>
4650
+ }
4651
+ : unknown
4652
+
4653
+ type UnnestColumnsDialect<
4654
+ Columns extends UnnestColumnsInput,
4655
+ Dialect extends string,
4656
+ TextDb extends Expression.DbType.Any,
4657
+ NumericDb extends Expression.DbType.Any,
4658
+ BoolDb extends Expression.DbType.Any,
4659
+ TimestampDb extends Expression.DbType.Any,
4660
+ NullDb extends Expression.DbType.Any
4661
+ > = Columns[UnnestColumnKeys<Columns>][number] extends infer Value extends ExpressionInput
4662
+ ? DialectOfDialectInput<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4663
+ : never
4664
+
4665
+ type UnnestColumnsDialectInput<
4666
+ Columns extends UnnestColumnsInput,
4667
+ Dialect extends string,
4668
+ TextDb extends Expression.DbType.Any,
4669
+ NumericDb extends Expression.DbType.Any,
4670
+ BoolDb extends Expression.DbType.Any,
4671
+ TimestampDb extends Expression.DbType.Any,
4672
+ NullDb extends Expression.DbType.Any
4673
+ > = Exclude<UnnestColumnsDialect<Columns, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>, Dialect | "standard"> extends never
4674
+ ? unknown
4675
+ : {
4676
+ readonly __effect_qb_error__: "effect-qb: unnest columns cannot mix dialects"
4677
+ readonly __effect_qb_dialect__: UnnestColumnsDialect<Columns, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4678
+ }
4679
+
4374
4680
  type UnnestRowShape<Shape extends Record<string, readonly unknown[]>> = {
4375
4681
  readonly [K in keyof Shape]: Shape[K] extends readonly (infer Item)[] ? Item : never
4376
4682
  }
4377
4683
 
4378
4684
  type ValuesOutputShape<
4379
- Row extends ValuesRowInput,
4685
+ Rows extends ValuesRowsInput,
4380
4686
  Dialect extends string,
4381
4687
  TextDb extends Expression.DbType.Any,
4382
4688
  NumericDb extends Expression.DbType.Any,
@@ -4384,7 +4690,7 @@ type ValuesOutputShape<
4384
4690
  TimestampDb extends Expression.DbType.Any,
4385
4691
  NullDb extends Expression.DbType.Any
4386
4692
  > = {
4387
- readonly [K in keyof Row]: DialectAsExpression<Row[K], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4693
+ readonly [K in keyof Rows[0]]: DialectAsExpression<ValuesColumnInput<Rows[number], K>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4388
4694
  }
4389
4695
 
4390
4696
  type UnnestOutputShape<
@@ -4423,19 +4729,44 @@ type DistinctOnUnsupportedError<Dialect extends string> = {
4423
4729
  readonly __effect_qb_hint__: "Use postgres.Query.distinctOn(...) or regular distinct()/grouping logic"
4424
4730
  }
4425
4731
 
4732
+ type FullJoinUnsupportedError<Dialect extends string> = {
4733
+ readonly __effect_qb_error__: "effect-qb: fullJoin(...) is only supported by the postgres dialect"
4734
+ readonly __effect_qb_dialect__: Dialect
4735
+ readonly __effect_qb_hint__: "Use leftJoin/rightJoin with nullable handling or switch to postgres.Query.fullJoin(...)"
4736
+ }
4737
+
4738
+ type ReturningUnsupportedError<Dialect extends string> = {
4739
+ readonly __effect_qb_error__: "effect-qb: returning(...) is only supported by the postgres dialect"
4740
+ readonly __effect_qb_dialect__: Dialect
4741
+ readonly __effect_qb_hint__: "Use postgres.Query.returning(...) or run a follow-up select after MySQL mutations"
4742
+ }
4743
+
4744
+ type MysqlCteStatementError<PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>> =
4745
+ PlanValue & {
4746
+ readonly __effect_qb_error__: "effect-qb: mysql cte sources only accept select-like query plans"
4747
+ readonly __effect_qb_statement__: StatementOfPlan<PlanValue>
4748
+ readonly __effect_qb_hint__: "Use select(...) or a set operator before wrapping a MySQL plan in with(...)"
4749
+ }
4750
+
4751
+ type MysqlCteCompatiblePlan<
4752
+ PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>
4753
+ > = StatementOfPlan<PlanValue> extends "select" | "set"
4754
+ ? DerivedSourceCompatiblePlan<PlanValue>
4755
+ : MysqlCteStatementError<PlanValue>
4756
+
4426
4757
  type DistinctOnApi<Dialect extends string> = Dialect extends "postgres"
4427
- ? <Values extends readonly ExpressionInput[]>(
4758
+ ? <Values extends readonly [ExpressionInput, ...ExpressionInput[]]>(
4428
4759
  ...values: Values
4429
4760
  ) => <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
4430
4761
  plan: PlanValue & RequireSelectStatement<PlanValue>
4431
4762
  ) => QueryPlan<
4432
4763
  SelectionOfPlan<PlanValue>,
4433
- RequiredOfPlan<PlanValue>,
4764
+ AddExpressionRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, Values[number]>,
4434
4765
  AvailableOfPlan<PlanValue>,
4435
- PlanDialectOf<PlanValue>,
4766
+ PlanDialectOf<PlanValue> | DialectOfDialectInput<Values[number], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4436
4767
  GroupedOfPlan<PlanValue>,
4437
4768
  ScopedNamesOfPlan<PlanValue>,
4438
- OutstandingOfPlan<PlanValue>,
4769
+ AddExpressionRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, Values[number]>,
4439
4770
  AssumptionsOfPlan<PlanValue>,
4440
4771
  CapabilitiesOfPlan<PlanValue>,
4441
4772
  StatementOfPlan<PlanValue>
@@ -4468,6 +4799,27 @@ type MysqlConflictWhereError<Values> = Values & {
4468
4799
  readonly __effect_qb_hint__: "Move the condition into the update assignment expressions or use the Postgres dialect"
4469
4800
  }
4470
4801
 
4802
+ type UpdateValuesNonEmptyError<Values> = Values & {
4803
+ readonly __effect_qb_error__: "effect-qb: update statements require at least one assignment"
4804
+ }
4805
+
4806
+ type UpdateValuesNonEmptyConstraint<Values> =
4807
+ [Extract<keyof Values, string>] extends [never]
4808
+ ? UpdateValuesNonEmptyError<Values>
4809
+ : unknown
4810
+
4811
+ type NestedUpdateValuesNonEmptyConstraint<Values> =
4812
+ [Extract<keyof Values, string>] extends [never]
4813
+ ? UpdateValuesNonEmptyError<Values>
4814
+ : true extends {
4815
+ [K in Extract<keyof Values, string>]:
4816
+ Values[K] extends Record<string, unknown>
4817
+ ? [Extract<keyof Values[K], string>] extends [never] ? false : true
4818
+ : false
4819
+ }[Extract<keyof Values, string>]
4820
+ ? unknown
4821
+ : UpdateValuesNonEmptyError<Values>
4822
+
4471
4823
  type InsertShapeExtraKeys<TargetShape, SourceShape> = Exclude<Extract<keyof SourceShape, string>, Extract<keyof TargetShape, string>>
4472
4824
  type InsertShapeMissingKeys<TargetShape, SourceShape> = Exclude<RequiredKeys<TargetShape>, Extract<keyof SourceShape, string>>
4473
4825
  type InsertShapeMismatchedKeys<TargetShape, SourceShape> = Extract<{
@@ -4561,10 +4913,15 @@ type InsertSourceRequired<Source> =
4561
4913
  Source extends QueryPlan<any, any, any, any, any, any, any, any, any, any> ? RequiredOfPlan<Source> :
4562
4914
  never
4563
4915
 
4916
+ type InsertSourceDialect<Source> =
4917
+ Source extends QueryPlan<any, any, any, any, any, any, any, any, any, any> ? PlanDialectOf<Source> :
4918
+ Source extends SourceLike ? SourceDialectOf<Source> :
4919
+ never
4920
+
4564
4921
  type ConflictColumnTarget<
4565
4922
  Target extends MutationTargetLike,
4566
4923
  Columns extends DdlColumnInput
4567
- > = ValidateTargetColumns<Target, NormalizeDdlColumns<Columns>>
4924
+ > = ValidateTargetColumnInput<Target, Columns>
4568
4925
 
4569
4926
  type ConflictTargetInput<
4570
4927
  Target extends MutationTargetLike,
@@ -4585,6 +4942,11 @@ type ConflictTargetInput<
4585
4942
  readonly constraint?: string
4586
4943
  }>)
4587
4944
 
4945
+ type ConflictConstraintNameConstraint<Target> =
4946
+ Target extends { readonly constraint: infer Constraint extends string }
4947
+ ? { readonly constraint: NonEmptyStringInput<Constraint> }
4948
+ : unknown
4949
+
4588
4950
  type ConflictActionInput<
4589
4951
  Target extends MutationTargetLike,
4590
4952
  Dialect extends string,
@@ -4594,6 +4956,55 @@ type ConflictActionInput<
4594
4956
  readonly where?: Dialect extends "postgres" ? PredicateInput : MysqlConflictWhereError<PredicateInput>
4595
4957
  }
4596
4958
 
4959
+ type ConflictActionUpdateNonEmptyConstraint<Options> =
4960
+ Options extends { readonly update: infer Values }
4961
+ ? UpdateValuesNonEmptyConstraint<Values>
4962
+ : unknown
4963
+
4964
+ type ConflictTargetPredicate<Target> =
4965
+ Target extends { readonly where?: infer Predicate } ? Extract<Predicate, PredicateInput> : never
4966
+
4967
+ type ConflictActionPredicate<Options> =
4968
+ Options extends { readonly where?: infer Predicate } ? Extract<Predicate, PredicateInput> : never
4969
+
4970
+ type MutationDialectFromValues<
4971
+ Values extends Record<string, unknown>,
4972
+ Dialect extends string,
4973
+ TextDb extends Expression.DbType.Any,
4974
+ NumericDb extends Expression.DbType.Any,
4975
+ BoolDb extends Expression.DbType.Any,
4976
+ TimestampDb extends Expression.DbType.Any,
4977
+ NullDb extends Expression.DbType.Any
4978
+ > = {
4979
+ [K in keyof Values]: Values[K] extends ExpressionInput
4980
+ ? DialectOfDialectInput<Values[K], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
4981
+ : never
4982
+ }[keyof Values]
4983
+
4984
+ type ConflictRequired<
4985
+ UpdateValues extends MutationInputOf<any> | undefined,
4986
+ Options,
4987
+ ConflictTarget
4988
+ > =
4989
+ | MutationRequiredFromValues<Exclude<UpdateValues, undefined>>
4990
+ | RequiredFromInput<ConflictActionPredicate<Options>>
4991
+ | RequiredFromInput<ConflictTargetPredicate<ConflictTarget>>
4992
+
4993
+ type ConflictDialect<
4994
+ UpdateValues extends MutationInputOf<any> | undefined,
4995
+ Options,
4996
+ ConflictTarget,
4997
+ Dialect extends string,
4998
+ TextDb extends Expression.DbType.Any,
4999
+ NumericDb extends Expression.DbType.Any,
5000
+ BoolDb extends Expression.DbType.Any,
5001
+ TimestampDb extends Expression.DbType.Any,
5002
+ NullDb extends Expression.DbType.Any
5003
+ > =
5004
+ | MutationDialectFromValues<Exclude<UpdateValues, undefined>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5005
+ | DialectOfDialectInput<ConflictActionPredicate<Options>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5006
+ | DialectOfDialectInput<ConflictTargetPredicate<ConflictTarget>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5007
+
4597
5008
  type MergeWhenMatchedDelete<
4598
5009
  Predicate extends PredicateInput | undefined = undefined
4599
5010
  > = {
@@ -4621,16 +5032,33 @@ type MergeWhenNotMatched<
4621
5032
  readonly predicate?: Predicate
4622
5033
  }
4623
5034
 
5035
+ type MergeMatchedOption<
5036
+ Target extends MutationTargetLike,
5037
+ MatchedValues extends MutationInputOf<Table.UpdateOf<Target>>,
5038
+ MatchedPredicate extends PredicateInput | undefined = undefined
5039
+ > = MergeWhenMatchedDelete<MatchedPredicate> | MergeWhenMatchedUpdate<Target, MatchedValues, MatchedPredicate>
5040
+
5041
+ type MergeNotMatchedOption<
5042
+ Target extends MutationTargetLike,
5043
+ InsertValues extends MutationInputOf<Table.InsertOf<Target>>,
5044
+ NotMatchedPredicate extends PredicateInput | undefined = undefined
5045
+ > = MergeWhenNotMatched<Target, InsertValues, NotMatchedPredicate>
5046
+
4624
5047
  type MergeOptions<
4625
5048
  Target extends MutationTargetLike,
4626
5049
  MatchedValues extends MutationInputOf<Table.UpdateOf<Target>>,
4627
5050
  InsertValues extends MutationInputOf<Table.InsertOf<Target>>,
4628
5051
  MatchedPredicate extends PredicateInput | undefined = undefined,
4629
5052
  NotMatchedPredicate extends PredicateInput | undefined = undefined
4630
- > = {
4631
- readonly whenMatched?: MergeWhenMatchedDelete<MatchedPredicate> | MergeWhenMatchedUpdate<Target, MatchedValues, MatchedPredicate>
4632
- readonly whenNotMatched?: MergeWhenNotMatched<Target, InsertValues, NotMatchedPredicate>
4633
- }
5053
+ > =
5054
+ | {
5055
+ readonly whenMatched: MergeMatchedOption<Target, MatchedValues, MatchedPredicate>
5056
+ readonly whenNotMatched?: MergeNotMatchedOption<Target, InsertValues, NotMatchedPredicate>
5057
+ }
5058
+ | {
5059
+ readonly whenMatched?: MergeMatchedOption<Target, MatchedValues, MatchedPredicate>
5060
+ readonly whenNotMatched: MergeNotMatchedOption<Target, InsertValues, NotMatchedPredicate>
5061
+ }
4634
5062
 
4635
5063
  type RequireSelectStatement<PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>> =
4636
5064
  StatementOfPlan<PlanValue> extends "select" ? unknown : never
@@ -4662,6 +5090,38 @@ type MutationOrderLimitSupported<PlanValue extends QueryPlan<any, any, any, any,
4662
5090
  ? StatementOfPlan<PlanValue> extends "update" | "delete" ? unknown : never
4663
5091
  : never
4664
5092
 
5093
+ type MutationTargetTupleDialectConstraint<
5094
+ Targets extends MutationTargetTuple,
5095
+ Dialect extends string
5096
+ > = Exclude<TableDialectOf<Targets[number]>, Dialect | "standard"> extends never ? unknown : never
5097
+
5098
+ type DuplicateMutationTargetSourceName<
5099
+ Targets extends readonly MutationTargetLike[],
5100
+ Seen extends string = never
5101
+ > = Targets extends readonly [infer Head extends MutationTargetLike, ...infer Tail extends readonly MutationTargetLike[]]
5102
+ ? SourceNameOf<Head> extends infer Name extends string
5103
+ ? string extends Name
5104
+ ? DuplicateMutationTargetSourceName<Tail, Seen>
5105
+ : Name extends Seen
5106
+ ? Name
5107
+ : DuplicateMutationTargetSourceName<Tail, Seen | Name>
5108
+ : never
5109
+ : never
5110
+
5111
+ type MutationTargetTupleDuplicateNameError<Name extends string> = {
5112
+ readonly __effect_qb_error__: "effect-qb: mutation target source names must be unique"
5113
+ readonly __effect_qb_duplicate_source_name__: Name
5114
+ readonly __effect_qb_hint__: "Alias duplicate mutation targets with Table.alias(...)"
5115
+ }
5116
+
5117
+ type MutationTargetTupleUniqueNamesConstraint<
5118
+ Targets extends MutationTargetTuple
5119
+ > = DuplicateMutationTargetSourceName<Targets> extends infer Name extends string
5120
+ ? [Name] extends [never]
5121
+ ? unknown
5122
+ : MutationTargetTupleDuplicateNameError<Name>
5123
+ : unknown
5124
+
4665
5125
  type MutationRequiredFromValues<Values extends Record<string, unknown>> = {
4666
5126
  [K in keyof Values]: Values[K] extends Expression.Any ? RequiredFromDependencies<DependenciesOf<Values[K]>> : never
4667
5127
  }[keyof Values]
@@ -4675,6 +5135,59 @@ type NestedMutationRequiredFromValues<Values> =
4675
5135
  }[keyof Values]
4676
5136
  : never
4677
5137
 
5138
+ type NestedMutationDialectFromValues<
5139
+ Values,
5140
+ Dialect extends string,
5141
+ TextDb extends Expression.DbType.Any,
5142
+ NumericDb extends Expression.DbType.Any,
5143
+ BoolDb extends Expression.DbType.Any,
5144
+ TimestampDb extends Expression.DbType.Any,
5145
+ NullDb extends Expression.DbType.Any
5146
+ > =
5147
+ Values extends ExpressionInput
5148
+ ? DialectOfDialectInput<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5149
+ : Values extends Record<string, unknown>
5150
+ ? {
5151
+ [K in keyof Values]: NestedMutationDialectFromValues<Values[K], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5152
+ }[keyof Values]
5153
+ : never
5154
+
5155
+ type KnownMutationDialectFromValues<
5156
+ Values,
5157
+ Dialect extends string,
5158
+ TextDb extends Expression.DbType.Any,
5159
+ NumericDb extends Expression.DbType.Any,
5160
+ BoolDb extends Expression.DbType.Any,
5161
+ TimestampDb extends Expression.DbType.Any,
5162
+ NullDb extends Expression.DbType.Any
5163
+ > = NestedMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb> extends infer Current
5164
+ ? Current extends string
5165
+ ? string extends Current ? never : Current
5166
+ : never
5167
+ : never
5168
+
5169
+ type KnownIncompatibleMutationDialectFromValues<
5170
+ Values,
5171
+ Dialect extends string,
5172
+ TextDb extends Expression.DbType.Any,
5173
+ NumericDb extends Expression.DbType.Any,
5174
+ BoolDb extends Expression.DbType.Any,
5175
+ TimestampDb extends Expression.DbType.Any,
5176
+ NullDb extends Expression.DbType.Any
5177
+ > = Exclude<KnownMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>, Dialect | "standard">
5178
+
5179
+ type MutationValuesDialectConstraint<
5180
+ Values,
5181
+ Dialect extends string,
5182
+ TextDb extends Expression.DbType.Any,
5183
+ NumericDb extends Expression.DbType.Any,
5184
+ BoolDb extends Expression.DbType.Any,
5185
+ TimestampDb extends Expression.DbType.Any,
5186
+ NullDb extends Expression.DbType.Any
5187
+ > = KnownIncompatibleMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb> extends never
5188
+ ? unknown
5189
+ : never
5190
+
4678
5191
  type MutationAssignments<Shape extends Record<string, unknown>> = {
4679
5192
  readonly [K in keyof Shape]: QueryAst.AssignmentClause
4680
5193
  }
@@ -4708,12 +5221,40 @@ type InsertDirectSource =
4708
5221
 
4709
5222
  type FromInput = SourceLike | InsertDirectSource
4710
5223
 
5224
+ type SourceDialectConstraint<
5225
+ CurrentSource extends SourceLike,
5226
+ Dialect extends string
5227
+ > = [SourceDialectOf<CurrentSource>] extends [never]
5228
+ ? unknown
5229
+ : Exclude<SourceDialectOf<CurrentSource>, Dialect | "standard"> extends never
5230
+ ? unknown
5231
+ : Dialect extends "standard"
5232
+ ? unknown
5233
+ : never
5234
+
5235
+ type SourceRequirementConstraint<
5236
+ PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>,
5237
+ CurrentSource extends SourceLike
5238
+ > = [SourceRequiredOf<CurrentSource>] extends [never]
5239
+ ? unknown
5240
+ : Exclude<SourceRequiredOf<CurrentSource>, ScopedNamesOfPlan<PlanValue>> extends never
5241
+ ? unknown
5242
+ : SourceRequirementError<CurrentSource>
5243
+
4711
5244
  type SelectFromConstraint<
4712
5245
  PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>,
4713
5246
  CurrentSource extends SourceLike
4714
5247
  > =
4715
5248
  RequireSelectStatement<PlanValue> &
4716
- (SourceNameOf<CurrentSource> extends OutstandingOfPlan<PlanValue> ? unknown : never) &
5249
+ (
5250
+ SourceNameOf<CurrentSource> extends OutstandingOfPlan<PlanValue>
5251
+ ? unknown
5252
+ : [OutstandingOfPlan<PlanValue>] extends [never]
5253
+ ? [ScopedNamesOfPlan<PlanValue>] extends [never]
5254
+ ? unknown
5255
+ : never
5256
+ : never
5257
+ ) &
4717
5258
  (SourceRequiredOf<CurrentSource> extends never ? unknown : SourceRequirementError<CurrentSource>)
4718
5259
 
4719
5260
  type UpdateFromConstraint<
@@ -4730,7 +5271,7 @@ type InsertFromConstraint<
4730
5271
  Dialect extends string
4731
5272
  > =
4732
5273
  RequirePendingInsertStatement<PlanValue> &
4733
- (InsertSourceOfPlanInput<PlanValue, CurrentSource, Dialect> extends CurrentSource
5274
+ (CurrentSource extends InsertSourceOfPlanInput<PlanValue, CurrentSource, Dialect>
4734
5275
  ? unknown
4735
5276
  : InsertSourceOfPlanInput<PlanValue, CurrentSource, Dialect>)
4736
5277
 
@@ -4784,12 +5325,12 @@ type InsertFromResult<
4784
5325
  Dialect extends string
4785
5326
  > = QueryPlan<
4786
5327
  SelectionOfPlan<PlanValue>,
4787
- Exclude<InsertSourceRequired<CurrentSource>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5328
+ InsertSourceRequired<CurrentSource>,
4788
5329
  AvailableOfPlan<PlanValue>,
4789
- PlanDialectOf<PlanValue>,
5330
+ PlanDialectOf<PlanValue> | InsertSourceDialect<CurrentSource>,
4790
5331
  GroupedOfPlan<PlanValue>,
4791
5332
  ScopedNamesOfPlan<PlanValue>,
4792
- Exclude<InsertSourceRequired<CurrentSource>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5333
+ InsertSourceRequired<CurrentSource>,
4793
5334
  AssumptionsOfPlan<PlanValue>,
4794
5335
  CurrentSource extends QueryPlan<any, any, any, any, any, any, any, any, any, any>
4795
5336
  ? MergeCapabilities<CapabilitiesOfPlan<PlanValue>, CapabilitiesOfPlan<CurrentSource>>
@@ -4806,15 +5347,17 @@ type FromPlanConstraint<
4806
5347
  Dialect extends string
4807
5348
  > =
4808
5349
  CurrentSource extends SourceLike
4809
- ? StatementOfPlan<PlanValue> extends "select"
4810
- ? SelectFromConstraint<PlanValue, CurrentSource>
4811
- : StatementOfPlan<PlanValue> extends "update"
4812
- ? UpdateFromConstraint<PlanValue, CurrentSource>
4813
- : StatementOfPlan<PlanValue> extends "insert"
4814
- ? CurrentSource extends AnyValuesSource | AnyUnnestSource
4815
- ? InsertFromConstraint<PlanValue, CurrentSource, Dialect>
4816
- : never
4817
- : never
5350
+ ? SourceDialectConstraint<CurrentSource, Dialect> & (
5351
+ StatementOfPlan<PlanValue> extends "select"
5352
+ ? SelectFromConstraint<PlanValue, CurrentSource>
5353
+ : StatementOfPlan<PlanValue> extends "update"
5354
+ ? UpdateFromConstraint<PlanValue, CurrentSource>
5355
+ : StatementOfPlan<PlanValue> extends "insert"
5356
+ ? CurrentSource extends AnyValuesSource | AnyUnnestSource
5357
+ ? InsertFromConstraint<PlanValue, CurrentSource, Dialect>
5358
+ : never
5359
+ : never
5360
+ )
4818
5361
  : CurrentSource extends InsertDirectSource
4819
5362
  ? StatementOfPlan<PlanValue> extends "insert"
4820
5363
  ? InsertFromConstraint<PlanValue, CurrentSource, Dialect>
@@ -4869,7 +5412,10 @@ export type PublicStructuredFromResult<
4869
5412
  Exclude<OutstandingOfPlan<PlanValue>, SourceNameOf<CurrentSource>>,
4870
5413
  AssumptionsOfPlan<PlanValue>,
4871
5414
  MergeCapabilities<CapabilitiesOfPlan<PlanValue>, SourceCapabilitiesOf<CurrentSource>>,
4872
- StatementOfPlan<PlanValue>
5415
+ StatementOfPlan<PlanValue>,
5416
+ MutationTargetOfPlan<PlanValue>,
5417
+ InsertSourceStateOfPlan<PlanValue>,
5418
+ FactsOfPlan<PlanValue>
4873
5419
  >
4874
5420
  : StatementOfPlan<PlanValue> extends "update"
4875
5421
  ? QueryPlan<
@@ -4882,7 +5428,10 @@ export type PublicStructuredFromResult<
4882
5428
  Exclude<OutstandingOfPlan<PlanValue>, SourceNameOf<CurrentSource>>,
4883
5429
  AssumptionsOfPlan<PlanValue>,
4884
5430
  MergeCapabilities<CapabilitiesOfPlan<PlanValue>, SourceCapabilitiesOf<CurrentSource>>,
4885
- StatementOfPlan<PlanValue>
5431
+ StatementOfPlan<PlanValue>,
5432
+ MutationTargetOfPlan<PlanValue>,
5433
+ InsertSourceStateOfPlan<PlanValue>,
5434
+ FactsOfPlan<PlanValue>
4886
5435
  >
4887
5436
  : StatementOfPlan<PlanValue> extends "insert"
4888
5437
  ? CurrentSource extends AnyValuesSource | AnyUnnestSource
@@ -4890,7 +5439,7 @@ export type PublicStructuredFromResult<
4890
5439
  SelectionOfPlan<PlanValue>,
4891
5440
  never,
4892
5441
  AvailableOfPlan<PlanValue>,
4893
- PlanDialectOf<PlanValue>,
5442
+ PlanDialectOf<PlanValue> | SourceDialectOf<CurrentSource>,
4894
5443
  GroupedOfPlan<PlanValue>,
4895
5444
  ScopedNamesOfPlan<PlanValue>,
4896
5445
  never,
@@ -4898,7 +5447,8 @@ export type PublicStructuredFromResult<
4898
5447
  CapabilitiesOfPlan<PlanValue>,
4899
5448
  StatementOfPlan<PlanValue>,
4900
5449
  MutationTargetOfPlan<PlanValue>,
4901
- "ready"
5450
+ "ready",
5451
+ FactsOfPlan<PlanValue>
4902
5452
  >
4903
5453
  : FromPlanResult<PlanValue, CurrentSource, Dialect>
4904
5454
  : FromPlanResult<PlanValue, CurrentSource, Dialect>
@@ -4944,7 +5494,7 @@ type AsCurriedResult<
4944
5494
  function as<
4945
5495
  Alias extends string
4946
5496
  >(
4947
- alias: Alias
5497
+ alias: LiteralStringInput<Alias>
4948
5498
  ): <Value extends AsCurriedInput<Dialect>>(
4949
5499
  value: Value
4950
5500
  ) => AsCurriedResult<Value, Alias, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
@@ -4953,21 +5503,21 @@ type AsCurriedResult<
4953
5503
  Alias extends string
4954
5504
  >(
4955
5505
  value: Value,
4956
- alias: Alias
4957
- ): DialectAsExpression<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5506
+ alias: LiteralStringInput<Alias>
5507
+ ): ProjectionAliasedExpression<DialectAsExpression<Value, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>, Alias>
4958
5508
  function as<
4959
5509
  Rows extends ValuesRowsInput,
4960
5510
  Alias extends string
4961
5511
  >(
4962
5512
  value: ValuesInput<
4963
5513
  Rows,
4964
- ValuesOutputShape<Rows[0], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5514
+ ValuesOutputShape<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4965
5515
  Dialect
4966
5516
  >,
4967
- alias: Alias
5517
+ alias: LiteralStringInput<Alias>
4968
5518
  ): ValuesSource<
4969
5519
  Rows,
4970
- ValuesOutputShape<Rows[0], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5520
+ ValuesOutputShape<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
4971
5521
  Alias,
4972
5522
  Dialect
4973
5523
  >
@@ -4975,12 +5525,12 @@ type AsCurriedResult<
4975
5525
  PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>,
4976
5526
  Alias extends string
4977
5527
  >(
4978
- value: CompletePlan<PlanValue>,
4979
- alias: Alias
5528
+ value: DerivedTableCompatiblePlan<PlanValue>,
5529
+ alias: LiteralStringInput<Alias>
4980
5530
  ): DerivedSource<PlanValue, Alias>
4981
5531
  function as(valueOrAlias: unknown, alias?: string): unknown {
4982
5532
  if (alias === undefined) {
4983
- return (value: unknown) => as(value as any, valueOrAlias as string)
5533
+ return (value: unknown) => as(value as any, valueOrAlias as never)
4984
5534
  }
4985
5535
  const resolvedAlias = alias
4986
5536
  const value = valueOrAlias
@@ -5020,20 +5570,20 @@ type AsCurriedResult<
5020
5570
  function with_<
5021
5571
  Alias extends string
5022
5572
  >(
5023
- alias: Alias
5573
+ alias: LiteralStringInput<Alias>
5024
5574
  ): <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
5025
- value: CompletePlan<PlanValue>
5575
+ value: MysqlCteCompatiblePlan<PlanValue>
5026
5576
  ) => import("../../internal/query.js").CteSource<PlanValue, Alias>
5027
5577
  function with_<
5028
5578
  PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>,
5029
5579
  Alias extends string
5030
5580
  >(
5031
- value: CompletePlan<PlanValue>,
5032
- alias: Alias
5581
+ value: MysqlCteCompatiblePlan<PlanValue>,
5582
+ alias: LiteralStringInput<Alias>
5033
5583
  ): import("../../internal/query.js").CteSource<PlanValue, Alias>
5034
5584
  function with_(valueOrAlias: unknown, alias?: string): unknown {
5035
5585
  if (alias === undefined) {
5036
- return (value: unknown) => with_(value as any, valueOrAlias as string)
5586
+ return (value: unknown) => with_(value as any, valueOrAlias as never)
5037
5587
  }
5038
5588
  return makeCteSource(
5039
5589
  valueOrAlias as CompletePlan<QueryPlan<any, any, any, any, any, any, any, any, any, any>>,
@@ -5044,20 +5594,20 @@ type AsCurriedResult<
5044
5594
  function withRecursive_<
5045
5595
  Alias extends string
5046
5596
  >(
5047
- alias: Alias
5597
+ alias: LiteralStringInput<Alias>
5048
5598
  ): <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
5049
- value: CompletePlan<PlanValue>
5599
+ value: MysqlCteCompatiblePlan<PlanValue>
5050
5600
  ) => import("../../internal/query.js").CteSource<PlanValue, Alias>
5051
5601
  function withRecursive_<
5052
5602
  PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>,
5053
5603
  Alias extends string
5054
5604
  >(
5055
- value: CompletePlan<PlanValue>,
5056
- alias: Alias
5605
+ value: MysqlCteCompatiblePlan<PlanValue>,
5606
+ alias: LiteralStringInput<Alias>
5057
5607
  ): import("../../internal/query.js").CteSource<PlanValue, Alias>
5058
5608
  function withRecursive_(valueOrAlias: unknown, alias?: string): unknown {
5059
5609
  if (alias === undefined) {
5060
- return (value: unknown) => withRecursive_(value as any, valueOrAlias as string)
5610
+ return (value: unknown) => withRecursive_(value as any, valueOrAlias as never)
5061
5611
  }
5062
5612
  return makeCteSource(
5063
5613
  valueOrAlias as CompletePlan<QueryPlan<any, any, any, any, any, any, any, any, any, any>>,
@@ -5069,20 +5619,20 @@ type AsCurriedResult<
5069
5619
  function lateral<
5070
5620
  Alias extends string
5071
5621
  >(
5072
- alias: Alias
5622
+ alias: LiteralStringInput<Alias>
5073
5623
  ): <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
5074
- value: PlanValue
5624
+ value: LateralSourceCompatiblePlan<PlanValue>
5075
5625
  ) => import("../../internal/query.js").LateralSource<PlanValue, Alias>
5076
5626
  function lateral<
5077
5627
  PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>,
5078
5628
  Alias extends string
5079
5629
  >(
5080
- value: PlanValue,
5081
- alias: Alias
5630
+ value: LateralSourceCompatiblePlan<PlanValue>,
5631
+ alias: LiteralStringInput<Alias>
5082
5632
  ): import("../../internal/query.js").LateralSource<PlanValue, Alias>
5083
5633
  function lateral(valueOrAlias: unknown, alias?: string): unknown {
5084
5634
  if (alias === undefined) {
5085
- return (value: unknown) => lateral(value as any, valueOrAlias as string)
5635
+ return (value: unknown) => lateral(value as any, valueOrAlias as never)
5086
5636
  }
5087
5637
  return makeLateralSource(
5088
5638
  valueOrAlias as QueryPlan<any, any, any, any, any, any, any, any, any, any>,
@@ -5094,9 +5644,11 @@ type AsCurriedResult<
5094
5644
  Rows extends ValuesRowsInput
5095
5645
  >(
5096
5646
  rows: Rows
5647
+ & ValuesRowsShapeInput<Rows>
5648
+ & ValuesRowsDialectInput<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5097
5649
  ) => ValuesInput<
5098
5650
  Rows,
5099
- ValuesOutputShape<Rows[0], Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5651
+ ValuesOutputShape<Rows, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5100
5652
  Dialect
5101
5653
  >
5102
5654
 
@@ -5104,8 +5656,10 @@ type AsCurriedResult<
5104
5656
  Columns extends UnnestColumnsInput,
5105
5657
  Alias extends string
5106
5658
  >(
5107
- columns: Columns,
5108
- alias: Alias
5659
+ columns: Columns
5660
+ & UnnestColumnsShapeInput<Columns>
5661
+ & UnnestColumnsDialectInput<Columns, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5662
+ alias: LiteralStringInput<Alias>
5109
5663
  ) => UnnestSource<
5110
5664
  UnnestOutputShape<Columns, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5111
5665
  Alias,
@@ -5118,10 +5672,10 @@ type AsCurriedResult<
5118
5672
  Step extends NumericExpressionInput | undefined = undefined,
5119
5673
  Alias extends string = "series"
5120
5674
  >(
5121
- start: Start,
5122
- stop: Stop,
5123
- step?: Step,
5124
- alias?: Alias
5675
+ start: Start & NumericExpressionDialectInput<Start, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5676
+ stop: Stop & NumericExpressionDialectInput<Stop, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5677
+ step?: Step & (Step extends NumericExpressionInput ? NumericExpressionDialectInput<Step, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb> : unknown),
5678
+ alias?: LiteralStringInput<Alias>
5125
5679
  ) => Dialect extends "postgres"
5126
5680
  ? TableFunctionSource<
5127
5681
  GenerateSeriesOutputShape<Start, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
@@ -5131,8 +5685,45 @@ type AsCurriedResult<
5131
5685
  >
5132
5686
  : GenerateSeriesUnsupportedError<Dialect>
5133
5687
 
5134
- export type SelectApi = <Selection extends SelectionShape>(
5135
- selection: Selection
5688
+ type SelectSelectionNonEmptyError<Selection> = Selection & {
5689
+ readonly __effect_qb_error__: "effect-qb: mysql select statements require at least one selected expression"
5690
+ }
5691
+
5692
+ type SelectionRootObjectError<Selection> = Selection & {
5693
+ readonly __effect_qb_error__: "effect-qb: selections must be projection objects"
5694
+ readonly __effect_qb_hint__: "Use select({ value: expression }) or returning({ value: expression })"
5695
+ }
5696
+
5697
+ type SelectionRootObjectConstraint<Selection> =
5698
+ Selection extends Expression.Any ? SelectionRootObjectError<Selection> : unknown
5699
+
5700
+ type SelectionNestedEmptyError<Selection> = Selection & {
5701
+ readonly __effect_qb_error__: "effect-qb: projection objects cannot contain empty nested selections"
5702
+ }
5703
+
5704
+ type SelectionHasEmptyNestedObject<Selection, IsRoot extends boolean> =
5705
+ Selection extends Expression.Any
5706
+ ? false
5707
+ : Selection extends Record<string, any>
5708
+ ? [Extract<keyof Selection, string>] extends [never]
5709
+ ? IsRoot extends true ? false : true
5710
+ : true extends {
5711
+ [K in Extract<keyof Selection, string>]: SelectionHasEmptyNestedObject<Selection[K], false>
5712
+ }[Extract<keyof Selection, string>]
5713
+ ? true
5714
+ : false
5715
+ : false
5716
+
5717
+ type SelectionNestedNonEmptyConstraint<Selection> =
5718
+ SelectionHasEmptyNestedObject<Selection, true> extends true ? SelectionNestedEmptyError<Selection> : unknown
5719
+
5720
+ type SelectSelectionNonEmptyConstraint<Selection> =
5721
+ [Extract<keyof Selection, string>] extends [never]
5722
+ ? SelectSelectionNonEmptyError<Selection>
5723
+ : unknown
5724
+
5725
+ export type SelectApi = <const Selection extends SelectionShape>(
5726
+ selection: Selection & SelectionRootObjectConstraint<Selection> & SelectionNestedNonEmptyConstraint<Selection> & SelectSelectionNonEmptyConstraint<Selection> & SelectionProjectionAliasCollisionConstraint<Selection>
5136
5727
  ) => QueryPlan<
5137
5728
  Selection,
5138
5729
  ExtractRequired<Selection>,
@@ -5169,7 +5760,7 @@ type AsCurriedResult<
5169
5760
  getQueryState,
5170
5761
  currentRequiredList,
5171
5762
  dedupeGroupedExpressions
5172
- }) as {
5763
+ }) as unknown as {
5173
5764
  readonly values: ValuesApi
5174
5765
  readonly unnest: UnnestApi
5175
5766
  readonly generateSeries: GenerateSeriesApi
@@ -5191,7 +5782,10 @@ type AsCurriedResult<
5191
5782
  never,
5192
5783
  TrueFormula,
5193
5784
  CapabilitiesOfPlan<LeftPlanValue> | CapabilitiesOfPlan<RightPlanValue>,
5194
- "set"
5785
+ "set",
5786
+ any,
5787
+ "ready",
5788
+ CommonSetFacts<LeftPlanValue, RightPlanValue>
5195
5789
  >
5196
5790
 
5197
5791
  type SetOperationApi = <
@@ -5259,10 +5853,10 @@ type AsCurriedResult<
5259
5853
  keyof AvailableOfPlan<PlanValue> extends never ? never : unknown
5260
5854
  ) & (
5261
5855
  SourceNameOf<CurrentTable> extends ScopedNamesOfPlan<PlanValue> ? never : unknown
5262
- )
5856
+ ) & SourceRequirementConstraint<PlanValue, CurrentTable> & SourceDialectConstraint<CurrentTable, Dialect>
5263
5857
  ) => QueryPlan<
5264
5858
  SelectionOfPlan<PlanValue>,
5265
- AddJoinRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, never, "cross">,
5859
+ AddJoinRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, never, "cross", SourceRequiredOf<CurrentTable>>,
5266
5860
  AddAvailable<
5267
5861
  AvailableOfPlan<PlanValue>,
5268
5862
  SourceNameOf<CurrentTable>,
@@ -5273,10 +5867,13 @@ type AsCurriedResult<
5273
5867
  PlanDialectOf<PlanValue> | SourceDialectOf<CurrentTable>,
5274
5868
  GroupedOfPlan<PlanValue>,
5275
5869
  ScopedNamesOfPlan<PlanValue> | SourceNameOf<CurrentTable>,
5276
- AddJoinRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, never, "cross">,
5870
+ AddJoinRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, never, "cross", SourceRequiredOf<CurrentTable>>,
5277
5871
  AssumptionsOfPlan<PlanValue>,
5278
5872
  MergeCapabilities<CapabilitiesOfPlan<PlanValue>, SourceCapabilitiesOf<CurrentTable>>,
5279
- StatementOfPlan<PlanValue>
5873
+ StatementOfPlan<PlanValue>,
5874
+ MutationTargetOfPlan<PlanValue>,
5875
+ InsertSourceStateOfPlan<PlanValue>,
5876
+ FactsOfPlan<PlanValue>
5280
5877
  >
5281
5878
 
5282
5879
  type JoinApi = <
@@ -5293,10 +5890,10 @@ type AsCurriedResult<
5293
5890
  keyof AvailableOfPlan<PlanValue> extends never ? never : unknown
5294
5891
  ) & (
5295
5892
  SourceNameOf<CurrentTable> extends ScopedNamesOfPlan<PlanValue> ? never : unknown
5296
- )
5893
+ ) & SourceRequirementConstraint<PlanValue, CurrentTable> & SourceDialectConstraint<CurrentTable, Dialect>
5297
5894
  ) => QueryPlan<
5298
5895
  SelectionOfPlan<PlanValue>,
5299
- AddJoinRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind>,
5896
+ AddJoinRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind, SourceRequiredOf<CurrentTable>>,
5300
5897
  AvailableAfterJoin<
5301
5898
  AvailableOfPlan<PlanValue>,
5302
5899
  SourceNameOf<CurrentTable>,
@@ -5307,7 +5904,7 @@ type AsCurriedResult<
5307
5904
  PlanDialectOf<PlanValue> | SourceDialectOf<CurrentTable> | DialectOfDialectInput<Predicate, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5308
5905
  GroupedOfPlan<PlanValue>,
5309
5906
  ScopedNamesOfPlan<PlanValue> | SourceNameOf<CurrentTable>,
5310
- AddJoinRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind>,
5907
+ AddJoinRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind, SourceRequiredOf<CurrentTable>>,
5311
5908
  PlanAssumptionsAfterJoin<PlanValue, Predicate, Kind, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5312
5909
  MergeCapabilities<CapabilitiesOfPlan<PlanValue>, SourceCapabilitiesOf<CurrentTable>>,
5313
5910
  StatementOfPlan<PlanValue>,
@@ -5328,10 +5925,10 @@ type AsCurriedResult<
5328
5925
  keyof AvailableOfPlan<PlanValue> extends never ? never : unknown
5329
5926
  ) & (
5330
5927
  SourceNameOf<CurrentTable> extends ScopedNamesOfPlan<PlanValue> ? never : unknown
5331
- )
5928
+ ) & SourceRequirementConstraint<PlanValue, CurrentTable> & SourceDialectConstraint<CurrentTable, Dialect>
5332
5929
  ) => QueryPlan<
5333
5930
  SelectionOfPlan<PlanValue>,
5334
- AddJoinRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind>,
5931
+ AddJoinRequired<RequiredOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind, SourceRequiredOf<CurrentTable>>,
5335
5932
  AvailableAfterJoin<
5336
5933
  AvailableOfPlan<PlanValue>,
5337
5934
  SourceNameOf<CurrentTable>,
@@ -5342,7 +5939,7 @@ type AsCurriedResult<
5342
5939
  PlanDialectOf<PlanValue> | SourceDialectOf<CurrentTable> | DialectOfDialectInput<Predicate, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5343
5940
  GroupedOfPlan<PlanValue>,
5344
5941
  ScopedNamesOfPlan<PlanValue> | SourceNameOf<CurrentTable>,
5345
- AddJoinRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind>,
5942
+ AddJoinRequired<OutstandingOfPlan<PlanValue>, AvailableOfPlan<PlanValue>, SourceNameOf<CurrentTable>, Predicate, Kind, SourceRequiredOf<CurrentTable>>,
5346
5943
  PlanAssumptionsAfterJoin<PlanValue, Predicate, Kind, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5347
5944
  MergeCapabilities<CapabilitiesOfPlan<PlanValue>, SourceCapabilitiesOf<CurrentTable>>,
5348
5945
  StatementOfPlan<PlanValue>,
@@ -5351,6 +5948,8 @@ type AsCurriedResult<
5351
5948
  PlanFactsAfterJoin<PlanValue, Predicate, Kind, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5352
5949
  >
5353
5950
 
5951
+ type FullJoinApi = Dialect extends "postgres" ? BinaryJoinApi<"full"> : FullJoinUnsupportedError<Dialect>
5952
+
5354
5953
  type OrderByApi = <Value extends ExpressionInput>(
5355
5954
  value: Value,
5356
5955
  direction?: OrderDirection
@@ -5548,7 +6147,7 @@ type AsCurriedResult<
5548
6147
 
5549
6148
  const rightJoin = ((table, on) => (join as any)("right", table, on)) as BinaryJoinApi<"right">
5550
6149
 
5551
- const fullJoin = ((table, on) => (join as any)("full", table, on)) as BinaryJoinApi<"full">
6150
+ const fullJoin = ((table: any, on: any) => (join as any)("full", table, on)) as unknown as FullJoinApi
5552
6151
 
5553
6152
  const distinctOn = {
5554
6153
  __effect_qb_error__: "effect-qb: distinctOn(...) is only supported by the postgres dialect",
@@ -5577,26 +6176,39 @@ type AsCurriedResult<
5577
6176
  FactsOfPlan<PlanValue>
5578
6177
  >
5579
6178
 
5580
- type ReturningApi = <Selection extends SelectionShape>(
5581
- selection: Selection
5582
- ) =>
5583
- <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
5584
- plan: PlanValue & RequireMutationStatement<PlanValue>
5585
- ) => QueryPlan<
5586
- Selection,
5587
- Exclude<RequiredOfPlan<PlanValue> | ExtractRequired<Selection>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5588
- AvailableOfPlan<PlanValue>,
5589
- PlanDialectOf<PlanValue> | ExtractDialect<Selection>,
5590
- GroupedOfPlan<PlanValue>,
5591
- ScopedNamesOfPlan<PlanValue>,
5592
- Exclude<OutstandingOfPlan<PlanValue> | ExtractRequired<Selection>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5593
- AssumptionsOfPlan<PlanValue>,
5594
- CapabilitiesOfPlan<PlanValue>,
5595
- StatementOfPlan<PlanValue>,
5596
- MutationTargetOfPlan<PlanValue>,
5597
- InsertSourceStateOfPlan<PlanValue>,
5598
- FactsOfPlan<PlanValue>
5599
- >
6179
+ type ReturningSelectionNonEmptyError<Selection> = Selection & {
6180
+ readonly __effect_qb_error__: "effect-qb: returning(...) requires at least one selected expression"
6181
+ }
6182
+
6183
+ type ReturningSelectionNonEmptyConstraint<Selection> =
6184
+ Selection extends Expression.Any
6185
+ ? unknown
6186
+ : [Extract<keyof Selection, string>] extends [never]
6187
+ ? ReturningSelectionNonEmptyError<Selection>
6188
+ : unknown
6189
+
6190
+ type ReturningApi = Dialect extends "postgres"
6191
+ ? <const Selection extends SelectionShape>(
6192
+ selection: Selection & SelectionRootObjectConstraint<Selection> & SelectionNestedNonEmptyConstraint<Selection> & ReturningSelectionNonEmptyConstraint<Selection> & SelectionProjectionAliasCollisionConstraint<Selection>
6193
+ ) =>
6194
+ <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
6195
+ plan: PlanValue & RequireMutationStatement<PlanValue>
6196
+ ) => QueryPlan<
6197
+ Selection,
6198
+ Exclude<RequiredOfPlan<PlanValue> | ExtractRequired<Selection>, AvailableNames<AvailableOfPlan<PlanValue>>>,
6199
+ AvailableOfPlan<PlanValue>,
6200
+ PlanDialectOf<PlanValue> | ExtractDialect<Selection>,
6201
+ GroupedOfPlan<PlanValue>,
6202
+ ScopedNamesOfPlan<PlanValue>,
6203
+ Exclude<OutstandingOfPlan<PlanValue> | ExtractRequired<Selection>, AvailableNames<AvailableOfPlan<PlanValue>>>,
6204
+ AssumptionsOfPlan<PlanValue>,
6205
+ CapabilitiesOfPlan<PlanValue>,
6206
+ StatementOfPlan<PlanValue>,
6207
+ MutationTargetOfPlan<PlanValue>,
6208
+ InsertSourceStateOfPlan<PlanValue>,
6209
+ FactsOfPlan<PlanValue>
6210
+ >
6211
+ : ReturningUnsupportedError<Dialect>
5600
6212
 
5601
6213
  export interface InsertApi {
5602
6214
  <Target extends MutationTargetLike>(
@@ -5618,12 +6230,12 @@ type AsCurriedResult<
5618
6230
  >
5619
6231
  <Target extends MutationTargetLike, Values extends Record<string, unknown>>(
5620
6232
  target: Target,
5621
- values: MutationValuesInput<"insert", Target, Values>
6233
+ values: MutationValuesInput<"insert", Target, Values> & MutationValuesDialectConstraint<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5622
6234
  ): QueryPlan<
5623
6235
  {},
5624
6236
  Exclude<MutationRequiredFromValues<Values>, SourceNameOf<Target>>,
5625
6237
  AddAvailable<{}, SourceNameOf<Target>>,
5626
- TableDialectOf<Target>,
6238
+ TableDialectOf<Target> | KnownMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5627
6239
  never,
5628
6240
  SourceNameOf<Target>,
5629
6241
  Exclude<MutationRequiredFromValues<Values>, SourceNameOf<Target>>,
@@ -5645,21 +6257,22 @@ type AsCurriedResult<
5645
6257
  Target extends MutationTargetLike,
5646
6258
  const Columns extends DdlColumnInput,
5647
6259
  UpdateValues extends MutationInputOf<Table.UpdateOf<Target>> | undefined = MutationInputOf<Table.UpdateOf<Target>> | undefined,
5648
- Options extends ConflictActionInput<Target, Dialect, UpdateValues> = ConflictActionInput<Target, Dialect, UpdateValues>
6260
+ Options extends ConflictActionInput<Target, Dialect, UpdateValues> = ConflictActionInput<Target, Dialect, UpdateValues>,
6261
+ const ConflictTarget extends ConflictTargetInput<Target, Dialect, Columns> = ConflictTargetInput<Target, Dialect, Columns>
5649
6262
  >(
5650
- target: ConflictTargetInput<Target, Dialect, Columns>,
5651
- options?: Options
6263
+ target: ConflictTarget & ConflictConstraintNameConstraint<ConflictTarget>,
6264
+ options?: Options & ConflictActionUpdateNonEmptyConstraint<Options>
5652
6265
  ) =>
5653
6266
  <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
5654
6267
  plan: PlanValue & RequireInsertStatement<PlanValue>
5655
6268
  ) => QueryPlan<
5656
6269
  SelectionOfPlan<PlanValue>,
5657
- Exclude<RequiredOfPlan<PlanValue> | MutationRequiredFromValues<Exclude<UpdateValues, undefined>> | RequiredFromInput<Extract<Options["where"], PredicateInput>>, AvailableNames<AvailableOfPlan<PlanValue>>>,
6270
+ Exclude<RequiredOfPlan<PlanValue> | ConflictRequired<UpdateValues, Options, ConflictTarget>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5658
6271
  AvailableOfPlan<PlanValue>,
5659
- PlanDialectOf<PlanValue>,
6272
+ PlanDialectOf<PlanValue> | ConflictDialect<UpdateValues, Options, ConflictTarget, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5660
6273
  GroupedOfPlan<PlanValue>,
5661
6274
  ScopedNamesOfPlan<PlanValue>,
5662
- Exclude<OutstandingOfPlan<PlanValue> | MutationRequiredFromValues<Exclude<UpdateValues, undefined>> | RequiredFromInput<Extract<Options["where"], PredicateInput>>, AvailableNames<AvailableOfPlan<PlanValue>>>,
6275
+ Exclude<OutstandingOfPlan<PlanValue> | ConflictRequired<UpdateValues, Options, ConflictTarget>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5663
6276
  AssumptionsOfPlan<PlanValue>,
5664
6277
  CapabilitiesOfPlan<PlanValue>,
5665
6278
  StatementOfPlan<PlanValue>,
@@ -5670,13 +6283,13 @@ type AsCurriedResult<
5670
6283
 
5671
6284
  interface UpdateApi {
5672
6285
  <Targets extends MutationTargetTuple, Values extends UpdateInputOfTarget<Targets>>(
5673
- target: Dialect extends "mysql" ? Targets : never,
5674
- values: Values
6286
+ target: Dialect extends "mysql" ? Targets & MutationTargetTupleDialectConstraint<Targets, Dialect> & MutationTargetTupleUniqueNamesConstraint<Targets> : never,
6287
+ values: Values & NestedUpdateValuesNonEmptyConstraint<Values> & MutationValuesDialectConstraint<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5675
6288
  ): QueryPlan<
5676
6289
  {},
5677
6290
  Exclude<NestedMutationRequiredFromValues<Values>, MutationTargetNamesOf<Targets>>,
5678
6291
  AddAvailableMany<{}, MutationTargetNamesOf<Targets>>,
5679
- TableDialectOf<Targets[0]>,
6292
+ TableDialectOf<Targets[0]> | KnownMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5680
6293
  never,
5681
6294
  MutationTargetNamesOf<Targets>,
5682
6295
  Exclude<NestedMutationRequiredFromValues<Values>, MutationTargetNamesOf<Targets>>,
@@ -5689,12 +6302,12 @@ type AsCurriedResult<
5689
6302
  >
5690
6303
  <Target extends MutationTargetLike, Values extends Record<string, unknown>>(
5691
6304
  target: Target,
5692
- values: MutationValuesInput<"update", Target, Values>
6305
+ values: MutationValuesInput<"update", Target, Values> & UpdateValuesNonEmptyConstraint<Values> & MutationValuesDialectConstraint<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5693
6306
  ): QueryPlan<
5694
6307
  {},
5695
6308
  Exclude<MutationRequiredFromValues<Values>, SourceNameOf<Target>>,
5696
6309
  AddAvailable<{}, SourceNameOf<Target>>,
5697
- TableDialectOf<Target>,
6310
+ TableDialectOf<Target> | KnownMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5698
6311
  never,
5699
6312
  SourceNameOf<Target>,
5700
6313
  Exclude<MutationRequiredFromValues<Values>, SourceNameOf<Target>>,
@@ -5711,20 +6324,22 @@ type AsCurriedResult<
5711
6324
  Target extends MutationTargetLike,
5712
6325
  Values extends MutationInputOf<Table.InsertOf<Target>>,
5713
6326
  const Columns extends DdlColumnInput,
5714
- UpdateValues extends MutationInputOf<Table.UpdateOf<Target>>
6327
+ UpdateValues extends MutationInputOf<Table.UpdateOf<Target>> | undefined = undefined
5715
6328
  >(
5716
6329
  target: Target,
5717
- values: Values,
5718
- conflictColumns: ValidateTargetColumns<Target, NormalizeDdlColumns<Columns>>,
5719
- updateValues?: UpdateValues
6330
+ values: Values & MutationValuesDialectConstraint<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
6331
+ conflictColumns: ValidateTargetColumnInput<Target, Columns>,
6332
+ updateValues?: UpdateValues & UpdateValuesNonEmptyConstraint<Exclude<UpdateValues, undefined>> & MutationValuesDialectConstraint<Exclude<UpdateValues, undefined>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
5720
6333
  ) => QueryPlan<
5721
6334
  {},
5722
- Exclude<MutationRequiredFromValues<Values> | MutationRequiredFromValues<UpdateValues>, SourceNameOf<Target>>,
6335
+ Exclude<MutationRequiredFromValues<Values> | MutationRequiredFromValues<Exclude<UpdateValues, undefined>>, SourceNameOf<Target>>,
5723
6336
  AddAvailable<{}, SourceNameOf<Target>>,
5724
- TableDialectOf<Target>,
6337
+ | TableDialectOf<Target>
6338
+ | KnownMutationDialectFromValues<Values, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>
6339
+ | KnownMutationDialectFromValues<Exclude<UpdateValues, undefined>, Dialect, TextDb, NumericDb, BoolDb, TimestampDb, NullDb>,
5725
6340
  never,
5726
6341
  SourceNameOf<Target>,
5727
- Exclude<MutationRequiredFromValues<Values> | MutationRequiredFromValues<UpdateValues>, SourceNameOf<Target>>,
6342
+ Exclude<MutationRequiredFromValues<Values> | MutationRequiredFromValues<Exclude<UpdateValues, undefined>>, SourceNameOf<Target>>,
5728
6343
  TrueFormula,
5729
6344
  "write",
5730
6345
  "insert",
@@ -5752,7 +6367,7 @@ type AsCurriedResult<
5752
6367
  EmptyFacts
5753
6368
  >
5754
6369
  <Targets extends MutationTargetTuple>(
5755
- target: Dialect extends "mysql" ? Targets : never
6370
+ target: Dialect extends "mysql" ? Targets & MutationTargetTupleDialectConstraint<Targets, Dialect> & MutationTargetTupleUniqueNamesConstraint<Targets> : never
5756
6371
  ): QueryPlan<
5757
6372
  {},
5758
6373
  never,
@@ -5789,7 +6404,13 @@ type AsCurriedResult<
5789
6404
  EmptyFacts
5790
6405
  >
5791
6406
 
5792
- type MergeApi = <
6407
+ type MergeUnsupportedError<Dialect extends string> = {
6408
+ readonly __effect_qb_error__: "effect-qb: merge(...) is only supported by the postgres dialect"
6409
+ readonly __effect_qb_dialect__: Dialect
6410
+ readonly __effect_qb_hint__: "Use postgres.Query.merge(...) or dialect-specific insert/update/delete logic"
6411
+ }
6412
+
6413
+ type MergeSupportedApi = <
5793
6414
  Target extends MutationTargetLike,
5794
6415
  Source extends SourceLike,
5795
6416
  On extends PredicateInput,
@@ -5801,9 +6422,9 @@ type AsCurriedResult<
5801
6422
  target: Target,
5802
6423
  source: Source & (
5803
6424
  SourceRequiredOf<Source> extends never ? unknown : SourceRequirementError<Source>
5804
- ),
6425
+ ) & SourceDialectConstraint<Source, Dialect>,
5805
6426
  on: On,
5806
- options?: MergeOptions<Target, MatchedValues, InsertValues, MatchedPredicate, NotMatchedPredicate>
6427
+ options: MergeOptions<Target, MatchedValues, InsertValues, MatchedPredicate, NotMatchedPredicate>
5807
6428
  ) => QueryPlan<
5808
6429
  {},
5809
6430
  Exclude<
@@ -5846,7 +6467,10 @@ type AsCurriedResult<
5846
6467
  EmptyFacts
5847
6468
  >
5848
6469
 
6470
+ type MergeApi = Dialect extends "postgres" ? MergeSupportedApi : MergeUnsupportedError<Dialect>
6471
+
5849
6472
  const mutationRuntime = makeDslMutationRuntime({
6473
+ profile,
5850
6474
  makePlan,
5851
6475
  getAst,
5852
6476
  getQueryState,
@@ -5859,7 +6483,7 @@ type AsCurriedResult<
5859
6483
  buildConflictTarget,
5860
6484
  mutationTargetClauses,
5861
6485
  mutationAvailableSources,
5862
- normalizeColumnList,
6486
+ normalizeConflictColumns,
5863
6487
  targetSourceDetails,
5864
6488
  sourceDetails
5865
6489
  })
@@ -5875,63 +6499,21 @@ type AsCurriedResult<
5875
6499
  ): QueryPlan<any, any, any, any, any, any, any, any, any, "insert", MutationTargetLike, "ready"> =>
5876
6500
  mutationRuntime.attachInsertSource(plan, source)
5877
6501
 
5878
- const onConflict: OnConflictApi = <
5879
- Target extends MutationTargetLike,
5880
- const Columns extends DdlColumnInput,
5881
- UpdateValues extends MutationInputOf<Table.UpdateOf<Target>> | undefined = MutationInputOf<Table.UpdateOf<Target>> | undefined,
5882
- Options extends ConflictActionInput<Target, Dialect, UpdateValues> = ConflictActionInput<Target, Dialect, UpdateValues>
5883
- >(
5884
- target: ConflictTargetInput<Target, Dialect, Columns>,
5885
- options: Options = {} as Options
5886
- ) =>
5887
- <PlanValue extends QueryPlan<any, any, any, any, any, any, any, any, any, any>>(
5888
- plan: PlanValue & RequireInsertStatement<PlanValue>
5889
- ): QueryPlan<
5890
- SelectionOfPlan<PlanValue>,
5891
- Exclude<RequiredOfPlan<PlanValue> | MutationRequiredFromValues<Exclude<UpdateValues, undefined>> | RequiredFromInput<Extract<Options["where"], PredicateInput>>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5892
- AvailableOfPlan<PlanValue>,
5893
- PlanDialectOf<PlanValue>,
5894
- GroupedOfPlan<PlanValue>,
5895
- ScopedNamesOfPlan<PlanValue>,
5896
- Exclude<OutstandingOfPlan<PlanValue> | MutationRequiredFromValues<Exclude<UpdateValues, undefined>> | RequiredFromInput<Extract<Options["where"], PredicateInput>>, AvailableNames<AvailableOfPlan<PlanValue>>>,
5897
- AssumptionsOfPlan<PlanValue>,
5898
- CapabilitiesOfPlan<PlanValue>,
5899
- StatementOfPlan<PlanValue>,
5900
- MutationTargetOfPlan<PlanValue>,
5901
- InsertSourceStateOfPlan<PlanValue>,
5902
- FactsOfPlan<PlanValue>
5903
- > => mutationRuntime.onConflict(target, options)(plan)
6502
+ const onConflict = ((target: unknown, options: unknown = {}) =>
6503
+ (plan: QueryPlan<any, any, any, any, any, any, any, any, any, any>) =>
6504
+ mutationRuntime.onConflict(target, options)(plan)) as OnConflictApi
5904
6505
 
5905
6506
  const update: UpdateApi = ((
5906
6507
  target: MutationTargetInput,
5907
6508
  values: Record<string, unknown>
5908
6509
  ) => mutationRuntime.update(target, values)) as UpdateApi
5909
6510
 
5910
- const upsert: UpsertApi = <
5911
- Target extends MutationTargetLike,
5912
- Values extends MutationInputOf<Table.InsertOf<Target>>,
5913
- const Columns extends DdlColumnInput,
5914
- UpdateValues extends MutationInputOf<Table.UpdateOf<Target>>
5915
- >(
5916
- target: Target,
5917
- values: Values,
5918
- conflictColumns: ValidateTargetColumns<Target, NormalizeDdlColumns<Columns>>,
5919
- updateValues?: UpdateValues
5920
- ): QueryPlan<
5921
- {},
5922
- Exclude<MutationRequiredFromValues<Values> | MutationRequiredFromValues<UpdateValues>, SourceNameOf<Target>>,
5923
- AddAvailable<{}, SourceNameOf<Target>>,
5924
- TableDialectOf<Target>,
5925
- never,
5926
- SourceNameOf<Target>,
5927
- Exclude<MutationRequiredFromValues<Values> | MutationRequiredFromValues<UpdateValues>, SourceNameOf<Target>>,
5928
- TrueFormula,
5929
- "write",
5930
- "insert",
5931
- Target,
5932
- "ready",
5933
- EmptyFacts
5934
- > => mutationRuntime.upsert(target, values, conflictColumns as string | readonly string[], updateValues)
6511
+ const upsert = ((
6512
+ target: MutationTargetLike,
6513
+ values: Record<string, unknown>,
6514
+ conflictColumns: DdlColumnInput,
6515
+ updateValues?: Record<string, unknown>
6516
+ ) => mutationRuntime.upsert(target, values, conflictColumns as string | readonly string[], updateValues)) as UpsertApi
5935
6517
 
5936
6518
  const delete_: DeleteApi = ((
5937
6519
  target: MutationTargetInput
@@ -5958,7 +6540,7 @@ type AsCurriedResult<
5958
6540
  EmptyFacts
5959
6541
  > => mutationRuntime.truncate(target, options)
5960
6542
 
5961
- const merge: MergeApi = <
6543
+ const merge = (<
5962
6544
  Target extends MutationTargetLike,
5963
6545
  Source extends SourceLike,
5964
6546
  On extends PredicateInput,
@@ -5972,7 +6554,7 @@ type AsCurriedResult<
5972
6554
  SourceRequiredOf<Source> extends never ? unknown : SourceRequirementError<Source>
5973
6555
  ),
5974
6556
  on: On,
5975
- options: MergeOptions<Target, MatchedValues, InsertValues, MatchedPredicate, NotMatchedPredicate> = {}
6557
+ options: MergeOptions<Target, MatchedValues, InsertValues, MatchedPredicate, NotMatchedPredicate>
5976
6558
  ): QueryPlan<
5977
6559
  {},
5978
6560
  Exclude<
@@ -6013,7 +6595,7 @@ type AsCurriedResult<
6013
6595
  any,
6014
6596
  "ready",
6015
6597
  EmptyFacts
6016
- > => mutationRuntime.merge(target, source, on, options)
6598
+ > => mutationRuntime.merge(target, source, on, options)) as unknown as MergeApi
6017
6599
 
6018
6600
  type TransactionApi = (options?: TransactionOptions) => QueryPlan<
6019
6601
  {},
@@ -6054,7 +6636,7 @@ type AsCurriedResult<
6054
6636
  "rollback"
6055
6637
  >
6056
6638
 
6057
- type SavepointApi = <Name extends string>(name: Name) => QueryPlan<
6639
+ type SavepointApi = <Name extends string>(name: NonEmptyStringInput<Name>) => QueryPlan<
6058
6640
  {},
6059
6641
  never,
6060
6642
  {},
@@ -6067,7 +6649,7 @@ type AsCurriedResult<
6067
6649
  "savepoint"
6068
6650
  >
6069
6651
 
6070
- type RollbackToApi = <Name extends string>(name: Name) => QueryPlan<
6652
+ type RollbackToApi = <Name extends string>(name: NonEmptyStringInput<Name>) => QueryPlan<
6071
6653
  {},
6072
6654
  never,
6073
6655
  {},
@@ -6080,7 +6662,7 @@ type AsCurriedResult<
6080
6662
  "rollbackTo"
6081
6663
  >
6082
6664
 
6083
- type ReleaseSavepointApi = <Name extends string>(name: Name) => QueryPlan<
6665
+ type ReleaseSavepointApi = <Name extends string>(name: NonEmptyStringInput<Name>) => QueryPlan<
6084
6666
  {},
6085
6667
  never,
6086
6668
  {},
@@ -6125,10 +6707,10 @@ type AsCurriedResult<
6125
6707
  "dropTable"
6126
6708
  >
6127
6709
 
6128
- type CreateIndexApi = <Target extends SchemaTableLike, const Columns extends DdlColumnInput>(
6710
+ type CreateIndexApi = <Target extends SchemaTableLike, const Columns extends DdlColumnInput, Name extends string = string>(
6129
6711
  target: Target,
6130
- columns: Columns & ValidateDdlColumns<Target, NormalizeDdlColumns<Columns>>,
6131
- options?: CreateIndexOptions
6712
+ columns: Columns & ValidateDdlColumnInput<Target, Columns>,
6713
+ options?: CreateIndexOptions<Name>
6132
6714
  ) => QueryPlan<
6133
6715
  {},
6134
6716
  never,
@@ -6142,10 +6724,10 @@ type AsCurriedResult<
6142
6724
  "createIndex"
6143
6725
  >
6144
6726
 
6145
- type DropIndexApi = <Target extends SchemaTableLike, const Columns extends DdlColumnInput>(
6727
+ type DropIndexApi = <Target extends SchemaTableLike, const Columns extends DdlColumnInput, Name extends string = string>(
6146
6728
  target: Target,
6147
- columns: Columns & ValidateDdlColumns<Target, NormalizeDdlColumns<Columns>>,
6148
- options?: DropIndexOptions
6729
+ columns: Columns & ValidateDdlColumnInput<Target, Columns>,
6730
+ options?: DropIndexOptions<Name>
6149
6731
  ) => QueryPlan<
6150
6732
  {},
6151
6733
  never,