diff --git a/packages/effect-lens/src/Lens.test.ts b/packages/effect-lens/src/Lens.test.ts index c0707c3..0bd111c 100644 --- a/packages/effect-lens/src/Lens.test.ts +++ b/packages/effect-lens/src/Lens.test.ts @@ -1,5 +1,5 @@ import { describe, expect, test } from "bun:test" -import { Chunk, Context, Effect, Layer, Option, SubscriptionRef } from "effect" +import { Chunk, Context, Effect, Option, SubscriptionRef } from "effect" import * as Lens from "./Lens.js" @@ -56,18 +56,18 @@ describe("Lens", () => { expect(result[1]).toEqual(Option.some(50)) // 100 / 2 }) - test("provide supplies a service to get and modify", async () => { + test("provideContext supplies a service to get and modify", async () => { const result = await Effect.runPromise( Effect.flatMap( SubscriptionRef.make(10), parent => { - const lens = Lens.provide( + const lens = Lens.provideContext( Lens.mapEffect( Lens.fromSubscriptionRef(parent), n => Effect.map(Offset, ({ value }) => n + value), (_n, next) => Effect.map(Offset, ({ value }) => next - value), ), - Layer.succeed(Offset, { value: 5 }), + Context.make(Offset, { value: 5 }), ) return Effect.flatMap( diff --git a/packages/effect-lens/src/Lens.ts b/packages/effect-lens/src/Lens.ts index 491235d..4a23c27 100644 --- a/packages/effect-lens/src/Lens.ts +++ b/packages/effect-lens/src/Lens.ts @@ -1,4 +1,4 @@ -import { Array, Chunk, type Context, Effect, Function, identity, type Layer, type ManagedRuntime, Option, Pipeable, Predicate, Readable, type Runtime, Stream, type SubscriptionRef, type SynchronizedRef } from "effect" +import { Array, Chunk, type Context, Effect, Function, identity, type ManagedRuntime, Option, Pipeable, Predicate, Readable, type Runtime, Stream, type SubscriptionRef, type SynchronizedRef } from "effect" import type { NoSuchElementException } from "effect/Cause" import * as Subscribable from "./Subscribable.js" @@ -269,54 +269,41 @@ export const mapStream: { get modify() { return self.modify }, })) + /** - * Provides the requirements of a `Lens`, removing them from both the read and write environments. - * - * Accepts the same provider forms as `Effect.provide`: one or more `Layer`s, a `Context`, - * a `Runtime`, or a `ManagedRuntime`. - * - * Layer providers may add their construction errors to both the read and write error channels. + * Provides a `Context` to a `Lens`, removing it from both the read and write environments. */ -export const provide: { - ]>( - layers: Layers, - ): (self: Lens) => Lens< - A, - ER | { [k in keyof Layers]: Layer.Layer.Error }[number], - EW | { [k in keyof Layers]: Layer.Layer.Error }[number], - { [k in keyof Layers]: Layer.Layer.Context }[number] | Exclude }[number]>, - { [k in keyof Layers]: Layer.Layer.Context }[number] | Exclude }[number]> - > - ( - layer: Layer.Layer, - ): (self: Lens) => Lens, RIn | Exclude> +export const provideContext: { + ( + self: Lens, + context: Context.Context, + ): Lens, Exclude> ( context: Context.Context, ): (self: Lens) => Lens, Exclude> +} = Function.dual(2, ( + self: Lens, + context: Context.Context, +): Lens, Exclude> => make({ + get get() { return Effect.provide(self.get, context) }, + get changes() { return Stream.provideSomeContext(self.changes, context) }, + modify: ( + f: (a: A) => Effect.Effect + ) => Effect.provide(self.modify(f), context), +})) + +/** + * Provides a `Runtime` or `ManagedRuntime` to a `Lens`, removing it from both the read and write environments. + * + * `ManagedRuntime` may add its construction errors to both the read and write error channels. + */ +export const provideRuntime: { ( runtime: Runtime.Runtime, ): (self: Lens) => Lens, Exclude> ( managedRuntime: ManagedRuntime.ManagedRuntime, ): (self: Lens) => Lens, Exclude> - ]>( - self: Lens, - layers: Layers, - ): Lens< - A, - ER | { [k in keyof Layers]: Layer.Layer.Error }[number], - EW | { [k in keyof Layers]: Layer.Layer.Error }[number], - { [k in keyof Layers]: Layer.Layer.Context }[number] | Exclude }[number]>, - { [k in keyof Layers]: Layer.Layer.Context }[number] | Exclude }[number]> - > - ( - self: Lens, - layer: Layer.Layer, - ): Lens, RIn | Exclude> - ( - self: Lens, - context: Context.Context, - ): Lens, Exclude> ( self: Lens, runtime: Runtime.Runtime, @@ -325,22 +312,20 @@ export const provide: { self: Lens, runtime: ManagedRuntime.ManagedRuntime, ): Lens, Exclude> -} = Function.dual(2, ( +} = Function.dual(2, ( self: Lens, - layer: Layer.Layer, -): Lens, RIn | Exclude> => make({ - get get() { return Effect.provide(self.get, layer) }, + runtime: Runtime.Runtime, +) => make, Exclude>({ + get get() { return Effect.provide(self.get, runtime) }, get changes() { - return Stream.unwrapScoped( - Effect.map( - Effect.provide(Effect.context(), layer), - context => Stream.provideContext(self.changes, context), - ), - ) + return Stream.unwrap(Effect.map( + Effect.provide(Effect.context(), runtime), + context => Stream.provideContext(self.changes, context), + )) }, modify: ( f: (a: A) => Effect.Effect - ) => Effect.provide(self.modify(f), layer), + ) => Effect.provide(self.modify(f), runtime), })) /**