effect 3.9.2 → 3.10.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 (202) hide show
  1. package/Arbitrary/package.json +6 -0
  2. package/FastCheck/package.json +6 -0
  3. package/JSONSchema/package.json +6 -0
  4. package/ParseResult/package.json +6 -0
  5. package/Pretty/package.json +6 -0
  6. package/Schema/package.json +6 -0
  7. package/SchemaAST/package.json +6 -0
  8. package/TSubscriptionRef/package.json +6 -0
  9. package/dist/cjs/Arbitrary.js +490 -0
  10. package/dist/cjs/Arbitrary.js.map +1 -0
  11. package/dist/cjs/Effect.js +247 -16
  12. package/dist/cjs/Effect.js.map +1 -1
  13. package/dist/cjs/FastCheck.js +17 -0
  14. package/dist/cjs/FastCheck.js.map +1 -0
  15. package/dist/cjs/Inspectable.js +43 -3
  16. package/dist/cjs/Inspectable.js.map +1 -1
  17. package/dist/cjs/JSONSchema.js +418 -0
  18. package/dist/cjs/JSONSchema.js.map +1 -0
  19. package/dist/cjs/ParseResult.js +1539 -0
  20. package/dist/cjs/ParseResult.js.map +1 -0
  21. package/dist/cjs/Predicate.js +3 -1
  22. package/dist/cjs/Predicate.js.map +1 -1
  23. package/dist/cjs/Pretty.js +183 -0
  24. package/dist/cjs/Pretty.js.map +1 -0
  25. package/dist/cjs/Schema.js +5529 -0
  26. package/dist/cjs/Schema.js.map +1 -0
  27. package/dist/cjs/SchemaAST.js +2365 -0
  28. package/dist/cjs/SchemaAST.js.map +1 -0
  29. package/dist/cjs/Stream.js +17 -3
  30. package/dist/cjs/Stream.js.map +1 -1
  31. package/dist/cjs/TPubSub.js +9 -1
  32. package/dist/cjs/TPubSub.js.map +1 -1
  33. package/dist/cjs/TQueue.js.map +1 -1
  34. package/dist/cjs/TRef.js.map +1 -1
  35. package/dist/cjs/TSubscriptionRef.js +96 -0
  36. package/dist/cjs/TSubscriptionRef.js.map +1 -0
  37. package/dist/cjs/index.js +18 -2
  38. package/dist/cjs/index.js.map +1 -1
  39. package/dist/cjs/internal/cause.js +2 -2
  40. package/dist/cjs/internal/cause.js.map +1 -1
  41. package/dist/cjs/internal/core.js +4 -4
  42. package/dist/cjs/internal/core.js.map +1 -1
  43. package/dist/cjs/internal/fiberRuntime.js +14 -12
  44. package/dist/cjs/internal/fiberRuntime.js.map +1 -1
  45. package/dist/cjs/internal/logger.js +7 -6
  46. package/dist/cjs/internal/logger.js.map +1 -1
  47. package/dist/cjs/internal/redacted.js +4 -0
  48. package/dist/cjs/internal/redacted.js.map +1 -1
  49. package/dist/cjs/internal/schema/errors.js +116 -0
  50. package/dist/cjs/internal/schema/errors.js.map +1 -0
  51. package/dist/cjs/internal/schema/filters.js +41 -0
  52. package/dist/cjs/internal/schema/filters.js.map +1 -0
  53. package/dist/cjs/internal/schema/util.js +96 -0
  54. package/dist/cjs/internal/schema/util.js.map +1 -0
  55. package/dist/cjs/internal/stm/core.js +2 -3
  56. package/dist/cjs/internal/stm/core.js.map +1 -1
  57. package/dist/cjs/internal/stm/tPubSub.js.map +1 -1
  58. package/dist/cjs/internal/stm/tQueue.js +1 -2
  59. package/dist/cjs/internal/stm/tQueue.js.map +1 -1
  60. package/dist/cjs/internal/stm/tRef.js +6 -2
  61. package/dist/cjs/internal/stm/tRef.js.map +1 -1
  62. package/dist/cjs/internal/stm/tSubscriptionRef.js +178 -0
  63. package/dist/cjs/internal/stm/tSubscriptionRef.js.map +1 -0
  64. package/dist/cjs/internal/stream.js +36 -16
  65. package/dist/cjs/internal/stream.js.map +1 -1
  66. package/dist/cjs/internal/version.js +1 -1
  67. package/dist/cjs/internal/version.js.map +1 -1
  68. package/dist/dts/Arbitrary.d.ts +45 -0
  69. package/dist/dts/Arbitrary.d.ts.map +1 -0
  70. package/dist/dts/Effect.d.ts +298 -30
  71. package/dist/dts/Effect.d.ts.map +1 -1
  72. package/dist/dts/FastCheck.d.ts +9 -0
  73. package/dist/dts/FastCheck.d.ts.map +1 -0
  74. package/dist/dts/Inspectable.d.ts +28 -0
  75. package/dist/dts/Inspectable.d.ts.map +1 -1
  76. package/dist/dts/JSONSchema.d.ts +181 -0
  77. package/dist/dts/JSONSchema.d.ts.map +1 -0
  78. package/dist/dts/ParseResult.d.ts +551 -0
  79. package/dist/dts/ParseResult.d.ts.map +1 -0
  80. package/dist/dts/Predicate.d.ts.map +1 -1
  81. package/dist/dts/Pretty.d.ts +26 -0
  82. package/dist/dts/Pretty.d.ts.map +1 -0
  83. package/dist/dts/Schema.d.ts +4562 -0
  84. package/dist/dts/Schema.d.ts.map +1 -0
  85. package/dist/dts/SchemaAST.d.ts +1321 -0
  86. package/dist/dts/SchemaAST.d.ts.map +1 -0
  87. package/dist/dts/Stream.d.ts +67 -2
  88. package/dist/dts/Stream.d.ts.map +1 -1
  89. package/dist/dts/TPubSub.d.ts +8 -0
  90. package/dist/dts/TPubSub.d.ts.map +1 -1
  91. package/dist/dts/TQueue.d.ts +7 -7
  92. package/dist/dts/TQueue.d.ts.map +1 -1
  93. package/dist/dts/TRef.d.ts +2 -1
  94. package/dist/dts/TRef.d.ts.map +1 -1
  95. package/dist/dts/TSubscriptionRef.d.ts +251 -0
  96. package/dist/dts/TSubscriptionRef.d.ts.map +1 -0
  97. package/dist/dts/index.d.ts +32 -0
  98. package/dist/dts/index.d.ts.map +1 -1
  99. package/dist/dts/internal/fiberRuntime.d.ts.map +1 -1
  100. package/dist/dts/internal/schema/errors.d.ts +2 -0
  101. package/dist/dts/internal/schema/errors.d.ts.map +1 -0
  102. package/dist/dts/internal/schema/filters.d.ts +2 -0
  103. package/dist/dts/internal/schema/filters.d.ts.map +1 -0
  104. package/dist/dts/internal/schema/util.d.ts +2 -0
  105. package/dist/dts/internal/schema/util.d.ts.map +1 -0
  106. package/dist/dts/internal/stm/tRef.d.ts +3 -1
  107. package/dist/dts/internal/stm/tRef.d.ts.map +1 -1
  108. package/dist/dts/internal/stm/tSubscriptionRef.d.ts +2 -0
  109. package/dist/dts/internal/stm/tSubscriptionRef.d.ts.map +1 -0
  110. package/dist/dts/internal/stream.d.ts.map +1 -1
  111. package/dist/esm/Arbitrary.js +472 -0
  112. package/dist/esm/Arbitrary.js.map +1 -0
  113. package/dist/esm/Effect.js +256 -18
  114. package/dist/esm/Effect.js.map +1 -1
  115. package/dist/esm/FastCheck.js +9 -0
  116. package/dist/esm/FastCheck.js.map +1 -0
  117. package/dist/esm/Inspectable.js +39 -2
  118. package/dist/esm/Inspectable.js.map +1 -1
  119. package/dist/esm/JSONSchema.js +408 -0
  120. package/dist/esm/JSONSchema.js.map +1 -0
  121. package/dist/esm/ParseResult.js +1503 -0
  122. package/dist/esm/ParseResult.js.map +1 -0
  123. package/dist/esm/Predicate.js +2 -1
  124. package/dist/esm/Predicate.js.map +1 -1
  125. package/dist/esm/Pretty.js +173 -0
  126. package/dist/esm/Pretty.js.map +1 -0
  127. package/dist/esm/Schema.js +5328 -0
  128. package/dist/esm/Schema.js.map +1 -0
  129. package/dist/esm/SchemaAST.js +2300 -0
  130. package/dist/esm/SchemaAST.js.map +1 -0
  131. package/dist/esm/Stream.js +14 -0
  132. package/dist/esm/Stream.js.map +1 -1
  133. package/dist/esm/TPubSub.js +8 -0
  134. package/dist/esm/TPubSub.js.map +1 -1
  135. package/dist/esm/TQueue.js.map +1 -1
  136. package/dist/esm/TRef.js.map +1 -1
  137. package/dist/esm/TSubscriptionRef.js +87 -0
  138. package/dist/esm/TSubscriptionRef.js.map +1 -0
  139. package/dist/esm/index.js +32 -0
  140. package/dist/esm/index.js.map +1 -1
  141. package/dist/esm/internal/cause.js +3 -3
  142. package/dist/esm/internal/cause.js.map +1 -1
  143. package/dist/esm/internal/core.js +4 -4
  144. package/dist/esm/internal/core.js.map +1 -1
  145. package/dist/esm/internal/fiberRuntime.js +14 -12
  146. package/dist/esm/internal/fiberRuntime.js.map +1 -1
  147. package/dist/esm/internal/logger.js +7 -6
  148. package/dist/esm/internal/logger.js.map +1 -1
  149. package/dist/esm/internal/redacted.js +4 -0
  150. package/dist/esm/internal/redacted.js.map +1 -1
  151. package/dist/esm/internal/schema/errors.js +87 -0
  152. package/dist/esm/internal/schema/errors.js.map +1 -0
  153. package/dist/esm/internal/schema/filters.js +35 -0
  154. package/dist/esm/internal/schema/filters.js.map +1 -0
  155. package/dist/esm/internal/schema/util.js +78 -0
  156. package/dist/esm/internal/schema/util.js.map +1 -0
  157. package/dist/esm/internal/stm/core.js +1 -2
  158. package/dist/esm/internal/stm/core.js.map +1 -1
  159. package/dist/esm/internal/stm/tPubSub.js.map +1 -1
  160. package/dist/esm/internal/stm/tQueue.js +1 -2
  161. package/dist/esm/internal/stm/tQueue.js.map +1 -1
  162. package/dist/esm/internal/stm/tRef.js +5 -1
  163. package/dist/esm/internal/stm/tRef.js.map +1 -1
  164. package/dist/esm/internal/stm/tSubscriptionRef.js +166 -0
  165. package/dist/esm/internal/stm/tSubscriptionRef.js.map +1 -0
  166. package/dist/esm/internal/stream.js +33 -15
  167. package/dist/esm/internal/stream.js.map +1 -1
  168. package/dist/esm/internal/version.js +1 -1
  169. package/dist/esm/internal/version.js.map +1 -1
  170. package/package.json +68 -1
  171. package/src/Arbitrary.ts +563 -0
  172. package/src/Effect.ts +302 -31
  173. package/src/FastCheck.ts +9 -0
  174. package/src/Inspectable.ts +56 -2
  175. package/src/JSONSchema.ts +601 -0
  176. package/src/ParseResult.ts +2027 -0
  177. package/src/Predicate.ts +3 -1
  178. package/src/Pretty.ts +204 -0
  179. package/src/Schema.ts +10388 -0
  180. package/src/SchemaAST.ts +2827 -0
  181. package/src/Stream.ts +77 -9
  182. package/src/TPubSub.ts +9 -0
  183. package/src/TQueue.ts +7 -7
  184. package/src/TRef.ts +2 -1
  185. package/src/TSubscriptionRef.ts +284 -0
  186. package/src/index.ts +40 -0
  187. package/src/internal/cause.ts +3 -3
  188. package/src/internal/core-effect.ts +2 -2
  189. package/src/internal/core.ts +4 -4
  190. package/src/internal/fiberRuntime.ts +14 -12
  191. package/src/internal/logger.ts +7 -6
  192. package/src/internal/redacted.ts +4 -0
  193. package/src/internal/schema/errors.ts +189 -0
  194. package/src/internal/schema/filters.ts +86 -0
  195. package/src/internal/schema/util.ts +113 -0
  196. package/src/internal/stm/core.ts +1 -2
  197. package/src/internal/stm/tPubSub.ts +1 -0
  198. package/src/internal/stm/tQueue.ts +2 -2
  199. package/src/internal/stm/tRef.ts +7 -2
  200. package/src/internal/stm/tSubscriptionRef.ts +286 -0
  201. package/src/internal/stream.ts +97 -20
  202. package/src/internal/version.ts +1 -1
@@ -0,0 +1,563 @@
1
+ /**
2
+ * @since 3.10.0
3
+ */
4
+
5
+ import * as Arr from "./Array.js"
6
+ import * as FastCheck from "./FastCheck.js"
7
+ import * as errors_ from "./internal/schema/errors.js"
8
+ import * as filters_ from "./internal/schema/filters.js"
9
+ import * as util_ from "./internal/schema/util.js"
10
+ import * as Option from "./Option.js"
11
+ import * as Predicate from "./Predicate.js"
12
+ import type * as Schema from "./Schema.js"
13
+ import * as AST from "./SchemaAST.js"
14
+
15
+ /**
16
+ * @category model
17
+ * @since 3.10.0
18
+ */
19
+ export interface LazyArbitrary<A> {
20
+ (fc: typeof FastCheck): FastCheck.Arbitrary<A>
21
+ }
22
+
23
+ /**
24
+ * @category annotations
25
+ * @since 3.10.0
26
+ */
27
+ export interface ArbitraryGenerationContext {
28
+ readonly depthIdentifier?: string
29
+ readonly maxDepth: number
30
+ }
31
+
32
+ /**
33
+ * @category annotations
34
+ * @since 3.10.0
35
+ */
36
+ export type ArbitraryAnnotation<A, TypeParameters extends ReadonlyArray<any> = readonly []> = (
37
+ ...arbitraries: [
38
+ ...{ readonly [K in keyof TypeParameters]: LazyArbitrary<TypeParameters[K]> },
39
+ ctx: ArbitraryGenerationContext
40
+ ]
41
+ ) => LazyArbitrary<A>
42
+
43
+ /**
44
+ * Returns a LazyArbitrary for the `A` type of the provided schema.
45
+ *
46
+ * @category arbitrary
47
+ * @since 3.10.0
48
+ */
49
+ export const makeLazy = <A, I, R>(schema: Schema.Schema<A, I, R>): LazyArbitrary<A> =>
50
+ go(schema.ast, { maxDepth: 2 }, [])
51
+
52
+ /**
53
+ * Returns a fast-check Arbitrary for the `A` type of the provided schema.
54
+ *
55
+ * @category arbitrary
56
+ * @since 3.10.0
57
+ */
58
+ export const make = <A, I, R>(schema: Schema.Schema<A, I, R>): FastCheck.Arbitrary<A> => makeLazy(schema)(FastCheck)
59
+
60
+ const getArbitraryAnnotation = AST.getAnnotation<ArbitraryAnnotation<any, any>>(AST.ArbitraryAnnotationId)
61
+
62
+ const getRefinementFromArbitrary = (
63
+ ast: AST.Refinement,
64
+ ctx: Context,
65
+ path: ReadonlyArray<PropertyKey>
66
+ ) => {
67
+ const constraints = combineConstraints(ctx.constraints, getConstraints(ast))
68
+ return go(ast.from, constraints ? { ...ctx, constraints } : ctx, path)
69
+ }
70
+
71
+ const getSuspendedContext = (
72
+ ctx: Context,
73
+ ast: AST.Suspend
74
+ ): Context => {
75
+ if (ctx.depthIdentifier !== undefined) {
76
+ return ctx
77
+ }
78
+ const depthIdentifier = AST.getIdentifierAnnotation(ast).pipe(
79
+ Option.orElse(() => AST.getIdentifierAnnotation(ast.f())),
80
+ Option.getOrElse(() => "SuspendDefaultDepthIdentifier")
81
+ )
82
+ return { ...ctx, depthIdentifier }
83
+ }
84
+
85
+ const getSuspendedArray = (
86
+ fc: typeof FastCheck,
87
+ depthIdentifier: string,
88
+ maxDepth: number,
89
+ item: FastCheck.Arbitrary<any>,
90
+ constraints?: FastCheck.ArrayConstraints
91
+ ) => {
92
+ let minLength = 1
93
+ let maxLength = 2
94
+ if (constraints && constraints.minLength !== undefined && constraints.minLength > minLength) {
95
+ minLength = constraints.minLength
96
+ if (minLength > maxLength) {
97
+ maxLength = minLength
98
+ }
99
+ }
100
+ return fc.oneof(
101
+ { maxDepth, depthIdentifier },
102
+ fc.constant([]),
103
+ fc.array(item, { minLength, maxLength })
104
+ )
105
+ }
106
+
107
+ interface Context extends ArbitraryGenerationContext {
108
+ readonly constraints?: Constraints
109
+ }
110
+
111
+ const go = (
112
+ ast: AST.AST,
113
+ ctx: Context,
114
+ path: ReadonlyArray<PropertyKey>
115
+ ): LazyArbitrary<any> => {
116
+ const hook = getArbitraryAnnotation(ast)
117
+ if (Option.isSome(hook)) {
118
+ switch (ast._tag) {
119
+ case "Declaration":
120
+ return hook.value(...ast.typeParameters.map((p) => go(p, ctx, path)), ctx)
121
+ case "Refinement":
122
+ return hook.value(getRefinementFromArbitrary(ast, ctx, path), ctx)
123
+ default:
124
+ return hook.value(ctx)
125
+ }
126
+ }
127
+ switch (ast._tag) {
128
+ case "Declaration": {
129
+ throw new Error(errors_.getArbitraryMissingAnnotationErrorMessage(path, ast))
130
+ }
131
+ case "Literal":
132
+ return (fc) => fc.constant(ast.literal)
133
+ case "UniqueSymbol":
134
+ return (fc) => fc.constant(ast.symbol)
135
+ case "UndefinedKeyword":
136
+ return (fc) => fc.constant(undefined)
137
+ case "NeverKeyword":
138
+ return () => {
139
+ throw new Error(errors_.getArbitraryUnsupportedErrorMessage(path, ast))
140
+ }
141
+ case "UnknownKeyword":
142
+ case "AnyKeyword":
143
+ case "VoidKeyword":
144
+ return (fc) => fc.anything()
145
+ case "StringKeyword":
146
+ return (fc) => {
147
+ if (ctx.constraints) {
148
+ switch (ctx.constraints._tag) {
149
+ case "StringConstraints":
150
+ return fc.string(ctx.constraints.constraints)
151
+ }
152
+ }
153
+ return fc.string()
154
+ }
155
+ case "NumberKeyword":
156
+ return (fc) => {
157
+ if (ctx.constraints) {
158
+ switch (ctx.constraints._tag) {
159
+ case "NumberConstraints":
160
+ return fc.float(ctx.constraints.constraints)
161
+ case "IntegerConstraints":
162
+ return fc.integer(ctx.constraints.constraints)
163
+ }
164
+ }
165
+ return fc.float()
166
+ }
167
+ case "BooleanKeyword":
168
+ return (fc) => fc.boolean()
169
+ case "BigIntKeyword":
170
+ return (fc) => {
171
+ if (ctx.constraints) {
172
+ switch (ctx.constraints._tag) {
173
+ case "BigIntConstraints":
174
+ return fc.bigInt(ctx.constraints.constraints)
175
+ }
176
+ }
177
+ return fc.bigInt()
178
+ }
179
+ case "SymbolKeyword":
180
+ return (fc) => fc.string().map((s) => Symbol.for(s))
181
+ case "ObjectKeyword":
182
+ return (fc) => fc.oneof(fc.object(), fc.array(fc.anything()))
183
+ case "TemplateLiteral": {
184
+ return (fc) => {
185
+ const string = fc.string({ maxLength: 5 })
186
+ const number = fc.float({ noDefaultInfinity: true }).filter((n) => !Number.isNaN(n))
187
+ const components: Array<FastCheck.Arbitrary<string | number>> = [fc.constant(ast.head)]
188
+ for (const span of ast.spans) {
189
+ if (AST.isStringKeyword(span.type)) {
190
+ components.push(string)
191
+ } else {
192
+ components.push(number)
193
+ }
194
+ components.push(fc.constant(span.literal))
195
+ }
196
+ return fc.tuple(...components).map((spans) => spans.join(""))
197
+ }
198
+ }
199
+ case "TupleType": {
200
+ const elements: Array<LazyArbitrary<any>> = []
201
+ let hasOptionals = false
202
+ let i = 0
203
+ for (const element of ast.elements) {
204
+ elements.push(go(element.type, ctx, path.concat(i++)))
205
+ if (element.isOptional) {
206
+ hasOptionals = true
207
+ }
208
+ }
209
+ const rest = ast.rest.map((annotatedAST) => go(annotatedAST.type, ctx, path))
210
+ return (fc) => {
211
+ // ---------------------------------------------
212
+ // handle elements
213
+ // ---------------------------------------------
214
+ let output = fc.tuple(...elements.map((arb) => arb(fc)))
215
+ if (hasOptionals) {
216
+ const indexes = fc.tuple(
217
+ ...ast.elements.map((element) => element.isOptional ? fc.boolean() : fc.constant(true))
218
+ )
219
+ output = output.chain((tuple) =>
220
+ indexes.map((booleans) => {
221
+ for (const [i, b] of booleans.reverse().entries()) {
222
+ if (!b) {
223
+ tuple.splice(booleans.length - i, 1)
224
+ }
225
+ }
226
+ return tuple
227
+ })
228
+ )
229
+ }
230
+
231
+ // ---------------------------------------------
232
+ // handle rest element
233
+ // ---------------------------------------------
234
+ if (Arr.isNonEmptyReadonlyArray(rest)) {
235
+ const [head, ...tail] = rest
236
+ const item = head(fc)
237
+ const constraints: FastCheck.ArrayConstraints | undefined =
238
+ ctx.constraints && ctx.constraints._tag === "ArrayConstraints"
239
+ ? ctx.constraints.constraints
240
+ : undefined
241
+ output = output.chain((as) => {
242
+ return (ctx.depthIdentifier !== undefined
243
+ ? getSuspendedArray(fc, ctx.depthIdentifier, ctx.maxDepth, item, constraints)
244
+ : fc.array(item, constraints)).map((rest) => [...as, ...rest])
245
+ })
246
+ // ---------------------------------------------
247
+ // handle post rest elements
248
+ // ---------------------------------------------
249
+ for (let j = 0; j < tail.length; j++) {
250
+ output = output.chain((as) => tail[j](fc).map((a) => [...as, a]))
251
+ }
252
+ }
253
+
254
+ return output
255
+ }
256
+ }
257
+ case "TypeLiteral": {
258
+ const propertySignaturesTypes = ast.propertySignatures.map((ps) => go(ps.type, ctx, path.concat(ps.name)))
259
+ const indexSignatures = ast.indexSignatures.map((is) =>
260
+ [go(is.parameter, ctx, path), go(is.type, ctx, path)] as const
261
+ )
262
+ return (fc) => {
263
+ const arbs: any = {}
264
+ const requiredKeys: Array<PropertyKey> = []
265
+ // ---------------------------------------------
266
+ // handle property signatures
267
+ // ---------------------------------------------
268
+ for (let i = 0; i < propertySignaturesTypes.length; i++) {
269
+ const ps = ast.propertySignatures[i]
270
+ const name = ps.name
271
+ if (!ps.isOptional) {
272
+ requiredKeys.push(name)
273
+ }
274
+ arbs[name] = propertySignaturesTypes[i](fc)
275
+ }
276
+ let output = fc.record<any, any>(arbs, { requiredKeys })
277
+ // ---------------------------------------------
278
+ // handle index signatures
279
+ // ---------------------------------------------
280
+ for (let i = 0; i < indexSignatures.length; i++) {
281
+ const key = indexSignatures[i][0](fc)
282
+ const value = indexSignatures[i][1](fc)
283
+ output = output.chain((o) => {
284
+ const item = fc.tuple(key, value)
285
+ const arr = ctx.depthIdentifier !== undefined ?
286
+ getSuspendedArray(fc, ctx.depthIdentifier, ctx.maxDepth, item) :
287
+ fc.array(item)
288
+ return arr.map((tuples) => ({ ...Object.fromEntries(tuples), ...o }))
289
+ })
290
+ }
291
+
292
+ return output
293
+ }
294
+ }
295
+ case "Union": {
296
+ const types = ast.types.map((member) => go(member, ctx, path))
297
+ return (fc) => fc.oneof(...types.map((arb) => arb(fc)))
298
+ }
299
+ case "Enums": {
300
+ if (ast.enums.length === 0) {
301
+ throw new Error(errors_.getArbitraryEmptyEnumErrorMessage(path))
302
+ }
303
+ return (fc) => fc.oneof(...ast.enums.map(([_, value]) => fc.constant(value)))
304
+ }
305
+ case "Refinement": {
306
+ const from = getRefinementFromArbitrary(ast, ctx, path)
307
+ return (fc) => from(fc).filter((a) => Option.isNone(ast.filter(a, AST.defaultParseOption, ast)))
308
+ }
309
+ case "Suspend": {
310
+ const get = util_.memoizeThunk(() => {
311
+ return go(ast.f(), getSuspendedContext(ctx, ast), path)
312
+ })
313
+ return (fc) => fc.constant(null).chain(() => get()(fc))
314
+ }
315
+ case "Transformation":
316
+ return go(ast.to, ctx, path)
317
+ }
318
+ }
319
+
320
+ /** @internal */
321
+ export class NumberConstraints {
322
+ readonly _tag = "NumberConstraints"
323
+ readonly constraints: FastCheck.FloatConstraints
324
+ constructor(options: {
325
+ readonly min?: number | undefined
326
+ readonly max?: number | undefined
327
+ readonly noNaN?: boolean | undefined
328
+ readonly noDefaultInfinity?: boolean | undefined
329
+ }) {
330
+ this.constraints = {}
331
+ if (Predicate.isNumber(options.min)) {
332
+ this.constraints.min = Math.fround(options.min)
333
+ }
334
+ if (Predicate.isNumber(options.max)) {
335
+ this.constraints.max = Math.fround(options.max)
336
+ }
337
+ if (Predicate.isBoolean(options.noNaN)) {
338
+ this.constraints.noNaN = options.noNaN
339
+ }
340
+ if (Predicate.isBoolean(options.noDefaultInfinity)) {
341
+ this.constraints.noDefaultInfinity = options.noDefaultInfinity
342
+ }
343
+ }
344
+ }
345
+
346
+ /** @internal */
347
+ export class StringConstraints {
348
+ readonly _tag = "StringConstraints"
349
+ readonly constraints: FastCheck.StringSharedConstraints
350
+ constructor(options: {
351
+ readonly minLength?: number | undefined
352
+ readonly maxLength?: number | undefined
353
+ }) {
354
+ this.constraints = {}
355
+ if (Predicate.isNumber(options.minLength)) {
356
+ this.constraints.minLength = options.minLength
357
+ }
358
+ if (Predicate.isNumber(options.maxLength)) {
359
+ this.constraints.maxLength = options.maxLength
360
+ }
361
+ }
362
+ }
363
+
364
+ /** @internal */
365
+ export class IntegerConstraints {
366
+ readonly _tag = "IntegerConstraints"
367
+ readonly constraints: FastCheck.IntegerConstraints
368
+ constructor(options: {
369
+ readonly min?: number | undefined
370
+ readonly max?: number | undefined
371
+ }) {
372
+ this.constraints = {}
373
+ if (Predicate.isNumber(options.min)) {
374
+ this.constraints.min = options.min
375
+ }
376
+ if (Predicate.isNumber(options.max)) {
377
+ this.constraints.max = options.max
378
+ }
379
+ }
380
+ }
381
+
382
+ /** @internal */
383
+ export class ArrayConstraints {
384
+ readonly _tag = "ArrayConstraints"
385
+ readonly constraints: FastCheck.ArrayConstraints
386
+ constructor(options: {
387
+ readonly minLength?: number | undefined
388
+ readonly maxLength?: number | undefined
389
+ }) {
390
+ this.constraints = {}
391
+ if (Predicate.isNumber(options.minLength)) {
392
+ this.constraints.minLength = options.minLength
393
+ }
394
+ if (Predicate.isNumber(options.maxLength)) {
395
+ this.constraints.maxLength = options.maxLength
396
+ }
397
+ }
398
+ }
399
+
400
+ /** @internal */
401
+ export class BigIntConstraints {
402
+ readonly _tag = "BigIntConstraints"
403
+ readonly constraints: FastCheck.BigIntConstraints
404
+ constructor(options: {
405
+ readonly min?: bigint | undefined
406
+ readonly max?: bigint | undefined
407
+ }) {
408
+ this.constraints = {}
409
+ if (Predicate.isBigInt(options.min)) {
410
+ this.constraints.min = options.min
411
+ }
412
+ if (Predicate.isBigInt(options.max)) {
413
+ this.constraints.max = options.max
414
+ }
415
+ }
416
+ }
417
+
418
+ /** @internal */
419
+ export type Constraints =
420
+ | NumberConstraints
421
+ | StringConstraints
422
+ | IntegerConstraints
423
+ | ArrayConstraints
424
+ | BigIntConstraints
425
+
426
+ /** @internal */
427
+ export const getConstraints = (ast: AST.Refinement): Constraints | undefined => {
428
+ const TypeAnnotationId = ast.annotations[AST.SchemaIdAnnotationId]
429
+ const jsonSchema: any = ast.annotations[AST.JSONSchemaAnnotationId]
430
+ switch (TypeAnnotationId) {
431
+ // int
432
+ case filters_.IntSchemaId:
433
+ return new IntegerConstraints({})
434
+ // number
435
+ case filters_.GreaterThanSchemaId:
436
+ case filters_.GreaterThanOrEqualToSchemaId:
437
+ case filters_.LessThanSchemaId:
438
+ case filters_.LessThanOrEqualToSchemaId:
439
+ case filters_.BetweenSchemaId:
440
+ return new NumberConstraints({
441
+ min: jsonSchema.exclusiveMinimum ?? jsonSchema.minimum,
442
+ max: jsonSchema.exclusiveMaximum ?? jsonSchema.maximum
443
+ })
444
+ // bigint
445
+ case filters_.GreaterThanBigintSchemaId:
446
+ case filters_.GreaterThanOrEqualToBigIntSchemaId:
447
+ case filters_.LessThanBigIntSchemaId:
448
+ case filters_.LessThanOrEqualToBigIntSchemaId:
449
+ case filters_.BetweenBigintSchemaId: {
450
+ const constraints: any = ast.annotations[TypeAnnotationId]
451
+ return new BigIntConstraints(constraints)
452
+ }
453
+ // string
454
+ case filters_.MinLengthSchemaId:
455
+ case filters_.MaxLengthSchemaId:
456
+ case filters_.LengthSchemaId:
457
+ return new StringConstraints(jsonSchema)
458
+ // array
459
+ case filters_.MinItemsSchemaId:
460
+ case filters_.MaxItemsSchemaId:
461
+ case filters_.ItemsCountSchemaId:
462
+ return new ArrayConstraints({
463
+ minLength: jsonSchema.minItems,
464
+ maxLength: jsonSchema.maxItems
465
+ })
466
+ }
467
+ }
468
+
469
+ /** @internal */
470
+ export const combineConstraints = (
471
+ c1: Constraints | undefined,
472
+ c2: Constraints | undefined
473
+ ): Constraints | undefined => {
474
+ if (c1 === undefined) {
475
+ return c2
476
+ }
477
+ if (c2 === undefined) {
478
+ return c1
479
+ }
480
+ switch (c1._tag) {
481
+ case "ArrayConstraints": {
482
+ switch (c2._tag) {
483
+ case "ArrayConstraints":
484
+ return new ArrayConstraints({
485
+ minLength: getMax(c1.constraints.minLength, c2.constraints.minLength),
486
+ maxLength: getMin(c1.constraints.maxLength, c2.constraints.maxLength)
487
+ })
488
+ }
489
+ break
490
+ }
491
+ case "NumberConstraints": {
492
+ switch (c2._tag) {
493
+ case "NumberConstraints":
494
+ return new NumberConstraints({
495
+ min: getMax(c1.constraints.min, c2.constraints.min),
496
+ max: getMin(c1.constraints.max, c2.constraints.max),
497
+ noNaN: getOr(c1.constraints.noNaN, c2.constraints.noNaN),
498
+ noDefaultInfinity: getOr(c1.constraints.noDefaultInfinity, c2.constraints.noDefaultInfinity)
499
+ })
500
+ case "IntegerConstraints":
501
+ return new IntegerConstraints({
502
+ min: getMax(c1.constraints.min, c2.constraints.min),
503
+ max: getMin(c1.constraints.max, c2.constraints.max)
504
+ })
505
+ }
506
+ break
507
+ }
508
+ case "BigIntConstraints": {
509
+ switch (c2._tag) {
510
+ case "BigIntConstraints":
511
+ return new BigIntConstraints({
512
+ min: getMax(c1.constraints.min, c2.constraints.min),
513
+ max: getMin(c1.constraints.max, c2.constraints.max)
514
+ })
515
+ }
516
+ break
517
+ }
518
+ case "StringConstraints": {
519
+ switch (c2._tag) {
520
+ case "StringConstraints":
521
+ return new StringConstraints({
522
+ minLength: getMax(c1.constraints.minLength, c2.constraints.minLength),
523
+ maxLength: getMin(c1.constraints.maxLength, c2.constraints.maxLength)
524
+ })
525
+ }
526
+ break
527
+ }
528
+ case "IntegerConstraints": {
529
+ switch (c2._tag) {
530
+ case "NumberConstraints":
531
+ case "IntegerConstraints": {
532
+ return new IntegerConstraints({
533
+ min: getMax(c1.constraints.min, c2.constraints.min),
534
+ max: getMin(c1.constraints.max, c2.constraints.max)
535
+ })
536
+ }
537
+ }
538
+ break
539
+ }
540
+ }
541
+ }
542
+
543
+ const getOr = (a: boolean | undefined, b: boolean | undefined): boolean | undefined => {
544
+ return a === undefined ? b : b === undefined ? a : a || b
545
+ }
546
+
547
+ function getMax(n1: bigint | undefined, n2: bigint | undefined): bigint | undefined
548
+ function getMax(n1: number | undefined, n2: number | undefined): number | undefined
549
+ function getMax(
550
+ n1: bigint | number | undefined,
551
+ n2: bigint | number | undefined
552
+ ): bigint | number | undefined {
553
+ return n1 === undefined ? n2 : n2 === undefined ? n1 : n1 <= n2 ? n2 : n1
554
+ }
555
+
556
+ function getMin(n1: bigint | undefined, n2: bigint | undefined): bigint | undefined
557
+ function getMin(n1: number | undefined, n2: number | undefined): number | undefined
558
+ function getMin(
559
+ n1: bigint | number | undefined,
560
+ n2: bigint | number | undefined
561
+ ): bigint | number | undefined {
562
+ return n1 === undefined ? n2 : n2 === undefined ? n1 : n1 <= n2 ? n1 : n2
563
+ }