effect 3.3.5 → 3.4.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 (98) hide show
  1. package/Micro/package.json +6 -0
  2. package/dist/cjs/Array.js +18 -3
  3. package/dist/cjs/Array.js.map +1 -1
  4. package/dist/cjs/Chunk.js +13 -2
  5. package/dist/cjs/Chunk.js.map +1 -1
  6. package/dist/cjs/Effect.js +110 -8
  7. package/dist/cjs/Effect.js.map +1 -1
  8. package/dist/cjs/Either.js +31 -1
  9. package/dist/cjs/Either.js.map +1 -1
  10. package/dist/cjs/ManagedRuntime.js.map +1 -1
  11. package/dist/cjs/Micro.js +2383 -0
  12. package/dist/cjs/Micro.js.map +1 -0
  13. package/dist/cjs/Option.js +1 -2
  14. package/dist/cjs/Option.js.map +1 -1
  15. package/dist/cjs/Schedule.js +2 -2
  16. package/dist/cjs/Stream.js.map +1 -1
  17. package/dist/cjs/Tuple.js +16 -9
  18. package/dist/cjs/Tuple.js.map +1 -1
  19. package/dist/cjs/index.js +4 -2
  20. package/dist/cjs/index.js.map +1 -1
  21. package/dist/cjs/internal/core-effect.js +4 -2
  22. package/dist/cjs/internal/core-effect.js.map +1 -1
  23. package/dist/cjs/internal/core.js +12 -2
  24. package/dist/cjs/internal/core.js.map +1 -1
  25. package/dist/cjs/internal/fiberRuntime.js +32 -0
  26. package/dist/cjs/internal/fiberRuntime.js.map +1 -1
  27. package/dist/cjs/internal/stream.js.map +1 -1
  28. package/dist/cjs/internal/version.js +1 -1
  29. package/dist/dts/Array.d.ts +14 -0
  30. package/dist/dts/Array.d.ts.map +1 -1
  31. package/dist/dts/Cause.d.ts +1 -1
  32. package/dist/dts/Chunk.d.ts +11 -0
  33. package/dist/dts/Chunk.d.ts.map +1 -1
  34. package/dist/dts/Effect.d.ts +109 -5
  35. package/dist/dts/Effect.d.ts.map +1 -1
  36. package/dist/dts/Either.d.ts +35 -0
  37. package/dist/dts/Either.d.ts.map +1 -1
  38. package/dist/dts/ManagedRuntime.d.ts +15 -0
  39. package/dist/dts/ManagedRuntime.d.ts.map +1 -1
  40. package/dist/dts/Micro.d.ts +2002 -0
  41. package/dist/dts/Micro.d.ts.map +1 -0
  42. package/dist/dts/Option.d.ts +2 -0
  43. package/dist/dts/Option.d.ts.map +1 -1
  44. package/dist/dts/Schedule.d.ts +2 -2
  45. package/dist/dts/Stream.d.ts +45 -6
  46. package/dist/dts/Stream.d.ts.map +1 -1
  47. package/dist/dts/Tuple.d.ts +18 -0
  48. package/dist/dts/Tuple.d.ts.map +1 -1
  49. package/dist/dts/index.d.ts +7 -0
  50. package/dist/dts/index.d.ts.map +1 -1
  51. package/dist/dts/internal/core-effect.d.ts.map +1 -1
  52. package/dist/dts/internal/core.d.ts.map +1 -1
  53. package/dist/dts/internal/fiberRuntime.d.ts.map +1 -1
  54. package/dist/esm/Array.js +14 -0
  55. package/dist/esm/Array.js.map +1 -1
  56. package/dist/esm/Chunk.js +11 -0
  57. package/dist/esm/Chunk.js.map +1 -1
  58. package/dist/esm/Effect.js +107 -5
  59. package/dist/esm/Effect.js.map +1 -1
  60. package/dist/esm/Either.js +30 -0
  61. package/dist/esm/Either.js.map +1 -1
  62. package/dist/esm/ManagedRuntime.js.map +1 -1
  63. package/dist/esm/Micro.js +2307 -0
  64. package/dist/esm/Micro.js.map +1 -0
  65. package/dist/esm/Option.js +1 -1
  66. package/dist/esm/Option.js.map +1 -1
  67. package/dist/esm/Schedule.js +2 -2
  68. package/dist/esm/Stream.js.map +1 -1
  69. package/dist/esm/Tuple.js +15 -8
  70. package/dist/esm/Tuple.js.map +1 -1
  71. package/dist/esm/index.js +7 -0
  72. package/dist/esm/index.js.map +1 -1
  73. package/dist/esm/internal/core-effect.js +2 -0
  74. package/dist/esm/internal/core-effect.js.map +1 -1
  75. package/dist/esm/internal/core.js +10 -1
  76. package/dist/esm/internal/core.js.map +1 -1
  77. package/dist/esm/internal/fiberRuntime.js +32 -0
  78. package/dist/esm/internal/fiberRuntime.js.map +1 -1
  79. package/dist/esm/internal/stream.js.map +1 -1
  80. package/dist/esm/internal/version.js +1 -1
  81. package/package.json +9 -1
  82. package/src/Array.ts +15 -0
  83. package/src/Cause.ts +1 -1
  84. package/src/Chunk.ts +12 -0
  85. package/src/Effect.ts +117 -5
  86. package/src/Either.ts +51 -0
  87. package/src/ManagedRuntime.ts +16 -0
  88. package/src/Micro.ts +3826 -0
  89. package/src/Option.ts +12 -1
  90. package/src/Schedule.ts +2 -2
  91. package/src/Stream.ts +60 -8
  92. package/src/Tuple.ts +18 -8
  93. package/src/index.ts +8 -0
  94. package/src/internal/core-effect.ts +33 -0
  95. package/src/internal/core.ts +18 -1
  96. package/src/internal/fiberRuntime.ts +32 -0
  97. package/src/internal/stream.ts +8 -4
  98. package/src/internal/version.ts +1 -1
@@ -1,4 +1,4 @@
1
- let moduleVersion = "3.3.5";
1
+ let moduleVersion = "3.4.0";
2
2
  export const getCurrentVersion = () => moduleVersion;
3
3
  export const setCurrentVersion = version => {
4
4
  moduleVersion = version;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "effect",
3
- "version": "3.3.5",
3
+ "version": "3.4.0",
4
4
  "description": "The missing standard library for TypeScript, for writing production-grade software.",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -372,6 +372,11 @@
372
372
  "import": "./dist/esm/MetricState.js",
373
373
  "default": "./dist/cjs/MetricState.js"
374
374
  },
375
+ "./Micro": {
376
+ "types": "./dist/dts/Micro.d.ts",
377
+ "import": "./dist/esm/Micro.js",
378
+ "default": "./dist/cjs/Micro.js"
379
+ },
375
380
  "./ModuleVersion": {
376
381
  "types": "./dist/dts/ModuleVersion.d.ts",
377
382
  "import": "./dist/esm/ModuleVersion.js",
@@ -1020,6 +1025,9 @@
1020
1025
  "MetricState": [
1021
1026
  "./dist/dts/MetricState.d.ts"
1022
1027
  ],
1028
+ "Micro": [
1029
+ "./dist/dts/Micro.d.ts"
1030
+ ],
1023
1031
  "ModuleVersion": [
1024
1032
  "./dist/dts/ModuleVersion.d.ts"
1025
1033
  ],
package/src/Array.ts CHANGED
@@ -145,6 +145,21 @@ export const replicate: {
145
145
  export const fromIterable = <A>(collection: Iterable<A>): Array<A> =>
146
146
  Array.isArray(collection) ? collection : Array.from(collection)
147
147
 
148
+ /**
149
+ * Creates a new `Array` from a value that might not be an iterable.
150
+ *
151
+ * @example
152
+ * import { Array } from "effect"
153
+ *
154
+ * assert.deepStrictEqual(Array.ensure("a"), ["a"])
155
+ * assert.deepStrictEqual(Array.ensure(["a"]), ["a"])
156
+ * assert.deepStrictEqual(Array.ensure(["a", "b", "c"]), ["a", "b", "c"])
157
+ *
158
+ * @category constructors
159
+ * @since 3.3.0
160
+ */
161
+ export const ensure = <A>(self: ReadonlyArray<A> | A): Array<A> => Array.isArray(self) ? self : [self as A]
162
+
148
163
  /**
149
164
  * Takes a record and returns an array of tuples containing its keys and values.
150
165
  *
package/src/Cause.ts CHANGED
@@ -192,7 +192,7 @@ export interface CauseReducer<in C, in E, in out Z> {
192
192
  */
193
193
  export interface YieldableError extends Pipeable, Inspectable, Readonly<Error> {
194
194
  readonly [Effect.EffectTypeId]: Effect.Effect.VarianceStruct<never, this, never>
195
- readonly [Stream.StreamTypeId]: Effect.Effect.VarianceStruct<never, this, never>
195
+ readonly [Stream.StreamTypeId]: Stream.Stream.VarianceStruct<never, this, never>
196
196
  readonly [Sink.SinkTypeId]: Sink.Sink.VarianceStruct<never, unknown, never, this, never>
197
197
  readonly [Channel.ChannelTypeId]: Channel.Channel.VarianceStruct<never, unknown, this, unknown, never, unknown, never>
198
198
  [Symbol.iterator](): Effect.EffectGenerator<Effect.Effect<never, this, never>>
package/src/Chunk.ts CHANGED
@@ -819,6 +819,8 @@ export const head: <A>(self: Chunk<A>) => Option<A> = get(0)
819
819
  /**
820
820
  * Returns the first element of this chunk.
821
821
  *
822
+ * It will throw an error if the chunk is empty.
823
+ *
822
824
  * @since 2.0.0
823
825
  * @category unsafe
824
826
  */
@@ -843,11 +845,21 @@ export const last = <A>(self: Chunk<A>): Option<A> => get(self, self.length - 1)
843
845
  /**
844
846
  * Returns the last element of this chunk.
845
847
  *
848
+ * It will throw an error if the chunk is empty.
849
+ *
846
850
  * @since 2.0.0
847
851
  * @category unsafe
848
852
  */
849
853
  export const unsafeLast = <A>(self: Chunk<A>): A => unsafeGet(self, self.length - 1)
850
854
 
855
+ /**
856
+ * Returns the last element of this non empty chunk.
857
+ *
858
+ * @since 3.4.0
859
+ * @category elements
860
+ */
861
+ export const lastNonEmpty: <A>(self: NonEmptyChunk<A>) => A = unsafeLast
862
+
851
863
  /**
852
864
  * @since 2.0.0
853
865
  */
package/src/Effect.ts CHANGED
@@ -291,7 +291,7 @@ export const isEffect: (u: unknown) => u is Effect<unknown, unknown, unknown> =
291
291
  * yield* cached.pipe(Effect.andThen(Console.log))
292
292
  * })
293
293
  *
294
- * // Effect.runFork(program)
294
+ * Effect.runFork(program)
295
295
  * // Output:
296
296
  * // expensive task...
297
297
  * // result 1
@@ -336,7 +336,7 @@ export const cachedWithTTL: {
336
336
  * yield* cached.pipe(Effect.andThen(Console.log))
337
337
  * })
338
338
  *
339
- * // Effect.runFork(program)
339
+ * Effect.runFork(program)
340
340
  * // Output:
341
341
  * // expensive task...
342
342
  * // result 1
@@ -385,7 +385,7 @@ export const cachedInvalidateWithTTL: {
385
385
  * yield* cached.pipe(Effect.andThen(Console.log))
386
386
  * })
387
387
  *
388
- * // Effect.runFork(program)
388
+ * Effect.runFork(program)
389
389
  * // Output:
390
390
  * // non-cached version:
391
391
  * // expensive task...
@@ -422,7 +422,7 @@ export const cached: <A, E, R>(self: Effect<A, E, R>) => Effect<Effect<A, E, R>>
422
422
  * console.log(yield* memoized(10))
423
423
  * })
424
424
  *
425
- * // Effect.runFork(program)
425
+ * Effect.runFork(program)
426
426
  * // Example Output:
427
427
  * // non-memoized version:
428
428
  * // 2
@@ -453,7 +453,7 @@ export const cachedFunction: <A, B, E, R>(
453
453
  * yield* Effect.repeatN(task2, 2)
454
454
  * })
455
455
  *
456
- * // Effect.runFork(program)
456
+ * Effect.runFork(program)
457
457
  * // Output:
458
458
  * // task1
459
459
  * // task1
@@ -2159,6 +2159,40 @@ export const uninterruptibleMask: <A, E, R>(
2159
2159
  f: (restore: <AX, EX, RX>(effect: Effect<AX, EX, RX>) => Effect<AX, EX, RX>) => Effect<A, E, R>
2160
2160
  ) => Effect<A, E, R> = core.uninterruptibleMask
2161
2161
 
2162
+ // -------------------------------------------------------------------------------------
2163
+ // lifting
2164
+ // -------------------------------------------------------------------------------------
2165
+
2166
+ /**
2167
+ * Transforms a `Predicate` function into an `Effect` returning the input value if the predicate returns `true`
2168
+ * or failing with specified error if the predicate fails
2169
+ *
2170
+ * @param predicate - A `Predicate` function that takes in a value of type `A` and returns a boolean.
2171
+ *
2172
+ * @example
2173
+ * import { Effect } from "effect"
2174
+ *
2175
+ * const isPositive = (n: number): boolean => n > 0
2176
+ *
2177
+ * // succeeds with `1`
2178
+ * Effect.liftPredicate(1, isPositive, n => `${n} is not positive`)
2179
+ *
2180
+ * // fails with `"0 is not positive"`
2181
+ * Effect.liftPredicate(0, isPositive, n => `${n} is not positive`)
2182
+ *
2183
+ * @category lifting
2184
+ * @since 3.4.0
2185
+ */
2186
+ export const liftPredicate: {
2187
+ <A, B extends A, E>(
2188
+ refinement: Refinement<NoInfer<A>, B>,
2189
+ orFailWith: (a: NoInfer<A>) => E
2190
+ ): (a: A) => Effect<B, E>
2191
+ <A, E>(predicate: Predicate<NoInfer<A>>, orFailWith: (a: NoInfer<A>) => E): (a: A) => Effect<A, E>
2192
+ <A, E, B extends A>(self: A, refinement: Refinement<A, B>, orFailWith: (a: A) => E): Effect<B, E>
2193
+ <A, E>(self: A, predicate: Predicate<NoInfer<A>>, orFailWith: (a: NoInfer<A>) => E): Effect<A, E>
2194
+ } = effect.liftPredicate
2195
+
2162
2196
  // -------------------------------------------------------------------------------------
2163
2197
  // mapping
2164
2198
  // -------------------------------------------------------------------------------------
@@ -5152,6 +5186,55 @@ export const validateWith: {
5152
5186
  } = fiberRuntime.validateWith
5153
5187
 
5154
5188
  /**
5189
+ * The `Effect.zip` function allows you to combine two effects into a single
5190
+ * effect. This combined effect yields a tuple containing the results of both
5191
+ * input effects once they succeed.
5192
+ *
5193
+ * Note that `Effect.zip` processes effects sequentially: it first completes the
5194
+ * effect on the left and then the effect on the right.
5195
+ *
5196
+ * If you want to run the effects concurrently, you can use the `concurrent` option.
5197
+ *
5198
+ * @example
5199
+ * import { Effect } from "effect"
5200
+ *
5201
+ * const task1 = Effect.succeed(1).pipe(
5202
+ * Effect.delay("200 millis"),
5203
+ * Effect.tap(Effect.log("task1 done"))
5204
+ * )
5205
+ * const task2 = Effect.succeed("hello").pipe(
5206
+ * Effect.delay("100 millis"),
5207
+ * Effect.tap(Effect.log("task2 done"))
5208
+ * )
5209
+ *
5210
+ * const task3 = Effect.zip(task1, task2)
5211
+ *
5212
+ * Effect.runPromise(task3).then(console.log)
5213
+ * // Output:
5214
+ * // timestamp=... level=INFO fiber=#0 message="task1 done"
5215
+ * // timestamp=... level=INFO fiber=#0 message="task2 done"
5216
+ * // [ 1, 'hello' ]
5217
+ *
5218
+ * @example
5219
+ * import { Effect } from "effect"
5220
+ *
5221
+ * const task1 = Effect.succeed(1).pipe(
5222
+ * Effect.delay("200 millis"),
5223
+ * Effect.tap(Effect.log("task1 done"))
5224
+ * )
5225
+ * const task2 = Effect.succeed("hello").pipe(
5226
+ * Effect.delay("100 millis"),
5227
+ * Effect.tap(Effect.log("task2 done"))
5228
+ * )
5229
+ *
5230
+ * const task3 = Effect.zip(task1, task2, { concurrent: true })
5231
+ *
5232
+ * Effect.runPromise(task3).then(console.log)
5233
+ * // Output:
5234
+ * // timestamp=... level=INFO fiber=#0 message="task2 done"
5235
+ * // timestamp=... level=INFO fiber=#0 message="task1 done"
5236
+ * // [ 1, 'hello' ]
5237
+ *
5155
5238
  * @since 2.0.0
5156
5239
  * @category zipping
5157
5240
  */
@@ -5246,6 +5329,35 @@ export const zipRight: {
5246
5329
  } = fiberRuntime.zipRightOptions
5247
5330
 
5248
5331
  /**
5332
+ * The `Effect.zipWith` function operates similarly to {@link zip} by combining
5333
+ * two effects. However, instead of returning a tuple, it allows you to apply a
5334
+ * function to the results of the combined effects, transforming them into a
5335
+ * single value
5336
+ *
5337
+ * @example
5338
+ * import { Effect } from "effect"
5339
+ *
5340
+ * const task1 = Effect.succeed(1).pipe(
5341
+ * Effect.delay("200 millis"),
5342
+ * Effect.tap(Effect.log("task1 done"))
5343
+ * )
5344
+ * const task2 = Effect.succeed("hello").pipe(
5345
+ * Effect.delay("100 millis"),
5346
+ * Effect.tap(Effect.log("task2 done"))
5347
+ * )
5348
+ *
5349
+ * const task3 = Effect.zipWith(
5350
+ * task1,
5351
+ * task2,
5352
+ * (number, string) => number + string.length
5353
+ * )
5354
+ *
5355
+ * Effect.runPromise(task3).then(console.log)
5356
+ * // Output:
5357
+ * // timestamp=... level=INFO fiber=#3 message="task1 done"
5358
+ * // timestamp=... level=INFO fiber=#2 message="task2 done"
5359
+ * // 6
5360
+ *
5249
5361
  * @since 2.0.0
5250
5362
  * @category zipping
5251
5363
  */
package/src/Either.ts CHANGED
@@ -389,6 +389,57 @@ export const match: {
389
389
  }): B | C => isLeft(self) ? onLeft(self.left) : onRight(self.right)
390
390
  )
391
391
 
392
+ /**
393
+ * Transforms a `Predicate` function into a `Right` of the input value if the predicate returns `true`
394
+ * or `Left` of the result of the provided function if the predicate returns false
395
+ *
396
+ * @param predicate - A `Predicate` function that takes in a value of type `A` and returns a boolean.
397
+ *
398
+ * @example
399
+ * import { pipe, Either } from "effect"
400
+ *
401
+ * const isPositive = (n: number): boolean => n > 0
402
+ *
403
+ * assert.deepStrictEqual(
404
+ * pipe(
405
+ * 1,
406
+ * Either.liftPredicate(isPositive, n => `${n} is not positive`)
407
+ * ),
408
+ * Either.right(1)
409
+ * )
410
+ * assert.deepStrictEqual(
411
+ * pipe(
412
+ * 0,
413
+ * Either.liftPredicate(isPositive, n => `${n} is not positive`)
414
+ * ),
415
+ * Either.left("0 is not positive")
416
+ * )
417
+ *
418
+ * @category lifting
419
+ * @since 3.4.0
420
+ */
421
+ export const liftPredicate: {
422
+ <A, B extends A, E>(refinement: Refinement<NoInfer<A>, B>, orLeftWith: (a: NoInfer<A>) => E): (a: A) => Either<B, E>
423
+ <A, E>(
424
+ predicate: Predicate<NoInfer<A>>,
425
+ orLeftWith: (a: NoInfer<A>) => E
426
+ ): (a: A) => Either<A, E>
427
+ <A, E, B extends A>(
428
+ self: A,
429
+ refinement: Refinement<A, B>,
430
+ orLeftWith: (a: A) => E
431
+ ): Either<B, E>
432
+ <A, E>(
433
+ self: A,
434
+ predicate: Predicate<NoInfer<A>>,
435
+ orLeftWith: (a: NoInfer<A>) => E
436
+ ): Either<A, E>
437
+ } = dual(
438
+ 3,
439
+ <A, E>(a: A, predicate: Predicate<A>, orLeftWith: (a: A) => E): Either<A, E> =>
440
+ predicate(a) ? right(a) : left(orLeftWith(a))
441
+ )
442
+
392
443
  /**
393
444
  * Filter the right value with the provided function.
394
445
  * If the predicate fails, set the left value with the result of the provided function.
@@ -9,6 +9,22 @@ import type * as Layer from "./Layer.js"
9
9
  import type { Pipeable } from "./Pipeable.js"
10
10
  import type * as Runtime from "./Runtime.js"
11
11
 
12
+ /**
13
+ * @since 3.4.0
14
+ */
15
+ export declare namespace ManagedRuntime {
16
+ /**
17
+ * @category type-level
18
+ * @since 3.4.0
19
+ */
20
+ export type Context<T extends ManagedRuntime<any, any>> = [T] extends [ManagedRuntime<infer R, infer _E>] ? R : never
21
+ /**
22
+ * @category type-level
23
+ * @since 3.4.0
24
+ */
25
+ export type Error<T extends ManagedRuntime<any, any>> = [T] extends [ManagedRuntime<infer _R, infer E>] ? E : never
26
+ }
27
+
12
28
  /**
13
29
  * @since 2.0.0
14
30
  * @category models