effect 3.12.11 → 3.13.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 (204) hide show
  1. package/README.md +38 -49
  2. package/dist/cjs/Channel.js.map +1 -1
  3. package/dist/cjs/DateTime.js +17 -1
  4. package/dist/cjs/DateTime.js.map +1 -1
  5. package/dist/cjs/Differ.js.map +1 -1
  6. package/dist/cjs/Duration.js +128 -1
  7. package/dist/cjs/Duration.js.map +1 -1
  8. package/dist/cjs/Effect.js +175 -37
  9. package/dist/cjs/Effect.js.map +1 -1
  10. package/dist/cjs/Either.js +2 -1
  11. package/dist/cjs/Either.js.map +1 -1
  12. package/dist/cjs/FiberHandle.js +54 -21
  13. package/dist/cjs/FiberHandle.js.map +1 -1
  14. package/dist/cjs/FiberMap.js +51 -24
  15. package/dist/cjs/FiberMap.js.map +1 -1
  16. package/dist/cjs/FiberSet.js +50 -17
  17. package/dist/cjs/FiberSet.js.map +1 -1
  18. package/dist/cjs/HashMap.js +19 -1
  19. package/dist/cjs/HashMap.js.map +1 -1
  20. package/dist/cjs/HashSet.js +9 -1
  21. package/dist/cjs/HashSet.js.map +1 -1
  22. package/dist/cjs/Layer.js +21 -1
  23. package/dist/cjs/Layer.js.map +1 -1
  24. package/dist/cjs/Match.js +659 -38
  25. package/dist/cjs/Match.js.map +1 -1
  26. package/dist/cjs/RcMap.js +11 -1
  27. package/dist/cjs/RcMap.js.map +1 -1
  28. package/dist/cjs/Reloadable.js.map +1 -1
  29. package/dist/cjs/STM.js.map +1 -1
  30. package/dist/cjs/Schedule.js +1074 -309
  31. package/dist/cjs/Schedule.js.map +1 -1
  32. package/dist/cjs/Schema.js +73 -1
  33. package/dist/cjs/Schema.js.map +1 -1
  34. package/dist/cjs/Stream.js.map +1 -1
  35. package/dist/cjs/internal/channel.js.map +1 -1
  36. package/dist/cjs/internal/core-effect.js.map +1 -1
  37. package/dist/cjs/internal/core.js +27 -3
  38. package/dist/cjs/internal/core.js.map +1 -1
  39. package/dist/cjs/internal/dateTime.js +4 -1
  40. package/dist/cjs/internal/dateTime.js.map +1 -1
  41. package/dist/cjs/internal/differ.js +4 -0
  42. package/dist/cjs/internal/differ.js.map +1 -1
  43. package/dist/cjs/internal/effect/circular.js +3 -2
  44. package/dist/cjs/internal/effect/circular.js.map +1 -1
  45. package/dist/cjs/internal/fiberRuntime.js +21 -7
  46. package/dist/cjs/internal/fiberRuntime.js.map +1 -1
  47. package/dist/cjs/internal/hashMap.js +10 -1
  48. package/dist/cjs/internal/hashMap.js.map +1 -1
  49. package/dist/cjs/internal/keyedPool.js +1 -1
  50. package/dist/cjs/internal/keyedPool.js.map +1 -1
  51. package/dist/cjs/internal/layer.js.map +1 -1
  52. package/dist/cjs/internal/rcMap.js +86 -56
  53. package/dist/cjs/internal/rcMap.js.map +1 -1
  54. package/dist/cjs/internal/reloadable.js.map +1 -1
  55. package/dist/cjs/internal/schedule.js.map +1 -1
  56. package/dist/cjs/internal/sink.js.map +1 -1
  57. package/dist/cjs/internal/stm/stm.js.map +1 -1
  58. package/dist/cjs/internal/stream.js.map +1 -1
  59. package/dist/cjs/internal/version.js +1 -1
  60. package/dist/cjs/internal/version.js.map +1 -1
  61. package/dist/dts/Channel.d.ts +4 -4
  62. package/dist/dts/Channel.d.ts.map +1 -1
  63. package/dist/dts/DateTime.d.ts +16 -0
  64. package/dist/dts/DateTime.d.ts.map +1 -1
  65. package/dist/dts/Differ.d.ts +2 -1
  66. package/dist/dts/Differ.d.ts.map +1 -1
  67. package/dist/dts/Duration.d.ts +64 -0
  68. package/dist/dts/Duration.d.ts.map +1 -1
  69. package/dist/dts/Effect.d.ts +402 -30
  70. package/dist/dts/Effect.d.ts.map +1 -1
  71. package/dist/dts/Either.d.ts +7 -0
  72. package/dist/dts/Either.d.ts.map +1 -1
  73. package/dist/dts/FiberHandle.d.ts +26 -0
  74. package/dist/dts/FiberHandle.d.ts.map +1 -1
  75. package/dist/dts/FiberMap.d.ts +26 -0
  76. package/dist/dts/FiberMap.d.ts.map +1 -1
  77. package/dist/dts/FiberSet.d.ts +25 -0
  78. package/dist/dts/FiberSet.d.ts.map +1 -1
  79. package/dist/dts/HashMap.d.ts +38 -0
  80. package/dist/dts/HashMap.d.ts.map +1 -1
  81. package/dist/dts/HashSet.d.ts +7 -0
  82. package/dist/dts/HashSet.d.ts.map +1 -1
  83. package/dist/dts/Layer.d.ts +32 -13
  84. package/dist/dts/Layer.d.ts.map +1 -1
  85. package/dist/dts/Match.d.ts +731 -48
  86. package/dist/dts/Match.d.ts.map +1 -1
  87. package/dist/dts/RcMap.d.ts +32 -0
  88. package/dist/dts/RcMap.d.ts.map +1 -1
  89. package/dist/dts/Reloadable.d.ts +13 -13
  90. package/dist/dts/Reloadable.d.ts.map +1 -1
  91. package/dist/dts/STM.d.ts +4 -4
  92. package/dist/dts/STM.d.ts.map +1 -1
  93. package/dist/dts/Schedule.d.ts +2294 -633
  94. package/dist/dts/Schedule.d.ts.map +1 -1
  95. package/dist/dts/Schema.d.ts +40 -4
  96. package/dist/dts/Schema.d.ts.map +1 -1
  97. package/dist/dts/Stream.d.ts +8 -8
  98. package/dist/dts/Stream.d.ts.map +1 -1
  99. package/dist/dts/Trie.d.ts +7 -7
  100. package/dist/dts/Trie.d.ts.map +1 -1
  101. package/dist/dts/index.d.ts +25 -0
  102. package/dist/dts/index.d.ts.map +1 -1
  103. package/dist/dts/internal/stm/stm.d.ts +2 -2
  104. package/dist/dts/internal/stm/stm.d.ts.map +1 -1
  105. package/dist/esm/Channel.js.map +1 -1
  106. package/dist/esm/DateTime.js +16 -0
  107. package/dist/esm/DateTime.js.map +1 -1
  108. package/dist/esm/Differ.js.map +1 -1
  109. package/dist/esm/Duration.js +124 -0
  110. package/dist/esm/Duration.js.map +1 -1
  111. package/dist/esm/Effect.js +170 -32
  112. package/dist/esm/Effect.js.map +1 -1
  113. package/dist/esm/Either.js +7 -0
  114. package/dist/esm/Either.js.map +1 -1
  115. package/dist/esm/FiberHandle.js +48 -18
  116. package/dist/esm/FiberHandle.js.map +1 -1
  117. package/dist/esm/FiberMap.js +46 -22
  118. package/dist/esm/FiberMap.js.map +1 -1
  119. package/dist/esm/FiberSet.js +45 -15
  120. package/dist/esm/FiberSet.js.map +1 -1
  121. package/dist/esm/HashMap.js +17 -0
  122. package/dist/esm/HashMap.js.map +1 -1
  123. package/dist/esm/HashSet.js +7 -0
  124. package/dist/esm/HashSet.js.map +1 -1
  125. package/dist/esm/Layer.js +20 -0
  126. package/dist/esm/Layer.js.map +1 -1
  127. package/dist/esm/Match.js +665 -40
  128. package/dist/esm/Match.js.map +1 -1
  129. package/dist/esm/RcMap.js +10 -0
  130. package/dist/esm/RcMap.js.map +1 -1
  131. package/dist/esm/Reloadable.js.map +1 -1
  132. package/dist/esm/STM.js.map +1 -1
  133. package/dist/esm/Schedule.js +1074 -309
  134. package/dist/esm/Schedule.js.map +1 -1
  135. package/dist/esm/Schema.js +71 -0
  136. package/dist/esm/Schema.js.map +1 -1
  137. package/dist/esm/Stream.js.map +1 -1
  138. package/dist/esm/index.js +25 -0
  139. package/dist/esm/index.js.map +1 -1
  140. package/dist/esm/internal/channel.js.map +1 -1
  141. package/dist/esm/internal/core-effect.js.map +1 -1
  142. package/dist/esm/internal/core.js +23 -0
  143. package/dist/esm/internal/core.js.map +1 -1
  144. package/dist/esm/internal/dateTime.js +2 -0
  145. package/dist/esm/internal/dateTime.js.map +1 -1
  146. package/dist/esm/internal/differ.js +4 -0
  147. package/dist/esm/internal/differ.js.map +1 -1
  148. package/dist/esm/internal/effect/circular.js +3 -2
  149. package/dist/esm/internal/effect/circular.js.map +1 -1
  150. package/dist/esm/internal/fiberRuntime.js +18 -5
  151. package/dist/esm/internal/fiberRuntime.js.map +1 -1
  152. package/dist/esm/internal/hashMap.js +9 -0
  153. package/dist/esm/internal/hashMap.js.map +1 -1
  154. package/dist/esm/internal/keyedPool.js +1 -1
  155. package/dist/esm/internal/keyedPool.js.map +1 -1
  156. package/dist/esm/internal/layer.js.map +1 -1
  157. package/dist/esm/internal/rcMap.js +85 -55
  158. package/dist/esm/internal/rcMap.js.map +1 -1
  159. package/dist/esm/internal/reloadable.js.map +1 -1
  160. package/dist/esm/internal/schedule.js.map +1 -1
  161. package/dist/esm/internal/sink.js.map +1 -1
  162. package/dist/esm/internal/stm/stm.js.map +1 -1
  163. package/dist/esm/internal/stream.js.map +1 -1
  164. package/dist/esm/internal/version.js +1 -1
  165. package/dist/esm/internal/version.js.map +1 -1
  166. package/package.json +2 -1
  167. package/src/Channel.ts +14 -17
  168. package/src/DateTime.ts +17 -8
  169. package/src/Differ.ts +2 -1
  170. package/src/Duration.ts +147 -0
  171. package/src/Effect.ts +528 -140
  172. package/src/Either.ts +9 -0
  173. package/src/FiberHandle.ts +95 -35
  174. package/src/FiberMap.ts +104 -39
  175. package/src/FiberSet.ts +93 -24
  176. package/src/HashMap.ts +40 -0
  177. package/src/HashSet.ts +8 -0
  178. package/src/Layer.ts +94 -40
  179. package/src/Match.ts +733 -49
  180. package/src/RcMap.ts +34 -0
  181. package/src/Reloadable.ts +17 -27
  182. package/src/STM.ts +10 -17
  183. package/src/Schedule.ts +2325 -653
  184. package/src/Schema.ts +81 -4
  185. package/src/Stream.ts +26 -33
  186. package/src/Trie.ts +7 -7
  187. package/src/index.ts +25 -0
  188. package/src/internal/channel.ts +37 -39
  189. package/src/internal/core-effect.ts +84 -84
  190. package/src/internal/core.ts +80 -0
  191. package/src/internal/dateTime.ts +3 -0
  192. package/src/internal/differ.ts +4 -0
  193. package/src/internal/effect/circular.ts +3 -2
  194. package/src/internal/fiberRuntime.ts +31 -6
  195. package/src/internal/hashMap.ts +16 -0
  196. package/src/internal/keyedPool.ts +1 -1
  197. package/src/internal/layer.ts +52 -52
  198. package/src/internal/rcMap.ts +131 -89
  199. package/src/internal/reloadable.ts +25 -28
  200. package/src/internal/schedule.ts +29 -23
  201. package/src/internal/sink.ts +16 -15
  202. package/src/internal/stm/stm.ts +54 -46
  203. package/src/internal/stream.ts +100 -100
  204. package/src/internal/version.ts +1 -1
package/dist/cjs/Match.js CHANGED
@@ -9,190 +9,811 @@ var Predicate = _interopRequireWildcard(require("./Predicate.js"));
9
9
  function _getRequireWildcardCache(e) { if ("function" != typeof WeakMap) return null; var r = new WeakMap(), t = new WeakMap(); return (_getRequireWildcardCache = function (e) { return e ? t : r; })(e); }
10
10
  function _interopRequireWildcard(e, r) { if (!r && e && e.__esModule) return e; if (null === e || "object" != typeof e && "function" != typeof e) return { default: e }; var t = _getRequireWildcardCache(r); if (t && t.has(e)) return t.get(e); var n = { __proto__: null }, a = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var u in e) if ("default" !== u && {}.hasOwnProperty.call(e, u)) { var i = a ? Object.getOwnPropertyDescriptor(e, u) : null; i && (i.get || i.set) ? Object.defineProperty(n, u, i) : n[u] = e[u]; } return n.default = e, t && t.set(e, n), n; }
11
11
  /**
12
- * @category type ids
12
+ * @category Symbols
13
13
  * @since 1.0.0
14
14
  */
15
15
  const MatcherTypeId = exports.MatcherTypeId = internal.TypeId;
16
16
  /**
17
- * @category constructors
17
+ * Creates a matcher for a specific type.
18
+ *
19
+ * **Details**
20
+ *
21
+ * This function defines a `Matcher` that operates on a given type, allowing you
22
+ * to specify conditions for handling different cases. Once the matcher is
23
+ * created, you can use pattern-matching functions like {@link when} to define
24
+ * how different values should be processed.
25
+ *
26
+ * @see {@link value} for creating a matcher from a specific value.
27
+ *
28
+ * @example
29
+ * ```ts
30
+ * // Title: Matching Numbers and Strings
31
+ * import { Match } from "effect"
32
+ *
33
+ * // Create a matcher for values that are either strings or numbers
34
+ * //
35
+ * // ┌─── (u: string | number) => string
36
+ * // ▼
37
+ * const match = Match.type<string | number>().pipe(
38
+ * // Match when the value is a number
39
+ * Match.when(Match.number, (n) => `number: ${n}`),
40
+ * // Match when the value is a string
41
+ * Match.when(Match.string, (s) => `string: ${s}`),
42
+ * // Ensure all possible cases are handled
43
+ * Match.exhaustive
44
+ * )
45
+ *
46
+ * console.log(match(0))
47
+ * // Output: "number: 0"
48
+ *
49
+ * console.log(match("hello"))
50
+ * // Output: "string: hello"
51
+ * ```
52
+ *
53
+ * @category Creating a matcher
18
54
  * @since 1.0.0
19
55
  */
20
56
  const type = exports.type = internal.type;
21
57
  /**
22
- * @category constructors
58
+ * Creates a matcher from a specific value.
59
+ *
60
+ * **Details**
61
+ *
62
+ * This function allows you to define a `Matcher` directly from a given value,
63
+ * rather than from a type. This is useful when working with known values,
64
+ * enabling structured pattern matching on objects, primitives, or any data
65
+ * structure.
66
+ *
67
+ * Once the matcher is created, you can use pattern-matching functions like
68
+ * {@link when} to define how different cases should be handled.
69
+ *
70
+ * @see {@link type} for creating a matcher from a specific type.
71
+ *
72
+ * @example
73
+ * ```ts
74
+ * // Title: Matching an Object by Property
75
+ * import { Match } from "effect"
76
+ *
77
+ * const input = { name: "John", age: 30 }
78
+ *
79
+ * // Create a matcher for the specific object
80
+ * const result = Match.value(input).pipe(
81
+ * // Match when the 'name' property is "John"
82
+ * Match.when(
83
+ * { name: "John" },
84
+ * (user) => `${user.name} is ${user.age} years old`
85
+ * ),
86
+ * // Provide a fallback if no match is found
87
+ * Match.orElse(() => "Oh, not John")
88
+ * )
89
+ *
90
+ * console.log(result)
91
+ * // Output: "John is 30 years old"
92
+ * ```
93
+ *
94
+ * @category Creating a matcher
23
95
  * @since 1.0.0
24
96
  */
25
97
  const value = exports.value = internal.value;
26
98
  /**
27
- * @category constructors
99
+ * @category Creating a matcher
28
100
  * @since 1.0.0
29
101
  */
30
102
  const valueTags = exports.valueTags = internal.valueTags;
31
103
  /**
32
- * @category constructors
104
+ * @category Creating a matcher
33
105
  * @since 1.0.0
34
106
  */
35
107
  const typeTags = exports.typeTags = internal.typeTags;
36
108
  /**
37
- * @category combinators
109
+ * Ensures that all branches of a matcher return a specific type.
110
+ *
111
+ * **Details**
112
+ *
113
+ * This function enforces a consistent return type across all pattern-matching
114
+ * branches. By specifying a return type, TypeScript will check that every
115
+ * matching condition produces a value of the expected type.
116
+ *
117
+ * **Important:** This function must be the first step in the matcher pipeline.
118
+ * If used later, TypeScript will not enforce type consistency correctly.
119
+ *
120
+ * @example
121
+ * ```ts
122
+ * // Title: Validating Return Type Consistency
123
+ * import { Match } from "effect"
124
+ *
125
+ * const match = Match.type<{ a: number } | { b: string }>().pipe(
126
+ * // Ensure all branches return a string
127
+ * Match.withReturnType<string>(),
128
+ * // ❌ Type error: 'number' is not assignable to type 'string'
129
+ * // @ts-expect-error
130
+ * Match.when({ a: Match.number }, (_) => _.a),
131
+ * // ✅ Correct: returns a string
132
+ * Match.when({ b: Match.string }, (_) => _.b),
133
+ * Match.exhaustive
134
+ * )
135
+ * ```
136
+ *
38
137
  * @since 1.0.0
39
138
  */
40
139
  const withReturnType = exports.withReturnType = internal.withReturnType;
41
140
  /**
42
- * @category combinators
141
+ * Defines a condition for matching values.
142
+ *
143
+ * **Details**
144
+ *
145
+ * This function enables pattern matching by checking whether a given value
146
+ * satisfies a condition. It supports both direct value comparisons and
147
+ * predicate functions. If the condition is met, the associated function is
148
+ * executed.
149
+ *
150
+ * This function is useful when defining matchers that need to check for
151
+ * specific values or apply logical conditions to determine a match. It works
152
+ * well with structured objects and primitive types.
153
+ *
154
+ * @see {@link whenOr} Use this when multiple patterns should match in a single
155
+ * condition.
156
+ * @see {@link whenAnd} Use this when a value must match all provided patterns.
157
+ * @see {@link orElse} Provides a fallback when no patterns match.
158
+ *
159
+ * @example
160
+ * ```ts
161
+ * // Title: Matching with Values and Predicates
162
+ * import { Match } from "effect"
163
+ *
164
+ * // Create a matcher for objects with an "age" property
165
+ * const match = Match.type<{ age: number }>().pipe(
166
+ * // Match when age is greater than 18
167
+ * Match.when({ age: (age) => age > 18 }, (user) => `Age: ${user.age}`),
168
+ * // Match when age is exactly 18
169
+ * Match.when({ age: 18 }, () => "You can vote"),
170
+ * // Fallback case for all other ages
171
+ * Match.orElse((user) => `${user.age} is too young`)
172
+ * )
173
+ *
174
+ * console.log(match({ age: 20 }))
175
+ * // Output: "Age: 20"
176
+ *
177
+ * console.log(match({ age: 18 }))
178
+ * // Output: "You can vote"
179
+ *
180
+ * console.log(match({ age: 4 }))
181
+ * // Output: "4 is too young"
182
+ * ```
183
+ *
184
+ * @category Defining patterns
43
185
  * @since 1.0.0
44
186
  */
45
187
  const when = exports.when = internal.when;
46
188
  /**
47
- * @category combinators
189
+ * Matches one of multiple patterns in a single condition.
190
+ *
191
+ * **Details**
192
+ *
193
+ * This function allows defining a condition where a value matches any of the
194
+ * provided patterns. If a match is found, the associated function is executed.
195
+ * It simplifies cases where multiple patterns share the same handling logic.
196
+ *
197
+ * Unlike {@link when}, which requires separate conditions for each pattern,
198
+ * this function enables combining them into a single statement, making the
199
+ * matcher more concise.
200
+ *
201
+ * @example
202
+ * ```ts
203
+ * import { Match } from "effect"
204
+ *
205
+ * type ErrorType =
206
+ * | { readonly _tag: "NetworkError"; readonly message: string }
207
+ * | { readonly _tag: "TimeoutError"; readonly duration: number }
208
+ * | { readonly _tag: "ValidationError"; readonly field: string }
209
+ *
210
+ * const handleError = Match.type<ErrorType>().pipe(
211
+ * Match.whenOr(
212
+ * { _tag: "NetworkError" },
213
+ * { _tag: "TimeoutError" },
214
+ * () => "Retry the request"
215
+ * ),
216
+ * Match.when({ _tag: "ValidationError" }, (_) => `Invalid field: ${_.field}`),
217
+ * Match.exhaustive
218
+ * )
219
+ *
220
+ * console.log(handleError({ _tag: "NetworkError", message: "No connection" }))
221
+ * // Output: "Retry the request"
222
+ *
223
+ * console.log(handleError({ _tag: "ValidationError", field: "email" }))
224
+ * // Output: "Invalid field: email"
225
+ * ```
226
+ *
227
+ * @category Defining patterns
48
228
  * @since 1.0.0
49
229
  */
50
230
  const whenOr = exports.whenOr = internal.whenOr;
51
231
  /**
52
- * @category combinators
232
+ * Matches a value that satisfies all provided patterns.
233
+ *
234
+ * **Details**
235
+ *
236
+ * This function allows defining a condition where a value must match all the
237
+ * given patterns simultaneously. If the value satisfies every pattern, the
238
+ * associated function is executed.
239
+ *
240
+ * Unlike {@link when}, which matches a single pattern at a time, this function
241
+ * ensures that multiple conditions are met before executing the callback. It is
242
+ * useful when checking for values that need to fulfill multiple criteria at
243
+ * once.
244
+ *
245
+ * @example
246
+ * ```ts
247
+ * import { Match } from "effect"
248
+ *
249
+ * type User = { readonly age: number; readonly role: "admin" | "user" }
250
+ *
251
+ * const checkUser = Match.type<User>().pipe(
252
+ * Match.whenAnd(
253
+ * { age: (n) => n >= 18 },
254
+ * { role: "admin" },
255
+ * () => "Admin access granted"
256
+ * ),
257
+ * Match.orElse(() => "Access denied")
258
+ * )
259
+ *
260
+ * console.log(checkUser({ age: 20, role: "admin" }))
261
+ * // Output: "Admin access granted"
262
+ *
263
+ * console.log(checkUser({ age: 20, role: "user" }))
264
+ * // Output: "Access denied"
265
+ * ```
266
+ *
267
+ * @category Defining patterns
53
268
  * @since 1.0.0
54
269
  */
55
270
  const whenAnd = exports.whenAnd = internal.whenAnd;
56
271
  /**
57
- * @category combinators
272
+ * Matches values based on a specified discriminant field.
273
+ *
274
+ * **Details**
275
+ *
276
+ * This function is used to define pattern matching on objects that follow a
277
+ * **discriminated union** structure, where a specific field (e.g., `type`,
278
+ * `kind`, `_tag`) determines the variant of the object. It allows matching
279
+ * multiple values of the discriminant and provides a function to handle the
280
+ * matched cases.
281
+ *
282
+ * @example
283
+ * ```ts
284
+ * import { Match, pipe } from "effect"
285
+ *
286
+ * const match = pipe(
287
+ * Match.type<{ type: "A"; a: string } | { type: "B"; b: number } | { type: "C"; c: boolean }>(),
288
+ * Match.discriminator("type")("A", "B", (_) => `A or B: ${_.type}`),
289
+ * Match.discriminator("type")("C", (_) => `C(${_.c})`),
290
+ * Match.exhaustive
291
+ * )
292
+ * ```
293
+ *
294
+ * @category Defining patterns
58
295
  * @since 1.0.0
59
296
  */
60
297
  const discriminator = exports.discriminator = internal.discriminator;
61
298
  /**
62
- * @category combinators
299
+ * Matches values where a specified field starts with a given prefix.
300
+ *
301
+ * **Details**
302
+ *
303
+ * This function is useful for working with discriminated unions where the
304
+ * discriminant field follows a hierarchical or namespaced structure. It allows
305
+ * you to match values based on whether the specified field starts with a given
306
+ * prefix, making it easier to handle grouped cases.
307
+ *
308
+ * Instead of checking for exact matches, this function lets you match values
309
+ * that share a common prefix. For example, if your discriminant field contains
310
+ * hierarchical names like `"A"`, `"A.A"`, and `"B"`, you can match all values
311
+ * starting with `"A"` using a single rule.
312
+ *
313
+ * @example
314
+ * ```ts
315
+ * import { Match, pipe } from "effect"
316
+ *
317
+ * const match = pipe(
318
+ * Match.type<{ type: "A" } | { type: "B" } | { type: "A.A" } | {}>(),
319
+ * Match.discriminatorStartsWith("type")("A", (_) => 1 as const),
320
+ * Match.discriminatorStartsWith("type")("B", (_) => 2 as const),
321
+ * Match.orElse((_) => 3 as const)
322
+ * )
323
+ *
324
+ * console.log(match({ type: "A" })) // 1
325
+ * console.log(match({ type: "B" })) // 2
326
+ * console.log(match({ type: "A.A" })) // 1
327
+ * ```
328
+ *
329
+ * @category Defining patterns
63
330
  * @since 1.0.0
64
331
  */
65
332
  const discriminatorStartsWith = exports.discriminatorStartsWith = internal.discriminatorStartsWith;
66
333
  /**
67
- * @category combinators
334
+ * Matches values based on a field that serves as a discriminator, mapping each
335
+ * possible value to a corresponding handler.
336
+ *
337
+ * **Details**
338
+ *
339
+ * This function simplifies working with discriminated unions by letting you
340
+ * define a set of handlers for each possible value of a given field. Instead of
341
+ * chaining multiple calls to {@link discriminator}, this function allows
342
+ * defining all possible cases at once using an object where the keys are the
343
+ * possible values of the field, and the values are the corresponding handler
344
+ * functions.
345
+ *
346
+ * @example
347
+ * ```ts
348
+ * import { Match, pipe } from "effect"
349
+ *
350
+ * const match = pipe(
351
+ * Match.type<{ type: "A"; a: string } | { type: "B"; b: number } | { type: "C"; c: boolean }>(),
352
+ * Match.discriminators("type")({
353
+ * A: (a) => a.a,
354
+ * B: (b) => b.b,
355
+ * C: (c) => c.c
356
+ * }),
357
+ * Match.exhaustive
358
+ * )
359
+ * ```
360
+ *
361
+ * @category Defining patterns
68
362
  * @since 1.0.0
69
363
  */
70
364
  const discriminators = exports.discriminators = internal.discriminators;
71
365
  /**
72
- * @category combinators
366
+ * Matches values based on a discriminator field and **ensures all cases are
367
+ * handled**.
368
+ *
369
+ * **Details*+
370
+ *
371
+ * This function is similar to {@link discriminators}, but **requires that all
372
+ * possible cases** are explicitly handled. It is useful when working with
373
+ * discriminated unions, where a specific field (e.g., `"type"`) determines the
374
+ * shape of an object. Each possible value of the field must have a
375
+ * corresponding handler, ensuring **exhaustiveness checking** at compile time.
376
+ *
377
+ * This function **does not require** `Match.exhaustive` at the end of the
378
+ * pipeline because it enforces exhaustiveness by design.
379
+ *
380
+ * @example
381
+ * ```ts
382
+ * import { Match, pipe } from "effect"
383
+ *
384
+ * const match = pipe(
385
+ * Match.type<{ type: "A"; a: string } | { type: "B"; b: number } | { type: "C"; c: boolean }>(),
386
+ * Match.discriminatorsExhaustive("type")({
387
+ * A: (a) => a.a,
388
+ * B: (b) => b.b,
389
+ * C: (c) => c.c
390
+ * })
391
+ * )
392
+ * ```
393
+ *
394
+ * @category Defining patterns
73
395
  * @since 1.0.0
74
396
  */
75
397
  const discriminatorsExhaustive = exports.discriminatorsExhaustive = internal.discriminatorsExhaustive;
76
398
  /**
77
- * @category combinators
399
+ * The `Match.tag` function allows pattern matching based on the `_tag` field in
400
+ * a [Discriminated Union](https://www.typescriptlang.org/docs/handbook/typescript-in-5-minutes-func.html#discriminated-unions).
401
+ * You can specify multiple tags to match within a single pattern.
402
+ *
403
+ * **Note**
404
+ *
405
+ * The `Match.tag` function relies on the convention within the Effect ecosystem
406
+ * of naming the tag field as `"_tag"`. Ensure that your discriminated unions
407
+ * follow this naming convention for proper functionality.
408
+ *
409
+ * @example
410
+ * ```ts
411
+ * // Title: Matching a Discriminated Union by Tag
412
+ * import { Match } from "effect"
413
+ *
414
+ * type Event =
415
+ * | { readonly _tag: "fetch" }
416
+ * | { readonly _tag: "success"; readonly data: string }
417
+ * | { readonly _tag: "error"; readonly error: Error }
418
+ * | { readonly _tag: "cancel" }
419
+ *
420
+ * // Create a Matcher for Either<number, string>
421
+ * const match = Match.type<Event>().pipe(
422
+ * // Match either "fetch" or "success"
423
+ * Match.tag("fetch", "success", () => `Ok!`),
424
+ * // Match "error" and extract the error message
425
+ * Match.tag("error", (event) => `Error: ${event.error.message}`),
426
+ * // Match "cancel"
427
+ * Match.tag("cancel", () => "Cancelled"),
428
+ * Match.exhaustive
429
+ * )
430
+ *
431
+ * console.log(match({ _tag: "success", data: "Hello" }))
432
+ * // Output: "Ok!"
433
+ *
434
+ * console.log(match({ _tag: "error", error: new Error("Oops!") }))
435
+ * // Output: "Error: Oops!"
436
+ * ```
437
+ *
438
+ * @category Defining patterns
78
439
  * @since 1.0.0
79
440
  */
80
441
  const tag = exports.tag = internal.tag;
81
442
  /**
82
- * @category combinators
443
+ * Matches values where the `_tag` field starts with a given prefix.
444
+ *
445
+ * **Details**
446
+ *
447
+ * This function allows you to match on values in a **discriminated union**
448
+ * based on whether the `_tag` field starts with a specified prefix. It is
449
+ * useful for handling hierarchical or namespaced tags, where multiple related
450
+ * cases share a common prefix.
451
+ *
452
+ * @example
453
+ * ```ts
454
+ * import { Match, pipe } from "effect"
455
+ *
456
+ * const match = pipe(
457
+ * Match.type<{ _tag: "A" } | { _tag: "B" } | { _tag: "A.A" } | {}>(),
458
+ * Match.tagStartsWith("A", (_) => 1 as const),
459
+ * Match.tagStartsWith("B", (_) => 2 as const),
460
+ * Match.orElse((_) => 3 as const)
461
+ * )
462
+ *
463
+ * console.log(match({ _tag: "A" })) // 1
464
+ * console.log(match({ _tag: "B" })) // 2
465
+ * console.log(match({ _tag: "A.A" })) // 1
466
+ * ```
467
+ *
468
+ * @category Defining patterns
83
469
  * @since 1.0.0
84
470
  */
85
471
  const tagStartsWith = exports.tagStartsWith = internal.tagStartsWith;
86
472
  /**
87
- * @category combinators
473
+ * Matches values based on their `_tag` field, mapping each tag to a
474
+ * corresponding handler.
475
+ *
476
+ * **Details**
477
+ *
478
+ * This function provides a way to handle discriminated unions by mapping `_tag`
479
+ * values to specific functions. Each handler receives the matched value and
480
+ * returns a transformed result. If all possible tags are handled, you can
481
+ * enforce exhaustiveness using `Match.exhaustive` to ensure no case is missed.
482
+ *
483
+ * @example
484
+ * ```ts
485
+ * import { Match, pipe } from "effect"
486
+ *
487
+ * const match = pipe(
488
+ * Match.type<{ _tag: "A"; a: string } | { _tag: "B"; b: number } | { _tag: "C"; c: boolean }>(),
489
+ * Match.tags({
490
+ * A: (a) => a.a,
491
+ * B: (b) => b.b,
492
+ * C: (c) => c.c
493
+ * }),
494
+ * Match.exhaustive
495
+ * )
496
+ * ```
497
+ *
498
+ * @category Defining patterns
88
499
  * @since 1.0.0
89
500
  */
90
501
  const tags = exports.tags = internal.tags;
91
502
  /**
92
- * @category combinators
503
+ * Matches values based on their `_tag` field and requires handling of all
504
+ * possible cases.
505
+ *
506
+ * **Details**
507
+ *
508
+ * This function is designed for **discriminated unions** where every possible
509
+ * `_tag` value must have a corresponding handler. Unlike {@link tags}, this
510
+ * function ensures **exhaustiveness**, meaning all cases must be explicitly
511
+ * handled. If a `_tag` value is missing from the mapping, TypeScript will
512
+ * report an error.
513
+ *
514
+ * @example
515
+ * ```ts
516
+ * import { Match, pipe } from "effect"
517
+ *
518
+ * const match = pipe(
519
+ * Match.type<{ _tag: "A"; a: string } | { _tag: "B"; b: number } | { _tag: "C"; c: boolean }>(),
520
+ * Match.tagsExhaustive({
521
+ * A: (a) => a.a,
522
+ * B: (b) => b.b,
523
+ * C: (c) => c.c
524
+ * })
525
+ * )
526
+ * ```
527
+ *
528
+ * @category Defining patterns
93
529
  * @since 1.0.0
94
530
  */
95
531
  const tagsExhaustive = exports.tagsExhaustive = internal.tagsExhaustive;
96
532
  /**
97
- * @category combinators
533
+ * Excludes a specific value from matching while allowing all others.
534
+ *
535
+ * **Details**
536
+ *
537
+ * This function is useful when you need to **handle all values except one or
538
+ * more specific cases**. Instead of listing all possible matches manually, this
539
+ * function simplifies the logic by allowing you to specify values to exclude.
540
+ * Any excluded value will bypass the provided function and continue matching
541
+ * through other cases.
542
+ *
543
+ * @example
544
+ * ```ts
545
+ * // Title: Ignoring a Specific Value
546
+ * import { Match } from "effect"
547
+ *
548
+ * // Create a matcher for string or number values
549
+ * const match = Match.type<string | number>().pipe(
550
+ * // Match any value except "hi", returning "ok"
551
+ * Match.not("hi", () => "ok"),
552
+ * // Fallback case for when the value is "hi"
553
+ * Match.orElse(() => "fallback")
554
+ * )
555
+ *
556
+ * console.log(match("hello"))
557
+ * // Output: "ok"
558
+ *
559
+ * console.log(match("hi"))
560
+ * // Output: "fallback"
561
+ * ```
562
+ *
563
+ * @category Defining patterns
98
564
  * @since 1.0.0
99
565
  */
100
566
  const not = exports.not = internal.not;
101
567
  /**
102
- * @category predicates
568
+ * Matches non-empty strings.
569
+ *
570
+ * @category Predicates
103
571
  * @since 1.0.0
104
572
  */
105
573
  const nonEmptyString = exports.nonEmptyString = internal.nonEmptyString;
106
574
  /**
107
- * @category predicates
575
+ * Matches a specific set of literal values (e.g., `Match.is("a", 42, true)`).
576
+ *
577
+ * @category Predicates
108
578
  * @since 1.0.0
109
579
  */
110
580
  const is = exports.is = internal.is;
111
581
  /**
112
- * @category predicates
582
+ * Matches values of type `string`.
583
+ *
584
+ * @category Predicates
113
585
  * @since 1.0.0
114
586
  */
115
587
  const string = exports.string = Predicate.isString;
116
588
  /**
117
- * @category predicates
589
+ * Matches values of type `number`.
590
+ *
591
+ * @category Predicates
118
592
  * @since 1.0.0
119
593
  */
120
594
  const number = exports.number = Predicate.isNumber;
121
595
  /**
122
- * @category predicates
596
+ * Matches any value without restrictions.
597
+ *
598
+ * @category Predicates
123
599
  * @since 1.0.0
124
600
  */
125
601
  const any = exports.any = internal.any;
126
602
  /**
127
- * @category predicates
603
+ * Matches any defined (non-null and non-undefined) value.
604
+ *
605
+ * @category Predicates
128
606
  * @since 1.0.0
129
607
  */
130
608
  const defined = exports.defined = internal.defined;
131
609
  /**
132
- * @category predicates
610
+ * Matches values of type `boolean`.
611
+ *
612
+ * @category Predicates
133
613
  * @since 1.0.0
134
614
  */
135
615
  const boolean = exports.boolean = Predicate.isBoolean;
136
616
  const _undefined = exports.undefined = Predicate.isUndefined;
137
617
  const _null = exports.null = Predicate.isNull;
138
618
  /**
139
- * @category predicates
619
+ * Matches values of type `bigint`.
620
+ *
621
+ * @category Predicates
140
622
  * @since 1.0.0
141
623
  */
142
624
  const bigint = exports.bigint = Predicate.isBigInt;
143
625
  /**
144
- * @category predicates
626
+ * Matches values of type `symbol`.
627
+ *
628
+ * @category Predicates
145
629
  * @since 1.0.0
146
630
  */
147
631
  const symbol = exports.symbol = Predicate.isSymbol;
148
632
  /**
149
- * @category predicates
633
+ * Matches values that are instances of `Date`.
634
+ *
635
+ * @category Predicates
150
636
  * @since 1.0.0
151
637
  */
152
638
  const date = exports.date = Predicate.isDate;
153
639
  /**
154
- * @category predicates
640
+ * Matches objects where keys are `string` or `symbol` and values are `unknown`.
641
+ *
642
+ * @category Predicates
155
643
  * @since 1.0.0
156
644
  */
157
645
  const record = exports.record = Predicate.isRecord;
158
646
  /**
159
- * @category predicates
647
+ * Matches instances of a given class.
648
+ *
649
+ * @category Predicates
160
650
  * @since 1.0.0
161
651
  */
162
652
  const instanceOf = exports.instanceOf = internal.instanceOf;
163
653
  /**
164
- * @category predicates
654
+ * @category Predicates
165
655
  * @since 1.0.0
166
656
  */
167
657
  const instanceOfUnsafe = exports.instanceOfUnsafe = internal.instanceOf;
168
658
  /**
169
- * @category conversions
659
+ * Provides a fallback value when no patterns match.
660
+ *
661
+ * **Details**
662
+ *
663
+ * This function ensures that a matcher always returns a valid result, even if
664
+ * no defined patterns match. It acts as a default case, similar to the
665
+ * `default` clause in a `switch` statement or the final `else` in an `if-else`
666
+ * chain.
667
+ *
668
+ * @example
669
+ * ```ts
670
+ * // Title: Providing a Default Value When No Patterns Match
671
+ * import { Match } from "effect"
672
+ *
673
+ * // Create a matcher for string or number values
674
+ * const match = Match.type<string | number>().pipe(
675
+ * // Match when the value is "a"
676
+ * Match.when("a", () => "ok"),
677
+ * // Fallback when no patterns match
678
+ * Match.orElse(() => "fallback")
679
+ * )
680
+ *
681
+ * console.log(match("a"))
682
+ * // Output: "ok"
683
+ *
684
+ * console.log(match("b"))
685
+ * // Output: "fallback"
686
+ * ```
687
+ *
688
+ * @category Completion
170
689
  * @since 1.0.0
171
690
  */
172
691
  const orElse = exports.orElse = internal.orElse;
173
- /**
174
- * @category conversions
692
+ // TODO(4.0): Rename to "orThrow"? Like Either.getOrThrow
693
+ /**
694
+ * Throws an error if no pattern matches.
695
+ *
696
+ * **Details**
697
+ *
698
+ * This function finalizes a matcher by ensuring that if no patterns match, an
699
+ * error is thrown. It is useful when all cases should be covered, and any
700
+ * unexpected input should trigger an error instead of returning a default
701
+ * value.
702
+ *
703
+ * When used, this function removes the need for an explicit fallback case and
704
+ * ensures that an unmatched value is never silently ignored.
705
+ *
706
+ * @category Completion
175
707
  * @since 1.0.0
176
708
  */
177
709
  const orElseAbsurd = exports.orElseAbsurd = internal.orElseAbsurd;
178
710
  /**
179
- * @category conversions
711
+ * Wraps the match result in an `Either`, distinguishing matched and unmatched
712
+ * cases.
713
+ *
714
+ * **Details**
715
+ *
716
+ * This function ensures that the result of a matcher is always wrapped in an
717
+ * `Either`, allowing clear differentiation between successful matches
718
+ * (`Right(value)`) and cases where no pattern matched (`Left(unmatched
719
+ * value)`).
720
+ *
721
+ * This approach is particularly useful when handling optional values or when an
722
+ * unmatched case should be explicitly handled rather than returning a default
723
+ * value or throwing an error.
724
+ *
725
+ * @example
726
+ * ```ts
727
+ * // Title: Extracting a User Role with Either
728
+ * import { Match } from "effect"
729
+ *
730
+ * type User = { readonly role: "admin" | "editor" | "viewer" }
731
+ *
732
+ * // Create a matcher to extract user roles
733
+ * const getRole = Match.type<User>().pipe(
734
+ * Match.when({ role: "admin" }, () => "Has full access"),
735
+ * Match.when({ role: "editor" }, () => "Can edit content"),
736
+ * Match.either // Wrap the result in an Either
737
+ * )
738
+ *
739
+ * console.log(getRole({ role: "admin" }))
740
+ * // Output: { _id: 'Either', _tag: 'Right', right: 'Has full access' }
741
+ *
742
+ * console.log(getRole({ role: "viewer" }))
743
+ * // Output: { _id: 'Either', _tag: 'Left', left: { role: 'viewer' } }
744
+ * ```
745
+ *
746
+ * @category Completion
180
747
  * @since 1.0.0
181
748
  */
182
749
  const either = exports.either = internal.either;
183
750
  /**
184
- * @category conversions
751
+ * Wraps the match result in an `Option`, representing an optional match.
752
+ *
753
+ * **Details**
754
+ *
755
+ * This function ensures that the result of a matcher is wrapped in an `Option`,
756
+ * making it easy to handle cases where no pattern matches. If a match is found,
757
+ * it returns `Some(value)`, otherwise, it returns `None`.
758
+ *
759
+ * This is useful in cases where a missing match is expected and should be
760
+ * handled explicitly rather than throwing an error or returning a default
761
+ * value.
762
+ *
763
+ * @example
764
+ * ```ts
765
+ * // Title: Extracting a User Role with Option
766
+ * import { Match } from "effect"
767
+ *
768
+ * type User = { readonly role: "admin" | "editor" | "viewer" }
769
+ *
770
+ * // Create a matcher to extract user roles
771
+ * const getRole = Match.type<User>().pipe(
772
+ * Match.when({ role: "admin" }, () => "Has full access"),
773
+ * Match.when({ role: "editor" }, () => "Can edit content"),
774
+ * Match.option // Wrap the result in an Option
775
+ * )
776
+ *
777
+ * console.log(getRole({ role: "admin" }))
778
+ * // Output: { _id: 'Option', _tag: 'Some', value: 'Has full access' }
779
+ *
780
+ * console.log(getRole({ role: "viewer" }))
781
+ * // Output: { _id: 'Option', _tag: 'None' }
782
+ * ```
783
+ *
784
+ * @category Completion
185
785
  * @since 1.0.0
186
786
  */
187
787
  const option = exports.option = internal.option;
188
788
  /**
189
- * @category conversions
789
+ * The `Match.exhaustive` method finalizes the pattern matching process by
790
+ * ensuring that all possible cases are accounted for. If any case is missing,
791
+ * TypeScript will produce a type error. This is particularly useful when
792
+ * working with unions, as it helps prevent unintended gaps in pattern matching.
793
+ *
794
+ * @example
795
+ * ```ts
796
+ * // Title: Ensuring All Cases Are Covered
797
+ * import { Match } from "effect"
798
+ *
799
+ * // Create a matcher for string or number values
800
+ * const match = Match.type<string | number>().pipe(
801
+ * // Match when the value is a number
802
+ * Match.when(Match.number, (n) => `number: ${n}`),
803
+ * // Mark the match as exhaustive, ensuring all cases are handled
804
+ * // TypeScript will throw an error if any case is missing
805
+ * // @ts-expect-error Type 'string' is not assignable to type 'never'
806
+ * Match.exhaustive
807
+ * )
808
+ * ```
809
+ *
810
+ * @category Completion
190
811
  * @since 1.0.0
191
812
  */
192
813
  const exhaustive = exports.exhaustive = internal.exhaustive;
193
814
  /**
194
815
  * @since 1.0.0
195
- * @category type ids
816
+ * @category Symbols
196
817
  */
197
818
  const SafeRefinementId = exports.SafeRefinementId = /*#__PURE__*/Symbol.for("effect/SafeRefinement");
198
819
  const Fail = /*#__PURE__*/Symbol.for("effect/Fail");