@rivetkit/effect 0.0.0-codex-rivetkit-cli-preview.5e414a8
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/dist/Action.d.ts +104 -0
- package/dist/Action.d.ts.map +1 -0
- package/dist/Action.js +50 -0
- package/dist/Action.js.map +1 -0
- package/dist/Actor.d.ts +133 -0
- package/dist/Actor.d.ts.map +1 -0
- package/dist/Actor.js +104 -0
- package/dist/Actor.js.map +1 -0
- package/dist/Client.d.ts +31 -0
- package/dist/Client.d.ts.map +1 -0
- package/dist/Client.js +98 -0
- package/dist/Client.js.map +1 -0
- package/dist/Logger.d.ts +29 -0
- package/dist/Logger.d.ts.map +1 -0
- package/dist/Logger.js +31 -0
- package/dist/Logger.js.map +1 -0
- package/dist/Registry.d.ts +72 -0
- package/dist/Registry.d.ts.map +1 -0
- package/dist/Registry.js +125 -0
- package/dist/Registry.js.map +1 -0
- package/dist/RivetError.d.ts +438 -0
- package/dist/RivetError.d.ts.map +1 -0
- package/dist/RivetError.js +873 -0
- package/dist/RivetError.js.map +1 -0
- package/dist/State.d.ts +123 -0
- package/dist/State.d.ts.map +1 -0
- package/dist/State.js +104 -0
- package/dist/State.js.map +1 -0
- package/dist/internal/ActionDispatcher.d.ts +14 -0
- package/dist/internal/ActionDispatcher.d.ts.map +1 -0
- package/dist/internal/ActionDispatcher.js +100 -0
- package/dist/internal/ActionDispatcher.js.map +1 -0
- package/dist/internal/ActionErrorEnvelope.d.ts +11 -0
- package/dist/internal/ActionErrorEnvelope.d.ts.map +1 -0
- package/dist/internal/ActionErrorEnvelope.js +14 -0
- package/dist/internal/ActionErrorEnvelope.js.map +1 -0
- package/dist/internal/ActorInstanceManager.d.ts +28 -0
- package/dist/internal/ActorInstanceManager.d.ts.map +1 -0
- package/dist/internal/ActorInstanceManager.js +51 -0
- package/dist/internal/ActorInstanceManager.js.map +1 -0
- package/dist/internal/ActorStateAdapter.d.ts +18 -0
- package/dist/internal/ActorStateAdapter.d.ts.map +1 -0
- package/dist/internal/ActorStateAdapter.js +29 -0
- package/dist/internal/ActorStateAdapter.js.map +1 -0
- package/dist/internal/StateOptions.d.ts +12 -0
- package/dist/internal/StateOptions.d.ts.map +1 -0
- package/dist/internal/StateOptions.js +2 -0
- package/dist/internal/StateOptions.js.map +1 -0
- package/dist/internal/logging.d.ts +23 -0
- package/dist/internal/logging.d.ts.map +1 -0
- package/dist/internal/logging.js +162 -0
- package/dist/internal/logging.js.map +1 -0
- package/dist/internal/tracing.d.ts +23 -0
- package/dist/internal/tracing.d.ts.map +1 -0
- package/dist/internal/tracing.js +30 -0
- package/dist/internal/tracing.js.map +1 -0
- package/dist/internal/utils.d.ts +7 -0
- package/dist/internal/utils.d.ts.map +1 -0
- package/dist/internal/utils.js +7 -0
- package/dist/internal/utils.js.map +1 -0
- package/dist/mod.d.ts +8 -0
- package/dist/mod.d.ts.map +1 -0
- package/dist/mod.js +8 -0
- package/dist/mod.js.map +1 -0
- package/package.json +46 -0
- package/src/Action.ts +231 -0
- package/src/Actor.test-d.ts +603 -0
- package/src/Actor.test.ts +206 -0
- package/src/Actor.ts +550 -0
- package/src/Client.test.ts +210 -0
- package/src/Client.ts +216 -0
- package/src/Logger.ts +43 -0
- package/src/Registry.test-d.ts +126 -0
- package/src/Registry.test.ts +411 -0
- package/src/Registry.ts +243 -0
- package/src/RivetError.test.ts +188 -0
- package/src/RivetError.ts +1044 -0
- package/src/State.test.ts +181 -0
- package/src/State.ts +224 -0
- package/src/internal/ActionDispatcher.ts +192 -0
- package/src/internal/ActionErrorEnvelope.ts +19 -0
- package/src/internal/ActorInstanceManager.ts +143 -0
- package/src/internal/ActorStateAdapter.ts +88 -0
- package/src/internal/StateOptions.ts +17 -0
- package/src/internal/logging.test.ts +288 -0
- package/src/internal/logging.ts +237 -0
- package/src/internal/tracing.ts +42 -0
- package/src/internal/utils.ts +12 -0
- package/src/mod.ts +7 -0
package/src/Actor.ts
ADDED
|
@@ -0,0 +1,550 @@
|
|
|
1
|
+
import {
|
|
2
|
+
Context,
|
|
3
|
+
Effect,
|
|
4
|
+
identity,
|
|
5
|
+
Layer,
|
|
6
|
+
Predicate,
|
|
7
|
+
type Record,
|
|
8
|
+
type Schema,
|
|
9
|
+
Scope,
|
|
10
|
+
Struct,
|
|
11
|
+
} from "effect";
|
|
12
|
+
import * as Rivetkit from "rivetkit";
|
|
13
|
+
import type * as RivetkitDb from "rivetkit/db";
|
|
14
|
+
import type * as Action from "./Action.ts";
|
|
15
|
+
import * as Client from "./Client.ts";
|
|
16
|
+
import * as ActionDispatcher from "./internal/ActionDispatcher.ts";
|
|
17
|
+
import * as ActorInstanceManager from "./internal/ActorInstanceManager.ts";
|
|
18
|
+
import * as ActorStateAdapter from "./internal/ActorStateAdapter.ts";
|
|
19
|
+
import { makeActorLogAnnotations } from "./internal/logging.ts";
|
|
20
|
+
import type * as StateOptions from "./internal/StateOptions.ts";
|
|
21
|
+
import * as Registry from "./Registry.ts";
|
|
22
|
+
import type * as RivetError from "./RivetError.ts";
|
|
23
|
+
import type * as State from "./State.ts";
|
|
24
|
+
|
|
25
|
+
const TypeId = "~@rivetkit/effect/Actor";
|
|
26
|
+
|
|
27
|
+
export const isActor = (u: unknown): u is Actor<any, any> =>
|
|
28
|
+
Predicate.hasProperty(u, TypeId);
|
|
29
|
+
|
|
30
|
+
const rivetkitActorOptionsKeys = [
|
|
31
|
+
"name",
|
|
32
|
+
"icon",
|
|
33
|
+
] as const satisfies ReadonlyArray<
|
|
34
|
+
keyof NonNullable<Rivetkit.ActorOptionsInput>
|
|
35
|
+
>;
|
|
36
|
+
|
|
37
|
+
export type RivetkitActorOptions = Pick<
|
|
38
|
+
NonNullable<Rivetkit.ActorOptionsInput>,
|
|
39
|
+
(typeof rivetkitActorOptionsKeys)[number]
|
|
40
|
+
>;
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Per-actor instance options. Combines the public
|
|
44
|
+
* `RivetkitActorOptions` (forwarded verbatim to `Rivetkit.actor`)
|
|
45
|
+
* with the effect-SDK-only options.
|
|
46
|
+
*/
|
|
47
|
+
export type Options<
|
|
48
|
+
State extends StateOptions.Any,
|
|
49
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
50
|
+
> = Readonly<RivetkitActorOptions> & {
|
|
51
|
+
readonly state?: State;
|
|
52
|
+
readonly db?: Database;
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
type StatelessOptions<
|
|
56
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
57
|
+
> = Readonly<RivetkitActorOptions> & {
|
|
58
|
+
readonly state?: never;
|
|
59
|
+
readonly db?: Database;
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
type StatefulOptions<
|
|
63
|
+
State extends StateOptions.Any,
|
|
64
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
65
|
+
> = Readonly<RivetkitActorOptions> & {
|
|
66
|
+
readonly state: State;
|
|
67
|
+
readonly db?: Database;
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
const splitOptions = <
|
|
71
|
+
State extends StateOptions.Any,
|
|
72
|
+
Database extends RivetkitDb.AnyDatabaseProvider,
|
|
73
|
+
>(
|
|
74
|
+
options: Options<State, Database>,
|
|
75
|
+
) => ({
|
|
76
|
+
rivetkitOptions: Struct.pick(options, rivetkitActorOptionsKeys),
|
|
77
|
+
effectOptions: Struct.omit(options, rivetkitActorOptionsKeys),
|
|
78
|
+
});
|
|
79
|
+
|
|
80
|
+
/**
|
|
81
|
+
* Per-instance identity carried inside the wake scope. An actor
|
|
82
|
+
* instance is addressable in two ways:
|
|
83
|
+
*
|
|
84
|
+
* - `(name, key)` — stable user-facing pair (e.g. "Counter", ["counter-123"])
|
|
85
|
+
* - `actorId` — opaque engine-assigned unique identifier
|
|
86
|
+
*
|
|
87
|
+
* Available inside `Actor.toLayer`'s wake effect via
|
|
88
|
+
* `yield* Actor.CurrentAddress`.
|
|
89
|
+
*/
|
|
90
|
+
export type ActorAddress = Pick<
|
|
91
|
+
Rivetkit.ActorContext<any, any, any, any, any, any, any, any>,
|
|
92
|
+
"actorId" | "name" | "key"
|
|
93
|
+
>;
|
|
94
|
+
|
|
95
|
+
/**
|
|
96
|
+
* Context tag for the current actor instance's address. Provided
|
|
97
|
+
* once per wake when the wake effect runs; capture it into a
|
|
98
|
+
* closure if action handlers need it.
|
|
99
|
+
*/
|
|
100
|
+
export class CurrentAddress extends Context.Service<
|
|
101
|
+
CurrentAddress,
|
|
102
|
+
ActorAddress
|
|
103
|
+
>()("@rivetkit/effect/Actor/CurrentAddress") {}
|
|
104
|
+
|
|
105
|
+
export class Sleep extends Context.Service<Sleep, Effect.Effect<void>>()(
|
|
106
|
+
"@rivetkit/effect/Actor/Sleep",
|
|
107
|
+
) {}
|
|
108
|
+
|
|
109
|
+
export type ActionRequest<A extends Action.Any> =
|
|
110
|
+
A extends Action.Action<
|
|
111
|
+
infer Tag,
|
|
112
|
+
infer Payload,
|
|
113
|
+
infer _Success,
|
|
114
|
+
infer _Error
|
|
115
|
+
>
|
|
116
|
+
? {
|
|
117
|
+
readonly _tag: Tag;
|
|
118
|
+
readonly action: A;
|
|
119
|
+
readonly payload: Payload["Type"];
|
|
120
|
+
}
|
|
121
|
+
: never;
|
|
122
|
+
|
|
123
|
+
type ActionHandlerServices<ActionHandlers> = {
|
|
124
|
+
readonly [Name in keyof ActionHandlers]: ActionHandlers[Name] extends (
|
|
125
|
+
...args: ReadonlyArray<any>
|
|
126
|
+
) => Effect.Effect<any, any, infer R>
|
|
127
|
+
? R
|
|
128
|
+
: never;
|
|
129
|
+
}[keyof ActionHandlers];
|
|
130
|
+
|
|
131
|
+
type RivetkitActorDefinitionFor<
|
|
132
|
+
State extends StateOptions.Any,
|
|
133
|
+
Database extends RivetkitDb.AnyDatabaseProvider,
|
|
134
|
+
> = Rivetkit.ActorDefinition<
|
|
135
|
+
StateOptions.Encoded<State>,
|
|
136
|
+
undefined,
|
|
137
|
+
undefined,
|
|
138
|
+
undefined,
|
|
139
|
+
undefined,
|
|
140
|
+
Database,
|
|
141
|
+
Record<never, never>,
|
|
142
|
+
Record<never, never>,
|
|
143
|
+
any
|
|
144
|
+
>;
|
|
145
|
+
|
|
146
|
+
export type WakeOptions<
|
|
147
|
+
ActorDefinition extends
|
|
148
|
+
Rivetkit.AnyActorDefinition = Rivetkit.AnyActorDefinition,
|
|
149
|
+
> = {
|
|
150
|
+
readonly rawRivetkitContext: Rivetkit.WakeContextOf<ActorDefinition>;
|
|
151
|
+
};
|
|
152
|
+
|
|
153
|
+
type RawWakeContextFor<
|
|
154
|
+
State extends StateOptions.Any,
|
|
155
|
+
Database extends RivetkitDb.AnyDatabaseProvider,
|
|
156
|
+
> = {
|
|
157
|
+
[Key in keyof Rivetkit.WakeContextOf<
|
|
158
|
+
RivetkitActorDefinitionFor<State, Database>
|
|
159
|
+
>]: Key extends "state"
|
|
160
|
+
? [State] extends [never]
|
|
161
|
+
? never
|
|
162
|
+
: StateOptions.Encoded<State>
|
|
163
|
+
: Rivetkit.WakeContextOf<
|
|
164
|
+
RivetkitActorDefinitionFor<State, Database>
|
|
165
|
+
>[Key];
|
|
166
|
+
};
|
|
167
|
+
|
|
168
|
+
type WakeOptionsFor<
|
|
169
|
+
StateDefinition extends StateOptions.Any,
|
|
170
|
+
Database extends RivetkitDb.AnyDatabaseProvider,
|
|
171
|
+
> = {
|
|
172
|
+
readonly rawRivetkitContext: RawWakeContextFor<StateDefinition, Database>;
|
|
173
|
+
} & ([StateDefinition] extends [never]
|
|
174
|
+
? unknown
|
|
175
|
+
: {
|
|
176
|
+
readonly state: State.State<
|
|
177
|
+
StateOptions.Decoded<StateDefinition>,
|
|
178
|
+
Schema.SchemaError
|
|
179
|
+
>;
|
|
180
|
+
});
|
|
181
|
+
|
|
182
|
+
type WakeFunction<ActionHandlers, R, W extends WakeOptions> =
|
|
183
|
+
| ((wakeOptions: W) => ActionHandlers)
|
|
184
|
+
| ((wakeOptions: W) => Effect.Effect<ActionHandlers, never, R>);
|
|
185
|
+
|
|
186
|
+
type Wake<ActionHandlers, R, RX, W extends WakeOptions> =
|
|
187
|
+
| ActionHandlers
|
|
188
|
+
| Effect.Effect<ActionHandlers, never, RX>
|
|
189
|
+
| WakeFunction<ActionHandlers, R, W>
|
|
190
|
+
| Effect.Effect<WakeFunction<ActionHandlers, R, W>, never, RX>;
|
|
191
|
+
|
|
192
|
+
export type AccessorKeyParam = string | Rivetkit.ActorKey;
|
|
193
|
+
|
|
194
|
+
/**
|
|
195
|
+
* A typed handle for one actor instance. Each action becomes a
|
|
196
|
+
* method that takes the action's payload-constructor input and
|
|
197
|
+
* returns an Effect with the action's success / typed error
|
|
198
|
+
* channels baked in.
|
|
199
|
+
*/
|
|
200
|
+
export type Handle<Actions extends Action.Any> = {
|
|
201
|
+
readonly [A in Actions as Action.Tag<A>]: (
|
|
202
|
+
payload: Action.PayloadConstructor<A>,
|
|
203
|
+
) => Effect.Effect<
|
|
204
|
+
Action.Success<A>,
|
|
205
|
+
Action.Error<A> | RivetError.RivetError,
|
|
206
|
+
Action.ServicesClient<A>
|
|
207
|
+
>;
|
|
208
|
+
};
|
|
209
|
+
|
|
210
|
+
/**
|
|
211
|
+
* Yielded by `Actor.client`. Address an actor instance by key, then
|
|
212
|
+
* dispatch typed action calls against the returned `Handle`.
|
|
213
|
+
*/
|
|
214
|
+
export type Accessor<Actions extends Action.Any> = {
|
|
215
|
+
readonly getOrCreate: (key: AccessorKeyParam) => Handle<Actions>;
|
|
216
|
+
};
|
|
217
|
+
|
|
218
|
+
type UnknownToNever<T> = unknown extends T ? never : T;
|
|
219
|
+
|
|
220
|
+
type ExcludeBuiltInWakeServices<
|
|
221
|
+
T,
|
|
222
|
+
_State extends StateOptions.Any,
|
|
223
|
+
> = UnknownToNever<Exclude<T, Scope.Scope | CurrentAddress | Sleep>>;
|
|
224
|
+
|
|
225
|
+
type ToLayerRequirements<
|
|
226
|
+
Actions extends Action.Any,
|
|
227
|
+
ActionHandlers,
|
|
228
|
+
State extends StateOptions.Any,
|
|
229
|
+
R,
|
|
230
|
+
RX,
|
|
231
|
+
> =
|
|
232
|
+
| ExcludeBuiltInWakeServices<R, State>
|
|
233
|
+
| ExcludeBuiltInWakeServices<RX, State>
|
|
234
|
+
| UnknownToNever<ActionHandlerServices<ActionHandlers>>
|
|
235
|
+
| UnknownToNever<Action.ServicesServer<Actions>>
|
|
236
|
+
| UnknownToNever<Action.ServicesClient<Actions>>
|
|
237
|
+
| Registry.Registry;
|
|
238
|
+
|
|
239
|
+
/**
|
|
240
|
+
* A Rivet Actor contract. It carries the action schemas and
|
|
241
|
+
* display options, but no server implementation.
|
|
242
|
+
*/
|
|
243
|
+
export interface Actor<
|
|
244
|
+
Name extends string,
|
|
245
|
+
Actions extends Action.Any = never,
|
|
246
|
+
> {
|
|
247
|
+
readonly [TypeId]: typeof TypeId;
|
|
248
|
+
readonly name: Name;
|
|
249
|
+
readonly actions: ReadonlyArray<Actions>;
|
|
250
|
+
|
|
251
|
+
of<ActionHandlers extends ActionHandlersFrom<Actions>>(
|
|
252
|
+
actionHandlers: ActionHandlers,
|
|
253
|
+
): ActionHandlers;
|
|
254
|
+
|
|
255
|
+
toLayer<
|
|
256
|
+
ActionHandlers extends ActionHandlersFrom<Actions>,
|
|
257
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
258
|
+
R = never,
|
|
259
|
+
RX = never,
|
|
260
|
+
>(
|
|
261
|
+
wake: Wake<ActionHandlers, R, RX, WakeOptionsFor<never, Database>>,
|
|
262
|
+
options: StatelessOptions<Database>,
|
|
263
|
+
): Layer.Layer<
|
|
264
|
+
never,
|
|
265
|
+
never,
|
|
266
|
+
ToLayerRequirements<Actions, ActionHandlers, never, R, RX>
|
|
267
|
+
>;
|
|
268
|
+
|
|
269
|
+
toLayer<
|
|
270
|
+
ActionHandlers extends ActionHandlersFrom<Actions>,
|
|
271
|
+
R = never,
|
|
272
|
+
RX = never,
|
|
273
|
+
>(
|
|
274
|
+
wake: Wake<ActionHandlers, R, RX, WakeOptionsFor<never, undefined>>,
|
|
275
|
+
): Layer.Layer<
|
|
276
|
+
never,
|
|
277
|
+
never,
|
|
278
|
+
ToLayerRequirements<Actions, ActionHandlers, never, R, RX>
|
|
279
|
+
>;
|
|
280
|
+
|
|
281
|
+
toLayer<
|
|
282
|
+
ActionHandlers extends ActionHandlersFrom<Actions>,
|
|
283
|
+
State extends StateOptions.Any,
|
|
284
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
285
|
+
R = never,
|
|
286
|
+
RX = never,
|
|
287
|
+
>(
|
|
288
|
+
wake: Wake<ActionHandlers, R, RX, WakeOptionsFor<State, Database>>,
|
|
289
|
+
options: StatefulOptions<State, Database>,
|
|
290
|
+
): Layer.Layer<
|
|
291
|
+
never,
|
|
292
|
+
never,
|
|
293
|
+
ToLayerRequirements<Actions, ActionHandlers, State, R, RX>
|
|
294
|
+
>;
|
|
295
|
+
|
|
296
|
+
/**
|
|
297
|
+
* Effect-yielded typed accessor for this actor. Provide a
|
|
298
|
+
* `Client.layer({ ... })` once at the program root; every
|
|
299
|
+
* `yield* SomeActor.client` then dispatches through the same
|
|
300
|
+
* transport.
|
|
301
|
+
*/
|
|
302
|
+
readonly client: Effect.Effect<Accessor<Actions>, never, Client.Client>;
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
export type Any = Actor<string, Action.AnyWithProps>;
|
|
306
|
+
|
|
307
|
+
export type ActionHandlersFrom<Actions extends Action.Any> = {
|
|
308
|
+
readonly [A in Actions as A["_tag"]]: (
|
|
309
|
+
envelope: ActionRequest<A>,
|
|
310
|
+
) => Action.ResultFrom<A, any>;
|
|
311
|
+
};
|
|
312
|
+
|
|
313
|
+
const Proto: Omit<Actor<any, any>, "name" | "actions"> = {
|
|
314
|
+
[TypeId]: TypeId,
|
|
315
|
+
toLayer<
|
|
316
|
+
Actions extends Action.AnyWithProps,
|
|
317
|
+
ActionHandlers extends ActionHandlersFrom<Actions>,
|
|
318
|
+
State extends StateOptions.Any = never,
|
|
319
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
320
|
+
R = never,
|
|
321
|
+
RX = never,
|
|
322
|
+
>(
|
|
323
|
+
this: Actor<string, Actions>,
|
|
324
|
+
wake: Wake<ActionHandlers, R, RX, WakeOptionsFor<State, Database>>,
|
|
325
|
+
options: Options<State, Database> = {},
|
|
326
|
+
) {
|
|
327
|
+
return makeRivetkitActor({
|
|
328
|
+
actor: this,
|
|
329
|
+
wakeHandler: toWakeHandler<
|
|
330
|
+
ActionHandlers,
|
|
331
|
+
R,
|
|
332
|
+
RX,
|
|
333
|
+
WakeOptionsFor<State, Database>
|
|
334
|
+
>(wake),
|
|
335
|
+
options,
|
|
336
|
+
}).pipe(
|
|
337
|
+
Effect.flatMap((rivetKitActor) =>
|
|
338
|
+
Registry.Registry.pipe(
|
|
339
|
+
Effect.flatMap((registry) =>
|
|
340
|
+
Effect.sync(() =>
|
|
341
|
+
registry.rivetkitActors.set(
|
|
342
|
+
this.name,
|
|
343
|
+
rivetKitActor,
|
|
344
|
+
),
|
|
345
|
+
),
|
|
346
|
+
),
|
|
347
|
+
),
|
|
348
|
+
),
|
|
349
|
+
Layer.effectDiscard,
|
|
350
|
+
);
|
|
351
|
+
},
|
|
352
|
+
get client() {
|
|
353
|
+
return Client.Client.pipe(
|
|
354
|
+
Effect.map((client) => client.makeActorAccessor(this as Any)),
|
|
355
|
+
);
|
|
356
|
+
},
|
|
357
|
+
of: identity,
|
|
358
|
+
};
|
|
359
|
+
|
|
360
|
+
/**
|
|
361
|
+
* Define a Rivet Actor contract.
|
|
362
|
+
*/
|
|
363
|
+
export const make = <
|
|
364
|
+
const Name extends string,
|
|
365
|
+
const Actions extends ReadonlyArray<Action.AnyWithProps> = readonly [],
|
|
366
|
+
>(
|
|
367
|
+
name: Name,
|
|
368
|
+
options?: {
|
|
369
|
+
readonly actions?: Actions;
|
|
370
|
+
},
|
|
371
|
+
): Actor<Name, Actions[number]> => {
|
|
372
|
+
const self = Object.create(Proto);
|
|
373
|
+
self.name = name;
|
|
374
|
+
self.actions = options?.actions ?? [];
|
|
375
|
+
return self;
|
|
376
|
+
};
|
|
377
|
+
|
|
378
|
+
export function toWakeHandler<
|
|
379
|
+
ActionHandlers extends object,
|
|
380
|
+
R,
|
|
381
|
+
RX,
|
|
382
|
+
W extends WakeOptions = WakeOptions,
|
|
383
|
+
>(
|
|
384
|
+
wake: Effect.Effect<
|
|
385
|
+
(wakeOptions: W) => Effect.Effect<ActionHandlers, never, R>,
|
|
386
|
+
never,
|
|
387
|
+
RX
|
|
388
|
+
>,
|
|
389
|
+
): (wakeOptions: W) => Effect.Effect<ActionHandlers, never, R | RX>;
|
|
390
|
+
export function toWakeHandler<
|
|
391
|
+
ActionHandlers extends object,
|
|
392
|
+
RX,
|
|
393
|
+
W extends WakeOptions = WakeOptions,
|
|
394
|
+
>(
|
|
395
|
+
wake: Effect.Effect<(wakeOptions: W) => ActionHandlers, never, RX>,
|
|
396
|
+
): (wakeOptions: W) => Effect.Effect<ActionHandlers, never, RX>;
|
|
397
|
+
export function toWakeHandler<
|
|
398
|
+
ActionHandlers extends object,
|
|
399
|
+
R,
|
|
400
|
+
W extends WakeOptions = WakeOptions,
|
|
401
|
+
>(
|
|
402
|
+
wake: (wakeOptions: W) => Effect.Effect<ActionHandlers, never, R>,
|
|
403
|
+
): (wakeOptions: W) => Effect.Effect<ActionHandlers, never, R>;
|
|
404
|
+
export function toWakeHandler<
|
|
405
|
+
ActionHandlers extends object,
|
|
406
|
+
W extends WakeOptions = WakeOptions,
|
|
407
|
+
>(
|
|
408
|
+
wake: (wakeOptions: W) => ActionHandlers,
|
|
409
|
+
): (wakeOptions: W) => Effect.Effect<ActionHandlers>;
|
|
410
|
+
export function toWakeHandler<
|
|
411
|
+
ActionHandlers extends object,
|
|
412
|
+
RX,
|
|
413
|
+
W extends WakeOptions = WakeOptions,
|
|
414
|
+
>(
|
|
415
|
+
wake: Effect.Effect<ActionHandlers, never, RX>,
|
|
416
|
+
): (wakeOptions: W) => Effect.Effect<ActionHandlers, never, RX>;
|
|
417
|
+
export function toWakeHandler<
|
|
418
|
+
ActionHandlers extends object,
|
|
419
|
+
W extends WakeOptions = WakeOptions,
|
|
420
|
+
>(wake: ActionHandlers): (wakeOptions: W) => Effect.Effect<ActionHandlers>;
|
|
421
|
+
export function toWakeHandler<
|
|
422
|
+
ActionHandlers extends object,
|
|
423
|
+
R,
|
|
424
|
+
RX,
|
|
425
|
+
W extends WakeOptions = WakeOptions,
|
|
426
|
+
>(
|
|
427
|
+
wake: Wake<ActionHandlers, R, RX, W>,
|
|
428
|
+
): (wakeOptions: W) => Effect.Effect<ActionHandlers, never, R | RX>;
|
|
429
|
+
export function toWakeHandler<
|
|
430
|
+
ActionHandlers extends object,
|
|
431
|
+
R,
|
|
432
|
+
RX,
|
|
433
|
+
W extends WakeOptions = WakeOptions,
|
|
434
|
+
>(wake: Wake<ActionHandlers, R, RX, W>) {
|
|
435
|
+
return (wakeOptions: W) => {
|
|
436
|
+
const wakeEffect = Effect.isEffect(wake)
|
|
437
|
+
? (wake as Effect.Effect<
|
|
438
|
+
ActionHandlers | WakeFunction<ActionHandlers, R, W>,
|
|
439
|
+
never,
|
|
440
|
+
RX
|
|
441
|
+
>)
|
|
442
|
+
: Effect.succeed(wake);
|
|
443
|
+
|
|
444
|
+
return wakeEffect.pipe(
|
|
445
|
+
Effect.flatMap((resolvedWake) => {
|
|
446
|
+
if (typeof resolvedWake === "function") {
|
|
447
|
+
const actionHandlers = resolvedWake(wakeOptions);
|
|
448
|
+
return Effect.isEffect(actionHandlers)
|
|
449
|
+
? actionHandlers
|
|
450
|
+
: Effect.succeed(actionHandlers);
|
|
451
|
+
}
|
|
452
|
+
|
|
453
|
+
return Effect.succeed(resolvedWake);
|
|
454
|
+
}),
|
|
455
|
+
);
|
|
456
|
+
};
|
|
457
|
+
}
|
|
458
|
+
|
|
459
|
+
const makeRivetkitActor = Effect.fnUntraced(function* <
|
|
460
|
+
Name extends string,
|
|
461
|
+
Actions extends Action.AnyWithProps,
|
|
462
|
+
ActionHandlers extends ActionHandlersFrom<Actions>,
|
|
463
|
+
RX,
|
|
464
|
+
State extends StateOptions.Any = never,
|
|
465
|
+
Database extends RivetkitDb.AnyDatabaseProvider = undefined,
|
|
466
|
+
>({
|
|
467
|
+
actor,
|
|
468
|
+
wakeHandler,
|
|
469
|
+
options,
|
|
470
|
+
}: {
|
|
471
|
+
readonly actor: Actor<Name, Actions>;
|
|
472
|
+
readonly wakeHandler: (
|
|
473
|
+
wakeOptions: WakeOptionsFor<State, Database>,
|
|
474
|
+
) => Effect.Effect<ActionHandlers, never, RX>;
|
|
475
|
+
readonly options: Options<State, Database>;
|
|
476
|
+
}) {
|
|
477
|
+
const { effectOptions, rivetkitOptions } = splitOptions(options);
|
|
478
|
+
const stateAdapter =
|
|
479
|
+
effectOptions.state === undefined
|
|
480
|
+
? undefined
|
|
481
|
+
: yield* ActorStateAdapter.make<State>(effectOptions.state);
|
|
482
|
+
|
|
483
|
+
const instanceManager = yield* ActorInstanceManager.make<
|
|
484
|
+
ActionHandlers,
|
|
485
|
+
State,
|
|
486
|
+
Database,
|
|
487
|
+
WakeOptionsFor<State, Database>
|
|
488
|
+
>({
|
|
489
|
+
wakeHandler: (wakeOptions) =>
|
|
490
|
+
wakeHandler(wakeOptions).pipe(
|
|
491
|
+
Effect.annotateLogs(
|
|
492
|
+
makeActorLogAnnotations(wakeOptions.rawRivetkitContext),
|
|
493
|
+
),
|
|
494
|
+
),
|
|
495
|
+
stateAdapter,
|
|
496
|
+
makeContext: (c, scope) =>
|
|
497
|
+
Context.mergeAll(
|
|
498
|
+
Context.make(CurrentAddress, {
|
|
499
|
+
actorId: c.actorId,
|
|
500
|
+
name: c.name,
|
|
501
|
+
key: c.key,
|
|
502
|
+
}),
|
|
503
|
+
Context.make(Scope.Scope, scope),
|
|
504
|
+
Context.make(
|
|
505
|
+
Sleep,
|
|
506
|
+
Effect.sync(() => c.sleep()),
|
|
507
|
+
),
|
|
508
|
+
),
|
|
509
|
+
makeWakeOptions: (c, state) =>
|
|
510
|
+
({
|
|
511
|
+
rawRivetkitContext: c,
|
|
512
|
+
...(state === undefined ? {} : { state }),
|
|
513
|
+
}) as WakeOptionsFor<State, Database>,
|
|
514
|
+
});
|
|
515
|
+
|
|
516
|
+
const actions = ActionDispatcher.make<
|
|
517
|
+
Name,
|
|
518
|
+
Actions,
|
|
519
|
+
ActionHandlers,
|
|
520
|
+
RivetkitActorDefinitionFor<State, Database>
|
|
521
|
+
>({
|
|
522
|
+
actor,
|
|
523
|
+
getInstance: instanceManager.get,
|
|
524
|
+
});
|
|
525
|
+
|
|
526
|
+
return Rivetkit.actor<
|
|
527
|
+
StateOptions.Encoded<State>,
|
|
528
|
+
undefined,
|
|
529
|
+
undefined,
|
|
530
|
+
undefined,
|
|
531
|
+
undefined,
|
|
532
|
+
Database,
|
|
533
|
+
Record<never, never>,
|
|
534
|
+
Record<never, never>,
|
|
535
|
+
any
|
|
536
|
+
>({
|
|
537
|
+
options: rivetkitOptions,
|
|
538
|
+
...(effectOptions.db ? { db: effectOptions.db } : {}),
|
|
539
|
+
onWake: instanceManager.onWake,
|
|
540
|
+
...(stateAdapter
|
|
541
|
+
? { createState: stateAdapter.createInitialState }
|
|
542
|
+
: {}),
|
|
543
|
+
actions,
|
|
544
|
+
...(instanceManager.onStateChange
|
|
545
|
+
? { onStateChange: instanceManager.onStateChange }
|
|
546
|
+
: {}),
|
|
547
|
+
onSleep: instanceManager.onTeardown,
|
|
548
|
+
onDestroy: instanceManager.onTeardown,
|
|
549
|
+
});
|
|
550
|
+
});
|