effect 4.0.0-beta.75 → 4.0.0-beta.76

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 (95) hide show
  1. package/dist/Schema.d.ts +102 -40
  2. package/dist/Schema.d.ts.map +1 -1
  3. package/dist/Schema.js +149 -78
  4. package/dist/Schema.js.map +1 -1
  5. package/dist/SchemaAST.d.ts.map +1 -1
  6. package/dist/SchemaAST.js +2 -1
  7. package/dist/SchemaAST.js.map +1 -1
  8. package/dist/SchemaRepresentation.d.ts +10 -1
  9. package/dist/SchemaRepresentation.d.ts.map +1 -1
  10. package/dist/SchemaRepresentation.js +12 -5
  11. package/dist/SchemaRepresentation.js.map +1 -1
  12. package/dist/SchemaTransformation.d.ts.map +1 -1
  13. package/dist/SchemaTransformation.js +57 -18
  14. package/dist/SchemaTransformation.js.map +1 -1
  15. package/dist/internal/schema/representation.js +1 -0
  16. package/dist/internal/schema/representation.js.map +1 -1
  17. package/dist/unstable/ai/McpSchema.js +1 -1
  18. package/dist/unstable/ai/McpSchema.js.map +1 -1
  19. package/dist/unstable/cli/CliError.js +1 -1
  20. package/dist/unstable/cli/CliError.js.map +1 -1
  21. package/dist/unstable/cluster/ClusterError.js +2 -2
  22. package/dist/unstable/cluster/ClusterError.js.map +1 -1
  23. package/dist/unstable/cluster/Reply.js +1 -1
  24. package/dist/unstable/cluster/Reply.js.map +1 -1
  25. package/dist/unstable/devtools/DevToolsSchema.js +5 -1
  26. package/dist/unstable/devtools/DevToolsSchema.js.map +1 -1
  27. package/dist/unstable/http/HttpClientError.js +1 -1
  28. package/dist/unstable/http/HttpClientError.js.map +1 -1
  29. package/dist/unstable/httpapi/HttpApiScalar.d.ts +2 -0
  30. package/dist/unstable/httpapi/HttpApiScalar.d.ts.map +1 -1
  31. package/dist/unstable/httpapi/HttpApiScalar.js +12 -6
  32. package/dist/unstable/httpapi/HttpApiScalar.js.map +1 -1
  33. package/dist/unstable/persistence/Persistable.js +1 -1
  34. package/dist/unstable/persistence/Persistable.js.map +1 -1
  35. package/dist/unstable/persistence/PersistedQueue.js +1 -1
  36. package/dist/unstable/persistence/PersistedQueue.js.map +1 -1
  37. package/dist/unstable/persistence/Persistence.js +1 -1
  38. package/dist/unstable/persistence/Persistence.js.map +1 -1
  39. package/dist/unstable/persistence/RateLimiter.js +1 -1
  40. package/dist/unstable/persistence/RateLimiter.js.map +1 -1
  41. package/dist/unstable/persistence/Redis.js +1 -1
  42. package/dist/unstable/persistence/Redis.js.map +1 -1
  43. package/dist/unstable/reactivity/AsyncResult.js +1 -1
  44. package/dist/unstable/reactivity/AsyncResult.js.map +1 -1
  45. package/dist/unstable/rpc/Rpc.d.ts +1 -1
  46. package/dist/unstable/rpc/Rpc.js +2 -2
  47. package/dist/unstable/rpc/Rpc.js.map +1 -1
  48. package/dist/unstable/rpc/RpcClient.js +1 -1
  49. package/dist/unstable/rpc/RpcClient.js.map +1 -1
  50. package/dist/unstable/rpc/RpcClientError.js +1 -1
  51. package/dist/unstable/rpc/RpcClientError.js.map +1 -1
  52. package/dist/unstable/rpc/RpcMessage.d.ts +2 -2
  53. package/dist/unstable/rpc/RpcMessage.js +3 -3
  54. package/dist/unstable/rpc/RpcMessage.js.map +1 -1
  55. package/dist/unstable/socket/Socket.js +3 -3
  56. package/dist/unstable/socket/Socket.js.map +1 -1
  57. package/dist/unstable/sql/SqlError.js +1 -1
  58. package/dist/unstable/sql/SqlError.js.map +1 -1
  59. package/dist/unstable/workers/WorkerError.js +4 -4
  60. package/dist/unstable/workers/WorkerError.js.map +1 -1
  61. package/dist/unstable/workflow/Activity.js +1 -1
  62. package/dist/unstable/workflow/Activity.js.map +1 -1
  63. package/dist/unstable/workflow/DurableDeferred.js +1 -1
  64. package/dist/unstable/workflow/DurableDeferred.js.map +1 -1
  65. package/dist/unstable/workflow/Workflow.js +2 -2
  66. package/dist/unstable/workflow/Workflow.js.map +1 -1
  67. package/package.json +1 -1
  68. package/src/Schema.ts +179 -117
  69. package/src/SchemaAST.ts +3 -1
  70. package/src/SchemaRepresentation.ts +12 -4
  71. package/src/SchemaTransformation.ts +75 -25
  72. package/src/internal/schema/representation.ts +1 -0
  73. package/src/unstable/ai/McpSchema.ts +1 -1
  74. package/src/unstable/cli/CliError.ts +1 -1
  75. package/src/unstable/cluster/ClusterError.ts +2 -2
  76. package/src/unstable/cluster/Reply.ts +1 -1
  77. package/src/unstable/devtools/DevToolsSchema.ts +1 -1
  78. package/src/unstable/http/HttpClientError.ts +1 -1
  79. package/src/unstable/httpapi/HttpApiScalar.ts +14 -7
  80. package/src/unstable/persistence/Persistable.ts +1 -1
  81. package/src/unstable/persistence/PersistedQueue.ts +1 -1
  82. package/src/unstable/persistence/Persistence.ts +1 -1
  83. package/src/unstable/persistence/RateLimiter.ts +1 -1
  84. package/src/unstable/persistence/Redis.ts +1 -1
  85. package/src/unstable/reactivity/AsyncResult.ts +1 -1
  86. package/src/unstable/rpc/Rpc.ts +3 -3
  87. package/src/unstable/rpc/RpcClient.ts +1 -1
  88. package/src/unstable/rpc/RpcClientError.ts +1 -1
  89. package/src/unstable/rpc/RpcMessage.ts +3 -3
  90. package/src/unstable/socket/Socket.ts +3 -3
  91. package/src/unstable/sql/SqlError.ts +1 -1
  92. package/src/unstable/workers/WorkerError.ts +4 -4
  93. package/src/unstable/workflow/Activity.ts +1 -1
  94. package/src/unstable/workflow/DurableDeferred.ts +1 -1
  95. package/src/unstable/workflow/Workflow.ts +2 -2
package/src/Schema.ts CHANGED
@@ -31,7 +31,7 @@
31
31
  * - Type guard: {@link is}
32
32
  * - Assertion: {@link asserts}
33
33
  * - Add constraints: `.check(...)` with filters like {@link isMinLength},
34
- * {@link isGreaterThan}, {@link isPattern}, {@link isUUID}
34
+ * {@link isGreaterThan}, {@link isPattern}, {@link isUUID}, {@link isGUID}
35
35
  * - Transform between schemas: {@link decodeTo}, {@link encodeTo}
36
36
  * - Add a default for missing keys: {@link withDecodingDefault}, {@link withDecodingDefaultKey}
37
37
  * - Create branded types: {@link brand}
@@ -6235,7 +6235,7 @@ export const isStringBigInt: (annotations?: Annotations.Filter) => SchemaAST.Fil
6235
6235
  export const isStringSymbol: (annotations?: Annotations.Filter) => SchemaAST.Filter<string> = SchemaAST.isStringSymbol
6236
6236
 
6237
6237
  /**
6238
- * Returns a RegExp for validating an RFC 4122 UUID.
6238
+ * Returns a RegExp for validating an RFC 9562 / RFC 4122 UUID.
6239
6239
  *
6240
6240
  * Optionally specify a version 1-8. If no version is specified (`undefined`), all versions are supported.
6241
6241
  */
@@ -6245,16 +6245,25 @@ const getUUIDRegExp = (version?: 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8): globalThis.RegE
6245
6245
  `^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-${version}[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12})$`
6246
6246
  )
6247
6247
  }
6248
- return /^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000)$/;
6248
+ return /^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|[fF]{8}-[fF]{4}-[fF]{4}-[fF]{4}-[fF]{12})$/;
6249
6249
  }
6250
6250
 
6251
6251
  /**
6252
- * Validates that a string is a valid Universally Unique Identifier (UUID).
6253
- * Optionally specify a version (1-8) to validate against a specific UUID version.
6254
- * If no version is specified (`undefined`), all versions are supported.
6252
+ * Validates that a string is a strict Universally Unique Identifier (UUID).
6253
+ *
6254
+ * **When to use**
6255
+ *
6256
+ * Use when you need UUID semantics, including version and RFC variant bits,
6257
+ * rather than only the dashed hexadecimal shape.
6255
6258
  *
6256
6259
  * **Details**
6257
6260
  *
6261
+ * Without a version argument, this accepts UUID versions 1 through 8, the nil
6262
+ * UUID (`00000000-0000-0000-0000-000000000000`), and the max UUID
6263
+ * (`ffffffff-ffff-ffff-ffff-ffffffffffff`). With a version argument, this
6264
+ * accepts only UUIDs with that version and RFC variant bits; nil and max UUIDs
6265
+ * are not versioned UUIDs and do not match version-specific checks.
6266
+ *
6258
6267
  * JSON Schema:
6259
6268
  *
6260
6269
  * This check corresponds to a `pattern` constraint in JSON Schema that matches
@@ -6265,6 +6274,7 @@ const getUUIDRegExp = (version?: 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8): globalThis.RegE
6265
6274
  * When generating test data with fast-check, this applies a `patterns`
6266
6275
  * constraint to ensure generated strings match the UUID pattern.
6267
6276
  *
6277
+ * @see {@link isGUID} for shape-only GUID validation.
6268
6278
  * @category String checks
6269
6279
  * @since 4.0.0
6270
6280
  */
@@ -6284,6 +6294,46 @@ export function isUUID(version?: 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8, annotations?: An
6284
6294
  )
6285
6295
  }
6286
6296
 
6297
+ const GUID_REGEXP = /^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$/
6298
+
6299
+ /**
6300
+ * Validates that a string has the GUID / UUID textual shape.
6301
+ *
6302
+ * **When to use**
6303
+ *
6304
+ * Use when you need to accept dashed hexadecimal identifiers without enforcing
6305
+ * UUID version or variant bits.
6306
+ *
6307
+ * **Details**
6308
+ *
6309
+ * This check accepts strings in the `8-4-4-4-12` hexadecimal form. JSON Schema
6310
+ * output includes the corresponding `pattern` constraint and intentionally does
6311
+ * not include `format: "uuid"` because GUID validation is looser than UUID
6312
+ * validation.
6313
+ *
6314
+ * Arbitrary:
6315
+ *
6316
+ * When generating test data with fast-check, this applies a `patterns`
6317
+ * constraint to ensure generated strings match the GUID pattern.
6318
+ *
6319
+ * @see {@link isUUID} for strict UUID validation.
6320
+ * @category String checks
6321
+ * @since 4.0.0
6322
+ */
6323
+ export function isGUID(annotations?: Annotations.Filter) {
6324
+ return isPattern(
6325
+ GUID_REGEXP,
6326
+ {
6327
+ expected: "a GUID",
6328
+ meta: {
6329
+ _tag: "isGUID",
6330
+ regExp: GUID_REGEXP
6331
+ },
6332
+ ...annotations
6333
+ }
6334
+ )
6335
+ }
6336
+
6287
6337
  /**
6288
6338
  * Validates that a string is a valid ULID (Universally Unique Lexicographically
6289
6339
  * Sortable Identifier).
@@ -8979,69 +9029,87 @@ export interface Error extends instanceOf<globalThis.Error> {
8979
9029
  readonly "Rebuild": Error
8980
9030
  }
8981
9031
 
8982
- const ErrorJsonEncoded = Struct({
8983
- message: String,
8984
- name: optionalKey(String),
8985
- stack: optionalKey(String)
8986
- })
8987
-
8988
9032
  /**
8989
- * Schema for JavaScript `Error` objects.
8990
- *
8991
- * **Details**
8992
- *
8993
- * Default JSON serializer:
8994
- * Encodes an `Error` as an object with `message` and optional `name` properties,
8995
- * and decodes that object back into an `Error`. The stack trace is omitted from
8996
- * the encoded form for security.
9033
+ * Options for {@link Error} and {@link Defect}.
8997
9034
  *
8998
- * @category schemas
9035
+ * @category options
8999
9036
  * @since 4.0.0
9000
9037
  */
9001
- export const Error: Error = instanceOf(globalThis.Error, {
9002
- typeConstructor: {
9003
- _tag: "Error"
9004
- },
9005
- generation: {
9006
- runtime: `Schema.Error`,
9007
- Type: `globalThis.Error`
9008
- },
9009
- expected: "Error",
9010
- toCodecJson: () => link<globalThis.Error>()(ErrorJsonEncoded, SchemaTransformation.errorFromErrorJsonEncoded()),
9011
- toArbitrary: () => (fc) => fc.string().map((message) => new globalThis.Error(message))
9012
- })
9038
+ export interface ErrorOptions {
9039
+ /**
9040
+ * Includes string stack traces in encoded `Error` values when set to `true`.
9041
+ *
9042
+ * @default false
9043
+ */
9044
+ readonly includeStack?: boolean | undefined
9045
+ /**
9046
+ * Excludes `Error.cause` values from encoded `Error` values when set to
9047
+ * `true`.
9048
+ *
9049
+ * @default false
9050
+ */
9051
+ readonly excludeCause?: boolean | undefined
9052
+ }
9053
+
9054
+ type ErrorOptionsKey = 0 | 1 | 2 | 3
9055
+
9056
+ const getErrorOptionsKey = (options?: ErrorOptions): ErrorOptionsKey =>
9057
+ ((options?.includeStack === true ? 1 : 0) |
9058
+ (options?.excludeCause === true ? 2 : 0)) as ErrorOptionsKey
9059
+
9060
+ const getErrorOptions = (key: ErrorOptionsKey): ErrorOptions | undefined => {
9061
+ switch (key) {
9062
+ case 0:
9063
+ return undefined
9064
+ case 1:
9065
+ return { includeStack: true }
9066
+ case 2:
9067
+ return { excludeCause: true }
9068
+ case 3:
9069
+ return { includeStack: true, excludeCause: true }
9070
+ }
9071
+ }
9072
+
9073
+ const errorSchemaCache: Array<Error | undefined> = []
9013
9074
 
9014
9075
  /**
9015
- * Schema for JavaScript `Error` objects that preserves stack traces in the JSON
9016
- * encoded form.
9076
+ * Schema for JavaScript `Error` objects.
9017
9077
  *
9018
9078
  * **Details**
9019
9079
  *
9020
9080
  * Default JSON serializer:
9081
+ *
9021
9082
  * Encodes an `Error` as an object with `message`, optional `name`, and optional
9022
- * `stack` properties, and decodes that object back into an `Error`.
9083
+ * `cause` properties, and decodes that object back into an `Error`. Stack
9084
+ * traces are omitted by default for security. Pass `{ includeStack: true }` to
9085
+ * include stack traces, or `{ excludeCause: true }` to omit causes.
9023
9086
  *
9024
- * @category schemas
9087
+ * @category constructors
9025
9088
  * @since 4.0.0
9026
9089
  */
9027
- export const ErrorWithStack: Error = instanceOf(globalThis.Error, {
9028
- typeConstructor: {
9029
- _tag: "ErrorWithStack"
9030
- },
9031
- generation: {
9032
- runtime: `Schema.ErrorWithStack`,
9033
- Type: `globalThis.Error`
9034
- },
9035
- expected: "Error",
9036
- toCodecJson: () =>
9037
- link<globalThis.Error>()(
9038
- ErrorJsonEncoded,
9039
- SchemaTransformation.errorFromErrorJsonEncoded({
9040
- includeStack: true
9041
- })
9042
- ),
9043
- toArbitrary: () => (fc) => fc.string().map((message) => new globalThis.Error(message))
9044
- })
9090
+ export function Error(options?: ErrorOptions): Error {
9091
+ const key = getErrorOptionsKey(options)
9092
+ const cached = errorSchemaCache[key]
9093
+ if (cached !== undefined) {
9094
+ return cached
9095
+ }
9096
+ const normalizedOptions = getErrorOptions(key)
9097
+ const schema = instanceOf(globalThis.Error, {
9098
+ typeConstructor: {
9099
+ _tag: "Error",
9100
+ ...(normalizedOptions === undefined ? {} : { options: normalizedOptions })
9101
+ },
9102
+ generation: {
9103
+ runtime: normalizedOptions !== undefined ? `Schema.Error(${format(normalizedOptions)})` : `Schema.Error()`,
9104
+ Type: `globalThis.Error`
9105
+ },
9106
+ expected: "Error",
9107
+ toCodecJson: () => link<globalThis.Error>()(JsonError, SchemaTransformation.errorFromJsonError(normalizedOptions)),
9108
+ toArbitrary: () => (fc) => fc.string().map((message) => new globalThis.Error(message))
9109
+ })
9110
+ errorSchemaCache[key] = schema
9111
+ return schema
9112
+ }
9045
9113
 
9046
9114
  /**
9047
9115
  * Type-level representation of {@link Defect}.
@@ -9049,80 +9117,63 @@ export const ErrorWithStack: Error = instanceOf(globalThis.Error, {
9049
9117
  * @category Defect
9050
9118
  * @since 3.10.0
9051
9119
  */
9052
- export interface Defect extends
9053
- Union<
9054
- readonly [
9055
- decodeTo<
9056
- Error,
9057
- Struct<{
9058
- readonly message: String
9059
- readonly name: optionalKey<String>
9060
- readonly stack: optionalKey<String>
9061
- }>
9062
- >,
9063
- decodeTo<Unknown, Any>
9064
- ]
9065
- >
9066
- {
9120
+ export interface Defect extends decodeTo<Unknown, typeof Json> {
9067
9121
  readonly "Rebuild": Defect
9068
9122
  }
9069
9123
 
9070
- const defectTransformation = new SchemaTransformation.Transformation(
9071
- SchemaGetter.passthrough(),
9072
- SchemaGetter.transform((u) => {
9073
- try {
9074
- return JSON.parse(JSON.stringify(u))
9075
- } catch {
9076
- return format(u)
9077
- }
9078
- })
9079
- )
9124
+ const defectSchemaCache: Array<Defect | undefined> = []
9080
9125
 
9081
9126
  /**
9082
- * Schema for defect values, accepting either JavaScript `Error` values encoded
9083
- * with `message` and optional `name`, or arbitrary unknown defect values.
9127
+ * Schema for unexpected defect values represented as `unknown` with a JSON
9128
+ * encoded form.
9129
+ *
9130
+ * **When to use**
9131
+ *
9132
+ * Use when you need a schema for `Cause` defects or other unexpected failures
9133
+ * whose runtime value may be any value.
9084
9134
  *
9085
9135
  * **Details**
9086
9136
  *
9087
- * Default JSON serializer:
9088
- * Unknown defects are serialized with `JSON.stringify` when possible and fall
9089
- * back to Effect's formatted representation when JSON serialization fails.
9137
+ * The encoded side is {@link Json}. During decoding, JSON objects with a string
9138
+ * `message` property are decoded into JavaScript `Error` values, preserving a
9139
+ * non-default `name` and any string `stack`. Other JSON values decode
9140
+ * unchanged.
9090
9141
  *
9091
- * @category constructors
9092
- * @since 3.10.0
9093
- */
9094
- export const Defect: Defect = Union([
9095
- ErrorJsonEncoded.pipe(decodeTo(Error, SchemaTransformation.errorFromErrorJsonEncoded())),
9096
- Any.pipe(decodeTo(
9097
- Unknown.annotate({
9098
- toCodecJson: () => link<unknown>()(Any, defectTransformation),
9099
- toArbitrary: () => (fc) => fc.json()
9100
- }),
9101
- defectTransformation
9102
- ))
9103
- ])
9104
-
9105
- /**
9106
- * Schema for defects that also includes stack traces in the encoded form.
9142
+ * During encoding, JavaScript `Error` values encode to JSON objects with
9143
+ * `name`, `message`, and optional `cause` properties. Pass
9144
+ * `{ includeStack: true }` to include string stack traces in encoded `Error`
9145
+ * defects, or `{ excludeCause: true }` to omit causes. Other values are
9146
+ * serialized through Effect's JSON formatter and then parsed back into JSON
9147
+ * when possible.
9107
9148
  *
9108
- * @category Defect
9149
+ * **Gotchas**
9150
+ *
9151
+ * This schema is for carrying defects across JSON boundaries, not for
9152
+ * preserving every JavaScript value exactly. Some values cannot round-trip
9153
+ * unchanged:
9154
+ *
9155
+ * - A non-`Error` object such as `{ message: "boom" }` encodes as an
9156
+ * error-shaped JSON object and decodes back as an `Error`.
9157
+ * - JSON serialization normalizes unsupported values. For example,
9158
+ * `undefined` array elements encode as `null`, unsupported object properties
9159
+ * are omitted, and circular references are dropped.
9160
+ * - Values that cannot be represented as JSON fall back to Effect's formatted
9161
+ * string representation.
9162
+ *
9163
+ * @see {@link Error} for a schema that only accepts JavaScript `Error` values.
9164
+ * @category constructors
9109
9165
  * @since 4.0.0
9110
9166
  */
9111
- export const DefectWithStack: Defect = Union([
9112
- ErrorJsonEncoded.pipe(decodeTo(
9113
- ErrorWithStack,
9114
- SchemaTransformation.errorFromErrorJsonEncoded({
9115
- includeStack: true
9116
- })
9117
- )),
9118
- Any.pipe(decodeTo(
9119
- Unknown.annotate({
9120
- toCodecJson: () => link<unknown>()(Any, defectTransformation),
9121
- toArbitrary: () => (fc) => fc.json()
9122
- }),
9123
- defectTransformation
9124
- ))
9125
- ])
9167
+ export function Defect(options?: ErrorOptions): Defect {
9168
+ const key = getErrorOptionsKey(options)
9169
+ const cached = defectSchemaCache[key]
9170
+ if (cached !== undefined) {
9171
+ return cached
9172
+ }
9173
+ const schema = Json.pipe(decodeTo(Unknown, SchemaTransformation.defectFromJson(getErrorOptions(key))))
9174
+ defectSchemaCache[key] = schema
9175
+ return schema
9176
+ }
9126
9177
 
9127
9178
  /**
9128
9179
  * Type-level representation returned by {@link Exit}.
@@ -13730,6 +13781,13 @@ export interface JsonObject {
13730
13781
  */
13731
13782
  export const Json: Codec<Json> = make(SchemaAST.Json)
13732
13783
 
13784
+ const JsonError = Struct({
13785
+ message: String,
13786
+ name: optionalKey(String),
13787
+ stack: optionalKey(String),
13788
+ cause: optionalKey(Json)
13789
+ })
13790
+
13733
13791
  /**
13734
13792
  * Recursive TypeScript type for mutable JSON values: `null`, `number`,
13735
13793
  * `boolean`, `string`, mutable arrays, or mutable string-keyed records.
@@ -14312,6 +14370,10 @@ export declare namespace Annotations {
14312
14370
  readonly regExp: globalThis.RegExp
14313
14371
  readonly version: 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | undefined
14314
14372
  }
14373
+ readonly isGUID: {
14374
+ readonly _tag: "isGUID"
14375
+ readonly regExp: globalThis.RegExp
14376
+ }
14315
14377
  readonly isULID: {
14316
14378
  readonly _tag: "isULID"
14317
14379
  readonly regExp: globalThis.RegExp
package/src/SchemaAST.ts CHANGED
@@ -93,6 +93,7 @@ import * as SchemaGetter from "./SchemaGetter.ts"
93
93
  import * as SchemaIssue from "./SchemaIssue.ts"
94
94
  import type * as SchemaParser from "./SchemaParser.ts"
95
95
  import * as SchemaTransformation from "./SchemaTransformation.ts"
96
+ import type * as FastCheck from "./testing/FastCheck.ts"
96
97
 
97
98
  /**
98
99
  * Discriminated union of all AST node types.
@@ -3790,7 +3791,8 @@ export const Json = new Declaration(
3790
3791
  Type: `Schema.Json`
3791
3792
  },
3792
3793
  expected: "JSON value",
3793
- toCodecJson: () => new Link(unknown, SchemaTransformation.passthrough())
3794
+ toCodecJson: () => new Link(unknown, SchemaTransformation.passthrough()),
3795
+ toArbitrary: () => (fc: typeof FastCheck) => fc.jsonValue()
3794
3796
  }
3795
3797
  )
3796
3798
 
@@ -612,6 +612,7 @@ export type StringMeta = Schema.Annotations.BuiltInMetaDefinitions[
612
612
  | "isLengthBetween"
613
613
  | "isTrimmed"
614
614
  | "isUUID"
615
+ | "isGUID"
615
616
  | "isULID"
616
617
  | "isBase64"
617
618
  | "isBase64Url"
@@ -973,6 +974,11 @@ const $IsUUID = Schema.Struct({
973
974
  version: Schema.UndefinedOr(Schema.Literals([1, 2, 3, 4, 5, 6, 7, 8]))
974
975
  }).annotate({ identifier: "IsUUID" })
975
976
 
977
+ const $IsGUID = Schema.Struct({
978
+ _tag: Schema.tag("isGUID"),
979
+ regExp: Schema.RegExp
980
+ }).annotate({ identifier: "IsGUID" })
981
+
976
982
  const $IsULID = Schema.Struct({
977
983
  _tag: Schema.tag("isULID"),
978
984
  regExp: Schema.RegExp
@@ -1061,6 +1067,7 @@ export const $StringMeta = Schema.Union([
1061
1067
  $IsStringSymbol,
1062
1068
  $IsTrimmed,
1063
1069
  $IsUUID,
1070
+ $IsGUID,
1064
1071
  $IsULID,
1065
1072
  $IsBase64,
1066
1073
  $IsBase64Url,
@@ -1832,9 +1839,7 @@ export const toSchemaDefaultReviver: Reviver<Schema.Top> = (s, recur) => {
1832
1839
  case "Date":
1833
1840
  return Schema.Date
1834
1841
  case "Error":
1835
- return Schema.Error
1836
- case "ErrorWithStack":
1837
- return Schema.ErrorWithStack
1842
+ return Schema.Error(typeConstructor.options as Schema.ErrorOptions | undefined)
1838
1843
  case "File":
1839
1844
  return Schema.File
1840
1845
  case "FormData":
@@ -2148,6 +2153,8 @@ export function toSchema<S extends Schema.Top = Schema.Top>(document: Document,
2148
2153
  return Schema.isTrimmed(a)
2149
2154
  case "isUUID":
2150
2155
  return Schema.isUUID(filter.meta.version, a)
2156
+ case "isGUID":
2157
+ return Schema.isGUID(a)
2151
2158
  case "isULID":
2152
2159
  return Schema.isULID(a)
2153
2160
  case "isBase64":
@@ -2779,6 +2786,7 @@ export function toCodeDocument(multiDocument: MultiDocument, options?: {
2779
2786
  const ca = a === "" ? "" : `, ${a}`
2780
2787
  switch (filter.meta._tag) {
2781
2788
  case "isTrimmed":
2789
+ case "isGUID":
2782
2790
  case "isULID":
2783
2791
  case "isBase64":
2784
2792
  case "isBase64Url":
@@ -2790,7 +2798,7 @@ export function toCodeDocument(multiDocument: MultiDocument, options?: {
2790
2798
  case "isInt":
2791
2799
  case "isUnique":
2792
2800
  case "isDateValid":
2793
- return `Schema.${filter.meta._tag}(${ca})`
2801
+ return `Schema.${filter.meta._tag}(${a})`
2794
2802
 
2795
2803
  case "isStringFinite":
2796
2804
  case "isStringBigInt":
@@ -89,9 +89,10 @@ import * as BigDecimal from "./BigDecimal.ts"
89
89
  import * as DateTime from "./DateTime.ts"
90
90
  import * as Duration from "./Duration.ts"
91
91
  import * as Effect from "./Effect.ts"
92
- import { formatDate } from "./Formatter.ts"
92
+ import { format, formatDate, formatJson } from "./Formatter.ts"
93
93
  import * as Option from "./Option.ts"
94
94
  import * as Predicate from "./Predicate.ts"
95
+ import type { ErrorOptions, Json } from "./Schema.ts"
95
96
  import type * as SchemaAST from "./SchemaAST.ts"
96
97
  import * as SchemaGetter from "./SchemaGetter.ts"
97
98
  import * as SchemaIssue from "./SchemaIssue.ts"
@@ -1075,35 +1076,84 @@ export const durationFromMillis: Transformation<Duration.Duration, number> = tra
1075
1076
  encode: (a) => Duration.toMillis(a)
1076
1077
  })
1077
1078
 
1078
- /** @internal */
1079
- export const errorFromErrorJsonEncoded = (options?: {
1080
- readonly includeStack?: boolean | undefined
1081
- }): Transformation<Error, {
1079
+ type JsonError = {
1082
1080
  message: string
1083
1081
  name?: string
1084
1082
  stack?: string
1085
- }> =>
1086
- transform({
1087
- decode: (i) => {
1088
- const err = new Error(i.message)
1089
- if (typeof i.name === "string" && i.name !== "Error") err.name = i.name
1090
- if (typeof i.stack === "string") err.stack = i.stack
1091
- return err
1092
- },
1093
- encode: (a) => {
1094
- const e: {
1095
- message: string
1096
- name?: string
1097
- stack?: string
1098
- } = {
1099
- name: a.name,
1100
- message: a.message
1101
- }
1102
- if (options?.includeStack && typeof a.stack === "string") {
1103
- e.stack = a.stack
1083
+ cause?: Json
1084
+ }
1085
+
1086
+ const isJsonError = (input: unknown): input is JsonError =>
1087
+ Predicate.isObject(input) && typeof input["message"] === "string"
1088
+
1089
+ const decodeJsonError = (input: JsonError): Error => {
1090
+ const hasCause = Object.hasOwn(input, "cause")
1091
+ const err = hasCause
1092
+ ? new Error(input.message, { cause: decodeDefect(input.cause as Json) })
1093
+ : new Error(input.message)
1094
+ if (typeof input.name === "string" && input.name !== "Error") err.name = input.name
1095
+ if (typeof input.stack === "string") err.stack = input.stack
1096
+ return err
1097
+ }
1098
+
1099
+ const encodeUnknownAsJson = (input: unknown): Json => {
1100
+ try {
1101
+ const json = formatJson(input)
1102
+ return json === undefined ? format(input) : JSON.parse(json)
1103
+ } catch {
1104
+ return format(input)
1105
+ }
1106
+ }
1107
+
1108
+ const encodeJsonError = (
1109
+ input: Error,
1110
+ options: ErrorOptions | undefined,
1111
+ encodeDefect: (input: unknown) => Json
1112
+ ): JsonError => {
1113
+ const encoded: JsonError = {
1114
+ name: input.name,
1115
+ message: input.message
1116
+ }
1117
+ if (options?.includeStack && typeof input.stack === "string") {
1118
+ encoded.stack = input.stack
1119
+ }
1120
+ if (!options?.excludeCause && input.cause !== undefined) {
1121
+ encoded.cause = encodeDefect(input.cause)
1122
+ }
1123
+ return encoded
1124
+ }
1125
+
1126
+ const makeEncodeDefect = (options?: ErrorOptions): (input: unknown) => Json => {
1127
+ const seen = new WeakSet<object>()
1128
+ const encode = (input: unknown): Json => {
1129
+ if (Predicate.isError(input)) {
1130
+ if (seen.has(input)) {
1131
+ return "[Circular]"
1104
1132
  }
1105
- return e
1133
+ seen.add(input)
1134
+ const encoded = encodeJsonError(input, options, encode)
1135
+ seen.delete(input)
1136
+ return encoded
1106
1137
  }
1138
+ return encodeUnknownAsJson(input)
1139
+ }
1140
+ return encode
1141
+ }
1142
+
1143
+ const decodeDefect = (input: Json): unknown => isJsonError(input) ? decodeJsonError(input) : input
1144
+
1145
+ /** @internal */
1146
+ export const errorFromJsonError = (options?: ErrorOptions): Transformation<Error, JsonError> =>
1147
+ transform({
1148
+ decode: decodeJsonError,
1149
+ encode: (input) => makeEncodeDefect(options)(input) as JsonError
1150
+ })
1151
+
1152
+ /** @internal */
1153
+ export const defectFromJson = (options?: ErrorOptions) =>
1154
+ transform({
1155
+ decode: decodeDefect,
1156
+ encode: makeEncodeDefect(options)
1107
1157
  })
1108
1158
 
1109
1159
  /**
@@ -660,6 +660,7 @@ export function toJsonSchemaMultiDocument(
660
660
  ? { allOf: [{ minItems: meta.minimum }, { maxItems: meta.maximum }] }
661
661
  : { allOf: [{ minLength: meta.minimum }, { maxLength: meta.maximum }] }
662
662
  case "isPattern":
663
+ case "isGUID":
663
664
  case "isULID":
664
665
  case "isBase64":
665
666
  case "isBase64Url":
@@ -2161,7 +2161,7 @@ export class ElicitationDeclined
2161
2161
  extends Schema.ErrorClass<ElicitationDeclined>("@effect/ai/McpSchema/ElicitationDeclined")({
2162
2162
  _tag: Schema.tag("ElicitationDeclined"),
2163
2163
  request: Elicit.payloadSchema,
2164
- cause: optional(Schema.Defect)
2164
+ cause: optional(Schema.Defect())
2165
2165
  })
2166
2166
  {}
2167
2167
 
@@ -481,7 +481,7 @@ export class UnknownSubcommand extends Schema.ErrorClass<UnknownSubcommand>(`${T
481
481
  */
482
482
  export class UserError extends Schema.ErrorClass<UserError>(`${TypeId}/UserError`)({
483
483
  _tag: Schema.tag("UserError"),
484
- cause: Schema.Defect
484
+ cause: Schema.Defect()
485
485
  }) {
486
486
  /**
487
487
  * Marks this value as a user handler error for runtime guards.
@@ -97,7 +97,7 @@ export class EntityNotAssignedToRunner
97
97
  */
98
98
  export class MalformedMessage extends Schema.ErrorClass<MalformedMessage>(`${TypeId}/MalformedMessage`)({
99
99
  _tag: Schema.tag("MalformedMessage"),
100
- cause: Schema.Defect
100
+ cause: Schema.Defect()
101
101
  }) {
102
102
  /**
103
103
  * Marks this value as a cluster error for runtime guards.
@@ -136,7 +136,7 @@ export class MalformedMessage extends Schema.ErrorClass<MalformedMessage>(`${Typ
136
136
  */
137
137
  export class PersistenceError extends Schema.ErrorClass<PersistenceError>(`${TypeId}/PersistenceError`)({
138
138
  _tag: Schema.tag("PersistenceError"),
139
- cause: Schema.Defect
139
+ cause: Schema.Defect()
140
140
  }) {
141
141
  /**
142
142
  * Marks this value as a cluster error for runtime guards.
@@ -111,7 +111,7 @@ export class ReplyWithContext<R extends Rpc.Any> extends Data.TaggedClass("Reply
111
111
  reply: new WithExit({
112
112
  requestId: options.requestId,
113
113
  id: options.id,
114
- exit: Exit.die(Schema.encodeSync(Schema.Defect)(options.defect))
114
+ exit: Exit.die(Schema.encodeSync(Schema.Defect())(options.defect))
115
115
  }),
116
116
  context: Context.empty() as any,
117
117
  rpc: neverRpc
@@ -64,7 +64,7 @@ export const SpanStatusEnded = Schema.Struct({
64
64
  _tag: Schema.tag("Ended"),
65
65
  startTime: Schema.BigInt,
66
66
  endTime: Schema.BigInt,
67
- exit: Schema.Exit(Schema.Void, Schema.DefectWithStack, Schema.DefectWithStack).pipe(
67
+ exit: Schema.Exit(Schema.Void, Schema.Defect({ includeStack: true }), Schema.Defect({ includeStack: true })).pipe(
68
68
  Schema.decodeTo(
69
69
  Schema.Exit(Schema.Unknown, Schema.Unknown, Schema.Unknown),
70
70
  SchemaTransformation.transform({
@@ -331,7 +331,7 @@ export class HttpClientErrorSchema extends Schema.ErrorClass<HttpClientErrorSche
331
331
  "EmptyBodyError"
332
332
  ] satisfies ReadonlyArray<HttpClientErrorReason["_tag"]>
333
333
  ),
334
- cause: Schema.optional(Schema.Defect)
334
+ cause: Schema.optional(Schema.Defect())
335
335
  }) {
336
336
  /**
337
337
  * Builds the serializable schema representation for an HTTP client error.