owlrunkit 0.21.0 → 0.22.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 (26) hide show
  1. package/CHANGELOG.md +40 -0
  2. package/README.md +50 -11
  3. package/integrations/codex/skills/owlcoda-runkit/SKILL.md +39 -14
  4. package/integrations/codex/skills/owlcoda-runkit/assets/templates/config.json +3 -3
  5. package/package.json +1 -1
  6. package/packages/attest/distribution-manifest-v1.json +10 -0
  7. package/packages/attest/src/quick.mjs +10 -0
  8. package/registry-release-policy-v2.json +5 -5
  9. package/sbom.spdx.json +4 -4
  10. package/scripts/runkit-contract/core-contract.mjs +6 -1
  11. package/scripts/runkit-contract/formal-workflow.mjs +1 -1
  12. package/scripts/runkit-contract/hook-recovery.mjs +496 -0
  13. package/scripts/runkit-contract/inspect-presentation.mjs +131 -0
  14. package/scripts/runkit-contract/onboarding-doctor.mjs +179 -4
  15. package/scripts/runkit-contract/project-cli-resolver.mjs +8 -0
  16. package/scripts/runkit-contract/registry-adoption.mjs +4 -4
  17. package/scripts/runkit-contract/runkit-bootstrap.mjs +1 -0
  18. package/scripts/runkit-contract/runkit-cli.mjs +62 -30
  19. package/scripts/runkit-contract/schemas/fleet-skill-upgrade-plan-v1.schema.json +1 -1
  20. package/scripts/runkit-contract/schemas/hook-recovery-v1.schema.json +592 -0
  21. package/scripts/runkit-contract/schemas/inspect-compact-v2.schema.json +122 -0
  22. package/scripts/runkit-contract/schemas/team-delivery-status-v3.schema.json +113 -0
  23. package/scripts/runkit-contract/schemas/team-recommendation-v2.schema.json +120 -0
  24. package/scripts/runkit-contract/sync-release-identity.mjs +1 -1
  25. package/scripts/runkit-contract/team-delivery.mjs +75 -0
  26. package/scripts/runkit-contract/team-project.mjs +62 -2
@@ -0,0 +1,113 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://owlcoda.com/schemas/runkit/team-delivery-status-v3.schema.json",
4
+ "title": "OwlCoda RunKit Team Delivery Status V3",
5
+ "type": "object",
6
+ "additionalProperties": false,
7
+ "required": [
8
+ "schemaVersion", "status", "graphSource", "persistedTeamGraph", "projectId",
9
+ "projectTruthHash", "projectOverall", "recommendation", "lanes", "pathConflicts",
10
+ "acceptanceGaps", "ownerTransitions", "externalGates", "deliveryLifecycle",
11
+ "unmodeledCandidateLanes", "warnings", "warningSummary", "advisorySummary",
12
+ "nextAction", "dispatch", "authorityBoundary", "authorizationGranted", "exitCode"
13
+ ],
14
+ "properties": {
15
+ "schemaVersion": { "const": "OwlCodaRunKitTeamDeliveryStatusV3" },
16
+ "status": { "const": "team_delivery_status" },
17
+ "graphSource": { "const": "project_driver" },
18
+ "persistedTeamGraph": { "const": false },
19
+ "projectId": { "$ref": "#/$defs/nullableText" },
20
+ "projectTruthHash": { "oneOf": [{ "type": "null" }, { "type": "string", "pattern": "^[a-f0-9]{64}$" }] },
21
+ "projectOverall": { "$ref": "#/$defs/text" },
22
+ "recommendation": {
23
+ "type": "object", "additionalProperties": false,
24
+ "required": ["teamCoordinationMode", "coordination", "reasonCodes"],
25
+ "properties": {
26
+ "teamCoordinationMode": { "enum": ["off", "team"] },
27
+ "coordination": { "enum": ["none", "project_driver_team"] },
28
+ "reasonCodes": { "$ref": "#/$defs/strings" }
29
+ }
30
+ },
31
+ "lanes": { "type": "array", "items": { "$ref": "team-delivery-status-v2.schema.json#/$defs/lane" } },
32
+ "pathConflicts": { "type": "array", "items": { "$ref": "team-delivery-status-v2.schema.json#/$defs/pathConflict" } },
33
+ "acceptanceGaps": { "type": "array", "items": { "$ref": "team-delivery-status-v2.schema.json#/$defs/acceptanceGap" } },
34
+ "ownerTransitions": { "type": "array", "items": { "$ref": "team-delivery-status-v2.schema.json#/$defs/ownerTransition" } },
35
+ "externalGates": { "type": "array", "items": { "$ref": "team-delivery-status-v2.schema.json#/$defs/externalGate" } },
36
+ "deliveryLifecycle": { "oneOf": [{ "type": "null" }, { "$ref": "team-delivery-status-v2.schema.json#/$defs/deliveryLifecycle" }] },
37
+ "unmodeledCandidateLanes": { "type": "array", "items": { "$ref": "team-delivery-status-v2.schema.json#/$defs/candidateLane" } },
38
+ "warnings": { "type": "array", "items": { "$ref": "#/$defs/advisory" } },
39
+ "warningSummary": { "$ref": "#/$defs/emptySummary" },
40
+ "advisorySummary": { "$ref": "#/$defs/advisorySummary" },
41
+ "nextAction": { "$ref": "#/$defs/nullableText" },
42
+ "dispatch": { "$ref": "team-delivery-status-v2.schema.json#/$defs/dispatch" },
43
+ "authorityBoundary": { "$ref": "team-delivery-status-v2.schema.json#/$defs/authorityBoundary" },
44
+ "authorizationGranted": { "const": false },
45
+ "exitCode": { "const": 0 }
46
+ },
47
+ "$defs": {
48
+ "text": { "type": "string", "minLength": 1 },
49
+ "nullableText": { "oneOf": [{ "type": "null" }, { "$ref": "#/$defs/text" }] },
50
+ "strings": { "type": "array", "uniqueItems": true, "items": { "$ref": "#/$defs/text" } },
51
+ "nonemptyStrings": { "type": "array", "minItems": 1, "uniqueItems": true, "items": { "$ref": "#/$defs/text" } },
52
+ "advisory": {
53
+ "type": "object", "additionalProperties": false,
54
+ "required": ["code", "workItemId", "message", "truthRefs", "severity", "blocking", "requiredAtGate", "recommendedAction"],
55
+ "properties": {
56
+ "code": { "const": "no_bound_verification_receipt" },
57
+ "workItemId": { "$ref": "#/$defs/text" },
58
+ "message": { "$ref": "#/$defs/text" },
59
+ "truthRefs": { "$ref": "#/$defs/nonemptyStrings" },
60
+ "severity": { "const": "advisory" },
61
+ "blocking": { "const": false },
62
+ "requiredAtGate": { "const": false },
63
+ "recommendedAction": { "enum": ["no_retroactive_action_required", "bind_quick_or_formal_receipt_if_reusable_evidence_is_required"] }
64
+ }
65
+ },
66
+ "advisoryGroup": {
67
+ "type": "object", "additionalProperties": false,
68
+ "required": ["code", "severity", "blocking", "count", "workItemIds", "requiredAtGate", "recommendedAction"],
69
+ "properties": {
70
+ "code": { "const": "no_bound_verification_receipt" },
71
+ "severity": { "const": "advisory" },
72
+ "blocking": { "const": false },
73
+ "count": { "type": "integer", "minimum": 1 },
74
+ "workItemIds": { "$ref": "#/$defs/nonemptyStrings" },
75
+ "requiredAtGate": { "const": false },
76
+ "recommendedAction": { "enum": ["no_retroactive_action_required", "bind_quick_or_formal_receipt_if_reusable_evidence_is_required", "review_individual_warning_actions"] }
77
+ }
78
+ },
79
+ "emptySummary": {
80
+ "type": "object", "additionalProperties": false,
81
+ "required": ["count", "groups"],
82
+ "properties": {
83
+ "count": { "const": 0 },
84
+ "groups": { "type": "array", "maxItems": 0 }
85
+ }
86
+ },
87
+ "advisorySummary": {
88
+ "type": "object", "additionalProperties": false,
89
+ "required": ["count", "groups"],
90
+ "properties": {
91
+ "count": { "type": "integer", "minimum": 0 },
92
+ "groups": { "type": "array", "items": { "$ref": "#/$defs/advisoryGroup" } }
93
+ }
94
+ }
95
+ },
96
+ "examples": [{
97
+ "schemaVersion": "OwlCodaRunKitTeamDeliveryStatusV3",
98
+ "status": "team_delivery_status",
99
+ "graphSource": "project_driver",
100
+ "persistedTeamGraph": false,
101
+ "projectId": null,
102
+ "projectTruthHash": null,
103
+ "projectOverall": "not_initialized",
104
+ "recommendation": { "teamCoordinationMode": "off", "coordination": "none", "reasonCodes": ["project_driver_not_initialized"] },
105
+ "lanes": [], "pathConflicts": [], "acceptanceGaps": [], "ownerTransitions": [],
106
+ "externalGates": [], "deliveryLifecycle": null, "unmodeledCandidateLanes": [],
107
+ "warnings": [], "warningSummary": { "count": 0, "groups": [] },
108
+ "advisorySummary": { "count": 0, "groups": [] }, "nextAction": null,
109
+ "dispatch": { "mode": "none", "permitted": false, "nextCommand": null },
110
+ "authorityBoundary": { "agentDispatch": false, "git": false, "release": false, "deployment": false, "production": false, "business": false, "automation": false, "money": false },
111
+ "authorizationGranted": false, "exitCode": 0
112
+ }]
113
+ }
@@ -0,0 +1,120 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://owlcoda.com/schemas/runkit/team-recommendation-v2.schema.json",
4
+ "title": "OwlCoda RunKit Team Recommendation V2",
5
+ "type": "object",
6
+ "additionalProperties": false,
7
+ "required": [
8
+ "schemaVersion", "status", "project", "continuity", "coordination",
9
+ "assurance", "reasonCodes", "rejectedLighterModes", "lanes",
10
+ "pathConflicts", "acceptanceGaps", "ownerTransitions", "estimatedOverhead",
11
+ "nextCommand", "dispatch", "authorityBoundary", "authorizationGranted",
12
+ "exitCode", "teamCoordinationMode"
13
+ ],
14
+ "properties": {
15
+ "schemaVersion": { "const": "OwlCodaRunKitTeamRecommendationV2" },
16
+ "status": { "const": "team_delivery_recommended" },
17
+ "project": {
18
+ "type": "object", "additionalProperties": false,
19
+ "required": ["present", "projectId", "projectTruthHash", "overall"],
20
+ "properties": {
21
+ "present": { "type": "boolean" },
22
+ "projectId": { "$ref": "#/$defs/nullableText" },
23
+ "projectTruthHash": { "oneOf": [{ "type": "null" }, { "type": "string", "pattern": "^[a-f0-9]{64}$" }] },
24
+ "overall": { "$ref": "#/$defs/nullableText" }
25
+ }
26
+ },
27
+ "teamCoordinationMode": { "enum": ["off", "team"] },
28
+ "continuity": { "enum": ["none", "project_driver"] },
29
+ "coordination": { "enum": ["none", "project_driver_team"] },
30
+ "assurance": {
31
+ "type": "object", "additionalProperties": false,
32
+ "required": ["changed", "selection", "reason"],
33
+ "properties": {
34
+ "changed": { "const": false },
35
+ "selection": { "const": "unchanged" },
36
+ "reason": { "const": "team_delivery_does_not_select_assurance" }
37
+ }
38
+ },
39
+ "reasonCodes": { "$ref": "#/$defs/strings" },
40
+ "rejectedLighterModes": {
41
+ "type": "array",
42
+ "items": {
43
+ "type": "object", "additionalProperties": false,
44
+ "required": ["mode", "reasonCodes"],
45
+ "properties": { "mode": { "const": "off" }, "reasonCodes": { "$ref": "#/$defs/nonemptyStrings" } }
46
+ }
47
+ },
48
+ "lanes": { "type": "array", "items": { "$ref": "#/$defs/lane" } },
49
+ "pathConflicts": { "type": "array", "items": { "$ref": "#/$defs/pathConflict" } },
50
+ "acceptanceGaps": { "type": "array", "items": { "$ref": "#/$defs/acceptanceGap" } },
51
+ "ownerTransitions": { "type": "array", "items": { "$ref": "#/$defs/ownerTransition" } },
52
+ "estimatedOverhead": {
53
+ "type": "object", "additionalProperties": false,
54
+ "required": ["additionalOperatorSteps", "potentialPortablePackets"],
55
+ "properties": {
56
+ "additionalOperatorSteps": { "type": "integer", "minimum": 0 },
57
+ "potentialPortablePackets": { "type": "integer", "minimum": 0 }
58
+ }
59
+ },
60
+ "nextCommand": { "$ref": "#/$defs/nullableText" },
61
+ "dispatch": { "$ref": "#/$defs/dispatch" },
62
+ "authorityBoundary": { "$ref": "#/$defs/authorityBoundary" },
63
+ "authorizationGranted": { "const": false },
64
+ "exitCode": { "const": 0 }
65
+ },
66
+ "$defs": {
67
+ "text": { "type": "string", "minLength": 1 },
68
+ "nullableText": { "oneOf": [{ "type": "null" }, { "$ref": "#/$defs/text" }] },
69
+ "strings": { "type": "array", "uniqueItems": true, "items": { "$ref": "#/$defs/text" } },
70
+ "nonemptyStrings": { "type": "array", "minItems": 1, "uniqueItems": true, "items": { "$ref": "#/$defs/text" } },
71
+ "lane": {
72
+ "type": "object", "additionalProperties": false,
73
+ "required": ["workItemId", "title", "status", "agentId", "dependencies", "unresolvedDependencies", "ownedPaths", "actionable", "parallelEligible", "coordinationFacts"],
74
+ "properties": {
75
+ "workItemId": { "$ref": "#/$defs/text" }, "title": { "$ref": "#/$defs/text" },
76
+ "status": { "$ref": "#/$defs/text" }, "agentId": { "$ref": "#/$defs/nullableText" },
77
+ "dependencies": { "$ref": "#/$defs/strings" }, "unresolvedDependencies": { "$ref": "#/$defs/strings" },
78
+ "ownedPaths": { "$ref": "#/$defs/nonemptyStrings" }, "actionable": { "type": "boolean" },
79
+ "parallelEligible": { "type": "boolean" }, "coordinationFacts": { "$ref": "#/$defs/strings" }
80
+ }
81
+ },
82
+ "pathConflict": {
83
+ "type": "object", "additionalProperties": false,
84
+ "required": ["leftWorkItemId", "leftPath", "rightWorkItemId", "rightPath"],
85
+ "properties": { "leftWorkItemId": { "$ref": "#/$defs/text" }, "leftPath": { "$ref": "#/$defs/text" }, "rightWorkItemId": { "$ref": "#/$defs/text" }, "rightPath": { "$ref": "#/$defs/text" } }
86
+ },
87
+ "acceptanceGap": {
88
+ "type": "object", "additionalProperties": false,
89
+ "required": ["workItemId", "code", "message"],
90
+ "properties": { "workItemId": { "$ref": "#/$defs/text" }, "code": { "const": "verification_model_family_unbound" }, "message": { "$ref": "#/$defs/text" } }
91
+ },
92
+ "ownerTransition": {
93
+ "type": "object", "additionalProperties": false,
94
+ "required": ["workItemId", "facts"],
95
+ "properties": { "workItemId": { "$ref": "#/$defs/text" }, "facts": { "$ref": "#/$defs/nonemptyStrings" } }
96
+ },
97
+ "dispatch": {
98
+ "type": "object", "additionalProperties": false,
99
+ "required": ["mode", "permitted", "nextCommand"],
100
+ "properties": { "mode": { "const": "none" }, "permitted": { "const": false }, "nextCommand": { "type": "null" } }
101
+ },
102
+ "authorityBoundary": {
103
+ "type": "object", "additionalProperties": false,
104
+ "required": ["agentDispatch", "git", "release", "deployment", "production", "business", "automation", "money"],
105
+ "properties": { "agentDispatch": { "const": false }, "git": { "const": false }, "release": { "const": false }, "deployment": { "const": false }, "production": { "const": false }, "business": { "const": false }, "automation": { "const": false }, "money": { "const": false } }
106
+ }
107
+ },
108
+ "examples": [{
109
+ "schemaVersion": "OwlCodaRunKitTeamRecommendationV2", "status": "team_delivery_recommended",
110
+ "project": { "present": false, "projectId": null, "projectTruthHash": null, "overall": null },
111
+ "teamCoordinationMode": "off", "continuity": "none", "coordination": "none",
112
+ "assurance": { "changed": false, "selection": "unchanged", "reason": "team_delivery_does_not_select_assurance" },
113
+ "reasonCodes": ["project_driver_not_initialized"], "rejectedLighterModes": [], "lanes": [],
114
+ "pathConflicts": [], "acceptanceGaps": [], "ownerTransitions": [],
115
+ "estimatedOverhead": { "additionalOperatorSteps": 0, "potentialPortablePackets": 0 },
116
+ "nextCommand": null, "dispatch": { "mode": "none", "permitted": false, "nextCommand": null },
117
+ "authorityBoundary": { "agentDispatch": false, "git": false, "release": false, "deployment": false, "production": false, "business": false, "automation": false, "money": false },
118
+ "authorizationGranted": false, "exitCode": 0
119
+ }]
120
+ }
@@ -252,7 +252,7 @@ export function verifyReleaseIdentitySurfacesV1(input) {
252
252
  if (registryGatedArtifact) {
253
253
  const rollback = releasePolicy.rollbackRelease.version;
254
254
  return markdown.includes(
255
- `Bundled release artifact: standalone \`owlrunkit@${core.coreVersion}\``,
255
+ `Bundled registry-gated artifact: standalone \`owlrunkit@${core.coreVersion}\``,
256
256
  )
257
257
  && markdown.includes(
258
258
  `provenance for \`owlrunkit@${core.coreVersion}\` is independently verified`,
@@ -678,6 +678,16 @@ export function recommendTeamDeliveryV1({ workspaceRoot } = {}) {
678
678
  return recommendationFromProject(currentProjectStatus(workspaceRoot), workspaceRoot);
679
679
  }
680
680
 
681
+ export function recommendTeamDeliveryV2(input = {}) {
682
+ const legacy = recommendTeamDeliveryV1(input);
683
+ const { recommendedMode, ...rest } = legacy;
684
+ return {
685
+ ...rest,
686
+ schemaVersion: "OwlCodaRunKitTeamRecommendationV2",
687
+ teamCoordinationMode: recommendedMode,
688
+ };
689
+ }
690
+
681
691
  function teamDeliveryStatusFromProject(project, workspaceRoot) {
682
692
  const recommendation = recommendationFromProject(project, workspaceRoot);
683
693
  return {
@@ -770,6 +780,29 @@ export function readTeamDeliveryStatusV2({ workspaceRoot } = {}) {
770
780
  };
771
781
  }
772
782
 
783
+ export function readTeamDeliveryStatusV3({ workspaceRoot } = {}) {
784
+ const legacy = readTeamDeliveryStatusV2({ workspaceRoot });
785
+ const warnings = legacy.warnings.map(warning => (
786
+ warning.code === "no_bound_verification_receipt"
787
+ ? { ...warning, severity: "advisory" }
788
+ : warning
789
+ ));
790
+ const actionableWarnings = warnings.filter(warning => warning.severity !== "advisory");
791
+ const advisories = warnings.filter(warning => warning.severity === "advisory");
792
+ return {
793
+ ...legacy,
794
+ schemaVersion: "OwlCodaRunKitTeamDeliveryStatusV3",
795
+ recommendation: {
796
+ teamCoordinationMode: legacy.recommendation.recommendedMode,
797
+ coordination: legacy.recommendation.coordination,
798
+ reasonCodes: [...legacy.recommendation.reasonCodes],
799
+ },
800
+ warnings,
801
+ warningSummary: aggregateWarningSummary(actionableWarnings),
802
+ advisorySummary: aggregateWarningSummary(advisories),
803
+ };
804
+ }
805
+
773
806
  function bindPacketToProject(packet, project, definition, issueCodes) {
774
807
  if (!projectBindingValid(packet.projectBinding)) return;
775
808
  if (project === null) {
@@ -975,6 +1008,22 @@ export function formatTeamDeliveryRecommendationHumanV1(result) {
975
1008
  ].join("\n");
976
1009
  }
977
1010
 
1011
+ export function formatTeamDeliveryRecommendationHumanV2(result) {
1012
+ return [
1013
+ `Team coordination: ${result.teamCoordinationMode}`,
1014
+ `Continuity: ${result.continuity}`,
1015
+ `Coordination: ${result.coordination}`,
1016
+ `Why: ${result.reasonCodes.join(", ") || "none"}`,
1017
+ `Lanes: ${result.lanes.length}`,
1018
+ `Path conflicts: ${result.pathConflicts.length}`,
1019
+ `Acceptance gaps: ${result.acceptanceGaps.length}`,
1020
+ `Next: ${result.nextCommand ?? "none"}`,
1021
+ "Agent dispatch: not permitted.",
1022
+ "Authority: no Git, release, deployment, production, business, automation, or money authorization granted.",
1023
+ "",
1024
+ ].join("\n");
1025
+ }
1026
+
978
1027
  export function formatTeamDeliveryStatusHumanV1(result) {
979
1028
  return [
980
1029
  `Team Delivery: ${result.recommendation.recommendedMode}`,
@@ -1018,6 +1067,32 @@ export function formatTeamDeliveryStatusHumanV2(result) {
1018
1067
  ].join("\n");
1019
1068
  }
1020
1069
 
1070
+ export function formatTeamDeliveryStatusHumanV3(result) {
1071
+ return [
1072
+ `Team coordination: ${result.recommendation.teamCoordinationMode}`,
1073
+ `Project: ${result.projectId ?? "not initialized"}`,
1074
+ `Project state: ${result.projectOverall}`,
1075
+ `Graph source: ${result.graphSource}`,
1076
+ `Persisted team graph: ${result.persistedTeamGraph ? "yes" : "no"}`,
1077
+ `Lanes: ${result.lanes.length}`,
1078
+ `Path conflicts: ${result.pathConflicts.length}`,
1079
+ `Acceptance gaps: ${result.acceptanceGaps.length}`,
1080
+ `External Gates: ${result.externalGates.length}`,
1081
+ `Unmodeled candidate lanes: ${result.unmodeledCandidateLanes.length}`,
1082
+ `Delivery: ${result.deliveryLifecycle?.currentStage ?? "not initialized"}`,
1083
+ ...(result.warningSummary.count > 0
1084
+ ? [`Warnings: ${result.warningSummary.count} (${result.warningSummary.groups.map(group => `${group.code}:${group.count}`).join(", ")})`]
1085
+ : []),
1086
+ ...(result.advisorySummary.count > 0
1087
+ ? [`Advisories: ${result.advisorySummary.count} (${result.advisorySummary.groups.map(group => `${group.code}:${group.count}`).join(", ")})`]
1088
+ : []),
1089
+ `Next: ${result.nextAction ?? "none"}`,
1090
+ "Agent dispatch: not permitted.",
1091
+ "Authority: not granted.",
1092
+ "",
1093
+ ].join("\n");
1094
+ }
1095
+
1021
1096
  export function formatTeamPacketValidationHumanV1(result) {
1022
1097
  return [
1023
1098
  `Team packet: ${result.status}`,
@@ -4475,6 +4475,36 @@ export function readTeamProjectStatusV4({ workspaceRoot }) {
4475
4475
  };
4476
4476
  }
4477
4477
 
4478
+ export function readTeamProjectHookSourceV1({ workspaceRoot }) {
4479
+ const loaded = loadProject(workspaceRoot);
4480
+ const normalizedRecords = loaded.events
4481
+ .map(({ event, ref }) => ({
4482
+ event: validateEventShape(event, loaded.definition),
4483
+ ref,
4484
+ }))
4485
+ .sort((left, right) => compareEventFacts(left.event, right.event));
4486
+ const rawProjectTruthHash = sha256(canonical({
4487
+ definition: loaded.definition,
4488
+ events: loaded.events.map(row => row.event),
4489
+ }));
4490
+ const normalizedStatus = projectStatus(
4491
+ loaded.definition,
4492
+ normalizedRecords,
4493
+ loaded.root,
4494
+ );
4495
+ const status = {
4496
+ ...statusV4DeliveryProjection({
4497
+ ...normalizedStatus,
4498
+ projectTruthHash: rawProjectTruthHash,
4499
+ }),
4500
+ exitCode: 0,
4501
+ };
4502
+ return {
4503
+ status,
4504
+ latestProjectFactAt: normalizedRecords.at(-1)?.event.occurredAt ?? null,
4505
+ };
4506
+ }
4507
+
4478
4508
  export function readTeamProjectHandoffWaitV1({ workspaceRoot }) {
4479
4509
  const { root, projectRoot: rootPath } = projectRoot(workspaceRoot);
4480
4510
  if (!existsSync(path.join(rootPath, "definition.json"))) {
@@ -4545,7 +4575,10 @@ export function readTeamProjectHandoffWaitV1({ workspaceRoot }) {
4545
4575
  };
4546
4576
  }
4547
4577
 
4548
- export function buildTeamProjectTakeoverV2({ workspaceRoot, agentId }) {
4578
+ function buildTeamProjectTakeover(
4579
+ { workspaceRoot, agentId },
4580
+ { includeTerminalFallback = true } = {},
4581
+ ) {
4549
4582
  safeIdentifier(agentId, "agentId");
4550
4583
  const loaded = loadProject(workspaceRoot);
4551
4584
  const status = projectStatus(loaded.definition, loaded.events, loaded.root);
@@ -4555,7 +4588,7 @@ export function buildTeamProjectTakeoverV2({ workspaceRoot, agentId }) {
4555
4588
  && row.pendingHandoff === null
4556
4589
  ))
4557
4590
  ?? responsibilities.find(row => !["completed", "failed"].includes(row.status))
4558
- ?? responsibilities.at(-1)
4591
+ ?? (includeTerminalFallback ? responsibilities.at(-1) : null)
4559
4592
  ?? null;
4560
4593
  const pendingForCurrent = current?.pendingHandoff ?? null;
4561
4594
  const pendingForAgent = status.workItems.find(row => (
@@ -4676,6 +4709,10 @@ export function buildTeamProjectTakeoverV2({ workspaceRoot, agentId }) {
4676
4709
  };
4677
4710
  }
4678
4711
 
4712
+ export function buildTeamProjectTakeoverV2(input) {
4713
+ return buildTeamProjectTakeover(input);
4714
+ }
4715
+
4679
4716
  export function buildTeamProjectTakeoverV1(input) {
4680
4717
  const {
4681
4718
  staleHandoffs: _staleHandoffs,
@@ -4720,6 +4757,29 @@ export function buildTeamProjectTakeoverV3(input) {
4720
4757
  };
4721
4758
  }
4722
4759
 
4760
+ export function buildTeamProjectTakeoverV4(input) {
4761
+ const legacy = buildTeamProjectTakeover(input, { includeTerminalFallback: false });
4762
+ const status = readTeamProjectStatusV3({ workspaceRoot: input.workspaceRoot });
4763
+ const byId = new Map(status.workItems.map(row => [row.workItemId, row]));
4764
+ return {
4765
+ ...legacy,
4766
+ schemaVersion: "OwlCodaRunKitTeamProjectTakeoverV4",
4767
+ projectHeadline: status.headline,
4768
+ dominantGap: status.dominantGap,
4769
+ projectNextAction: status.nextAction,
4770
+ projectNextActorId: status.nextActorId,
4771
+ currentResponsibility: legacy.currentResponsibility
4772
+ ? byId.get(legacy.currentResponsibility.workItemId) ?? null
4773
+ : null,
4774
+ allResponsibilities: legacy.allResponsibilities
4775
+ .map(row => byId.get(row.workItemId))
4776
+ .filter(Boolean),
4777
+ deliveryDisposition: status.deliveryDisposition,
4778
+ warnings: status.warnings,
4779
+ authorizationGranted: false,
4780
+ };
4781
+ }
4782
+
4723
4783
  export function formatTeamProjectStatusHumanV1(status) {
4724
4784
  const nextAction = status.nextAction === null ? "none" : singleLine(status.nextAction);
4725
4785
  return [