liminal 0.17.4 → 0.17.6

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.
package/Client.ts CHANGED
@@ -21,31 +21,19 @@ import {
21
21
  Cause,
22
22
  Result,
23
23
  flow,
24
- identity,
25
24
  } from "effect"
26
25
  import { Socket } from "effect/unstable/socket"
27
26
  import { Worker } from "effect/unstable/workers"
28
27
 
29
- import type { MethodDefinition } from "./Method.ts"
30
-
31
28
  import * as Diagnostic from "./_util/Diagnostic.ts"
32
29
  import { type ClientError, AuditionError, ConnectionError, type FError, UnresolvedError } from "./errors.ts"
33
30
  import { type F } from "./F.ts"
34
- import * as Protocol from "./Protocol.ts"
31
+ import { Protocol, type ProtocolDefinition } from "./Protocol.ts"
35
32
 
36
33
  const { debug, span } = Diagnostic.module("Client")
37
34
 
38
35
  export const TypeId = "~liminal/Client" as const
39
36
 
40
- export interface ClientDefinition<
41
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
42
- EventDefinitions extends Record<string, S.Struct.Fields>,
43
- > {
44
- readonly methods: MethodDefinitions
45
-
46
- readonly events: EventDefinitions
47
- }
48
-
49
37
  export interface ReplayConfig {
50
38
  readonly mode: "startup" | "all-subscribers"
51
39
 
@@ -58,60 +46,49 @@ interface EventTake<A, E> {
58
46
  readonly take: Take.Take<A, E>
59
47
  }
60
48
 
61
- export interface Session<
62
- ClientSelf,
63
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
64
- EventDefinitions extends Record<string, S.Struct.Fields>,
65
- > {
66
- readonly events: Stream.Stream<ReturnType<typeof S.TaggedUnion<EventDefinitions>>["Type"], ClientError>
49
+ export interface Session<Self, D extends ProtocolDefinition> {
50
+ readonly events: Stream.Stream<ReturnType<typeof S.TaggedUnion<D["events"]>>["Type"], ClientError | S.SchemaError>
67
51
 
68
- readonly f: F<ClientSelf, MethodDefinitions>
52
+ readonly f: F<Self, D>
69
53
 
70
54
  readonly end: Effect.Effect<void>
71
55
  }
72
56
 
73
- export type Service<
74
- ClientSelf,
75
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
76
- EventDefinitions extends Record<string, S.Struct.Fields>,
77
- > = RcRef.RcRef<Session<ClientSelf, MethodDefinitions, EventDefinitions>, ClientError>
57
+ export type Service<ClientSelf, D extends ProtocolDefinition> = RcRef.RcRef<Session<ClientSelf, D>, ClientError>
78
58
 
79
- export interface Client<
80
- ClientSelf,
81
- ClientId extends string,
82
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
83
- EventDefinitions extends Record<string, S.Struct.Fields>,
84
- > extends Context.Service<ClientSelf, Service<ClientSelf, MethodDefinitions, EventDefinitions>> {
85
- new (_: never): Context.ServiceClass.Shape<ClientId, Service<ClientSelf, MethodDefinitions, EventDefinitions>>
59
+ export interface Client<Self, ClientId extends string, D extends ProtocolDefinition> extends Context.Service<
60
+ Self,
61
+ Service<Self, D>
62
+ > {
63
+ new (_: never): Context.ServiceClass.Shape<ClientId, Service<Self, D>>
86
64
 
87
65
  readonly [TypeId]: typeof TypeId
88
66
 
89
- readonly definition: ClientDefinition<MethodDefinitions, EventDefinitions>
67
+ readonly definition: D
90
68
 
91
- readonly schema: Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>
69
+ readonly protocol: Protocol<D>
92
70
 
93
- readonly events: Stream.Stream<ReturnType<typeof S.TaggedUnion<EventDefinitions>>["Type"], ClientError, ClientSelf>
71
+ readonly events: Stream.Stream<
72
+ ReturnType<typeof S.TaggedUnion<D["events"]>>["Type"],
73
+ ClientError | S.SchemaError,
74
+ Self
75
+ >
94
76
 
95
- readonly f: F<ClientSelf, MethodDefinitions>
77
+ readonly f: F<Self, D>
96
78
 
97
- readonly invalidate: Effect.Effect<void, never, ClientSelf>
79
+ readonly invalidate: Effect.Effect<void, never, Self>
98
80
  }
99
81
 
100
82
  export const Service =
101
- <ClientSelf>() =>
102
- <
103
- ClientId extends string,
104
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
105
- EventDefinitions extends Record<string, S.Struct.Fields>,
106
- >(
107
- id: ClientId,
108
- definition: ClientDefinition<MethodDefinitions, EventDefinitions>,
109
- ): Client<ClientSelf, ClientId, MethodDefinitions, EventDefinitions> => {
110
- const tag = Context.Service<ClientSelf, Service<ClientSelf, MethodDefinitions, EventDefinitions>>()(id)
83
+ <Self>() =>
84
+ <Id extends string, D extends ProtocolDefinition>(id: Id, definition: D): Client<Self, Id, D> => {
85
+ const tag = Context.Service<Self, Service<Self, D>>()(id)
86
+
87
+ const protocol = Protocol(definition)
111
88
 
112
89
  const events = tag.asEffect().pipe(Effect.flatMap(RcRef.get), Effect.map(Struct.get("events")), Stream.unwrap)
113
90
 
114
- const f: F<ClientSelf, MethodDefinitions> = (_tag) =>
91
+ const f: F<Self, D> = (_tag) =>
115
92
  Effect.fnUntraced(function* (value) {
116
93
  const { f } = yield* tag.asEffect().pipe(Effect.flatMap(RcRef.get))
117
94
  return yield* f(_tag)(value)
@@ -131,54 +108,33 @@ export const Service =
131
108
  return Object.assign(tag, {
132
109
  [TypeId]: TypeId,
133
110
  definition,
134
- schema: Protocol.ProtocolSchemas(definition.methods, definition.events),
111
+ protocol,
135
112
  events,
136
113
  f,
137
114
  invalidate,
138
115
  })
139
116
  }
140
117
 
141
- export interface Transport<
142
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
143
- EventDefinitions extends Record<string, S.Struct.Fields>,
144
- > {
118
+ export interface ClientTransport<D extends ProtocolDefinition> {
145
119
  readonly listen: (
146
- publish: (
147
- message:
148
- | Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["actor"]["Type"]
149
- | typeof Protocol.TransportFailure.Type,
150
- ) => Effect.Effect<void, ClientError>,
151
- ) => Effect.Effect<
152
- void,
153
- ClientError,
154
- Scope.Scope | Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["actor"]["DecodingServices"]
155
- >
120
+ publish: (message: Protocol<D>["Actor"]["Type"]) => Effect.Effect<void, ClientError>,
121
+ ) => Effect.Effect<void, ClientError | S.SchemaError, Scope.Scope | Protocol<D>["Actor"]["DecodingServices"]>
156
122
 
157
123
  readonly send: (
158
- message: Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["f"]["payload"]["Type"],
159
- ) => Effect.Effect<
160
- void,
161
- ConnectionError,
162
- Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["f"]["payload"]["EncodingServices"]
163
- >
124
+ message: Protocol<D>["F"]["Payload"]["Type"],
125
+ ) => Effect.Effect<void, ClientError | S.SchemaError, Protocol<D>["F"]["Payload"]["EncodingServices"]>
164
126
  }
165
127
 
166
- const make = <
167
- ClientSelf,
168
- ClientId extends string,
169
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
170
- EventDefinitions extends Record<string, S.Struct.Fields>,
171
- R,
172
- >(
173
- client: Client<ClientSelf, ClientId, MethodDefinitions, EventDefinitions>,
174
- build: Effect.Effect<Transport<MethodDefinitions, EventDefinitions>, ClientError, R | Scope.Scope>,
128
+ const make = <Self, Id extends string, D extends ProtocolDefinition, R>(
129
+ client: Client<Self, Id, D>,
130
+ build: Effect.Effect<ClientTransport<D>, ClientError, R | Scope.Scope>,
175
131
  replay?: ReplayConfig | undefined,
176
132
  ) =>
177
133
  Effect.gen(function* () {
178
- const rcr: RcRef.RcRef<Session<ClientSelf, MethodDefinitions, EventDefinitions>, ClientError> = yield* RcRef.make({
134
+ const rcr: RcRef.RcRef<Session<Self, D>, ClientError> = yield* RcRef.make({
179
135
  acquire: Effect.gen(function* () {
180
- type _ = typeof client.schema
181
- type Event = ReturnType<typeof S.TaggedUnion<EventDefinitions>>["Type"]
136
+ type _ = typeof client.protocol
137
+ type Event = ReturnType<typeof S.TaggedUnion<D["events"]>>["Type"]
182
138
 
183
139
  yield* debug("AcquisitionStarted")
184
140
 
@@ -186,7 +142,7 @@ const make = <
186
142
 
187
143
  const audition = yield* Deferred.make<void>()
188
144
 
189
- const inflights: Record<string, Deferred.Deferred<_["f"]["success"]["Type"], FError<MethodDefinitions>>> = {}
145
+ const inflights: Record<string, Deferred.Deferred<_["F"]["Success"]["Type"], FError<D>>> = {}
190
146
  let callId = 0
191
147
  let takeCount = 0
192
148
  const pubsub = yield* PubSub.unbounded<EventTake<Event, ClientError>>()
@@ -228,33 +184,38 @@ const make = <
228
184
  const fiber = yield* listen(
229
185
  Effect.fnUntraced(function* (message) {
230
186
  switch (message._tag) {
231
- case "AuditionSuccess": {
232
- yield* debug("AuditionSucceeded")
187
+ case "Audition.Success": {
188
+ yield* debug("Audition.Succeeded")
233
189
  yield* Deferred.succeed(audition, void 0)
234
190
  return
235
191
  }
192
+ case "Audition.Failure": {
193
+ const { client, routed } = message
194
+ yield* debug("Audition.Failed", { client, routed })
195
+ return yield* new AuditionError({ value: { client, routed } })
196
+ }
236
197
  case "Event": {
237
198
  const { event } = message
238
- yield* debug("EventEmitted", { event })
199
+ yield* debug("Event.Emitted", { event })
239
200
  yield* publishTake([event as never], true)
240
201
  return
241
202
  }
242
- case "FSuccess":
243
- case "FFailure": {
203
+ case "F.Success":
204
+ case "F.Failure": {
244
205
  const { id } = message
245
206
  const deferred = inflights[id]
246
207
  if (deferred) {
247
208
  delete inflights[id]
248
209
  switch (message._tag) {
249
- case "FSuccess": {
210
+ case "F.Success": {
250
211
  const { _tag, value } = message.success as never
251
- yield* debug("CallSucceeded", { id, _tag, value })
212
+ yield* debug("Call.Succeeded", { id, _tag, value })
252
213
  yield* Deferred.succeed(deferred, value)
253
214
  return
254
215
  }
255
- case "FFailure": {
216
+ case "F.Failure": {
256
217
  const { _tag, value } = message.failure as never
257
- yield* debug("CallFailed", { id, _tag, value })
218
+ yield* debug("Call.Failed", { id, _tag, value })
258
219
  yield* Deferred.fail(deferred, value)
259
220
  return
260
221
  }
@@ -262,27 +223,17 @@ const make = <
262
223
  }
263
224
  return
264
225
  }
265
- case "AuditionFailure": {
266
- const { client, routed } = message
267
- yield* debug("AuditionFailed", { client, routed })
268
- return yield* new AuditionError({ value: { client, routed } })
269
- }
270
226
  case "Disconnect": {
271
227
  yield* debug("Disconnected")
272
228
  return
273
229
  }
274
- case "TransportFailure": {
275
- const { cause } = message
276
- yield* debug("TransportFailed", { cause })
277
- return yield* new ConnectionError({ cause })
278
- }
279
230
  }
280
231
  }),
281
232
  ).pipe(
282
233
  Effect.ensuring(
283
234
  Effect.all(
284
235
  [
285
- debug("ClientClosed", { unresolved: Record.keys(inflights).length }),
236
+ debug("Client.Closed", { unresolved: Record.keys(inflights).length }),
286
237
  Deferred.succeed(audition, void 0),
287
238
  RcRef.invalidate(rcr),
288
239
  ],
@@ -331,13 +282,31 @@ const make = <
331
282
  ),
332
283
  live(replayCount),
333
284
  )
334
- }).pipe(Stream.unwrap, Stream.interruptWhen(Fiber.join(fiber)))
285
+ }).pipe(
286
+ Stream.unwrap,
287
+ Stream.interruptWhen(
288
+ Fiber.await(fiber).pipe(
289
+ Effect.flatMap(
290
+ Exit.match({
291
+ onSuccess: () => Effect.void,
292
+ onFailure: flow(
293
+ Cause.findError,
294
+ Result.match({
295
+ onSuccess: Effect.fail,
296
+ onFailure: () => Effect.void,
297
+ }),
298
+ ),
299
+ }),
300
+ ),
301
+ ),
302
+ ),
303
+ )
335
304
 
336
305
  yield* Deferred.await(audition)
337
306
 
338
- const encodingServices = yield* Effect.context<_["f"]["payload"]["EncodingServices"]>()
307
+ const encodingServices = yield* Effect.context<_["F"]["Payload"]["EncodingServices"]>()
339
308
 
340
- const f: F<ClientSelf, MethodDefinitions> = (_tag) =>
309
+ const f: F<Self, D> = (_tag) =>
341
310
  Effect.fnUntraced(
342
311
  function* (value) {
343
312
  const exit = fiber.pollUnsafe()
@@ -347,23 +316,37 @@ const make = <
347
316
  onFailure: flow(
348
317
  Cause.findError,
349
318
  Result.match({
350
- onSuccess: identity,
319
+ onSuccess: Effect.fail,
351
320
  onFailure: () => new UnresolvedError(),
352
321
  }),
353
322
  ),
354
323
  })
355
324
  }
356
325
  const id = callId++
357
- const inflight = yield* Deferred.make<_["f"]["success"]["Type"], FError<MethodDefinitions>>()
326
+ const inflight = yield* Deferred.make<_["F"]["Success"]["Type"], FError<D>>()
358
327
  inflights[id] = inflight
359
328
  yield* send({
360
- _tag: "FPayload",
329
+ _tag: "F.Payload",
361
330
  id,
362
331
  payload: { _tag, value } as never,
363
332
  })
364
333
  return yield* Effect.raceFirst(
365
334
  Deferred.await(inflight),
366
- Fiber.join(fiber).pipe(Effect.andThen(() => new UnresolvedError().asEffect())),
335
+ Fiber.await(fiber).pipe(
336
+ Effect.flatMap(
337
+ (exit): Effect.Effect<never, ClientError | UnresolvedError | S.SchemaError> =>
338
+ Exit.match(exit, {
339
+ onSuccess: () => new UnresolvedError().asEffect(),
340
+ onFailure: flow(
341
+ Cause.findError,
342
+ Result.match({
343
+ onSuccess: Effect.fail,
344
+ onFailure: () => new UnresolvedError().asEffect(),
345
+ }),
346
+ ),
347
+ }),
348
+ ),
349
+ ),
367
350
  )
368
351
  },
369
352
  span("f"),
@@ -378,31 +361,27 @@ const make = <
378
361
  return rcr
379
362
  }).pipe(Layer.effect(client))
380
363
 
381
- export const layerSocket = <
382
- ClientSelf,
383
- ClientId extends string,
384
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
385
- EventDefinitions extends Record<string, S.Struct.Fields>,
386
- >({
364
+ export const layerSocket = <Self, Id extends string, D extends ProtocolDefinition>({
387
365
  client,
388
366
  url,
389
367
  protocols,
390
368
  replay,
391
369
  }: {
392
- readonly client: Client<ClientSelf, ClientId, MethodDefinitions, EventDefinitions>
370
+ readonly client: Client<Self, Id, D>
393
371
  readonly url?: string | undefined
394
372
  readonly protocols?: string | Array<string> | undefined
395
373
  readonly replay?: ReplayConfig | undefined
396
374
  }): Layer.Layer<
397
- ClientSelf,
375
+ Self,
398
376
  never,
399
377
  | Socket.WebSocketConstructor
400
- | Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["actor"]["DecodingServices"]
401
- | Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["f"]["payload"]["EncodingServices"]
378
+ | Protocol<D>["Actor"]["DecodingServices"]
379
+ | Protocol<D>["F"]["Payload"]["EncodingServices"]
402
380
  > =>
403
- make<ClientSelf, ClientId, MethodDefinitions, EventDefinitions, Socket.WebSocketConstructor>(
381
+ make<Self, Id, D, Socket.WebSocketConstructor>(
404
382
  client,
405
383
  Effect.gen(function* () {
384
+ const { protocol } = client
406
385
  const socket = yield* Socket.makeWebSocket(url ?? "/", {
407
386
  protocols: ["liminal", Encoding.encodeBase64Url(client.key), ...(protocols ? Array.ensure(protocols) : [])],
408
387
  })
@@ -412,49 +391,29 @@ export const layerSocket = <
412
391
  .runRaw((raw) =>
413
392
  pipe(
414
393
  raw instanceof Uint8Array ? new TextDecoder().decode(raw) : raw,
415
- S.decodeUnknownEffect(S.fromJsonString(S.toCodecJson(client.schema.actor))),
394
+ protocol.decodeActor,
416
395
  Effect.andThen(publish),
417
396
  ),
418
397
  )
419
398
  .pipe(
420
- Effect.catchTag(
421
- "SocketError",
399
+ Effect.catchIf(
400
+ Socket.isSocketError,
422
401
  Effect.fnUntraced(function* (cause) {
423
402
  const { reason } = cause
424
- switch (reason._tag) {
425
- case "SocketReadError":
426
- case "SocketWriteError":
427
- case "SocketOpenError": {
428
- yield* debug(reason._tag, { cause })
429
- return yield* publish({ _tag: "TransportFailure", cause })
430
- }
431
- case "SocketCloseError": {
432
- const { code, closeReason } = reason
433
- switch (code) {
434
- case 1000: {
435
- return yield* publish({ _tag: "Disconnect" })
436
- }
437
- case 4003: {
438
- return yield* S.decodeUnknownEffect(S.fromJsonString(Protocol.AuditionFailure))(
439
- closeReason,
440
- ).pipe(Effect.andThen(publish))
441
- }
442
- }
443
- yield* debug("SocketCloseError", { cause })
444
- return yield* publish({ _tag: "TransportFailure", cause })
445
- }
403
+ if (reason._tag === "SocketCloseError" && reason.code === 1000) {
404
+ yield* debug("Socket.Disconnected")
405
+ return yield* publish({ _tag: "Disconnect" })
446
406
  }
407
+ yield* debug(`SocketErrored.${reason._tag}`, { cause })
408
+ return yield* new ConnectionError({ cause })
447
409
  }),
448
410
  ),
449
- Effect.catchTag("SchemaError", Effect.die),
450
411
  )
451
412
  }, span("listen")),
452
413
  send: Effect.fnUntraced(
453
414
  function* (v) {
454
415
  const write = yield* socket.writer
455
- const message = yield* S.encodeEffect(S.fromJsonString(S.toCodecJson(client.schema.f.payload)))(v).pipe(
456
- Effect.mapError((cause) => new ConnectionError({ cause })),
457
- )
416
+ const message = yield* protocol.encodeFPayload(v)
458
417
  yield* write(message).pipe(
459
418
  Effect.catchTag("SocketError", (cause) => new ConnectionError({ cause }).asEffect()),
460
419
  )
@@ -467,36 +426,31 @@ export const layerSocket = <
467
426
  replay,
468
427
  )
469
428
 
470
- export const layerWorker = <
471
- ClientSelf,
472
- ClientId extends string,
473
- MethodDefinitions extends Record<string, MethodDefinition.Any>,
474
- EventDefinitions extends Record<string, S.Struct.Fields>,
475
- >({
429
+ export const layerWorker = <Self, Id extends string, D extends ProtocolDefinition>({
476
430
  client,
477
431
  replay,
478
432
  }: {
479
- readonly client: Client<ClientSelf, ClientId, MethodDefinitions, EventDefinitions>
433
+ readonly client: Client<Self, Id, D>
480
434
  readonly replay?: ReplayConfig | undefined
481
435
  }): Layer.Layer<
482
- ClientSelf,
436
+ Self,
483
437
  never,
484
438
  | Worker.WorkerPlatform
485
439
  | Worker.Spawner
486
- | Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["actor"]["DecodingServices"]
487
- | Protocol.ProtocolSchemas<MethodDefinitions, EventDefinitions>["f"]["payload"]["EncodingServices"]
440
+ | Protocol<D>["Actor"]["DecodingServices"]
441
+ | Protocol<D>["F"]["Payload"]["EncodingServices"]
488
442
  > =>
489
- make<ClientSelf, ClientId, MethodDefinitions, EventDefinitions, Worker.WorkerPlatform | Worker.Spawner>(
443
+ make<Self, Id, D, Worker.WorkerPlatform | Worker.Spawner>(
490
444
  client,
491
445
  Effect.gen(function* () {
492
- type T = typeof client.schema
446
+ type T = Protocol<D>
493
447
 
494
448
  const platform = yield* Worker.WorkerPlatform
495
449
  const backing = yield* platform
496
- .spawn<T["actor"]["Type"], T["f"]["payload"]["Type"] | string>(0)
450
+ .spawn<T["Actor"]["Type"], T["F"]["Payload"]["Type"] | string>(0)
497
451
  .pipe(Effect.catchTag("WorkerError", (cause) => new ConnectionError({ cause }).asEffect()))
498
452
 
499
- const send = (message: T["f"]["payload"]["Type"]) =>
453
+ const send = (message: T["F"]["Payload"]["Type"]) =>
500
454
  backing.send(message).pipe(
501
455
  Effect.catchTag("WorkerError", (cause) => new ConnectionError({ cause }).asEffect()),
502
456
  span("send"),
@@ -509,14 +463,14 @@ export const layerWorker = <
509
463
  backing.run(
510
464
  Effect.fnUntraced(function* (message) {
511
465
  yield* publish(message)
512
- if (message._tag === "Disconnect" || message._tag === "AuditionFailure") {
466
+ if (message._tag === "Disconnect" || message._tag === "Audition.Failure") {
513
467
  yield* Deferred.succeed(stop, void 0)
514
468
  }
515
469
  }),
516
470
  { onSpawn: backing.send(client.key).pipe(Effect.orDie) },
517
471
  ),
518
472
  Deferred.await(stop),
519
- ).pipe(Effect.catchTag("WorkerError", (cause) => publish({ _tag: "TransportFailure", cause })))
473
+ ).pipe(Effect.catchTag("WorkerError", (cause) => new ConnectionError({ cause }).asEffect()))
520
474
  }, span("listen")),
521
475
  send,
522
476
  }
package/ClientHandle.ts CHANGED
@@ -1,17 +1,14 @@
1
1
  import { Schema as S, Effect } from "effect"
2
2
 
3
+ import type { ProtocolDefinition } from "./Protocol.ts"
3
4
  import type { Send } from "./Send.ts"
4
5
 
5
6
  const TypeId = "~liminal/ClientHandle" as const
6
7
 
7
- export interface ClientHandle<
8
- ActorSelf,
9
- AttachmentFields extends S.Struct.Fields,
10
- EventDefinitions extends Record<string, S.Struct.Fields>,
11
- > {
8
+ export interface ClientHandle<ActorSelf, AttachmentFields extends S.Struct.Fields, D extends ProtocolDefinition> {
12
9
  readonly [TypeId]: typeof TypeId
13
10
 
14
- readonly send: Send<ActorSelf, EventDefinitions>
11
+ readonly send: Send<ActorSelf, D>
15
12
 
16
13
  readonly attachments: Effect.Effect<S.Struct<AttachmentFields>["Type"]>
17
14
 
@@ -22,17 +19,13 @@ export interface ClientHandle<
22
19
  readonly disconnect: Effect.Effect<void, never, ActorSelf>
23
20
  }
24
21
 
25
- export const make = <
26
- ActorSelf,
27
- AttachmentFields extends S.Struct.Fields,
28
- EventDefinitions extends Record<string, S.Struct.Fields>,
29
- >({
22
+ export const make = <ActorSelf, AttachmentFields extends S.Struct.Fields, D extends ProtocolDefinition>({
30
23
  send,
31
24
  attachments,
32
25
  save,
33
26
  disconnect,
34
27
  }: {
35
- readonly send: Send<ActorSelf, EventDefinitions>
28
+ readonly send: Send<ActorSelf, D>
36
29
 
37
30
  readonly attachments: Effect.Effect<S.Struct<AttachmentFields>["Type"]>
38
31
 
@@ -41,7 +34,7 @@ export const make = <
41
34
  ) => Effect.Effect<void, S.SchemaError, S.Struct<AttachmentFields>["EncodingServices"]>
42
35
 
43
36
  readonly disconnect: Effect.Effect<void, never, ActorSelf>
44
- }): ClientHandle<ActorSelf, AttachmentFields, EventDefinitions> => ({
37
+ }): ClientHandle<ActorSelf, AttachmentFields, D> => ({
45
38
  [TypeId]: TypeId,
46
39
  send,
47
40
  attachments,
package/F.ts CHANGED
@@ -1,12 +1,10 @@
1
- import { Record, Effect } from "effect"
1
+ import { Effect } from "effect"
2
2
 
3
3
  import type { FError } from "./errors.ts"
4
- import type { MethodDefinition } from "./Method.ts"
4
+ import type { ProtocolDefinition } from "./Protocol.ts"
5
5
 
6
- export type F<ClientSelf, MethodDefinitions extends Record<string, MethodDefinition.Any>> = <
7
- Method extends keyof MethodDefinitions,
8
- >(
6
+ export type F<Self, D extends ProtocolDefinition> = <Method extends keyof D["methods"]>(
9
7
  method: Method,
10
8
  ) => (
11
- payload: MethodDefinitions[Method]["payload"]["Type"],
12
- ) => Effect.Effect<MethodDefinitions[Method]["success"]["Type"], FError<MethodDefinitions>, ClientSelf>
9
+ payload: D["methods"][Method]["payload"]["Type"],
10
+ ) => Effect.Effect<D["methods"][Method]["success"]["Type"], FError<D>, Self>
package/Method.ts CHANGED
@@ -6,17 +6,9 @@ export interface MethodDefinition<Payload extends S.Top, Success extends S.Top,
6
6
  readonly failure: Failure
7
7
  }
8
8
 
9
- export declare namespace MethodDefinition {
10
- export type Any = MethodDefinition<S.Top, S.Top, S.Top>
9
+ export type Any = MethodDefinition<S.Top, S.Top, S.Top>
11
10
 
12
- export type Merge<T, U> = [T] extends [never]
13
- ? U
14
- : {
15
- [K in keyof T & keyof U]: T[K] extends U[K] ? (U[K] extends T[K] ? T[K] : never) : never
16
- }
17
- }
18
-
19
- export const define = <Payload extends S.Top, Success extends S.Top, Failure extends S.Top>({
11
+ export const make = <Payload extends S.Top, Success extends S.Top, Failure extends S.Top>({
20
12
  payload,
21
13
  success,
22
14
  failure,
@@ -26,12 +18,12 @@ export const define = <Payload extends S.Top, Success extends S.Top, Failure ext
26
18
  readonly failure: Failure
27
19
  }): MethodDefinition<Payload, Success, Failure> => ({ payload, success, failure })
28
20
 
29
- export type Handler<MethodDefinition extends MethodDefinition.Any, R> = (
21
+ export type Handler<MethodDefinition extends Any, R> = (
30
22
  payload: MethodDefinition["payload"]["Type"],
31
23
  ) => Effect.Effect<MethodDefinition["success"]["Type"], MethodDefinition["failure"]["Type"], R>
32
24
 
33
- export type Handlers<MethodDefinitions extends Record<string, MethodDefinition.Any>, R> = {
25
+ export type Handlers<MethodDefinitions extends Record<string, Any>, R> = {
34
26
  [K in keyof MethodDefinitions]: Handler<MethodDefinitions[K], R>
35
27
  }
36
28
 
37
- export const handler = <M extends MethodDefinition.Any, R>(_method: M, f: Handler<M, R>): Handler<M, R> => f
29
+ export const handler = <M extends Any, R>(_method: M, f: Handler<M, R>): Handler<M, R> => f