depa-actor 0.1.2 → 0.2.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 (86) hide show
  1. package/dist/core/ActorSystem.d.ts +1 -1
  2. package/dist/core/ActorSystem.d.ts.map +1 -1
  3. package/dist/dispatch/ActorDispatchAdapter.d.ts +1 -1
  4. package/dist/dispatch/ActorDispatchAdapter.d.ts.map +1 -1
  5. package/dist/execution/commandDeque.d.ts +121 -0
  6. package/dist/execution/commandDeque.d.ts.map +1 -0
  7. package/dist/execution/commandDeque.js +415 -0
  8. package/dist/execution/commandDeque.js.map +1 -0
  9. package/dist/execution/dispatcher.d.ts +72 -0
  10. package/dist/execution/dispatcher.d.ts.map +1 -0
  11. package/dist/execution/dispatcher.js +77 -0
  12. package/dist/execution/dispatcher.js.map +1 -0
  13. package/dist/execution/index.d.ts +7 -0
  14. package/dist/execution/index.d.ts.map +1 -0
  15. package/dist/execution/index.js +4 -0
  16. package/dist/execution/index.js.map +1 -0
  17. package/dist/execution/stack.d.ts +24 -0
  18. package/dist/execution/stack.d.ts.map +1 -0
  19. package/dist/execution/stack.js +84 -0
  20. package/dist/execution/stack.js.map +1 -0
  21. package/dist/index.d.ts +17 -15
  22. package/dist/index.d.ts.map +1 -1
  23. package/dist/index.js +9 -8
  24. package/dist/index.js.map +1 -1
  25. package/dist/orchestration/index.d.ts +8 -8
  26. package/dist/orchestration/index.d.ts.map +1 -1
  27. package/dist/orchestration/index.js +6 -6
  28. package/dist/orchestration/index.js.map +1 -1
  29. package/dist/orchestration/presets/aiAgent.d.ts +2 -2
  30. package/dist/orchestration/presets/aiAgent.d.ts.map +1 -1
  31. package/dist/orchestration/recovery.d.ts +2 -2
  32. package/dist/orchestration/recovery.d.ts.map +1 -1
  33. package/dist/orchestration/reducer.d.ts +2 -2
  34. package/dist/orchestration/reducer.d.ts.map +1 -1
  35. package/dist/orchestration/reducer.js +2 -2
  36. package/dist/orchestration/reducer.js.map +1 -1
  37. package/dist/orchestration/runtimeAdapter.d.ts +3 -3
  38. package/dist/orchestration/runtimeAdapter.d.ts.map +1 -1
  39. package/dist/orchestration/scheduler.d.ts +2 -2
  40. package/dist/orchestration/scheduler.d.ts.map +1 -1
  41. package/dist/orchestration/types.d.ts +1 -1
  42. package/dist/orchestration/types.d.ts.map +1 -1
  43. package/dist/pipeline/ActorPipeline.d.ts +1 -1
  44. package/dist/pipeline/ActorPipeline.d.ts.map +1 -1
  45. package/dist/runtime/ActorRuntime.d.ts +2 -2
  46. package/dist/runtime/ActorRuntime.d.ts.map +1 -1
  47. package/dist/runtime/ActorRuntime.js +1 -1
  48. package/dist/runtime/ActorRuntime.js.map +1 -1
  49. package/dist-cjs/core/ActorSystem.cjs +172 -0
  50. package/dist-cjs/core/types.cjs +10 -0
  51. package/dist-cjs/dispatch/ActorDispatchAdapter.cjs +40 -0
  52. package/dist-cjs/execution/commandDeque.cjs +430 -0
  53. package/dist-cjs/execution/dispatcher.cjs +79 -0
  54. package/dist-cjs/execution/index.cjs +24 -0
  55. package/dist-cjs/execution/stack.cjs +88 -0
  56. package/dist-cjs/index.cjs +52 -0
  57. package/dist-cjs/orchestration/index.cjs +19 -0
  58. package/dist-cjs/orchestration/presets/aiAgent.cjs +40 -0
  59. package/dist-cjs/orchestration/recovery.cjs +112 -0
  60. package/dist-cjs/orchestration/reducer.cjs +276 -0
  61. package/dist-cjs/orchestration/runtimeAdapter.cjs +14 -0
  62. package/dist-cjs/orchestration/scheduler.cjs +86 -0
  63. package/dist-cjs/orchestration/types.cjs +14 -0
  64. package/dist-cjs/package.json +3 -0
  65. package/dist-cjs/pipeline/ActorPipeline.cjs +34 -0
  66. package/dist-cjs/runtime/ActorRuntime.cjs +77 -0
  67. package/dist-cjs/runtime/completion.cjs +75 -0
  68. package/dist-cjs/runtime/indexing.cjs +34 -0
  69. package/dist-cjs/runtime/snapshot.cjs +14 -0
  70. package/package.json +6 -4
  71. package/src/core/ActorSystem.ts +1 -1
  72. package/src/dispatch/ActorDispatchAdapter.ts +1 -1
  73. package/src/execution/commandDeque.ts +656 -0
  74. package/src/execution/dispatcher.ts +188 -0
  75. package/src/execution/index.ts +58 -0
  76. package/src/execution/stack.ts +130 -0
  77. package/src/index.ts +67 -15
  78. package/src/orchestration/index.ts +8 -8
  79. package/src/orchestration/presets/aiAgent.ts +2 -2
  80. package/src/orchestration/recovery.ts +2 -2
  81. package/src/orchestration/reducer.ts +3 -3
  82. package/src/orchestration/runtimeAdapter.ts +3 -3
  83. package/src/orchestration/scheduler.ts +2 -2
  84. package/src/orchestration/types.ts +1 -1
  85. package/src/pipeline/ActorPipeline.ts +1 -1
  86. package/src/runtime/ActorRuntime.ts +2 -2
@@ -0,0 +1,19 @@
1
+ "use strict";
2
+ // depa-actor — Orchestration (Fiber Scheduling)
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.dispatchEffects = exports.createAiAgentSchedulerHooks = exports.scheduleOne = exports.selectNextFiberId = exports.computeEffectivePriority = exports.applyFailure = exports.reduceOrchestrator = exports.createOrchestratorState = exports.DEFAULT_ORCHESTRATOR_OPTIONS = void 0;
5
+ var types_js_1 = require("./types.cjs");
6
+ Object.defineProperty(exports, "DEFAULT_ORCHESTRATOR_OPTIONS", { enumerable: true, get: function () { return types_js_1.DEFAULT_ORCHESTRATOR_OPTIONS; } });
7
+ var reducer_js_1 = require("./reducer.cjs");
8
+ Object.defineProperty(exports, "createOrchestratorState", { enumerable: true, get: function () { return reducer_js_1.createOrchestratorState; } });
9
+ Object.defineProperty(exports, "reduceOrchestrator", { enumerable: true, get: function () { return reducer_js_1.reduceOrchestrator; } });
10
+ var recovery_js_1 = require("./recovery.cjs");
11
+ Object.defineProperty(exports, "applyFailure", { enumerable: true, get: function () { return recovery_js_1.applyFailure; } });
12
+ var scheduler_js_1 = require("./scheduler.cjs");
13
+ Object.defineProperty(exports, "computeEffectivePriority", { enumerable: true, get: function () { return scheduler_js_1.computeEffectivePriority; } });
14
+ Object.defineProperty(exports, "selectNextFiberId", { enumerable: true, get: function () { return scheduler_js_1.selectNextFiberId; } });
15
+ Object.defineProperty(exports, "scheduleOne", { enumerable: true, get: function () { return scheduler_js_1.scheduleOne; } });
16
+ var aiAgent_js_1 = require("./presets/aiAgent.cjs");
17
+ Object.defineProperty(exports, "createAiAgentSchedulerHooks", { enumerable: true, get: function () { return aiAgent_js_1.createAiAgentSchedulerHooks; } });
18
+ var runtimeAdapter_js_1 = require("./runtimeAdapter.cjs");
19
+ Object.defineProperty(exports, "dispatchEffects", { enumerable: true, get: function () { return runtimeAdapter_js_1.dispatchEffects; } });
@@ -0,0 +1,40 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createAiAgentSchedulerHooks = createAiAgentSchedulerHooks;
4
+ function isAiHumanWaitReason(reason) {
5
+ return reason === 'human_clarification' || reason === 'human_approval' || reason === 'human_answer';
6
+ }
7
+ function getEffectiveSuspendPolicy(fiber) {
8
+ const raw = fiber?.suspendPolicy;
9
+ return raw === 'continue_others' || raw === 'pause_all' ? raw : undefined;
10
+ }
11
+ function isBlockingLaneForPauseAll(lane) {
12
+ // Treat any non-background lane as blocking by default.
13
+ if (lane === 'background' || lane === 'collective') {
14
+ return false;
15
+ }
16
+ return true;
17
+ }
18
+ function isAllowedLaneDuringPauseAll(lane) {
19
+ return lane === 'background' || lane === 'collective';
20
+ }
21
+ function hasPauseAllHumanWaitInBlockingLane(state) {
22
+ return Object.values(state.fibers).some((fiber) => {
23
+ return (fiber?.status === 'suspended' &&
24
+ isAiHumanWaitReason(fiber?.waitingReason) &&
25
+ getEffectiveSuspendPolicy(fiber) === 'pause_all' &&
26
+ isBlockingLaneForPauseAll(fiber?.lane));
27
+ });
28
+ }
29
+ // AIAgent-compatible scheduling hooks:
30
+ // - When a pause_all human wait exists in a blocking lane (interactive/member), only allow background/collective lanes.
31
+ function createAiAgentSchedulerHooks() {
32
+ return {
33
+ filterCandidate: ({ state, fiber }) => {
34
+ if (!hasPauseAllHumanWaitInBlockingLane(state)) {
35
+ return true;
36
+ }
37
+ return isAllowedLaneDuringPauseAll(fiber?.lane);
38
+ },
39
+ };
40
+ }
@@ -0,0 +1,112 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.applyFailure = applyFailure;
4
+ function cloneFiberMap(state) {
5
+ return { ...state.fibers };
6
+ }
7
+ function buildDeadLetterEffects(state, fiber, reason) {
8
+ const effects = [
9
+ {
10
+ kind: 'dead_letter',
11
+ fiberId: fiber.id,
12
+ reason,
13
+ },
14
+ ];
15
+ const route = state.options.deadLetterFactory?.(fiber, reason);
16
+ if (route) {
17
+ effects.push({
18
+ kind: 'dead_letter',
19
+ fiberId: fiber.id,
20
+ reason,
21
+ to: route.to,
22
+ step: route.step,
23
+ });
24
+ }
25
+ return effects;
26
+ }
27
+ function computeRetryDelay(retryDelayMs, retryBackoffMultiplier, attempts) {
28
+ const base = Math.max(0, retryDelayMs);
29
+ const multiplier = Math.max(1, retryBackoffMultiplier);
30
+ return Math.floor(base * Math.pow(multiplier, Math.max(0, attempts - 1)));
31
+ }
32
+ function applyFailure(state, fiberId, now, error) {
33
+ const fiber = state.fibers[fiberId];
34
+ if (!fiber) {
35
+ return { state, effects: [] };
36
+ }
37
+ if (fiber.status === 'completed' || fiber.status === 'cancelled' || fiber.status === 'dead_letter') {
38
+ return { state, effects: [] };
39
+ }
40
+ const nextFibers = cloneFiberMap(state);
41
+ if (state.options.retryEnabled && fiber.attempts < fiber.maxAttempts) {
42
+ const nextAttempts = fiber.attempts + 1;
43
+ const delay = computeRetryDelay(state.options.retryDelayMs, state.options.retryBackoffMultiplier, nextAttempts);
44
+ const updated = {
45
+ ...fiber,
46
+ status: 'suspended',
47
+ waitingReason: 'retry_backoff',
48
+ suspendPolicy: undefined,
49
+ retryAt: now + delay,
50
+ timeoutAt: undefined,
51
+ attempts: nextAttempts,
52
+ lastError: error,
53
+ updatedAt: now,
54
+ };
55
+ nextFibers[fiberId] = updated;
56
+ return {
57
+ state: {
58
+ ...state,
59
+ fibers: nextFibers,
60
+ },
61
+ effects: [],
62
+ };
63
+ }
64
+ if (state.options.deadLetterEnabled) {
65
+ const updated = {
66
+ ...fiber,
67
+ status: 'dead_letter',
68
+ waitingReason: undefined,
69
+ suspendPolicy: undefined,
70
+ retryAt: undefined,
71
+ lastError: error,
72
+ updatedAt: now,
73
+ };
74
+ nextFibers[fiberId] = updated;
75
+ const deadLetters = [
76
+ ...state.deadLetters,
77
+ {
78
+ fiberId: fiber.id,
79
+ actorId: fiber.actorId,
80
+ reason: error,
81
+ at: now,
82
+ attempts: fiber.attempts,
83
+ step: fiber.step,
84
+ },
85
+ ];
86
+ return {
87
+ state: {
88
+ ...state,
89
+ fibers: nextFibers,
90
+ deadLetters,
91
+ },
92
+ effects: buildDeadLetterEffects(state, updated, error),
93
+ };
94
+ }
95
+ const updated = {
96
+ ...fiber,
97
+ status: 'failed',
98
+ waitingReason: undefined,
99
+ suspendPolicy: undefined,
100
+ retryAt: undefined,
101
+ lastError: error,
102
+ updatedAt: now,
103
+ };
104
+ nextFibers[fiberId] = updated;
105
+ return {
106
+ state: {
107
+ ...state,
108
+ fibers: nextFibers,
109
+ },
110
+ effects: [],
111
+ };
112
+ }
@@ -0,0 +1,276 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createOrchestratorState = createOrchestratorState;
4
+ exports.reduceOrchestrator = reduceOrchestrator;
5
+ const recovery_js_1 = require("./recovery.cjs");
6
+ const types_js_1 = require("./types.cjs");
7
+ function isTerminalStatus(status) {
8
+ return status === 'completed' || status === 'cancelled' || status === 'failed' || status === 'dead_letter';
9
+ }
10
+ function cloneFiberMap(state) {
11
+ return { ...state.fibers };
12
+ }
13
+ function upsertParentChildRelation(fibers, fiber, now) {
14
+ if (!fiber.parentId) {
15
+ return;
16
+ }
17
+ const parent = fibers[fiber.parentId];
18
+ if (!parent) {
19
+ return;
20
+ }
21
+ if (!parent.childIds.includes(fiber.id)) {
22
+ fibers[fiber.parentId] = {
23
+ ...parent,
24
+ childIds: [...parent.childIds, fiber.id],
25
+ updatedAt: now,
26
+ };
27
+ }
28
+ }
29
+ function createFiberRecord(input, now, order, state) {
30
+ const timeoutMs = input.timeoutMs ?? state.options.defaultTimeoutMs;
31
+ return {
32
+ id: input.id,
33
+ actorId: input.actorId,
34
+ parentId: input.parentId,
35
+ childIds: [],
36
+ lane: input.lane ?? 'default',
37
+ status: 'ready',
38
+ basePriority: input.basePriority,
39
+ age: 0,
40
+ attempts: 0,
41
+ maxAttempts: Math.max(0, input.maxAttempts ?? 0),
42
+ step: input.step,
43
+ waitingReason: undefined,
44
+ suspendPolicy: undefined,
45
+ timeoutMs: timeoutMs > 0 ? timeoutMs : undefined,
46
+ timeoutAt: undefined,
47
+ retryAt: undefined,
48
+ lastError: undefined,
49
+ order,
50
+ createdAt: now,
51
+ updatedAt: now,
52
+ };
53
+ }
54
+ function createOrchestratorState(options) {
55
+ const raw = (options ?? {});
56
+ const effectiveDefault = raw.defaultSuspendPolicy ??
57
+ types_js_1.DEFAULT_ORCHESTRATOR_OPTIONS.defaultSuspendPolicy;
58
+ const base = {
59
+ ...types_js_1.DEFAULT_ORCHESTRATOR_OPTIONS,
60
+ ...raw,
61
+ };
62
+ return {
63
+ options: {
64
+ ...base,
65
+ defaultSuspendPolicy: effectiveDefault,
66
+ },
67
+ fibers: {},
68
+ deadLetters: [],
69
+ sequence: 0,
70
+ };
71
+ }
72
+ function applyTick(state, now) {
73
+ let nextState = state;
74
+ let aggregatedEffects = [];
75
+ const ids = Object.keys(state.fibers);
76
+ for (const id of ids) {
77
+ const fiber = nextState.fibers[id];
78
+ if (!fiber) {
79
+ continue;
80
+ }
81
+ if (isTerminalStatus(fiber.status)) {
82
+ continue;
83
+ }
84
+ if (nextState.options.timeoutEnabled &&
85
+ fiber.timeoutAt !== undefined &&
86
+ now >= fiber.timeoutAt &&
87
+ (fiber.status === 'running' || fiber.status === 'ready' || fiber.status === 'suspended')) {
88
+ const timed = (0, recovery_js_1.applyFailure)(nextState, id, now, 'timeout');
89
+ nextState = timed.state;
90
+ aggregatedEffects = [...aggregatedEffects, ...timed.effects];
91
+ continue;
92
+ }
93
+ const iter = nextState.fibers[id];
94
+ if (iter &&
95
+ iter.status === 'suspended' &&
96
+ iter.waitingReason === 'retry_backoff' &&
97
+ iter.retryAt !== undefined &&
98
+ now >= iter.retryAt) {
99
+ nextState = {
100
+ ...nextState,
101
+ fibers: {
102
+ ...nextState.fibers,
103
+ [id]: {
104
+ ...iter,
105
+ status: 'ready',
106
+ waitingReason: undefined,
107
+ retryAt: undefined,
108
+ timeoutAt: undefined,
109
+ updatedAt: now,
110
+ },
111
+ },
112
+ };
113
+ }
114
+ }
115
+ return {
116
+ state: nextState,
117
+ effects: aggregatedEffects,
118
+ };
119
+ }
120
+ function reduceOrchestrator(state, action) {
121
+ if (action.type === 'tick') {
122
+ return applyTick(state, action.now);
123
+ }
124
+ if (action.type === 'spawn') {
125
+ const nextSequence = state.sequence + 1;
126
+ const nextFibers = cloneFiberMap(state);
127
+ const record = createFiberRecord(action.fiber, action.now, nextSequence, state);
128
+ nextFibers[action.fiber.id] = record;
129
+ upsertParentChildRelation(nextFibers, action.fiber, action.now);
130
+ return {
131
+ state: {
132
+ ...state,
133
+ sequence: nextSequence,
134
+ fibers: nextFibers,
135
+ },
136
+ effects: [],
137
+ };
138
+ }
139
+ const current = state.fibers[action.fiberId];
140
+ if (!current) {
141
+ return { state, effects: [] };
142
+ }
143
+ if (action.type === 'yield') {
144
+ if (isTerminalStatus(current.status)) {
145
+ return { state, effects: [] };
146
+ }
147
+ return {
148
+ state: {
149
+ ...state,
150
+ fibers: {
151
+ ...state.fibers,
152
+ [action.fiberId]: {
153
+ ...current,
154
+ status: 'ready',
155
+ waitingReason: undefined,
156
+ suspendPolicy: undefined,
157
+ timeoutAt: undefined,
158
+ step: action.nextStep ?? current.step,
159
+ updatedAt: action.now,
160
+ },
161
+ },
162
+ },
163
+ effects: [],
164
+ };
165
+ }
166
+ if (action.type === 'suspend') {
167
+ if (isTerminalStatus(current.status)) {
168
+ return { state, effects: [] };
169
+ }
170
+ const effectivePolicy = action.suspendPolicy ??
171
+ state.options.defaultSuspendPolicy ??
172
+ 'continue_others';
173
+ return {
174
+ state: {
175
+ ...state,
176
+ fibers: {
177
+ ...state.fibers,
178
+ [action.fiberId]: {
179
+ ...current,
180
+ status: 'suspended',
181
+ waitingReason: action.reason,
182
+ suspendPolicy: effectivePolicy,
183
+ timeoutAt: undefined,
184
+ updatedAt: action.now,
185
+ },
186
+ },
187
+ },
188
+ effects: [],
189
+ };
190
+ }
191
+ if (action.type === 'resume') {
192
+ if (isTerminalStatus(current.status)) {
193
+ return { state, effects: [] };
194
+ }
195
+ return {
196
+ state: {
197
+ ...state,
198
+ fibers: {
199
+ ...state.fibers,
200
+ [action.fiberId]: {
201
+ ...current,
202
+ status: 'ready',
203
+ waitingReason: undefined,
204
+ suspendPolicy: undefined,
205
+ retryAt: undefined,
206
+ timeoutAt: undefined,
207
+ step: action.nextStep ?? current.step,
208
+ updatedAt: action.now,
209
+ },
210
+ },
211
+ },
212
+ effects: [],
213
+ };
214
+ }
215
+ if (action.type === 'complete') {
216
+ return {
217
+ state: {
218
+ ...state,
219
+ fibers: {
220
+ ...state.fibers,
221
+ [action.fiberId]: {
222
+ ...current,
223
+ status: 'completed',
224
+ waitingReason: undefined,
225
+ suspendPolicy: undefined,
226
+ timeoutAt: undefined,
227
+ updatedAt: action.now,
228
+ },
229
+ },
230
+ },
231
+ effects: [],
232
+ };
233
+ }
234
+ if (action.type === 'fail') {
235
+ return (0, recovery_js_1.applyFailure)(state, action.fiberId, action.now, action.error);
236
+ }
237
+ if (action.type === 'cancel') {
238
+ const nextFibers = cloneFiberMap(state);
239
+ const queue = [action.fiberId];
240
+ const seen = new Set();
241
+ while (queue.length > 0) {
242
+ const id = queue.shift();
243
+ if (seen.has(id)) {
244
+ continue;
245
+ }
246
+ seen.add(id);
247
+ const item = nextFibers[id];
248
+ if (!item) {
249
+ continue;
250
+ }
251
+ nextFibers[id] = {
252
+ ...item,
253
+ status: 'cancelled',
254
+ waitingReason: undefined,
255
+ suspendPolicy: undefined,
256
+ timeoutAt: undefined,
257
+ retryAt: undefined,
258
+ lastError: action.reason,
259
+ updatedAt: action.now,
260
+ };
261
+ if (action.propagateToChildren) {
262
+ for (const childId of item.childIds) {
263
+ queue.push(childId);
264
+ }
265
+ }
266
+ }
267
+ return {
268
+ state: {
269
+ ...state,
270
+ fibers: nextFibers,
271
+ },
272
+ effects: [],
273
+ };
274
+ }
275
+ return { state, effects: [] };
276
+ }
@@ -0,0 +1,14 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.dispatchEffects = dispatchEffects;
4
+ function dispatchEffects(runtime, effects, senderId) {
5
+ const from = senderId ?? '__fiber_scheduler__';
6
+ for (const effect of effects) {
7
+ if (effect.kind === 'send') {
8
+ runtime.sendFrom(from, effect.to, effect.step.tag, effect.step.payload);
9
+ }
10
+ if (effect.kind === 'dead_letter' && effect.to && effect.step) {
11
+ runtime.sendFrom(from, effect.to, effect.step.tag, effect.step.payload);
12
+ }
13
+ }
14
+ }
@@ -0,0 +1,86 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.computeEffectivePriority = computeEffectivePriority;
4
+ exports.selectNextFiberId = selectNextFiberId;
5
+ exports.scheduleOne = scheduleOne;
6
+ function isSchedulable(fiber) {
7
+ return fiber.status === 'ready';
8
+ }
9
+ function computeEffectivePriority(fiber, agingStep) {
10
+ return fiber.basePriority - fiber.age * Math.max(0, agingStep);
11
+ }
12
+ function selectNextFiberId(state, now) {
13
+ const hooks = state.options.schedulerHooks;
14
+ const selectionNow = typeof now === 'number' ? now : Date.now();
15
+ let candidates = Object.values(state.fibers).filter(isSchedulable);
16
+ if (hooks?.filterCandidates) {
17
+ candidates = hooks.filterCandidates({ state, candidates, now: selectionNow });
18
+ }
19
+ else if (hooks?.filterCandidate) {
20
+ const f = hooks.filterCandidate;
21
+ candidates = candidates.filter(fiber => f({ state, fiber, now: selectionNow }));
22
+ }
23
+ if (candidates.length === 0) {
24
+ return undefined;
25
+ }
26
+ const agingStep = state.options.agingStep;
27
+ candidates.sort((a, b) => {
28
+ const pa = computeEffectivePriority(a, agingStep);
29
+ const pb = computeEffectivePriority(b, agingStep);
30
+ if (pa !== pb) {
31
+ return pa - pb;
32
+ }
33
+ return a.order - b.order;
34
+ });
35
+ return candidates[0]?.id;
36
+ }
37
+ function scheduleOne(state, now) {
38
+ const selectedFiberId = selectNextFiberId(state, now);
39
+ if (!selectedFiberId) {
40
+ return { state, effects: [] };
41
+ }
42
+ const selected = state.fibers[selectedFiberId];
43
+ if (!selected) {
44
+ return { state, effects: [] };
45
+ }
46
+ const timeoutMs = selected.timeoutMs ?? state.options.defaultTimeoutMs;
47
+ const timeoutAt = state.options.timeoutEnabled && timeoutMs > 0 ? now + timeoutMs : undefined;
48
+ const nextFibers = { ...state.fibers };
49
+ for (const [id, fiber] of Object.entries(state.fibers)) {
50
+ if (id === selectedFiberId) {
51
+ nextFibers[id] = {
52
+ ...fiber,
53
+ status: 'running',
54
+ age: 0,
55
+ timeoutAt,
56
+ updatedAt: now,
57
+ };
58
+ continue;
59
+ }
60
+ if (fiber.status === 'ready') {
61
+ nextFibers[id] = {
62
+ ...fiber,
63
+ age: fiber.age + Math.max(0, state.options.agingStep),
64
+ updatedAt: now,
65
+ };
66
+ }
67
+ }
68
+ const effects = [];
69
+ const withStep = nextFibers[selectedFiberId];
70
+ if (withStep?.step) {
71
+ effects.push({
72
+ kind: 'send',
73
+ fiberId: selectedFiberId,
74
+ to: withStep.actorId,
75
+ step: withStep.step,
76
+ });
77
+ }
78
+ return {
79
+ state: {
80
+ ...state,
81
+ fibers: nextFibers,
82
+ },
83
+ effects,
84
+ selectedFiberId,
85
+ };
86
+ }
@@ -0,0 +1,14 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.DEFAULT_ORCHESTRATOR_OPTIONS = void 0;
4
+ exports.DEFAULT_ORCHESTRATOR_OPTIONS = {
5
+ senderId: '__fiber_scheduler__',
6
+ agingStep: 1,
7
+ defaultSuspendPolicy: 'continue_others',
8
+ timeoutEnabled: false,
9
+ defaultTimeoutMs: 0,
10
+ retryEnabled: false,
11
+ retryDelayMs: 0,
12
+ retryBackoffMultiplier: 1,
13
+ deadLetterEnabled: false,
14
+ };
@@ -0,0 +1,3 @@
1
+ {
2
+ "type": "commonjs"
3
+ }
@@ -0,0 +1,34 @@
1
+ "use strict";
2
+ /**
3
+ * depa-actor — ActorPipeline
4
+ *
5
+ * Adapts the DOP 6-step pipeline (from depa-processor) to actor context.
6
+ *
7
+ * Mapping:
8
+ * OuterRuntime = ActorSelf
9
+ * OuterInput = envelope payload
10
+ * OuterConfig = actor state
11
+ *
12
+ * createPipelineHandler() wraps a pipeline definition into an ActorHandler.
13
+ */
14
+ Object.defineProperty(exports, "__esModule", { value: true });
15
+ exports.createPipelineHandler = createPipelineHandler;
16
+ // ─── createPipelineHandler ───────────────────────────────────────────
17
+ function createPipelineHandler(pipeline) {
18
+ return async (self, envelope) => {
19
+ const payload = envelope.payload;
20
+ const state = self.state;
21
+ // Step 1: Compute derived
22
+ const derived = pipeline.computeDerived(self, payload, state);
23
+ // Step 2: Transform runtime
24
+ const innerRuntime = pipeline.innerRuntime(self, payload, state, derived);
25
+ // Step 3: Transform input
26
+ const innerInput = pipeline.innerInput(self, payload, state, derived);
27
+ // Step 4: Transform config
28
+ const innerConfig = pipeline.innerConfig(self, payload, state, derived);
29
+ // Step 5: Core logic
30
+ const innerOutput = await pipeline.coreLogic(innerRuntime, innerInput, innerConfig);
31
+ // Step 6: Output (side effects on actor state / send messages)
32
+ await pipeline.output(self, payload, state, derived, innerOutput);
33
+ };
34
+ }
@@ -0,0 +1,77 @@
1
+ "use strict";
2
+ /**
3
+ * depa-actor — ActorRuntime
4
+ *
5
+ * Lifecycle and plugin layer over ActorSystem.
6
+ * ActorSystem = engine, ActorRuntime = managed environment.
7
+ *
8
+ * Future AiAgentVm will hold an ActorRuntime instance.
9
+ */
10
+ Object.defineProperty(exports, "__esModule", { value: true });
11
+ exports.ActorRuntime = void 0;
12
+ const ActorSystem_js_1 = require("../core/ActorSystem.cjs");
13
+ // ─── ActorRuntime ────────────────────────────────────────────────────
14
+ class ActorRuntime {
15
+ system;
16
+ plugins = [];
17
+ facets = new Map();
18
+ constructor(getRuntime, plugins) {
19
+ this.plugins = plugins ?? [];
20
+ this.system = new ActorSystem_js_1.ActorSystem(getRuntime, (entry) => this.handleLog(entry));
21
+ }
22
+ // ── Plugin management ──
23
+ addPlugin(plugin) {
24
+ this.plugins.push(plugin);
25
+ }
26
+ hasFacet(name) {
27
+ return this.facets.has(name);
28
+ }
29
+ getFacet(name) {
30
+ return this.facets.get(name);
31
+ }
32
+ setFacet(name, facet) {
33
+ this.facets.set(name, facet);
34
+ return facet;
35
+ }
36
+ ensureFacet(name, create) {
37
+ const existing = this.facets.get(name);
38
+ if (existing !== undefined) {
39
+ return existing;
40
+ }
41
+ const created = create();
42
+ this.facets.set(name, created);
43
+ return created;
44
+ }
45
+ // ── Delegated API (convenience) ──
46
+ register(id, def) {
47
+ this.system.register(id, def);
48
+ for (const p of this.plugins) {
49
+ p.onRegister?.(id, def);
50
+ }
51
+ }
52
+ unregister(id) {
53
+ this.system.unregister(id);
54
+ for (const p of this.plugins) {
55
+ p.onUnregister?.(id);
56
+ }
57
+ }
58
+ sendFrom(from, to, tag, payload) {
59
+ this.system.sendFrom(from, to, tag, payload);
60
+ }
61
+ refFrom(from, to) {
62
+ return this.system.refFrom(from, to);
63
+ }
64
+ ids() {
65
+ return this.system.ids();
66
+ }
67
+ has(id) {
68
+ return this.system.has(id);
69
+ }
70
+ // ── Internal ──
71
+ handleLog(entry) {
72
+ for (const p of this.plugins) {
73
+ p.onLog?.(entry);
74
+ }
75
+ }
76
+ }
77
+ exports.ActorRuntime = ActorRuntime;