@tomflow/proflow-platform-host 0.1.18 → 0.1.20
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/deployment/adapter.d.ts +10 -10
- package/dist/deployment/descriptor.d.ts +1 -1
- package/dist/deployment/descriptor.js +1 -1
- package/dist/src/index.d.ts +1 -0
- package/dist/src/index.js +78 -23
- package/package.json +8 -8
- package/proflow.module.json +1 -1
- package/CHANGELOG.md +0 -13
|
@@ -6,7 +6,7 @@ export declare const behaviorAdapter: {
|
|
|
6
6
|
ok: true;
|
|
7
7
|
status: "SUCCEEDED";
|
|
8
8
|
moduleRef: "platform-host";
|
|
9
|
-
moduleVersion: "0.1.
|
|
9
|
+
moduleVersion: "0.1.20";
|
|
10
10
|
data: {
|
|
11
11
|
endpoint: string;
|
|
12
12
|
stateRoot: string;
|
|
@@ -24,7 +24,7 @@ export declare const behaviorAdapter: {
|
|
|
24
24
|
readonly ok: true;
|
|
25
25
|
readonly status: "SUCCEEDED";
|
|
26
26
|
readonly moduleRef: "platform-host";
|
|
27
|
-
readonly moduleVersion: "0.1.
|
|
27
|
+
readonly moduleVersion: "0.1.20";
|
|
28
28
|
};
|
|
29
29
|
observedEffects: string[];
|
|
30
30
|
}>;
|
|
@@ -34,7 +34,7 @@ export declare const behaviorAdapter: {
|
|
|
34
34
|
ok: true;
|
|
35
35
|
status: "SUCCEEDED";
|
|
36
36
|
moduleRef: "platform-host";
|
|
37
|
-
moduleVersion: "0.1.
|
|
37
|
+
moduleVersion: "0.1.20";
|
|
38
38
|
data: {
|
|
39
39
|
setupStatus: "READY";
|
|
40
40
|
runtimeStatus: "RUNNING" | "STOPPED";
|
|
@@ -55,7 +55,7 @@ export declare const behaviorAdapter: {
|
|
|
55
55
|
ok: true;
|
|
56
56
|
status: "SUCCEEDED";
|
|
57
57
|
moduleRef: "platform-host";
|
|
58
|
-
moduleVersion: "0.1.
|
|
58
|
+
moduleVersion: "0.1.20";
|
|
59
59
|
data: {
|
|
60
60
|
endpoint: string;
|
|
61
61
|
stateRoot: string;
|
|
@@ -73,7 +73,7 @@ export declare const behaviorAdapter: {
|
|
|
73
73
|
ok: true;
|
|
74
74
|
status: "SUCCEEDED";
|
|
75
75
|
moduleRef: "platform-host";
|
|
76
|
-
moduleVersion: "0.1.
|
|
76
|
+
moduleVersion: "0.1.20";
|
|
77
77
|
data: {
|
|
78
78
|
docs: string;
|
|
79
79
|
};
|
|
@@ -86,7 +86,7 @@ export declare const behaviorAdapter: {
|
|
|
86
86
|
ok: true;
|
|
87
87
|
status: "SUCCEEDED";
|
|
88
88
|
moduleRef: "platform-host";
|
|
89
|
-
moduleVersion: "0.1.
|
|
89
|
+
moduleVersion: "0.1.20";
|
|
90
90
|
data: {
|
|
91
91
|
host: string;
|
|
92
92
|
port: number;
|
|
@@ -97,7 +97,7 @@ export declare const behaviorAdapter: {
|
|
|
97
97
|
result: {
|
|
98
98
|
contract: "deployment.result.v1";
|
|
99
99
|
moduleRef: "platform-host";
|
|
100
|
-
moduleVersion: "0.1.
|
|
100
|
+
moduleVersion: "0.1.20";
|
|
101
101
|
ok: false;
|
|
102
102
|
status: "FAILED";
|
|
103
103
|
error: {
|
|
@@ -114,7 +114,7 @@ export declare const behaviorAdapter: {
|
|
|
114
114
|
readonly ok: true;
|
|
115
115
|
readonly status: "SUCCEEDED";
|
|
116
116
|
readonly moduleRef: "platform-host";
|
|
117
|
-
readonly moduleVersion: "0.1.
|
|
117
|
+
readonly moduleVersion: "0.1.20";
|
|
118
118
|
};
|
|
119
119
|
observedEffects: string[];
|
|
120
120
|
} | {
|
|
@@ -123,11 +123,11 @@ export declare const behaviorAdapter: {
|
|
|
123
123
|
readonly ok: true;
|
|
124
124
|
readonly status: "SUCCEEDED";
|
|
125
125
|
readonly moduleRef: "platform-host";
|
|
126
|
-
readonly moduleVersion: "0.1.
|
|
126
|
+
readonly moduleVersion: "0.1.20";
|
|
127
127
|
} | {
|
|
128
128
|
contract: "deployment.result.v1";
|
|
129
129
|
moduleRef: "platform-host";
|
|
130
|
-
moduleVersion: "0.1.
|
|
130
|
+
moduleVersion: "0.1.20";
|
|
131
131
|
ok: false;
|
|
132
132
|
status: "FAILED";
|
|
133
133
|
error: {
|
|
@@ -3,7 +3,7 @@ export declare const descriptor: {
|
|
|
3
3
|
readonly contractVersion: "1.0.0";
|
|
4
4
|
readonly moduleRef: "platform-host";
|
|
5
5
|
readonly packageName: "@tomflow/proflow-platform-host";
|
|
6
|
-
readonly moduleVersion: "0.1.
|
|
6
|
+
readonly moduleVersion: "0.1.20";
|
|
7
7
|
readonly kind: "service";
|
|
8
8
|
readonly templateVersion: "1.0.0";
|
|
9
9
|
readonly platformCompatibility: ">=1.0.0 <2.0.0";
|
|
@@ -3,7 +3,7 @@ export const descriptor = {
|
|
|
3
3
|
contractVersion: "1.0.0",
|
|
4
4
|
moduleRef: "platform-host",
|
|
5
5
|
packageName: "@tomflow/proflow-platform-host",
|
|
6
|
-
moduleVersion: "0.1.
|
|
6
|
+
moduleVersion: "0.1.20",
|
|
7
7
|
kind: "service",
|
|
8
8
|
templateVersion: "1.0.0",
|
|
9
9
|
platformCompatibility: ">=1.0.0 <2.0.0",
|
package/dist/src/index.d.ts
CHANGED
package/dist/src/index.js
CHANGED
|
@@ -4,6 +4,7 @@ import { appendFile, chmod, mkdir, readFile, stat, writeFile, } from "node:fs/pr
|
|
|
4
4
|
import { createServer } from "node:http";
|
|
5
5
|
import { basename, dirname, isAbsolute, join, resolve } from "node:path";
|
|
6
6
|
import { createAgentRuntime } from "@tomflow/proflow-agent-runtime";
|
|
7
|
+
import { executionCapabilityIds, } from "@tomflow/proflow-execution-contracts";
|
|
7
8
|
import { applyMigrations } from "@tomflow/proflow-task-migration-runner";
|
|
8
9
|
import { createTaskServices, publicOperationNames, } from "@tomflow/proflow-task-orchestration";
|
|
9
10
|
import { SqliteTaskStore } from "@tomflow/proflow-task-store-sqlite";
|
|
@@ -324,6 +325,11 @@ function string(value, name) {
|
|
|
324
325
|
throw new TypeError(`${name} must be a non-empty string`);
|
|
325
326
|
return value;
|
|
326
327
|
}
|
|
328
|
+
function positiveInteger(value, name) {
|
|
329
|
+
if (!Number.isInteger(value) || Number(value) <= 0)
|
|
330
|
+
throw new TypeError(`${name} must be a positive integer`);
|
|
331
|
+
return Number(value);
|
|
332
|
+
}
|
|
327
333
|
function unwrap(result) {
|
|
328
334
|
if (!result.ok || result.data === undefined)
|
|
329
335
|
throw new Error(`OWNER_CONTRACT_FAILED:${JSON.stringify(result.error)}`);
|
|
@@ -628,6 +634,37 @@ async function constructGraph(config, executionCredential, modelCredential) {
|
|
|
628
634
|
}
|
|
629
635
|
return rawRecord;
|
|
630
636
|
};
|
|
637
|
+
const admissionError = (code, httpStatus = 403) => {
|
|
638
|
+
throw Object.assign(new Error(code), { httpStatus });
|
|
639
|
+
};
|
|
640
|
+
const admitExactNodeExecution = async (input, authenticatedRoleRef) => {
|
|
641
|
+
const taskId = string(input.taskId, "taskId");
|
|
642
|
+
const nodeId = string(input.nodeId, "nodeId");
|
|
643
|
+
const runNo = positiveInteger(input.runNo, "runNo");
|
|
644
|
+
const workerRef = await admitTaskParticipant(taskId, authenticatedRoleRef);
|
|
645
|
+
await agent.validateWorker({ authenticatedRoleRef, taskId, workerRef });
|
|
646
|
+
const taskFact = taskFacts(taskId);
|
|
647
|
+
const nodeContext = unwrap(task.queries.getNodeContext({ taskId, nodeId }));
|
|
648
|
+
if (taskFact.status !== "ACTIVE")
|
|
649
|
+
admissionError("EXECUTION_TASK_NOT_ACTIVE");
|
|
650
|
+
if (taskFact.currentNodeId !== nodeId)
|
|
651
|
+
admissionError("EXECUTION_NODE_NOT_CURRENT");
|
|
652
|
+
if (nodeContext.node.status !== "IN_PROGRESS")
|
|
653
|
+
admissionError("EXECUTION_NODE_NOT_RUNNING");
|
|
654
|
+
if (nodeContext.node.runNo !== runNo)
|
|
655
|
+
admissionError("EXECUTION_GENERATION_MISMATCH");
|
|
656
|
+
const nodeBinding = taskFact.roleBindings.find((binding) => binding.agentPackageRef === nodeContext.node.requiredAgentPackageRef);
|
|
657
|
+
if (!nodeBinding)
|
|
658
|
+
throw Object.assign(new Error("TASK_ROLE_BINDING_REQUIRED"), {
|
|
659
|
+
httpStatus: 403,
|
|
660
|
+
});
|
|
661
|
+
if (nodeBinding.roleRef !== authenticatedRoleRef)
|
|
662
|
+
admissionError("EXECUTION_ROLE_SCOPE_MISMATCH");
|
|
663
|
+
if (nodeBinding.workerRef !== workerRef ||
|
|
664
|
+
nodeContext.node.workerRef !== workerRef)
|
|
665
|
+
admissionError("EXECUTION_WORKER_SCOPE_MISMATCH");
|
|
666
|
+
return { taskId, nodeId, runNo, workerRef };
|
|
667
|
+
};
|
|
631
668
|
const route = async (operationId, authenticatedRoleRef, rawInput, context) => {
|
|
632
669
|
const role = agent.getRegisteredRole(authenticatedRoleRef);
|
|
633
670
|
if (!roleOperations[role.agentPackageRef]?.has(operationId))
|
|
@@ -687,26 +724,26 @@ async function constructGraph(config, executionCredential, modelCredential) {
|
|
|
687
724
|
: { ...canonicalTaskInput, actorRef });
|
|
688
725
|
if (operationId === "getTaskDocument")
|
|
689
726
|
return fileBridgeOutputForTaskResult(taskResult);
|
|
727
|
+
if (operationId === "getNodeContext" &&
|
|
728
|
+
roleOperations[role.agentPackageRef]?.has("executeCapability")) {
|
|
729
|
+
return {
|
|
730
|
+
...object(taskResult, "node context"),
|
|
731
|
+
executionCapabilityIds: [...executionCapabilityIds],
|
|
732
|
+
};
|
|
733
|
+
}
|
|
690
734
|
return taskResult;
|
|
691
735
|
}
|
|
692
736
|
if (operationId === "executeCapability") {
|
|
693
|
-
const
|
|
694
|
-
|
|
695
|
-
if (taskId) {
|
|
696
|
-
canonicalWorkerRef = await admitTaskParticipant(taskId, authenticatedRoleRef, typeof input.workerRef === "string" ? input.workerRef : undefined);
|
|
697
|
-
await agent.validateWorker({
|
|
698
|
-
authenticatedRoleRef,
|
|
699
|
-
taskId,
|
|
700
|
-
workerRef: canonicalWorkerRef,
|
|
701
|
-
});
|
|
702
|
-
}
|
|
737
|
+
const scope = await admitExactNodeExecution(input, authenticatedRoleRef);
|
|
738
|
+
const { workerRef: _suppliedWorkerRef, projectRoot: _suppliedProjectRoot, roleRef: _suppliedRoleRef, callerRef: _suppliedCallerRef, ...ownerInput } = input;
|
|
703
739
|
const result = await execution.invoke(operationId, {
|
|
704
|
-
...
|
|
740
|
+
...ownerInput,
|
|
705
741
|
callerRef: authenticatedRoleRef,
|
|
706
742
|
roleRef: authenticatedRoleRef,
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
743
|
+
taskId: scope.taskId,
|
|
744
|
+
nodeId: scope.nodeId,
|
|
745
|
+
runNo: scope.runNo,
|
|
746
|
+
workerRef: scope.workerRef,
|
|
710
747
|
});
|
|
711
748
|
// A normal Action may complete synchronously inside the current Worker Turn.
|
|
712
749
|
// Do not manufacture a Browser RESUME for every terminal Execution record.
|
|
@@ -858,14 +895,14 @@ async function constructGraph(config, executionCredential, modelCredential) {
|
|
|
858
895
|
return false;
|
|
859
896
|
if (request.runNo !== nodeContext.node.runNo)
|
|
860
897
|
return false;
|
|
861
|
-
if (!browserCapability &&
|
|
862
|
-
nodeContext.node.status !== "IN_PROGRESS")
|
|
898
|
+
if (!browserCapability && nodeContext.node.status !== "IN_PROGRESS")
|
|
863
899
|
return false;
|
|
864
900
|
const nodeBinding = taskFact.roleBindings.find((candidate) => candidate.agentPackageRef ===
|
|
865
901
|
nodeContext.node.requiredAgentPackageRef);
|
|
866
902
|
if (!nodeBinding?.workerRef)
|
|
867
903
|
return false;
|
|
868
|
-
const scopedRoleRef = request.roleRef ??
|
|
904
|
+
const scopedRoleRef = request.roleRef ??
|
|
905
|
+
(internalBrowserCaller ? undefined : request.callerRef);
|
|
869
906
|
if (scopedRoleRef !== nodeBinding.roleRef)
|
|
870
907
|
return false;
|
|
871
908
|
if (request.workerRef !== nodeBinding.workerRef)
|
|
@@ -903,6 +940,7 @@ async function constructGraph(config, executionCredential, modelCredential) {
|
|
|
903
940
|
const resumeWake = nodeContext.node.status === "IN_PROGRESS" &&
|
|
904
941
|
(trigger === "RECOVERY_RESUME" ||
|
|
905
942
|
trigger === "EXECUTION_RESULT_READY" ||
|
|
943
|
+
trigger === "TASK_RESUMED" ||
|
|
906
944
|
trigger === "PEER_REPLY_READY");
|
|
907
945
|
if (!readyWake && !resumeWake)
|
|
908
946
|
return false;
|
|
@@ -1157,6 +1195,22 @@ async function constructGraph(config, executionCredential, modelCredential) {
|
|
|
1157
1195
|
actorRef: "extension:human",
|
|
1158
1196
|
idempotencyKey: string(value.idempotencyKey, "idempotencyKey"),
|
|
1159
1197
|
}));
|
|
1198
|
+
if (operation === "message.acknowledge")
|
|
1199
|
+
return unwrap(task.commands.acknowledgeMessage({
|
|
1200
|
+
messageId: string(value.messageId, "messageId"),
|
|
1201
|
+
...(typeof value.resolution === "string"
|
|
1202
|
+
? { resolution: value.resolution }
|
|
1203
|
+
: {}),
|
|
1204
|
+
actorRef: "extension:human",
|
|
1205
|
+
idempotencyKey: string(value.idempotencyKey, "idempotencyKey"),
|
|
1206
|
+
}));
|
|
1207
|
+
if (operation === "task.resume")
|
|
1208
|
+
return unwrap(task.commands.resumeTask({
|
|
1209
|
+
taskId: string(value.taskId, "taskId"),
|
|
1210
|
+
expectedTaskVersion: positiveInteger(value.expectedTaskVersion, "expectedTaskVersion"),
|
|
1211
|
+
actorRef: "extension:human",
|
|
1212
|
+
idempotencyKey: string(value.idempotencyKey, "idempotencyKey"),
|
|
1213
|
+
}));
|
|
1160
1214
|
if (operation === "node.reopen")
|
|
1161
1215
|
return unwrap(task.commands.reopenNode({
|
|
1162
1216
|
taskId: string(value.taskId, "taskId"),
|
|
@@ -1458,15 +1512,16 @@ async function constructGraph(config, executionCredential, modelCredential) {
|
|
|
1458
1512
|
});
|
|
1459
1513
|
return admitExecutionRead(authenticatedRoleRef, record);
|
|
1460
1514
|
}
|
|
1461
|
-
const
|
|
1462
|
-
|
|
1463
|
-
if (taskId)
|
|
1464
|
-
canonicalWorkerRef = await admitTaskParticipant(taskId, authenticatedRoleRef, typeof value.workerRef === "string" ? value.workerRef : undefined);
|
|
1515
|
+
const scope = await admitExactNodeExecution(value, authenticatedRoleRef);
|
|
1516
|
+
const { workerRef: _suppliedWorkerRef, projectRoot: _suppliedProjectRoot, roleRef: _suppliedRoleRef, callerRef: _suppliedCallerRef, ...ownerInput } = value;
|
|
1465
1517
|
const record = await execution.invoke("lookupExecutionIntent", {
|
|
1466
|
-
...
|
|
1518
|
+
...ownerInput,
|
|
1467
1519
|
callerRef: authenticatedRoleRef,
|
|
1468
1520
|
roleRef: authenticatedRoleRef,
|
|
1469
|
-
|
|
1521
|
+
taskId: scope.taskId,
|
|
1522
|
+
nodeId: scope.nodeId,
|
|
1523
|
+
runNo: scope.runNo,
|
|
1524
|
+
workerRef: scope.workerRef,
|
|
1470
1525
|
});
|
|
1471
1526
|
return admitExecutionRead(authenticatedRoleRef, record);
|
|
1472
1527
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tomflow/proflow-platform-host",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.20",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"publishConfig": {
|
|
6
6
|
"access": "public"
|
|
@@ -24,19 +24,19 @@
|
|
|
24
24
|
],
|
|
25
25
|
"dependencies": {
|
|
26
26
|
"zod": "4.1.12",
|
|
27
|
-
"@tomflow/proflow-agent-runtime": "^0.1.13",
|
|
28
|
-
"@tomflow/proflow-execution-browser-extension": "^0.1.42",
|
|
29
27
|
"@tomflow/proflow-execution-contracts": "^0.1.10",
|
|
28
|
+
"@tomflow/proflow-task-store-sqlite": "^0.1.11",
|
|
29
|
+
"@tomflow/proflow-execution-browser-extension": "^0.1.50",
|
|
30
|
+
"@tomflow/proflow-task-orchestration": "^0.1.11",
|
|
30
31
|
"@tomflow/proflow-module-contract": "^0.1.13",
|
|
31
32
|
"@tomflow/proflow-task-migration-runner": "^0.1.11",
|
|
32
|
-
"@tomflow/proflow-
|
|
33
|
-
"@tomflow/proflow-task-orchestration": "^0.1.10"
|
|
33
|
+
"@tomflow/proflow-agent-runtime": "^0.1.14"
|
|
34
34
|
},
|
|
35
35
|
"devDependencies": {
|
|
36
|
-
"@tomflow/proflow-agent-gateway": "^0.1.
|
|
37
|
-
"@tomflow/proflow-
|
|
36
|
+
"@tomflow/proflow-agent-gateway": "^0.1.16",
|
|
37
|
+
"@tomflow/proflow-model-runtime": "^0.1.24",
|
|
38
38
|
"@tomflow/proflow-execution-runtime": "^0.1.18",
|
|
39
|
-
"@tomflow/proflow-
|
|
39
|
+
"@tomflow/proflow-deployment-conformance": "^0.1.13"
|
|
40
40
|
},
|
|
41
41
|
"description": "Provides the ProFlow local application composition root that binds Task, Agent, Execution and Model owner transports.",
|
|
42
42
|
"keywords": [
|
package/proflow.module.json
CHANGED
package/CHANGELOG.md
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
# @tomflow/proflow-platform-host
|
|
2
|
-
|
|
3
|
-
## 0.1.18
|
|
4
|
-
|
|
5
|
-
### Patch Changes
|
|
6
|
-
|
|
7
|
-
- Close Real-3 node generation identity fencing across Platform Host admission, durable Execution idempotency, and Observer/Approval resume provenance.
|
|
8
|
-
|
|
9
|
-
## 0.1.17
|
|
10
|
-
|
|
11
|
-
### Patch Changes
|
|
12
|
-
|
|
13
|
-
- Harden Real-3 Browser Carrier reality: controlled ChatGPT composer submission, authoritative action-permission classification, bounded binding-race deferral, Carrier Attention web relay and restart recovery, and human-deny precedence across automatic recovery.
|