swarph-cli 0.72.34__tar.gz → 0.72.36__tar.gz
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.
- {swarph_cli-0.72.34/src/swarph_cli.egg-info → swarph_cli-0.72.36}/PKG-INFO +1 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/pyproject.toml +1 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/__init__.py +1 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/backends.py +5 -3
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/board.py +53 -35
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/brain_ask.py +2 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/cell_probe.py +3 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/channel.py +6 -3
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/codegraph_hook.py +2 -1
- swarph_cli-0.72.36/src/swarph_cli/commands/commander.py +95 -0
- swarph_cli-0.72.36/src/swarph_cli/commands/committee.py +247 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/event.py +2 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/group.py +2 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/highlight.py +19 -6
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/mcp_server.py +3 -2
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/memory_emit_hook.py +6 -2
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/memory_sync.py +17 -3
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/mesh.py +16 -7
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/onboard.py +2 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/ratify.py +2 -2
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/roster.py +5 -3
- swarph_cli-0.72.36/src/swarph_cli/commit_trailers.py +31 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/slm.py +4 -2
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/duplicate_session.py +3 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway/server.py +3 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/guide/GUIDE.md +8 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/main.py +3 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/operator/api.py +7 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_service_reply.py +2 -0
- swarph_cli-0.72.36/src/swarph_cli/redact.py +417 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/stall_alert.py +2 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/backend.py +6 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36/src/swarph_cli.egg-info}/PKG-INFO +1 -1
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli.egg-info/SOURCES.txt +9 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1065_release.py +2 -0
- swarph_cli-0.72.36/tests/test_1297_commander.py +60 -0
- swarph_cli-0.72.36/tests/test_1301_restart_skew.py +64 -0
- swarph_cli-0.72.36/tests/test_1320_commit_trailers.py +56 -0
- swarph_cli-0.72.36/tests/test_1321_layered_redaction.py +1072 -0
- swarph_cli-0.72.36/tests/test_committee_command.py +160 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/LICENSE +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/README.md +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/setup.cfg +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/__main__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/claude_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/codex_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/pack.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/prices.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/providers.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/quality.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/refresh_prices.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/rules.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/runner.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/signal_score.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/bench/validate.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/caller.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/harden.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/lineage.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/liveness.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/manifest.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/paths.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/capture/verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/cell.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/chain_token.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/channel.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/_content.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/_display.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/_gateway_client.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/add.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/bench.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/board_merge_check.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/brain.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/cell.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/cell_selfcheck.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/chat.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/codegraph.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/codex_hook_output.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/codex_waker.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/compress.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/daemon.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/dreaming.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/gateway.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/gh_route.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/guide.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/hook_interpreter.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/hook_output.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/hooks.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/import_session.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/init.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/install_codex_hooks.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/install_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/install_multiplexer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/install_opencode_plugin.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/install_postcompact_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/install_wake_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/lane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/memory.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/monitor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/okf_links.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/peer_reply_drain.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/postcompact_hook_output.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/protocol_handler.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/rowclear_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/schedule.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/security.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/service.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/spawn.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/sweep.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/timeline.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/triage.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/version.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/wake_hook_output.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/commands/watchdog.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/compress/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/compress/levers.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/compress/marker.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/compress/verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/console_safe.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/delivery_queue.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dm_frame.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/candidates.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/clone.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/enrich.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/index_check.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/notify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/organize.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/probes.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/report.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/run.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/transcripts.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/dreaming/verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway/feature_registry.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway/lanes_control.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway/schema.sql +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway/services_control.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gateway_default.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/gh_identity.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/identity.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/launchd/swarph-codex-outbox.plist +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/launchd/swarph-codex-outbox.timer.plist +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/launchd/swarph-monitor.plist +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/launchd/swarph-watchdog.plist +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/launchd/swarph-watchdog.timer.plist +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/launchd_render.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/multiplexer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/operator/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/operator/__main__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/operator/cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/operator/config.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/operator/fmt.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/orphan_daemons.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/pane_probe.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/parsers/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/parsers/claude.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/opencode/plugin.js +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/_shim.cmd +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/postcompact-recall-grok.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/postcompact-recall.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/posttooluse-emit-antigravity.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/posttooluse-emit-claude.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/posttooluse-emit-grok.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/posttooluse-emit.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/posttooluse-recall.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/precompact-flag.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/preinvocation-recall-antigravity.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/payloads/postcompact/sessionstart-recall.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_executor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_executor_windows.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_reconciliation.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_reply_outbox.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_service_host.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_service_payload.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/peer_staging.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/query_filters.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/quota_sync.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/rowclear.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scripts/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scripts/dm_notify_filter.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scripts/ensure_monitor.sh +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scripts/install_codex_waker_windows.ps1 +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scripts/install_monitor_task_windows.ps1 +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scripts/wake_watchdog.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/scrub.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/service/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/service/app.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/service/providers.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/session_bridge.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/skills/i-have-adhd/LICENSE +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/skills/i-have-adhd/SKILL.md +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/source_text.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/codex-waker.default +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/peer-reply-drain.default +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-codex-outbox@.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-codex-outbox@.timer +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-codex-waker@.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-codex-waker@.timer +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-monitor-reexec.path +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-monitor-reexec.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-monitor@.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-peer-reply-drain@.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-peer-reply-drain@.timer +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-stuck-sweep.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-stuck-sweep.timer +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-triage.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-triage.timer +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-watchdog.default +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-watchdog.service +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/systemd/swarph-watchdog.timer +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/the_ten.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/timeline_paths.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/tokens.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/__init__.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/job.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/owners.json +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/router.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/rows.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli/triage/sensor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli.egg-info/dependency_links.txt +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli.egg-info/entry_points.txt +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli.egg-info/requires.txt +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/src/swarph_cli.egg-info/top_level.txt +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1006_board_publisher.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1006_session_board.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1010_strand_only.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1013_spawn_channel.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1017_muse_tui.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1034_copy_mode.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1050_surrogate_wake.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1052_opencode_deaf.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1059_watchdog_unread_env.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1061_roster_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1064_stuck_sweep.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1066_quiet_wakes.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1068_structured_accept_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1071_quota_sync.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1073_triage.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1073_triage_board.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1073_wheel_install.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1075_task_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1083_openai_decisions.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1144_cell_yaml_github.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1197_commander_taps.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1203_swarph_me_refusal.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1206_offer_question.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1214_egress.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1219_egress_probe.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1221_quota_windows.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1222_maybe_start_cap.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1228_quota_reach.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1243_the_ten.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1248_ship_price_table.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_124_register_merge.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1250_price_cache.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1256_commander_wake.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1261_mcp_install.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1262_wake_followups.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1265_wake_note.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1269_triage_label.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_126_pending_from_complete.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1278_dreaming_reach.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_1286_dm_unread_cursor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_132_ensure_monitor_state_dir.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_138_memory_navigate.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_139_tool_probe.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_183_card_anchor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_184_notify_honesty.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_201_win32_bash_refusal.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_243_onboard_per_peer_token.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_307_task4_ask_reply.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_312_codegraph_fuzzy_verb.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_319_refusal_exit_codes.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_323_mistral_backend.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_332_report_organize_findings.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_356_query_filters.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_397_gh_identity_router.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_397_router_preflight.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_402_one_identity_resolver.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_432_rowclear.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_467b_onboard_operator_credential.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_472_register_caller_binding.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_484_codex_queue_sink.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_513_duplicate_session.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_523_guide.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_524_conftest_hermeticity.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_532_accept_flag.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_535_version_capability.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_538_signal_bench.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_546_default_gateway.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_547_verbs_from_registry.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_548_gateway_remainder.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_552_codegraph_gateway.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_555_relay_row_shape.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_556_relay_freshness.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_559_edges_truncated.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_564_bootstrap_first_peer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_578_no_machine_specific_host_defaults.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_579_register_bootstrap_message.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_591_cli_step_graph.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_644_monitor_supervision.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_648_install_unit.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_654_reexec.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_656_owned_slm.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_684_dreaming_verb.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_689_pkg_version_order.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_715_grok_wake.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_716_timeline_one_path.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_723_grok_0251.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_724_ps1_ascii_or_bom.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_725_stdio_reconfigure.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_726_grok_limit_screen.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_729_arm_check_delivery_gap.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_729_dm_once.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_729_wake_watchdog.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_734_dreaming_enrich_degrade.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_735_dm_mcp_tools.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_739_wake_writer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_740_edit_project.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_762_cards_edit_priority.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_764_enrich_collapse.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_801_confirm_flow_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_802_stage_history.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_825_codegraph_hook_noise.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_825_install_posttooluse_only.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_825_remaining_cap_shred_bind.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_829_counterfactual_column.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_830_hook_binding_version.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_84_cli_labels.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_866_doctrine_guide.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_872_identity_refuses_not_warns.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_874_source_text.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_888_opencode_data_dir_can_fail.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_931_board_search.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_935_deadline_clock.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_937_dreaming_notify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_938_organize_line_limit.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_941_bench_backends.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_941_harness_342.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_945_same_line_pairing.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_955_prompt_audit.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_957_auth_http.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_959_venv_interpreter.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_960_channel.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_960_ensure_monitor_heartbeat.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_961_cursor_grok_footer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_961_loud_stop.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_963_plugin_manifest.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_964_channel_cell.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_965_mesh_wait.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_975_channel_hop.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_add_security_gate.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_add.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_hash.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_lib.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_mcp.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_skill.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_tool.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_artifact_uri.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_backends.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_claude_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_codex_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_pack.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_prices.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_quality.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_runner.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_bench_validate.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_board_card_thread.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_board_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_board_merge_check.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_board_obligation_close.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_brain_ask_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_brain_ask_env_diagnosis.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_brain_ask_identity_explicitness.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_brain_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_caller_meta_guard.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_capture_lineage.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_capture_liveness.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_capture_manifest.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_capture_paths.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_capture_security.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_cell_command_dispatch.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_cell_harden.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_cell_loader.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_cell_selfcheck.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_cell_verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_chain_token.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_channel_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_channel_poll_never_breaks_dms.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_channel_post.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_channel_wake_policy_filter.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_chat_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_claude_parser.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_claude_tmux_template.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_codegraph_caller_scope.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_codegraph_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_codegraph_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_codegraph_mcp.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_codex_waker.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_compress_caller_convention.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_compress_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_compress_levers.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_compress_marker.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_compress_verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_console_encoding_e2e.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_content_composition.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_copilot_membrane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_copilot_pane_reader.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_cursor_membrane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_daemon_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_daemon_console_encoding.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_daemon_delivery.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_delivery_queue.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_display_sanitize.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_ensure_monitor_no_peer_default.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_event_emit.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_feature_to_uri.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_gateway_brain.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_gateway_client.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_gateway_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_gateway_message_idempotency.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_gh_route_doctor_mesh_name.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_group_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_guide_commands_parse.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_guide_selfcheck.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_heartbeat_check.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_highlight_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hook_output.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_activity_marker.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_add.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_bundle.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_init.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_legacy_generation_removal.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_lifecycle.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_merge.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_win32_bash_wrapper.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_hooks_win32_command_path.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_import_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_inbox_identity_provenance.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_init_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_init_provider_menu.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_install_codex_hooks.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_install_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_install_multiplexer_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_install_postcompact_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_install_wake_hook.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_lane_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_launchd_units.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_main.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_main_unknown_verb_guard.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mcp_missing_hint.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mcp_server.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_memory_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_memory_emit_snippet.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_memory_gateway.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_memory_sync.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_memory_sync_membrane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_inbox_mark_read.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_inbox_sanitize.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_originate_thread_623.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_send_unknown_peer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_sidecar.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_sidecar_cursor_decoupled.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_sidecar_muse_sink.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_mesh_sidecar_wake_survives_read.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_meta_edge_identity.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_monitor_channel_poll.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_monitor_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_monitor_daemon_collision.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_monitor_self_name_verification.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_monitor_state_split.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_multiplexer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_muse_membrane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_muse_own_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_obligation_close_is_surfaced.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_okf_links.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_onboard_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_opencode_membrane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_opencode_plugin.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_operator_me.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_orphan_daemons.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_packaged_artifacts_exist.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_packaged_skills.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_executor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_executor_windows.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_reply_drain_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_reply_drain_supervisor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_reply_outbox.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_reply_transport.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_service_e2e.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_service_host.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_service_payload.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_peer_service_reply.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_postcompact_recall.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_process_liveness.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_protocol_handler.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_providers_isolation.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_ratify_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_readme_claims_no_gateway_default.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_repl_caller_convention.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_schedule_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_schedule_create_contract.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_scrub.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_security.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_service_app.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_service_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_service_providers.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_session_bridge_inject.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_session_bridge_probe.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_session_bridge_resolve.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_session_path_role_gate.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_shipped_units_match_the_cli.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_smoke_chat.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_smoke_one_shot.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_smoke_phase_5_5.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_base_hoist.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_identity_stamp.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_live_pin.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_mitosis_lineage.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_tmux_session.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_spawn_windows_relaunch.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_stall_alert.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_subprocess_decode_encoding.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_timeline_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_tmux_wake_runstate_defer.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_tmux_wake_session_reanchor.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_tmux_wake_stale.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_tmux_wake_submit_verify.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_token_file_one_parser.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_token_precedence_explicit_first.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_unified_token_resolver.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_version_command.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_version_consistency.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_vibe_membrane.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_dm_wake.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_dm_wake_cooldown.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_dm_wake_wiring.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_emit_health.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_install_flags.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_model_rung.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_watchdog_stale_peers.py +0 -0
- {swarph_cli-0.72.34 → swarph_cli-0.72.36}/tests/test_windows_waker_installer.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: swarph-cli
|
|
3
|
-
Version: 0.72.
|
|
3
|
+
Version: 0.72.36
|
|
4
4
|
Summary: The `swarph` binary — a multi-LLM CLI and mesh-gateway client + bundled server (`swarph gateway`): one-shot prompts across providers, interactive `chat`, multi-provider `spawn` (claude/codex/antigravity via a ProviderMembrane with subprocess billing-scrub), `mesh` send/inbox/register, `brain-ask` over the swarph-brain (gbrain) semantic memory, git-backed `assisted_memory`, per-invocation `gh` identity routing, a silent DM-wake hook, session `import`, and a stranded-session `watchdog`.
|
|
5
5
|
Author: Pierre Samson, Claude Opus
|
|
6
6
|
License: MIT
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "swarph-cli"
|
|
7
|
-
version = "0.72.
|
|
7
|
+
version = "0.72.36"
|
|
8
8
|
description = "The `swarph` binary — a multi-LLM CLI and mesh-gateway client + bundled server (`swarph gateway`): one-shot prompts across providers, interactive `chat`, multi-provider `spawn` (claude/codex/antigravity via a ProviderMembrane with subprocess billing-scrub), `mesh` send/inbox/register, `brain-ask` over the swarph-brain (gbrain) semantic memory, git-backed `assisted_memory`, per-invocation `gh` identity routing, a silent DM-wake hook, session `import`, and a stranded-session `watchdog`."
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
license = { text = "MIT" }
|
|
@@ -38,6 +38,8 @@ import urllib.request
|
|
|
38
38
|
from dataclasses import dataclass
|
|
39
39
|
from typing import Any, Callable, Optional, Protocol
|
|
40
40
|
|
|
41
|
+
from swarph_cli.redact import encode_outbound_json
|
|
42
|
+
|
|
41
43
|
|
|
42
44
|
@dataclass
|
|
43
45
|
class BackendResult:
|
|
@@ -510,7 +512,7 @@ class TypedHttpBackend:
|
|
|
510
512
|
body = _request_body(prompt, system)
|
|
511
513
|
req = urllib.request.Request(
|
|
512
514
|
endpoint,
|
|
513
|
-
data=
|
|
515
|
+
data=encode_outbound_json(body, caller="bench.SystemOneBackend.generate"),
|
|
514
516
|
headers={"Content-Type": "application/json"},
|
|
515
517
|
method="POST",
|
|
516
518
|
)
|
|
@@ -626,7 +628,7 @@ class HttpBackend:
|
|
|
626
628
|
scheme = self.auth.get("scheme") or ""
|
|
627
629
|
token = f"{scheme} {value}".strip() if scheme else value
|
|
628
630
|
headers[self.auth["header"]] = token
|
|
629
|
-
raw_body =
|
|
631
|
+
raw_body = encode_outbound_json(body, caller="bench.HttpBackend.generate")
|
|
630
632
|
self.calls += 1
|
|
631
633
|
if self.transport is not None:
|
|
632
634
|
status, reason, raw = self.transport(endpoint, headers, raw_body)
|
|
@@ -919,7 +921,7 @@ class DecisionsBackend:
|
|
|
919
921
|
scheme = self.auth.get("scheme") or ""
|
|
920
922
|
token = f"{scheme} {value}".strip() if scheme else value
|
|
921
923
|
headers[self.auth["header"]] = token
|
|
922
|
-
raw_body =
|
|
924
|
+
raw_body = encode_outbound_json(body, caller="bench.DecisionsBackend.generate")
|
|
923
925
|
self.calls += 1
|
|
924
926
|
if self.transport is not None:
|
|
925
927
|
status, reason, raw = self.transport(endpoint, headers, raw_body)
|
|
@@ -43,6 +43,7 @@ from swarph_cli.commands.mesh import (
|
|
|
43
43
|
_resolve_self_name,
|
|
44
44
|
_resolve_token,
|
|
45
45
|
)
|
|
46
|
+
from swarph_cli.redact import redact_text, redact_value, encode_outbound_json
|
|
46
47
|
|
|
47
48
|
|
|
48
49
|
_SENTINEL = object()
|
|
@@ -51,7 +52,7 @@ _SENTINEL = object()
|
|
|
51
52
|
# ── HTTP: PATCH (mesh.py has GET + POST; the board needs PATCH for move/link) ──
|
|
52
53
|
|
|
53
54
|
def _patch_json(url: str, body: dict, token: str, *, timeout: float = 10.0) -> tuple[int, dict]:
|
|
54
|
-
data =
|
|
55
|
+
data = encode_outbound_json(body, caller="board._patch_json")
|
|
55
56
|
req = urllib.request.Request(
|
|
56
57
|
url, data=data, method="PATCH",
|
|
57
58
|
headers={"Authorization": f"Bearer {token}", "Content-Type": "application/json"},
|
|
@@ -89,11 +90,12 @@ def _normalize_due_at(value: str) -> str:
|
|
|
89
90
|
|
|
90
91
|
|
|
91
92
|
def _card_add_payload(actor, project_id, title, *, body=None, ai2=False, priority=0,
|
|
92
|
-
labels=None, due_at=None) -> dict:
|
|
93
|
+
labels=None, due_at=None, opt_out=False) -> dict:
|
|
94
|
+
title = redact_text(title, opt_out=opt_out, caller="board.cards.add")
|
|
93
95
|
p = {"actor": actor, "project_id": int(project_id), "title": title,
|
|
94
96
|
"ai2": bool(ai2), "priority": int(priority)}
|
|
95
97
|
if body:
|
|
96
|
-
p["body"] = body
|
|
98
|
+
p["body"] = redact_text(body, opt_out=opt_out, caller="board.cards.add")
|
|
97
99
|
if labels:
|
|
98
100
|
p["labels"] = list(labels)
|
|
99
101
|
if due_at is not None:
|
|
@@ -151,7 +153,7 @@ def _format_obligations(data: dict) -> str:
|
|
|
151
153
|
|
|
152
154
|
|
|
153
155
|
def _card_edit_payload(actor, title, body, *, due_at=_SENTINEL, project_id=None,
|
|
154
|
-
priority=None) -> dict:
|
|
156
|
+
priority=None, opt_out=False) -> dict:
|
|
155
157
|
"""#191: the edit patch — title and/or body, the two fields that made a
|
|
156
158
|
card's text write-once until the gateway grew them (BoardCardPatch).
|
|
157
159
|
|
|
@@ -173,9 +175,9 @@ def _card_edit_payload(actor, title, body, *, due_at=_SENTINEL, project_id=None,
|
|
|
173
175
|
"""
|
|
174
176
|
patch = {"actor": actor}
|
|
175
177
|
if title is not None:
|
|
176
|
-
patch["title"] = title
|
|
178
|
+
patch["title"] = redact_text(title, opt_out=opt_out, caller="board.cards.edit")
|
|
177
179
|
if body is not None:
|
|
178
|
-
patch["body"] = body
|
|
180
|
+
patch["body"] = redact_text(body, opt_out=opt_out, caller="board.cards.edit")
|
|
179
181
|
if due_at is not _SENTINEL:
|
|
180
182
|
# "" is the gateway's CLEAR sentinel; None means "not mentioned" and the
|
|
181
183
|
# write is skipped while the old date is echoed back (#901).
|
|
@@ -190,7 +192,7 @@ def _card_edit_payload(actor, title, body, *, due_at=_SENTINEL, project_id=None,
|
|
|
190
192
|
return patch
|
|
191
193
|
|
|
192
194
|
|
|
193
|
-
def _write_card_preimage(actor, gateway, card_id, card, patch) -> Path:
|
|
195
|
+
def _write_card_preimage(actor, gateway, card_id, card, patch, *, opt_out=False) -> Path:
|
|
194
196
|
"""Append the card's CURRENT title and body to a local log BEFORE an edit
|
|
195
197
|
replaces them. Returns the path written.
|
|
196
198
|
|
|
@@ -213,10 +215,10 @@ def _write_card_preimage(actor, gateway, card_id, card, patch) -> Path:
|
|
|
213
215
|
"gateway": gateway,
|
|
214
216
|
"card": card_id,
|
|
215
217
|
"body_version": card.get("body_version"),
|
|
216
|
-
"prev_title": card.get("title"),
|
|
217
|
-
"prev_body": card.get("body"),
|
|
218
|
-
"new_title": patch.get("title"),
|
|
219
|
-
"new_body": patch.get("body"),
|
|
218
|
+
"prev_title": redact_text(card.get("title"), opt_out=opt_out, caller="board.cards.edit"),
|
|
219
|
+
"prev_body": redact_text(card.get("body"), opt_out=opt_out, caller="board.cards.edit"),
|
|
220
|
+
"new_title": redact_text(patch.get("title"), opt_out=opt_out, caller="board.cards.edit"),
|
|
221
|
+
"new_body": redact_text(patch.get("body"), opt_out=opt_out, caller="board.cards.edit"),
|
|
220
222
|
}
|
|
221
223
|
path = card_preimage_path()
|
|
222
224
|
path.parent.mkdir(parents=True, exist_ok=True)
|
|
@@ -251,10 +253,11 @@ def _apply_label(current: list, action: str, label: str) -> list:
|
|
|
251
253
|
return [x for x in cur if x != lab]
|
|
252
254
|
|
|
253
255
|
|
|
254
|
-
def _project_add_payload(actor, slug, title, *, goal=None) -> dict:
|
|
256
|
+
def _project_add_payload(actor, slug, title, *, goal=None, opt_out: bool = False) -> dict:
|
|
257
|
+
title = redact_text(title, opt_out=opt_out, caller="board.projects")
|
|
255
258
|
p = {"actor": actor, "slug": slug, "title": title}
|
|
256
259
|
if goal:
|
|
257
|
-
p["goal"] = goal
|
|
260
|
+
p["goal"] = redact_text(goal, opt_out=opt_out, caller="board.projects")
|
|
258
261
|
return p
|
|
259
262
|
|
|
260
263
|
|
|
@@ -546,7 +549,8 @@ def _say_line(resp: dict, card_id, to_node: str, *, reason: Optional[str] = None
|
|
|
546
549
|
|
|
547
550
|
|
|
548
551
|
def _card_say_payload(from_node: str, to_node: str, kind: str, content: str,
|
|
549
|
-
thread_uuid: str) -> dict:
|
|
552
|
+
thread_uuid: str, *, opt_out=False) -> dict:
|
|
553
|
+
content = redact_text(content, opt_out=opt_out, caller="board.cards.say")
|
|
550
554
|
return {
|
|
551
555
|
"from_node": from_node,
|
|
552
556
|
"to_node": to_node,
|
|
@@ -726,7 +730,7 @@ def _json_flag(flag: str, value: str):
|
|
|
726
730
|
|
|
727
731
|
def _ask_payload(self_name, what, *, holder=None, step=None, needs=None, hours=None,
|
|
728
732
|
done=None, accept=None, accept_json=None, kind="action",
|
|
729
|
-
timeout_hours=None, task=None, task_needs=None) -> dict:
|
|
733
|
+
timeout_hours=None, task=None, task_needs=None, opt_out=False) -> dict:
|
|
730
734
|
"""POST /board/cards/{id}/ask body. None = not mentioned = key ABSENT (#191's
|
|
731
735
|
rule; test_532 pins that a null `accept` on the wire would overwrite the
|
|
732
736
|
gateway's own normalization). No holder → `requested`; `me` → the caller's
|
|
@@ -736,6 +740,7 @@ def _ask_payload(self_name, what, *, holder=None, step=None, needs=None, hours=N
|
|
|
736
740
|
if accept is not None and accept_json is not None:
|
|
737
741
|
raise ValueError("pass --accept or --accept-json, not both — "
|
|
738
742
|
"one check per row")
|
|
743
|
+
what = redact_text(what, opt_out=opt_out, caller="board.cards.ask")
|
|
739
744
|
p = {"what": what, "created_by": self_name, "kind": kind}
|
|
740
745
|
if holder is not None:
|
|
741
746
|
p["holder"] = self_name if holder == "me" else holder
|
|
@@ -746,11 +751,11 @@ def _ask_payload(self_name, what, *, holder=None, step=None, needs=None, hours=N
|
|
|
746
751
|
if hours is not None:
|
|
747
752
|
p["hours"] = hours
|
|
748
753
|
if done is not None:
|
|
749
|
-
p["done"] = done
|
|
754
|
+
p["done"] = redact_text(done, opt_out=opt_out, caller="board.cards.ask")
|
|
750
755
|
if accept is not None:
|
|
751
|
-
p["accept"] = accept
|
|
756
|
+
p["accept"] = redact_text(accept, opt_out=opt_out, caller="board.cards.ask")
|
|
752
757
|
if accept_json is not None:
|
|
753
|
-
p["accept_json"] = accept_json
|
|
758
|
+
p["accept_json"] = redact_value(accept_json, opt_out=opt_out, caller="board.cards.ask")
|
|
754
759
|
if timeout_hours is not None:
|
|
755
760
|
p["timeout_hours"] = timeout_hours
|
|
756
761
|
if task is not None:
|
|
@@ -830,7 +835,7 @@ def _ask_line(d) -> str:
|
|
|
830
835
|
return line
|
|
831
836
|
|
|
832
837
|
|
|
833
|
-
def _confirm_flow_payload(actor: str, holders, what=None) -> dict:
|
|
838
|
+
def _confirm_flow_payload(actor: str, holders, what=None, *, opt_out=False) -> dict:
|
|
834
839
|
"""#801: {actor, holders: {step: peer}, what}. `--holder STEP=PEER` is parsed here so a
|
|
835
840
|
malformed override is refused before the request, naming the form."""
|
|
836
841
|
body = {"actor": actor}
|
|
@@ -844,7 +849,7 @@ def _confirm_flow_payload(actor: str, holders, what=None) -> dict:
|
|
|
844
849
|
out[step] = peer
|
|
845
850
|
body["holders"] = out
|
|
846
851
|
if what:
|
|
847
|
-
body["what"] = what
|
|
852
|
+
body["what"] = redact_text(what, opt_out=opt_out, caller="board.cards.confirm-flow")
|
|
848
853
|
return body
|
|
849
854
|
|
|
850
855
|
|
|
@@ -924,7 +929,7 @@ def _move_line(x) -> str:
|
|
|
924
929
|
return line
|
|
925
930
|
|
|
926
931
|
|
|
927
|
-
def _close_payload(outcome, evidence=None, evidence_json=None) -> dict:
|
|
932
|
+
def _close_payload(outcome, evidence=None, evidence_json=None, *, opt_out=False) -> dict:
|
|
928
933
|
"""POST /board/obligations/{id}/close body (#1068): --evidence and/or
|
|
929
934
|
--evidence-json, at least one. The CLI cannot know the row's stored
|
|
930
935
|
accept, so it sends what it was given — the gateway requires the map
|
|
@@ -934,15 +939,15 @@ def _close_payload(outcome, evidence=None, evidence_json=None) -> dict:
|
|
|
934
939
|
"--evidence-json")
|
|
935
940
|
p = {"outcome": outcome}
|
|
936
941
|
if evidence is not None:
|
|
937
|
-
p["evidence"] = evidence
|
|
942
|
+
p["evidence"] = redact_text(evidence, opt_out=opt_out, caller="board.obligations.close")
|
|
938
943
|
if evidence_json is not None:
|
|
939
|
-
p["evidence_json"] = evidence_json
|
|
944
|
+
p["evidence_json"] = redact_value(evidence_json, opt_out=opt_out, caller="board.obligations.close")
|
|
940
945
|
return p
|
|
941
946
|
|
|
942
947
|
|
|
943
948
|
def _amend_payload(step=None, holder=None, accept=None, hours=None,
|
|
944
949
|
needs_add=None, needs_remove=None, needs=None,
|
|
945
|
-
accept_json=None) -> dict:
|
|
950
|
+
accept_json=None, *, opt_out=False) -> dict:
|
|
946
951
|
"""PATCH /board/obligations/{id}/amend body. None = not mentioned; an empty
|
|
947
952
|
`holder` is a REAL value (clears → `requested`), so the test is
|
|
948
953
|
`is not None`, never truthiness (#191). `needs` is the contract's signed
|
|
@@ -953,6 +958,10 @@ def _amend_payload(step=None, holder=None, accept=None, hours=None,
|
|
|
953
958
|
if accept is not None and accept_json is not None:
|
|
954
959
|
raise ValueError("pass --accept or --accept-json, not both — "
|
|
955
960
|
"one check per row")
|
|
961
|
+
if accept is not None:
|
|
962
|
+
accept = redact_text(accept, opt_out=opt_out, caller="board.obligations")
|
|
963
|
+
if accept_json is not None:
|
|
964
|
+
accept_json = redact_value(accept_json, opt_out=opt_out, caller="board.obligations")
|
|
956
965
|
signed = _step_list(needs)
|
|
957
966
|
add = _step_list(needs_add) + [x for x in signed if not x.startswith("-")]
|
|
958
967
|
rem = _step_list(needs_remove) + [x[1:] for x in signed if x.startswith("-")]
|
|
@@ -1313,7 +1322,7 @@ def run_board(argv: list[str]) -> int:
|
|
|
1313
1322
|
st, d = _http_get_json(f"{gw}/board/projects", token)
|
|
1314
1323
|
return _out(st, d, _format_projects, aj)
|
|
1315
1324
|
if args.command == "add":
|
|
1316
|
-
st, d = _post_json(f"{gw}/board/projects", _project_add_payload(self_name, args.slug, args.title, goal=args.goal), token)
|
|
1325
|
+
st, d = _post_json(f"{gw}/board/projects", _project_add_payload(self_name, args.slug, args.title, goal=args.goal, opt_out=getattr(args, "no_redact", False)), token)
|
|
1317
1326
|
return _out(st, d, lambda x: f"created project #{x.get('id')} ({x.get('slug')})", aj)
|
|
1318
1327
|
|
|
1319
1328
|
if args.group == "obligations":
|
|
@@ -1332,7 +1341,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1332
1341
|
try:
|
|
1333
1342
|
evidence_json = (_json_flag("--evidence-json", args.evidence_json)
|
|
1334
1343
|
if args.evidence_json is not None else None)
|
|
1335
|
-
payload = _close_payload(args.outcome, evidence, evidence_json
|
|
1344
|
+
payload = _close_payload(args.outcome, evidence, evidence_json,
|
|
1345
|
+
opt_out=getattr(args, "no_redact", False))
|
|
1336
1346
|
except ValueError as exc:
|
|
1337
1347
|
print(f"swarph board obligations close: {exc}", file=sys.stderr)
|
|
1338
1348
|
return 2
|
|
@@ -1362,8 +1372,9 @@ def run_board(argv: list[str]) -> int:
|
|
|
1362
1372
|
st, d = _post_json(f"{gw}/board/obligations/{args.id}/take", {}, token)
|
|
1363
1373
|
return _out(st, d, _obligation_act_line, aj)
|
|
1364
1374
|
if args.command == "decline":
|
|
1375
|
+
why = redact_text(args.why, opt_out=getattr(args, "no_redact", False), caller="board.obligations")
|
|
1365
1376
|
st, d = _post_json(f"{gw}/board/obligations/{args.id}/decline",
|
|
1366
|
-
{"why":
|
|
1377
|
+
{"why": why}, token)
|
|
1367
1378
|
return _out(st, d, _obligation_act_line, aj)
|
|
1368
1379
|
if args.command == "amend":
|
|
1369
1380
|
try:
|
|
@@ -1373,7 +1384,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1373
1384
|
accept=args.accept, hours=args.hours,
|
|
1374
1385
|
needs_add=args.needs_add,
|
|
1375
1386
|
needs_remove=args.needs_remove, needs=args.needs,
|
|
1376
|
-
accept_json=accept_json
|
|
1387
|
+
accept_json=accept_json,
|
|
1388
|
+
opt_out=getattr(args, "no_redact", False))
|
|
1377
1389
|
except ValueError as exc:
|
|
1378
1390
|
print(f"swarph board obligations amend: {exc}", file=sys.stderr)
|
|
1379
1391
|
return 2
|
|
@@ -1385,6 +1397,7 @@ def run_board(argv: list[str]) -> int:
|
|
|
1385
1397
|
print("swarph board obligations withdraw: --reason is "
|
|
1386
1398
|
"whitespace-only", file=sys.stderr)
|
|
1387
1399
|
return 2
|
|
1400
|
+
reason = redact_text(reason, opt_out=getattr(args, "no_redact", False), caller="board.obligations")
|
|
1388
1401
|
st, d = _post_json(
|
|
1389
1402
|
f"{gw}/board/obligations/{args.id}/withdraw",
|
|
1390
1403
|
{"reason": reason}, token)
|
|
@@ -1441,7 +1454,7 @@ def run_board(argv: list[str]) -> int:
|
|
|
1441
1454
|
st, d = _post_json(f"{gw}/board/cards", _card_add_payload(
|
|
1442
1455
|
self_name, pid, title, body=body, ai2=args.ai2,
|
|
1443
1456
|
priority=args.priority, labels=getattr(args, "labels", None),
|
|
1444
|
-
due_at=args.due), token)
|
|
1457
|
+
due_at=args.due, opt_out=getattr(args, "no_redact", False)), token)
|
|
1445
1458
|
return _out(st, d, lambda x: f"created card #{x.get('id')} [{x.get('stage')}] (stage defaults to proposed — use `cards move` to advance)", aj)
|
|
1446
1459
|
if args.command == "label":
|
|
1447
1460
|
# READ the current set before replacing it. If the GET fails we must
|
|
@@ -1491,7 +1504,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1491
1504
|
try:
|
|
1492
1505
|
patch = _card_edit_payload(
|
|
1493
1506
|
self_name, title_text, body_text, due_at=args.due,
|
|
1494
|
-
project_id=project_id, priority=args.priority
|
|
1507
|
+
project_id=project_id, priority=args.priority,
|
|
1508
|
+
opt_out=getattr(args, "no_redact", False))
|
|
1495
1509
|
except ValueError as exc:
|
|
1496
1510
|
print(f"swarph board cards edit: {exc}", file=sys.stderr)
|
|
1497
1511
|
return 2
|
|
@@ -1508,7 +1522,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1508
1522
|
f"an unrecoverable one", file=sys.stderr)
|
|
1509
1523
|
return 1
|
|
1510
1524
|
try:
|
|
1511
|
-
pre = _write_card_preimage(self_name, gw, args.id, cur, patch
|
|
1525
|
+
pre = _write_card_preimage(self_name, gw, args.id, cur, patch,
|
|
1526
|
+
opt_out=getattr(args, "no_redact", False))
|
|
1512
1527
|
except OSError as exc:
|
|
1513
1528
|
print(f"swarph board cards edit: cannot write the pre-image log "
|
|
1514
1529
|
f"({exc}) — refusing to write, for the same reason: the "
|
|
@@ -1541,7 +1556,7 @@ def run_board(argv: list[str]) -> int:
|
|
|
1541
1556
|
# the row in one gateway call, or neither.
|
|
1542
1557
|
if args.holder is not None and args.holder_flag is not None:
|
|
1543
1558
|
print("swarph board cards ask: holder given twice (positional and "
|
|
1544
|
-
|
|
1559
|
+
"--holder) — pass one", file=sys.stderr)
|
|
1545
1560
|
return 2
|
|
1546
1561
|
holder = args.holder_flag or args.holder
|
|
1547
1562
|
if holder is None and args.step is None:
|
|
@@ -1562,7 +1577,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1562
1577
|
done=args.done, accept=args.accept,
|
|
1563
1578
|
accept_json=accept_json, kind=args.kind,
|
|
1564
1579
|
timeout_hours=args.timeout_hours,
|
|
1565
|
-
task=args.task, task_needs=args.task_needs
|
|
1580
|
+
task=args.task, task_needs=args.task_needs,
|
|
1581
|
+
opt_out=getattr(args, "no_redact", False))
|
|
1566
1582
|
except ValueError as exc:
|
|
1567
1583
|
print(f"swarph board cards ask: {exc}", file=sys.stderr)
|
|
1568
1584
|
return 2
|
|
@@ -1570,7 +1586,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1570
1586
|
return _out(st, d, _ask_line, args.json)
|
|
1571
1587
|
if args.command == "confirm-flow":
|
|
1572
1588
|
try:
|
|
1573
|
-
body = _confirm_flow_payload(self_name, args.holder, args.what
|
|
1589
|
+
body = _confirm_flow_payload(self_name, args.holder, args.what,
|
|
1590
|
+
opt_out=getattr(args, "no_redact", False))
|
|
1574
1591
|
except ValueError as e:
|
|
1575
1592
|
print(f"swarph board cards confirm-flow: {e}", file=sys.stderr)
|
|
1576
1593
|
return 2
|
|
@@ -1614,7 +1631,8 @@ def run_board(argv: list[str]) -> int:
|
|
|
1614
1631
|
return 1
|
|
1615
1632
|
st, d = _post_json(
|
|
1616
1633
|
f"{gw}/messages",
|
|
1617
|
-
_card_say_payload(self_name, to_node, args.kind, content, thread_uuid
|
|
1634
|
+
_card_say_payload(self_name, to_node, args.kind, content, thread_uuid,
|
|
1635
|
+
opt_out=getattr(args, "no_redact", False)),
|
|
1618
1636
|
token,
|
|
1619
1637
|
)
|
|
1620
1638
|
# A 403 here carries the gateway's explanation that attaching PUBLISHES
|
|
@@ -33,6 +33,7 @@ import urllib.request
|
|
|
33
33
|
|
|
34
34
|
from swarph_cli import identity
|
|
35
35
|
from swarph_cli import tokens
|
|
36
|
+
from swarph_cli.redact import encode_outbound_json
|
|
36
37
|
from pathlib import Path
|
|
37
38
|
from typing import Optional
|
|
38
39
|
|
|
@@ -204,7 +205,7 @@ def _resolve_token(token_file: Optional[str], self_name: str) -> Optional[str]:
|
|
|
204
205
|
def _http_post(url: str, body: dict, token: str,
|
|
205
206
|
accept: str = "application/json, text/event-stream",
|
|
206
207
|
timeout: int = 30) -> str:
|
|
207
|
-
data =
|
|
208
|
+
data = encode_outbound_json(body, caller="brain_ask._http_post")
|
|
208
209
|
req = urllib.request.Request(url, data=data, method="POST")
|
|
209
210
|
req.add_header("Content-Type", "application/json")
|
|
210
211
|
req.add_header("Accept", accept)
|
|
@@ -145,9 +145,11 @@ def gateway_memory_list(gateway: str, token: str, timeout: int = 15) -> list[str
|
|
|
145
145
|
gateway; :8792 is gbrain itself and speaks MCP at /mcp, where POST /memory is
|
|
146
146
|
correctly refused. A route named without its coordinate cost a peer a
|
|
147
147
|
measurement on 2026-09-05."""
|
|
148
|
+
from swarph_cli.redact import encode_outbound_json
|
|
149
|
+
|
|
148
150
|
req = urllib.request.Request(
|
|
149
151
|
gateway.rstrip("/") + "/memory",
|
|
150
|
-
data=
|
|
152
|
+
data=encode_outbound_json({"op": "list", "arguments": {}}, caller="cell_probe.gateway_memory_list"),
|
|
151
153
|
headers={"Authorization": "Bearer " + token,
|
|
152
154
|
"Content-Type": "application/json"})
|
|
153
155
|
doc = json.loads(urllib.request.urlopen(req, timeout=timeout).read())
|
|
@@ -18,6 +18,7 @@ from ._gateway_client import (
|
|
|
18
18
|
resolve_token,
|
|
19
19
|
)
|
|
20
20
|
from swarph_cli.console_safe import print_safe
|
|
21
|
+
from swarph_cli.redact import redact_text
|
|
21
22
|
|
|
22
23
|
|
|
23
24
|
def _build_parser() -> argparse.ArgumentParser:
|
|
@@ -74,9 +75,10 @@ def _build_parser() -> argparse.ArgumentParser:
|
|
|
74
75
|
|
|
75
76
|
# ── pure helpers (unit-tested) ────────────────────────────────────────────────
|
|
76
77
|
|
|
77
|
-
def _post_payload(self_name: str, channel: str, kind: str, content: str) -> dict:
|
|
78
|
+
def _post_payload(self_name: str, channel: str, kind: str, content: str, *, opt_out: bool = False) -> dict:
|
|
78
79
|
"""A channel post carries ``channel`` and NEVER ``to_node`` — the gateway
|
|
79
80
|
rejects a message with both ("exactly one of {to_node, channel} required")."""
|
|
81
|
+
content = redact_text(content, opt_out=opt_out, caller="channel.post")
|
|
80
82
|
return {"from_node": self_name, "channel": channel, "kind": kind, "content": content}
|
|
81
83
|
|
|
82
84
|
|
|
@@ -120,7 +122,7 @@ def _run_create(args: argparse.Namespace) -> int:
|
|
|
120
122
|
if args.visibility is not None:
|
|
121
123
|
body["visibility"] = args.visibility
|
|
122
124
|
if args.description is not None:
|
|
123
|
-
body["description"] = args.description
|
|
125
|
+
body["description"] = redact_text(args.description, opt_out=getattr(args, "no_redact", False), caller="channel.create")
|
|
124
126
|
status, payload = post_json(f"{base}/channels", body, token)
|
|
125
127
|
if not _ok(status):
|
|
126
128
|
return _fail("create", status, payload)
|
|
@@ -178,9 +180,10 @@ def _run_post(args: argparse.Namespace) -> int:
|
|
|
178
180
|
except ContentError as exc:
|
|
179
181
|
print(f"swarph channel post: {exc}", file=sys.stderr)
|
|
180
182
|
return 1
|
|
183
|
+
content = redact_text(content, opt_out=getattr(args, "no_redact", False), caller="channel.post") or ""
|
|
181
184
|
self_name, token, base = _ctx(args)
|
|
182
185
|
status, payload = post_json(
|
|
183
|
-
f"{base}/messages", _post_payload(self_name, args.name, args.kind, content), token
|
|
186
|
+
f"{base}/messages", _post_payload(self_name, args.name, args.kind, content, opt_out=getattr(args, "no_redact", False)), token
|
|
184
187
|
)
|
|
185
188
|
if not _ok(status):
|
|
186
189
|
return _fail("post", status, payload)
|
|
@@ -35,6 +35,7 @@ from pathlib import Path
|
|
|
35
35
|
from typing import Optional
|
|
36
36
|
from swarph_cli import identity
|
|
37
37
|
from swarph_cli.gateway_default import env_gateway
|
|
38
|
+
from swarph_cli.redact import encode_outbound_json
|
|
38
39
|
|
|
39
40
|
TIMEOUT_S = 6
|
|
40
41
|
MAX_ROWS = 6
|
|
@@ -326,7 +327,7 @@ def query_gateway(term: str, gateway: str, token: str,
|
|
|
326
327
|
"gateway host (#578) — the graph was never asked"}
|
|
327
328
|
req = urllib.request.Request(
|
|
328
329
|
f"{gateway.rstrip('/')}/codegraph",
|
|
329
|
-
data=
|
|
330
|
+
data=encode_outbound_json({"query": term, "limit": limit}, caller="codegraph_hook.query_gateway"),
|
|
330
331
|
headers={"Authorization": f"Bearer {token}",
|
|
331
332
|
"Content-Type": "application/json"},
|
|
332
333
|
method="POST",
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
"""``swarph commander`` — propose a decision or an action. Card #1297.
|
|
2
|
+
|
|
3
|
+
The cell asks. The commander decides, from the desktop, with a credential
|
|
4
|
+
this command never holds. ``ask`` posts a decision. ``request`` posts
|
|
5
|
+
``merge_pr`` or ``release_finish``. An MCP tool for the same queue is a
|
|
6
|
+
later card.
|
|
7
|
+
"""
|
|
8
|
+
from __future__ import annotations
|
|
9
|
+
|
|
10
|
+
import argparse
|
|
11
|
+
import sys
|
|
12
|
+
|
|
13
|
+
from swarph_cli.commands import mesh as mesh_cmd
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
def ask_body(question: str, options: list[str], card: int | None) -> dict:
|
|
17
|
+
body: dict = {"type": "decision", "question": question, "options": options}
|
|
18
|
+
if card is not None:
|
|
19
|
+
body["card_id"] = card
|
|
20
|
+
return body
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
def request_body(kind: str, *, repo: str | None, pr: int | None,
|
|
24
|
+
head: str | None, version: str | None, card: int | None) -> dict:
|
|
25
|
+
body: dict = {"type": kind, "pr": pr, "head_sha": head}
|
|
26
|
+
if kind == "merge_pr":
|
|
27
|
+
body["repo"] = repo
|
|
28
|
+
if kind == "release_finish":
|
|
29
|
+
body["version"] = version
|
|
30
|
+
if card is not None:
|
|
31
|
+
body["card_id"] = card
|
|
32
|
+
return body
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
def _build_parser() -> argparse.ArgumentParser:
|
|
36
|
+
p = argparse.ArgumentParser(prog="swarph commander")
|
|
37
|
+
sub = p.add_subparsers(dest="command", required=True)
|
|
38
|
+
|
|
39
|
+
ask = sub.add_parser("ask", help="propose a decision")
|
|
40
|
+
mesh_cmd._add_common(ask)
|
|
41
|
+
ask.add_argument("--question", required=True)
|
|
42
|
+
ask.add_argument("--options", default=None,
|
|
43
|
+
help="comma-separated choices, e.g. yes,no")
|
|
44
|
+
ask.add_argument("--card", type=int, default=None)
|
|
45
|
+
|
|
46
|
+
req = sub.add_parser("request", help="propose merge_pr or release_finish")
|
|
47
|
+
mesh_cmd._add_common(req)
|
|
48
|
+
req.add_argument("type", choices=["merge_pr", "release_finish"])
|
|
49
|
+
req.add_argument("--repo", default=None)
|
|
50
|
+
req.add_argument("--pr", type=int, default=None)
|
|
51
|
+
req.add_argument("--head", default=None)
|
|
52
|
+
req.add_argument("--version", default=None)
|
|
53
|
+
req.add_argument("--card", type=int, default=None)
|
|
54
|
+
return p
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
def _options(raw: str | None) -> list[str]:
|
|
58
|
+
if not raw:
|
|
59
|
+
return []
|
|
60
|
+
return [part.strip() for part in raw.split(",") if part.strip()]
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
def run_commander(argv: list[str]) -> int:
|
|
64
|
+
args = _build_parser().parse_args(argv)
|
|
65
|
+
try:
|
|
66
|
+
self_name = mesh_cmd._resolve_self_name(args.self_name)
|
|
67
|
+
token = mesh_cmd._resolve_token(self_name, args.token_file)
|
|
68
|
+
except RuntimeError as exc:
|
|
69
|
+
print(f"swarph commander: {exc}", file=sys.stderr)
|
|
70
|
+
return 1
|
|
71
|
+
gw = args.gateway.rstrip("/")
|
|
72
|
+
if args.command == "ask":
|
|
73
|
+
body = ask_body(args.question, _options(args.options), args.card)
|
|
74
|
+
else:
|
|
75
|
+
if args.pr is None or not args.head:
|
|
76
|
+
print("swarph commander request: --pr and --head are required",
|
|
77
|
+
file=sys.stderr)
|
|
78
|
+
return 2
|
|
79
|
+
if args.type == "merge_pr" and not args.repo:
|
|
80
|
+
print("swarph commander request: merge_pr requires --repo",
|
|
81
|
+
file=sys.stderr)
|
|
82
|
+
return 2
|
|
83
|
+
if args.type == "release_finish" and not args.version:
|
|
84
|
+
print("swarph commander request: release_finish requires --version",
|
|
85
|
+
file=sys.stderr)
|
|
86
|
+
return 2
|
|
87
|
+
body = request_body(args.type, repo=args.repo, pr=args.pr, head=args.head,
|
|
88
|
+
version=args.version, card=args.card)
|
|
89
|
+
status, payload = mesh_cmd._post_json(f"{gw}/commander/requests", body, token)
|
|
90
|
+
if status in (200, 201):
|
|
91
|
+
print(f"commander request #{payload.get('id')} {payload.get('status')}")
|
|
92
|
+
return 0
|
|
93
|
+
detail = payload.get("detail") if isinstance(payload, dict) else payload
|
|
94
|
+
print(f"swarph commander: {detail}", file=sys.stderr)
|
|
95
|
+
return 1
|