sneakoscope 2.0.8 → 2.0.10

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 (76) hide show
  1. package/README.md +8 -4
  2. package/crates/sks-core/Cargo.lock +1 -1
  3. package/crates/sks-core/Cargo.toml +1 -1
  4. package/crates/sks-core/src/main.rs +1 -1
  5. package/dist/.sks-build-stamp.json +4 -4
  6. package/dist/bin/sks.js +1 -1
  7. package/dist/build-manifest.json +33 -8
  8. package/dist/cli/command-registry.js +1 -0
  9. package/dist/commands/doctor.js +18 -1
  10. package/dist/commands/zellij-slot-pane.js +26 -0
  11. package/dist/commands/zellij.js +144 -1
  12. package/dist/core/agents/agent-orchestrator.js +202 -9
  13. package/dist/core/agents/agent-role-config.js +92 -0
  14. package/dist/core/agents/native-cli-session-swarm.js +230 -48
  15. package/dist/core/commands/mad-sks-command.js +17 -26
  16. package/dist/core/commands/naruto-command.js +155 -37
  17. package/dist/core/doctor/doctor-readiness-matrix.js +6 -0
  18. package/dist/core/fsx.js +1 -1
  19. package/dist/core/hooks-runtime.js +4 -0
  20. package/dist/core/init.js +1 -0
  21. package/dist/core/naruto/naruto-active-pool.js +141 -0
  22. package/dist/core/naruto/naruto-concurrency-governor.js +17 -2
  23. package/dist/core/naruto/naruto-real-worker-child.js +35 -0
  24. package/dist/core/naruto/naruto-real-worker-runtime.js +121 -0
  25. package/dist/core/naruto/naruto-work-graph.js +2 -1
  26. package/dist/core/release/release-gate-cache-v2.js +58 -4
  27. package/dist/core/release/release-gate-dag.js +36 -25
  28. package/dist/core/version.js +1 -1
  29. package/dist/core/zellij/zellij-dashboard-renderer.js +22 -6
  30. package/dist/core/zellij/zellij-launcher.js +3 -3
  31. package/dist/core/zellij/zellij-layout-builder.js +1 -1
  32. package/dist/core/zellij/zellij-right-column-layout-proof.js +42 -0
  33. package/dist/core/zellij/zellij-right-column-manager.js +304 -0
  34. package/dist/core/zellij/zellij-slot-pane-renderer.js +82 -0
  35. package/dist/core/zellij/zellij-ui-mode.js +16 -0
  36. package/dist/core/zellij/zellij-worker-pane-manager.js +152 -17
  37. package/dist/scripts/agent-role-config-repair-check.js +33 -0
  38. package/dist/scripts/codex-sdk-release-review-pipeline-check.js +5 -5
  39. package/dist/scripts/doctor-fix-proves-codex-read-check.js +26 -5
  40. package/dist/scripts/git-worktree-integration-primary-check.js +4 -2
  41. package/dist/scripts/git-worktree-integration-primary-runtime-check.js +20 -0
  42. package/dist/scripts/lib/codex-sdk-gate-lib.js +4 -0
  43. package/dist/scripts/mad-sks-zellij-default-pane-worker-check.js +2 -2
  44. package/dist/scripts/mutation-callsite-coverage-check.js +2 -1
  45. package/dist/scripts/naruto-concurrency-governor-check.js +2 -1
  46. package/dist/scripts/naruto-extreme-parallelism-check.js +22 -0
  47. package/dist/scripts/naruto-extreme-parallelism-real-check.js +42 -0
  48. package/dist/scripts/naruto-real-active-pool-check.js +39 -0
  49. package/dist/scripts/naruto-real-active-pool-runtime-check.js +53 -0
  50. package/dist/scripts/naruto-work-graph-check.js +1 -1
  51. package/dist/scripts/naruto-zellij-dynamic-right-column-check.js +48 -0
  52. package/dist/scripts/product-design-auto-install-check.js +3 -3
  53. package/dist/scripts/product-design-plugin-routing-check.js +3 -3
  54. package/dist/scripts/readme-architecture-imagegen-official-check.js +4 -3
  55. package/dist/scripts/release-cache-glob-hashing-check.js +42 -0
  56. package/dist/scripts/release-check-dynamic-execute.js +27 -1
  57. package/dist/scripts/release-check-dynamic.js +38 -11
  58. package/dist/scripts/release-check-stamp.js +7 -2
  59. package/dist/scripts/release-dag-full-coverage-check.js +35 -0
  60. package/dist/scripts/release-dynamic-performance-check.js +31 -1
  61. package/dist/scripts/release-gate-existence-audit.js +29 -33
  62. package/dist/scripts/release-parallel-speed-budget-check.js +67 -13
  63. package/dist/scripts/release-readiness-report.js +14 -3
  64. package/dist/scripts/zellij-dashboard-pane-check.js +6 -4
  65. package/dist/scripts/zellij-developer-controls-check.js +20 -0
  66. package/dist/scripts/zellij-dynamic-pane-lifecycle-check.js +21 -0
  67. package/dist/scripts/zellij-initial-main-only-blackbox.js +28 -0
  68. package/dist/scripts/zellij-right-column-geometry-proof.js +162 -0
  69. package/dist/scripts/zellij-right-column-headless-overflow-check.js +22 -0
  70. package/dist/scripts/zellij-right-column-manager-check.js +22 -0
  71. package/dist/scripts/zellij-slot-only-ui-check.js +22 -0
  72. package/dist/scripts/zellij-slot-pane-renderer-check.js +38 -0
  73. package/dist/scripts/zellij-worker-pane-manager-check.js +2 -1
  74. package/dist/scripts/zellij-worker-pane-manager-single-owner-check.js +7 -6
  75. package/package.json +23 -5
  76. package/schemas/zellij/zellij-right-column-state.schema.json +41 -0
package/README.md CHANGED
@@ -16,15 +16,19 @@ Set up this agent project with Sneakoscope Codex. Use [[mandarange/Sneakoscope-C
16
16
 
17
17
  ## Current Release
18
18
 
19
- SKS **2.0.8** makes the release path DAG-parallel by default and hardens the Naruto/MAD-SKS worktree proof chain. `release:check` now runs a manifest-backed DAG runner with resource-aware scheduling, hermetic per-gate environments, bounded logs, per-gate reports, cache proof, and parallel speed-budget evidence. Git worktree coding now preserves allocation manifests, detects dirty main worktrees, includes untracked content in exported diffs, emits one `git_apply_patch` envelope operation, applies worktree diffs through an integration queue, and locks retained dirty worktrees.
19
+ SKS **2.0.10** is the slot-only Zellij and Naruto runtime stabilization release. Compact slot panes are now the default visual worker surface, the initial Zellij session stays main-only until the first visible worker is reserved, overflow workers continue headlessly with runtime evidence instead of opening excess panes, and dashboard panes stay opt-in. The release path remains manifest-backed through the v2 DAG runner, with real Zellij/Naruto/worktree proof gates split into `real-check`.
20
20
 
21
21
  What changed:
22
22
 
23
+ - Zellij slot panes render compact worker slots without nested dashboard chrome, and right-column state records visible panes plus headless overflow lifecycle.
24
+ - Naruto active-pool checks now exercise real child-worker spawn/result collection paths, including high-fanout overflow and completed-worker collection order.
25
+ - Visible Zellij reservations are capped before pane launch so concurrent worker starts cannot over-open the right column.
26
+ - Git worktree integration now proves the primary repo receives validated worktree diffs, with rollback hash evidence recorded around the apply step.
27
+ - Agent role config repair detects stale generated role files and rewrites structured GPT-5.5-compatible configs atomically.
28
+ - Release gates now include slot-only UI, compact slot renderer, headless overflow, role-config repair, worktree primary-runtime, real active-pool, extreme real parallelism, and real right-column geometry checks.
29
+ - Release audit, dynamic selection, and stamp hashing use `release-gates.v2.json` as the manifest source of truth.
23
30
  - Git capability checks detect repo roots, Git dirs, worktree support, and safe cache roots while blocking in-repo worktree roots unless `SKS_ALLOW_IN_REPO_WORKTREES=1` is explicit.
24
31
  - Worker worktree allocation creates isolated branches/paths under `$SKS_WORKTREE_ROOT`, `$XDG_CACHE_HOME/sks/worktrees`, or `~/.cache/sks/worktrees`; main checkouts stay untouched until integration.
25
- - Worktree diff export records status, changed files, full-index binary diffs, and `git-worktree-diff` patch envelopes for parent-owned integration.
26
- - Integration worktrees apply worker diffs with `git apply --3way`, while cleanup removes only clean worktrees and retains dirty ones with a lock artifact.
27
- - Naruto work graphs, active-pool artifacts, Zellij dashboard titles, native worker intake, and GPT Final packs now carry worktree policy and WT/branch context.
28
32
  - Product Design plugin readiness now checks both local and remote Codex App catalogs, auto-installs the remote plugin when needed, and records the installed/enabled skill surface.
29
33
  - UI/design/PPT runtime routes prefer Product Design for research, ideation, audit, design QA, prototype, URL-to-code, image-to-code, share, and user-context steps.
30
34
  - Naruto read-only runs force write mode off, propagate no-patch reasons through worker proof, and skip changed-file lease checks when no write-capable patch envelope exists.
@@ -76,7 +76,7 @@ dependencies = [
76
76
 
77
77
  [[package]]
78
78
  name = "sks-core"
79
- version = "2.0.8"
79
+ version = "2.0.10"
80
80
  dependencies = [
81
81
  "serde_json",
82
82
  ]
@@ -1,6 +1,6 @@
1
1
  [package]
2
2
  name = "sks-core"
3
- version = "2.0.8"
3
+ version = "2.0.10"
4
4
  edition = "2021"
5
5
 
6
6
  [dependencies]
@@ -4,7 +4,7 @@ use std::io::{self, Read, Seek, SeekFrom};
4
4
  fn main() {
5
5
  let mut args = std::env::args().skip(1);
6
6
  match args.next().as_deref() {
7
- Some("--version") => println!("sks-rs 2.0.8"),
7
+ Some("--version") => println!("sks-rs 2.0.10"),
8
8
  Some("compact-info") => {
9
9
  let mut input = String::new();
10
10
  let _ = io::stdin().read_to_string(&mut input);
@@ -1,8 +1,8 @@
1
1
  {
2
2
  "schema": "sks.dist-build-stamp.v1",
3
3
  "package_name": "sneakoscope",
4
- "package_version": "2.0.8",
5
- "source_digest": "5009938d20628f783aa7ac19da170d2737fef89481b49d9c8dc3f2f97c0dcf9d",
6
- "source_file_count": 2004,
7
- "built_at_source_time": 1780739165211
4
+ "package_version": "2.0.10",
5
+ "source_digest": "ee8d0f4a75b8f5aeb6bfa26042f194cba01728768422448bf9b1e54748007137",
6
+ "source_file_count": 2030,
7
+ "built_at_source_time": 1780813031543
8
8
  }
package/dist/bin/sks.js CHANGED
@@ -1,5 +1,5 @@
1
1
  #!/usr/bin/env node
2
- const FAST_PACKAGE_VERSION = '2.0.8';
2
+ const FAST_PACKAGE_VERSION = '2.0.10';
3
3
  const args = process.argv.slice(2);
4
4
  try {
5
5
  if (args[0] === '--agent' && args[1] === 'worker') {
@@ -1,16 +1,16 @@
1
1
  {
2
2
  "schema": "sks.dist-build.v2",
3
- "version": "2.0.8",
4
- "package_version": "2.0.8",
3
+ "version": "2.0.10",
4
+ "package_version": "2.0.10",
5
5
  "typescript": true,
6
6
  "mjs_runtime_files": 0,
7
- "compiled_file_count": 1067,
8
- "compiled_js_count": 1067,
7
+ "compiled_file_count": 1092,
8
+ "compiled_js_count": 1092,
9
9
  "compiled_dts_count": 0,
10
- "source_digest": "5009938d20628f783aa7ac19da170d2737fef89481b49d9c8dc3f2f97c0dcf9d",
11
- "source_file_count": 2004,
12
- "source_files_hash": "045de0cf4e0b27b18838e5826c77f19ee281908588bbfde4a00a448b5a3c03eb",
13
- "source_list_hash": "045de0cf4e0b27b18838e5826c77f19ee281908588bbfde4a00a448b5a3c03eb",
10
+ "source_digest": "ee8d0f4a75b8f5aeb6bfa26042f194cba01728768422448bf9b1e54748007137",
11
+ "source_file_count": 2030,
12
+ "source_files_hash": "26a7831ee3d5b0909718d62eefcb828bfc074c18f454d5f46f5ebdf2ded482f6",
13
+ "source_list_hash": "26a7831ee3d5b0909718d62eefcb828bfc074c18f454d5f46f5ebdf2ded482f6",
14
14
  "src_mjs_runtime_files": 0,
15
15
  "dist_stamp_schema": "sks.dist-build-stamp.v1",
16
16
  "files": [
@@ -101,6 +101,7 @@
101
101
  "commands/versioning.js",
102
102
  "commands/wiki.js",
103
103
  "commands/zellij-lane.js",
104
+ "commands/zellij-slot-pane.js",
104
105
  "commands/zellij.js",
105
106
  "core/agents/agent-central-ledger.js",
106
107
  "core/agents/agent-cleanup-executor.js",
@@ -132,6 +133,7 @@
132
133
  "core/agents/agent-plan.js",
133
134
  "core/agents/agent-proof-evidence.js",
134
135
  "core/agents/agent-recursion-guard.js",
136
+ "core/agents/agent-role-config.js",
135
137
  "core/agents/agent-roster.js",
136
138
  "core/agents/agent-runner-codex-exec.js",
137
139
  "core/agents/agent-runner-fake.js",
@@ -433,6 +435,8 @@
433
435
  "core/naruto/naruto-gpt-final-pack.js",
434
436
  "core/naruto/naruto-parallel-patch-apply.js",
435
437
  "core/naruto/naruto-patch-transaction-batch.js",
438
+ "core/naruto/naruto-real-worker-child.js",
439
+ "core/naruto/naruto-real-worker-runtime.js",
436
440
  "core/naruto/naruto-role-policy.js",
437
441
  "core/naruto/naruto-verification-dag.js",
438
442
  "core/naruto/naruto-verification-pool.js",
@@ -631,7 +635,11 @@
631
635
  "core/zellij/zellij-layout-builder.js",
632
636
  "core/zellij/zellij-naruto-dashboard.js",
633
637
  "core/zellij/zellij-pane-proof.js",
638
+ "core/zellij/zellij-right-column-layout-proof.js",
639
+ "core/zellij/zellij-right-column-manager.js",
634
640
  "core/zellij/zellij-screen-proof.js",
641
+ "core/zellij/zellij-slot-pane-renderer.js",
642
+ "core/zellij/zellij-ui-mode.js",
635
643
  "core/zellij/zellij-worker-pane-manager.js",
636
644
  "scripts/agent-ast-aware-work-graph-check.js",
637
645
  "scripts/agent-backfill-replenishment-check.js",
@@ -686,6 +694,7 @@
686
694
  "scripts/agent-real-codex-parallel-workers-5-check.js",
687
695
  "scripts/agent-real-codex-parallel-workers-check.js",
688
696
  "scripts/agent-real-codex-patch-envelope-smoke.js",
697
+ "scripts/agent-role-config-repair-check.js",
689
698
  "scripts/agent-rollback-command-check.js",
690
699
  "scripts/agent-route-blackbox-lib.js",
691
700
  "scripts/agent-route-truth-backfill-check.js",
@@ -844,6 +853,7 @@
844
853
  "scripts/git-worktree-dirty-lock-check.js",
845
854
  "scripts/git-worktree-dirty-main-detection-check.js",
846
855
  "scripts/git-worktree-integration-primary-check.js",
856
+ "scripts/git-worktree-integration-primary-runtime-check.js",
847
857
  "scripts/git-worktree-manager-check.js",
848
858
  "scripts/git-worktree-manifest-append-check.js",
849
859
  "scripts/git-worktree-merge-queue-check.js",
@@ -922,9 +932,13 @@
922
932
  "scripts/mutation-callsite-coverage-check.js",
923
933
  "scripts/naruto-active-pool-check.js",
924
934
  "scripts/naruto-concurrency-governor-check.js",
935
+ "scripts/naruto-extreme-parallelism-check.js",
936
+ "scripts/naruto-extreme-parallelism-real-check.js",
925
937
  "scripts/naruto-gpt-final-pack-check.js",
926
938
  "scripts/naruto-parallel-patch-apply-check.js",
927
939
  "scripts/naruto-readonly-routing-check.js",
940
+ "scripts/naruto-real-active-pool-check.js",
941
+ "scripts/naruto-real-active-pool-runtime-check.js",
928
942
  "scripts/naruto-real-local-gpt-final-smoke.js",
929
943
  "scripts/naruto-role-distribution-check.js",
930
944
  "scripts/naruto-shadow-clone-swarm-check.js",
@@ -934,6 +948,7 @@
934
948
  "scripts/naruto-worktree-coding-check.js",
935
949
  "scripts/naruto-worktree-gpt-final-check.js",
936
950
  "scripts/naruto-worktree-zellij-ui-check.js",
951
+ "scripts/naruto-zellij-dynamic-right-column-check.js",
937
952
  "scripts/naruto-zellij-massive-ui-check.js",
938
953
  "scripts/non-recursive-pipeline-check.js",
939
954
  "scripts/npm-publish-performance-check.js",
@@ -973,9 +988,11 @@
973
988
  "scripts/qa-backfill-route-blackbox.js",
974
989
  "scripts/qa-patch-swarm-route-blackbox.js",
975
990
  "scripts/readme-architecture-imagegen-official-check.js",
991
+ "scripts/release-cache-glob-hashing-check.js",
976
992
  "scripts/release-check-dynamic-execute.js",
977
993
  "scripts/release-check-dynamic.js",
978
994
  "scripts/release-check-stamp.js",
995
+ "scripts/release-dag-full-coverage-check.js",
979
996
  "scripts/release-dist-freshness-check.js",
980
997
  "scripts/release-dynamic-performance-check.js",
981
998
  "scripts/release-gate-budget-check.js",
@@ -1067,7 +1084,10 @@
1067
1084
  "scripts/zellij-capability-check.js",
1068
1085
  "scripts/zellij-dashboard-pane-check.js",
1069
1086
  "scripts/zellij-dashboard-watch.js",
1087
+ "scripts/zellij-developer-controls-check.js",
1070
1088
  "scripts/zellij-doctor-readiness-check.js",
1089
+ "scripts/zellij-dynamic-pane-lifecycle-check.js",
1090
+ "scripts/zellij-initial-main-only-blackbox.js",
1071
1091
  "scripts/zellij-lane-renderer-check.js",
1072
1092
  "scripts/zellij-launch-command-truth-check.js",
1073
1093
  "scripts/zellij-layout-valid-check.js",
@@ -1075,7 +1095,12 @@
1075
1095
  "scripts/zellij-real-session-cleanup-check.js",
1076
1096
  "scripts/zellij-real-session-heartbeat-check.js",
1077
1097
  "scripts/zellij-real-session-launch-check.js",
1098
+ "scripts/zellij-right-column-geometry-proof.js",
1099
+ "scripts/zellij-right-column-headless-overflow-check.js",
1100
+ "scripts/zellij-right-column-manager-check.js",
1078
1101
  "scripts/zellij-screen-proof-check.js",
1102
+ "scripts/zellij-slot-only-ui-check.js",
1103
+ "scripts/zellij-slot-pane-renderer-check.js",
1079
1104
  "scripts/zellij-spawn-on-demand-layout-check.js",
1080
1105
  "scripts/zellij-ui-design-check.js",
1081
1106
  "scripts/zellij-worker-pane-manager-check.js",
@@ -104,6 +104,7 @@ export const COMMANDS = {
104
104
  hermes: entry('labs', 'Create Hermes Agent skill package', 'dist/commands/hermes.js', directCommand(() => import('../commands/hermes.js'), 'dist/commands/hermes.js')),
105
105
  tmux: entry('beta', 'Show removed-runtime migration notice', 'dist/commands/tmux.js', directCommand(() => import('../commands/tmux.js'), 'dist/commands/tmux.js')),
106
106
  'zellij-lane': entry('beta', 'Render a Zellij lane frame for SKS sessions', 'dist/commands/zellij-lane.js', directCommand(() => import('../commands/zellij-lane.js'), 'dist/commands/zellij-lane.js')),
107
+ 'zellij-slot-pane': entry('beta', 'Render a compact Zellij worker slot pane', 'dist/commands/zellij-slot-pane.js', directCommand(() => import('../commands/zellij-slot-pane.js'), 'dist/commands/zellij-slot-pane.js')),
107
108
  zellij: entry('beta', 'Inspect Zellij runtime status and explain repair (no auto-install)', 'dist/commands/zellij.js', directCommand(() => import('../commands/zellij.js'), 'dist/commands/zellij.js')),
108
109
  mad: entry('beta', 'MAD-SKS Zellij permission launcher', 'dist/commands/mad-sks.js', directCommand(() => import('../commands/mad-sks.js'), 'dist/commands/mad-sks.js')),
109
110
  'mad-sks': entry('beta', 'MAD-SKS scoped permission modifier', 'dist/commands/mad-sks.js', directCommand(() => import('../commands/mad-sks.js'), 'dist/commands/mad-sks.js')),
@@ -19,6 +19,7 @@ import { repairCodexAppFastUi } from '../core/codex-app/codex-app-fast-ui-repair
19
19
  import { resolveProviderContext } from '../core/provider/provider-context.js';
20
20
  import { readLocalModelConfig } from '../core/agents/ollama-worker-config.js';
21
21
  import { runSksUpdateNow } from '../core/update-check.js';
22
+ import { repairAgentRoleConfigs } from '../core/agents/agent-role-config.js';
22
23
  export async function run(_command, args = []) {
23
24
  const doctorFix = flag(args, '--fix');
24
25
  let setupRepair = null;
@@ -151,6 +152,20 @@ export async function run(_command, args = []) {
151
152
  const zellij = await checkZellijCapability({ root, require: process.env.SKS_REQUIRE_ZELLIJ === '1' });
152
153
  const localModel = await readLocalModelConfig().catch(() => null);
153
154
  const permissionProfiles = await inventoryCodexPermissionProfiles(root, { writeReport: true });
155
+ const agentRoleConfigRepair = await repairAgentRoleConfigs({
156
+ root,
157
+ apply: doctorFix,
158
+ reportPath: `${root}/.sneakoscope/reports/agent-role-config-repair.json`
159
+ }).catch((err) => ({
160
+ schema: 'sks.agent-role-config-repair.v1',
161
+ ok: false,
162
+ apply: doctorFix,
163
+ missing: [],
164
+ existing: [],
165
+ created: [],
166
+ warnings_suppressed: false,
167
+ blockers: [err?.message || String(err)]
168
+ }));
154
169
  const globalSksInstallCleanup = flag(args, '--fix') && !flag(args, '--local-only')
155
170
  ? await cleanDuplicateGlobalSksInstalls({ root, fix: true }).catch((err) => ({ schema: 'sks.global-sks-install-cleanup.v1', ok: false, fix: true, error: err?.message || String(err), blockers: ['global_sks_install_cleanup_exception'] }))
156
171
  : null;
@@ -166,6 +181,7 @@ export async function run(_command, args = []) {
166
181
  require_codex_doctor: flag(args, '--fix') || flag(args, '--require-actual-codex'),
167
182
  zellij,
168
183
  local_model: localModel,
184
+ agent_role_config: agentRoleConfigRepair,
169
185
  repair: configRepair,
170
186
  codex_app_ui: codexAppUi,
171
187
  require_codex_cli_config_load: flag(args, '--fix') || flag(args, '--require-actual-codex'),
@@ -191,6 +207,7 @@ export async function run(_command, args = []) {
191
207
  codex_doctor_diff: codexDoctorDiff,
192
208
  zellij,
193
209
  local_model: localModel,
210
+ agent_role_config: agentRoleConfigRepair,
194
211
  zellij_readiness: zellijReadiness,
195
212
  codex_permission_profiles: permissionProfiles,
196
213
  imagegen: {
@@ -201,7 +218,7 @@ export async function run(_command, args = []) {
201
218
  ready,
202
219
  sneakoscope: { ok: await exists(`${root}/.sneakoscope`) },
203
220
  package: { bytes: pkgBytes, human: formatBytes(pkgBytes) },
204
- repair: { sks_update: sksUpdate, setup: setupRepair, codex_config: configRepair, migration_journal: migrationJournal, global_sks_installs: globalSksInstallCleanup }
221
+ repair: { sks_update: sksUpdate, setup: setupRepair, codex_config: configRepair, migration_journal: migrationJournal, global_sks_installs: globalSksInstallCleanup, agent_role_config: agentRoleConfigRepair }
205
222
  };
206
223
  if (flag(args, '--json')) {
207
224
  printJson(result);
@@ -0,0 +1,26 @@
1
+ import { renderZellijSlotPaneFromArtifacts } from '../core/zellij/zellij-slot-pane-renderer.js';
2
+ export async function run(_command = 'zellij-slot-pane', args = []) {
3
+ const artifactDir = readOption(args, '--artifact-dir', process.cwd()) || process.cwd();
4
+ const slotId = readOption(args, '--slot', 'slot-001') || 'slot-001';
5
+ const generationIndex = Number(readOption(args, '--generation', '1') || 1);
6
+ const backend = readOption(args, '--backend', null);
7
+ const role = readOption(args, '--role', null);
8
+ const mode = readOption(args, '--mode', 'compact-slots');
9
+ const watch = hasFlag(args, '--watch');
10
+ const intervalMs = Math.max(250, Number(readOption(args, '--interval-ms', '1000') || 1000));
11
+ for (;;) {
12
+ const text = await renderZellijSlotPaneFromArtifacts({ artifactDir, slotId, generationIndex, backend, role, mode });
13
+ process.stdout.write('\x1Bc' + text + '\n');
14
+ if (!watch)
15
+ break;
16
+ await new Promise((resolve) => setTimeout(resolve, intervalMs));
17
+ }
18
+ }
19
+ function readOption(args, name, fallback) {
20
+ const index = args.indexOf(name);
21
+ return index >= 0 && args[index + 1] ? String(args[index + 1]) : fallback;
22
+ }
23
+ function hasFlag(args, flag) {
24
+ return args.includes(flag);
25
+ }
26
+ //# sourceMappingURL=zellij-slot-pane.js.map
@@ -1,10 +1,12 @@
1
1
  import path from 'node:path';
2
+ import fs from 'node:fs';
2
3
  import { projectRoot, readJson } from '../core/fsx.js';
3
4
  import { flag } from '../cli/args.js';
4
5
  import { printJson } from '../cli/output.js';
5
6
  import { checkZellijCapability } from '../core/zellij/zellij-capability.js';
6
7
  import { runZellij } from '../core/zellij/zellij-command.js';
7
8
  import { appendZellijLaneCommand, normalizeZellijSlot } from '../core/zellij/zellij-lane-runtime.js';
9
+ import { buildZellijDashboardSnapshot, renderZellijDashboardText } from '../core/zellij/zellij-dashboard-renderer.js';
8
10
  export const ZELLIJ_COMMAND_SCHEMA = 'sks.zellij-command.v1';
9
11
  export const ZELLIJ_REPAIR_SCHEMA = 'sks.zellij-repair.v1';
10
12
  function installHint() {
@@ -24,6 +26,14 @@ export async function run(_command = 'zellij', args = []) {
24
26
  return zellijRepair(root, args, json);
25
27
  if (sub === 'dispatch' || sub === 'send')
26
28
  return zellijDispatch(root, args, json);
29
+ if (sub === 'focus-worker')
30
+ return zellijFocusWorker(root, args, json);
31
+ if (sub === 'worker-logs')
32
+ return zellijWorkerLogs(root, args, json);
33
+ if (sub === 'dashboard')
34
+ return zellijDashboard(root, args, json);
35
+ if (sub === 'close-drained')
36
+ return zellijCloseDrained(root, args, json);
27
37
  return zellijStatus(root, args, json);
28
38
  }
29
39
  async function zellijStatus(root, args, json) {
@@ -63,6 +73,108 @@ async function zellijStatus(root, args, json) {
63
73
  if (!result.ok)
64
74
  process.exitCode = 1;
65
75
  }
76
+ async function zellijFocusWorker(root, args, json) {
77
+ const missionId = resolveMissionId(root, readOption(args, '--mission', readOption(args, '--mission-id', 'latest') || 'latest') || 'latest');
78
+ const slotId = normalizeZellijSlot(readOption(args, '--slot', positionalAfter(args, 'focus-worker') || 'slot-001'));
79
+ const state = await readJson(path.join(root, '.sneakoscope', 'missions', missionId, 'zellij-right-column-state.json'), null);
80
+ const worker = state?.visible_worker_panes?.find?.((row) => normalizeZellijSlot(row.slot_id) === slotId && row.pane_id);
81
+ const result = worker?.pane_id
82
+ ? await runZellij(['--session', state.session_name, 'action', 'focus-pane-id', String(worker.pane_id)], { cwd: root, timeoutMs: 5000, optional: true })
83
+ : null;
84
+ const out = {
85
+ schema: 'sks.zellij-focus-worker.v1',
86
+ ok: Boolean(worker?.pane_id) && (result?.ok !== false),
87
+ mission_id: missionId,
88
+ slot_id: slotId,
89
+ pane_id: worker?.pane_id || null,
90
+ session_name: state?.session_name || null,
91
+ result,
92
+ blockers: worker?.pane_id ? (result && !result.ok ? result.blockers : []) : ['worker_pane_not_found']
93
+ };
94
+ if (json)
95
+ printJson(out);
96
+ else
97
+ console.log(out.ok ? `Focused ${slotId} (${out.pane_id})` : `Worker pane not found: ${slotId}`);
98
+ if (!out.ok)
99
+ process.exitCode = 1;
100
+ }
101
+ async function zellijWorkerLogs(root, args, json) {
102
+ const missionId = resolveMissionId(root, readOption(args, '--mission', readOption(args, '--mission-id', 'latest') || 'latest') || 'latest');
103
+ const slotArg = positionalAfter(args, 'worker-logs') || readOption(args, '--slot', '');
104
+ const slotId = slotArg ? normalizeZellijSlot(slotArg) : null;
105
+ const swarm = await readJson(path.join(root, '.sneakoscope', 'missions', missionId, 'agents', 'agent-native-cli-session-swarm.json'), null);
106
+ const records = Array.isArray(swarm?.records) ? swarm.records : [];
107
+ const filtered = slotId ? records.filter((row) => normalizeZellijSlot(row.slot_id) === slotId) : records;
108
+ const out = {
109
+ schema: 'sks.zellij-worker-logs.v1',
110
+ ok: filtered.length > 0,
111
+ mission_id: missionId,
112
+ slot_id: slotId,
113
+ logs: filtered.map((row) => ({
114
+ slot_id: row.slot_id,
115
+ generation_index: row.generation_index,
116
+ status: row.status,
117
+ stdout_log: row.stdout_log ? path.join(root, '.sneakoscope', 'missions', missionId, 'agents', row.stdout_log) : null,
118
+ stderr_log: row.stderr_log ? path.join(root, '.sneakoscope', 'missions', missionId, 'agents', row.stderr_log) : null,
119
+ worker_artifact_dir: row.worker_artifact_dir
120
+ })),
121
+ blockers: filtered.length ? [] : ['worker_log_records_missing']
122
+ };
123
+ if (json)
124
+ printJson(out);
125
+ else
126
+ for (const log of out.logs)
127
+ console.log(`${log.slot_id} gen-${log.generation_index} ${log.status}\nstdout: ${log.stdout_log}\nstderr: ${log.stderr_log}`);
128
+ if (!out.ok)
129
+ process.exitCode = 1;
130
+ }
131
+ async function zellijDashboard(root, args, json) {
132
+ const missionId = resolveMissionId(root, readOption(args, '--mission', readOption(args, '--mission-id', 'latest') || 'latest') || 'latest');
133
+ const snapshot = await readJson(path.join(root, '.sneakoscope', 'missions', missionId, 'zellij-dashboard-snapshot.json'), null);
134
+ const state = await readJson(path.join(root, '.sneakoscope', 'missions', missionId, 'zellij-right-column-state.json'), null);
135
+ const watch = flag(args, '--watch');
136
+ const out = {
137
+ schema: 'sks.zellij-dashboard-command.v1',
138
+ ok: Boolean(snapshot || state),
139
+ mission_id: missionId,
140
+ snapshot,
141
+ right_column_state: state,
142
+ watch,
143
+ watch_command: `sks zellij dashboard --mission ${missionId} --watch`
144
+ };
145
+ if (json)
146
+ printJson(out);
147
+ else if (snapshot)
148
+ console.log(renderZellijDashboardText(buildZellijDashboardSnapshot({ ...snapshot, mission_id: snapshot.mission_id || missionId })));
149
+ else
150
+ console.log(JSON.stringify(state || out, null, 2));
151
+ if (!out.ok)
152
+ process.exitCode = 1;
153
+ }
154
+ async function zellijCloseDrained(root, args, json) {
155
+ const missionId = resolveMissionId(root, readOption(args, '--mission', readOption(args, '--mission-id', 'latest') || 'latest') || 'latest');
156
+ const state = await readJson(path.join(root, '.sneakoscope', 'missions', missionId, 'zellij-right-column-state.json'), null);
157
+ const rows = Array.isArray(state?.visible_worker_panes) ? state.visible_worker_panes.filter((row) => row.pane_id && (row.status === 'draining' || row.status === 'closed')) : [];
158
+ const results = [];
159
+ for (const row of rows) {
160
+ results.push(await runZellij(['--session', state.session_name, 'action', 'close-pane', '--pane-id', String(row.pane_id)], { cwd: root, timeoutMs: 5000, optional: true }));
161
+ }
162
+ const out = {
163
+ schema: 'sks.zellij-close-drained.v1',
164
+ ok: results.every((result) => result.ok !== false),
165
+ mission_id: missionId,
166
+ closed_count: results.filter((result) => result.ok).length,
167
+ attempted_count: results.length,
168
+ results,
169
+ blockers: results.flatMap((result) => result.ok ? [] : result.blockers)
170
+ };
171
+ if (json)
172
+ printJson(out);
173
+ else
174
+ console.log(`Closed drained panes: ${out.closed_count}/${out.attempted_count}`);
175
+ if (!out.ok)
176
+ process.exitCode = 1;
177
+ }
66
178
  async function zellijDispatch(root, args, json) {
67
179
  const missionId = readOption(args, '--mission', readOption(args, '--mission-id', 'latest') || 'latest') || 'latest';
68
180
  const slotId = normalizeZellijSlot(readOption(args, '--slot', 'slot-001'));
@@ -153,12 +265,16 @@ function printHelp(json) {
153
265
  schema: ZELLIJ_COMMAND_SCHEMA,
154
266
  subcommand: 'help',
155
267
  ok: true,
156
- usage: 'sks zellij status|repair|dispatch|send|capability [--require-real] [--json]',
268
+ usage: 'sks zellij status|repair|dispatch|send|focus-worker|worker-logs|dashboard|close-drained [--json]',
157
269
  subcommands: {
158
270
  status: 'Report Zellij runtime capability and interactive-route readiness.',
159
271
  repair: 'Explain how to install/repair Zellij (no automatic install).',
160
272
  dispatch: 'Append a nonblocking JSONL command for a lane; optionally write to a reconciled pane id with --write-pane.',
161
273
  send: 'Alias for dispatch.',
274
+ 'focus-worker': 'Focus a visible right-column worker pane by slot.',
275
+ 'worker-logs': 'Print stdout/stderr log paths for worker slots.',
276
+ dashboard: 'Render the latest dashboard snapshot; --watch prints watch metadata.',
277
+ 'close-drained': 'Close drained right-column panes.',
162
278
  capability: 'Alias for status.'
163
279
  }
164
280
  };
@@ -169,6 +285,10 @@ function printHelp(json) {
169
285
  console.log(' sks zellij status [--require-real] [--json]');
170
286
  console.log(' sks zellij repair [--explain] [--json]');
171
287
  console.log(' sks zellij dispatch --mission M --slot slot-001 --text "..." [--write-pane] [--json]');
288
+ console.log(' sks zellij focus-worker slot-001 [--mission M] [--json]');
289
+ console.log(' sks zellij worker-logs [slot-001] [--mission M] [--json]');
290
+ console.log(' sks zellij dashboard [--mission M] [--watch] [--json]');
291
+ console.log(' sks zellij close-drained [--mission M] [--json]');
172
292
  }
173
293
  }
174
294
  function defaultLedgerRoot(root, missionId) {
@@ -180,4 +300,27 @@ function readOption(args, name, fallback) {
180
300
  const index = args.indexOf(name);
181
301
  return index >= 0 && args[index + 1] ? String(args[index + 1]) : fallback;
182
302
  }
303
+ function positionalAfter(args, subcommand) {
304
+ const index = args.indexOf(subcommand);
305
+ for (const arg of args.slice(index >= 0 ? index + 1 : 1)) {
306
+ if (!String(arg).startsWith('-'))
307
+ return String(arg);
308
+ }
309
+ return null;
310
+ }
311
+ function resolveMissionId(root, requested) {
312
+ if (requested && requested !== 'latest')
313
+ return requested;
314
+ const dir = path.join(root, '.sneakoscope', 'missions');
315
+ try {
316
+ const rows = fs.readdirSync(dir)
317
+ .filter((name) => /^M-/.test(name))
318
+ .map((name) => ({ name, mtime: fs.statSync(path.join(dir, name)).mtimeMs }))
319
+ .sort((a, b) => b.mtime - a.mtime);
320
+ return rows[0]?.name || 'latest';
321
+ }
322
+ catch {
323
+ return 'latest';
324
+ }
325
+ }
183
326
  //# sourceMappingURL=zellij.js.map