From e916fe7627909c65a539a0c7328b32ae46069506 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=89=9B=E7=91=9E=E5=8D=9A?= <912906590@qq.com> Date: Tue, 25 Aug 2026 17:05:46 +0800 Subject: [PATCH 1/7] fix(goal): derive goal display title from task objective instead of project name MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: 牛瑞博 <912906590@qq.com> --- examples/bootstrap-command-pack-smoke.py | 76 ++++++++++++++++++++++++ loopx/bootstrap_command_pack.py | 48 +++++++++++++++ loopx/cli_commands/bootstrap_connect.py | 8 +++ loopx/cli_commands/start_goal.py | 11 ++++ 4 files changed, 143 insertions(+) diff --git a/examples/bootstrap-command-pack-smoke.py b/examples/bootstrap-command-pack-smoke.py index 812b6ca68..682dae650 100644 --- a/examples/bootstrap-command-pack-smoke.py +++ b/examples/bootstrap-command-pack-smoke.py @@ -722,6 +722,81 @@ def test_skill_slash_fallback_contract() -> None: assert "The five sections are output structure, while the execution contract is the evidence authority" in pr_review_normalized +def test_start_goal_guided_derives_display_name_from_goal_text() -> None: + with tempfile.TemporaryDirectory() as tmp: + project = Path(tmp) / "display-name-project" + project.mkdir() + write_connected_goal_fixture(project, goal_id="display-goal", agent_id="codex-test-agent") + + derived = run_json( + "start-goal", + "--guided", + "--project", + str(project), + "--goal-id", + "display-goal", + "--agent-id", + "codex-test-agent", + "--host-surface", + "codex-app", + "--goal-text", + "修复 scheduler state path 覆盖问题", + "--include-command-pack-detail", + ) + connect_command = str( + derived["command_pack"]["commands"]["goal_start_connect_if_needed"] + ) + assert "--display-name '修复 scheduler state path 覆盖问题'" in connect_command, connect_command + assert ( + derived["command_pack"].get("display_name") + == "修复 scheduler state path 覆盖问题" + ) + + explicit = run_json( + "start-goal", + "--guided", + "--project", + str(project), + "--goal-id", + "display-goal", + "--agent-id", + "codex-test-agent", + "--host-surface", + "codex-app", + "--goal-text", + "some objective", + "--display-name", + "Custom Title", + "--include-command-pack-detail", + ) + explicit_command = str( + explicit["command_pack"]["commands"]["goal_start_connect_if_needed"] + ) + assert "--display-name 'Custom Title'" in explicit_command, explicit_command + assert explicit["command_pack"].get("display_name") == "Custom Title" + + rejected = run_json( + "start-goal", + "--guided", + "--project", + str(project), + "--goal-id", + "display-goal", + "--agent-id", + "codex-test-agent", + "--host-surface", + "codex-app", + "--goal-text", + "/private/secret/path should not leak", + "--include-command-pack-detail", + ) + rejected_command = str( + rejected["command_pack"]["commands"]["goal_start_connect_if_needed"] + ) + assert "--display-name" not in rejected_command, rejected_command + assert rejected["command_pack"].get("display_name") is None + + def main() -> int: test_missing_project_stops_before_mutation() test_goal_text_invocation_plans_ranked_todos_before_activation() @@ -730,6 +805,7 @@ def main() -> int: test_connected_project_reuses_existing_state() test_linked_git_worktree_reuses_canonical_source_registry() test_skill_slash_fallback_contract() + test_start_goal_guided_derives_display_name_from_goal_text() print("bootstrap command pack smoke passed") return 0 diff --git a/loopx/bootstrap_command_pack.py b/loopx/bootstrap_command_pack.py index 617aa7db1..fdd1420a6 100644 --- a/loopx/bootstrap_command_pack.py +++ b/loopx/bootstrap_command_pack.py @@ -206,6 +206,7 @@ def _start_goal_command( capability_route: str | None, fine_grained: bool, include_command_pack_detail: bool, + display_name: str | None = None, ) -> str: return ( f"{shell_arg(cli_bin)} --format json start-goal --guided " @@ -223,6 +224,11 @@ def _start_goal_command( else "" ) + f" --goal-text {shell_arg(goal_text)}" + + ( + f" --display-name {shell_arg(display_name)}" + if display_name + else "" + ) + (" --include-command-pack-detail" if include_command_pack_detail else "") ) @@ -240,6 +246,7 @@ def _start_goal_detail_command( available_capabilities: list[str] | None, capability_route: str | None, fine_grained: bool, + display_name: str | None = None, ) -> str: return _start_goal_command( project=project, @@ -254,6 +261,7 @@ def _start_goal_detail_command( capability_route=capability_route, fine_grained=fine_grained, include_command_pack_detail=True, + display_name=display_name, ) @@ -310,6 +318,7 @@ def build_start_goal_host_surface_selection_packet( capability_route: str | None = None, fine_grained: bool = False, include_command_pack_detail: bool = False, + display_name: str | None = None, ) -> dict[str, Any]: """Fail closed when the caller has not identified the current Codex host.""" @@ -352,6 +361,11 @@ def build_start_goal_host_surface_selection_packet( else "" ) + f" --goal-text {shell_arg(normalized_goal_text)}" + + ( + f" --display-name {shell_arg(display_name)}" + if display_name + else "" + ) + (" --include-command-pack-detail" if include_command_pack_detail else "") ) choices.append( @@ -380,6 +394,7 @@ def build_start_goal_host_surface_selection_packet( "writes_now": False, "spends_quota_now": False, "goal_text": normalized_goal_text, + "display_name": display_name, "blocked_by": "host_surface_selection", "host_surface_selection_gate": gate, "ordered_steps": [ @@ -409,6 +424,7 @@ def build_start_goal_host_surface_selection_packet( "new_peer": new_peer, "host_surface": None, "goal_text": normalized_goal_text, + "display_name": display_name, "host_surface_selection_gate": gate, "recommended_next_step": { "kind": "select_host_surface", @@ -630,6 +646,20 @@ def _project_command(project: str, command: str) -> str: return "\n".join([f"cd {shell_arg(project)}", command]) +def derive_goal_display_name(goal_text: str | None) -> str | None: + """Derive a public-safe display title from goal text. + + The project name is only a fallback when no title can be derived. Goal text + is user-supplied task prose, so it is run through the public-safe compact + text boundary: whitespace is collapsed, the result is truncated, and any + local-path or credential-like surface makes the title unrevealable + (returns None) instead of leaking private material into a public goal title. + """ + from .control_plane.runtime.public_safety import public_safe_compact_text + + return public_safe_compact_text(goal_text, limit=132) + + def _goal_start_bootstrap_command( *, project: str, @@ -637,6 +667,7 @@ def _goal_start_bootstrap_command( goal_text: str | None, cli_bin: str, fine_grained: bool, + display_name: str | None = None, ) -> str: objective = goal_text or "" lines = [ @@ -650,6 +681,8 @@ def _goal_start_bootstrap_command( " --no-onboarding-scan \\", " --codex-app-heartbeat ask", ] + if display_name: + lines.insert(-1, f" --display-name {shell_arg(display_name)} \\") if fine_grained: lines[-1] += " \\" lines.append(" --fine-grained") @@ -719,6 +752,7 @@ def build_loopx_bootstrap_command_pack( capability_route: str | None = None, fine_grained: bool = False, resolve_linked_worktree_alias: bool = True, + display_name: str | None = None, ) -> dict[str, Any]: inspection = inspect_bootstrap_connection( project, @@ -836,6 +870,7 @@ def build_loopx_bootstrap_command_pack( goal_text=normalized_goal_text, cli_bin=cli_bin, fine_grained=fine_grained, + display_name=display_name, ) goal_start_plan_prompt = build_goal_start_prompt( goal_text=normalized_goal_text, @@ -916,9 +951,15 @@ def build_loopx_bootstrap_command_pack( if normalized_goal_text else "" ) + + ( + f" --display-name {shell_arg(display_name)}" + if display_name + else "" + ) ), "read_only": True, "goal_text": normalized_goal_text, + "display_name": display_name, "project": resolved_project, "goal_id": resolved_goal_id, "agent_id": selected_agent_id, @@ -1054,6 +1095,7 @@ def _build_multi_goal_start_selection_packet( capability_route: str | None, fine_grained: bool, include_command_pack_detail: bool, + display_name: str | None = None, ) -> dict[str, Any] | None: inspection = inspect_bootstrap_connection( project, @@ -1254,6 +1296,7 @@ def _build_multi_goal_start_selection_packet( available_capabilities=available_capabilities, capability_route=capability_route, fine_grained=fine_grained, + display_name=display_name, ) selected_command_pack = ( command_pack @@ -1322,6 +1365,7 @@ def build_start_goal_guided_packet( capability_route: str | None = None, fine_grained: bool = False, include_command_pack_detail: bool = False, + display_name: str | None = None, ) -> dict[str, Any]: if goal_id is None: selection_packet = _build_multi_goal_start_selection_packet( @@ -1336,6 +1380,7 @@ def build_start_goal_guided_packet( capability_route=capability_route, fine_grained=fine_grained, include_command_pack_detail=include_command_pack_detail, + display_name=display_name, ) if selection_packet is not None: return selection_packet @@ -1352,6 +1397,7 @@ def build_start_goal_guided_packet( capability_route=capability_route, fine_grained=fine_grained, resolve_linked_worktree_alias=False, + display_name=display_name, ) commands = command_pack.get("commands") commands = commands if isinstance(commands, dict) else {} @@ -1373,6 +1419,7 @@ def rerun_start_goal(selected_agent_id: str) -> str: capability_route=capability_route, fine_grained=fine_grained, include_command_pack_detail=False, + display_name=str(command_pack.get("display_name") or display_name or ""), ) fresh_registration = identity_selection_gate.get("fresh_agent_registration") @@ -1638,6 +1685,7 @@ def rerun_start_goal(selected_agent_id: str) -> str: available_capabilities=available_capabilities, capability_route=capability_route, fine_grained=fine_grained, + display_name=str(command_pack.get("display_name") or display_name or ""), ) selected_command_pack = ( command_pack diff --git a/loopx/cli_commands/bootstrap_connect.py b/loopx/cli_commands/bootstrap_connect.py index 1d854acf4..96ccb34b2 100644 --- a/loopx/cli_commands/bootstrap_connect.py +++ b/loopx/cli_commands/bootstrap_connect.py @@ -29,6 +29,13 @@ def register_bootstrap_connect_command(subparsers: argparse._SubParsersAction) - help="Create a new forked goal id instead of reusing an existing global goal route.", ) bootstrap_parser.add_argument("--objective", default=DEFAULT_OBJECTIVE, help="Initial goal objective.") + bootstrap_parser.add_argument( + "--display-name", + help=( + "Public display title for the goal. When omitted, no title is written " + "and the dashboard projection falls back to the project name." + ), + ) bootstrap_parser.add_argument("--domain", default=DEFAULT_DOMAIN, help="Goal domain label.") bootstrap_parser.add_argument("--role", choices=["controller", "subagent"], default="controller") bootstrap_parser.add_argument("--parent-goal-id", help="Parent goal id when --role subagent.") @@ -195,6 +202,7 @@ def handle_bootstrap_connect_command( runtime_root=runtime_root, goal_id=goal_id, objective=args.objective, + display_name=args.display_name, domain=args.domain, role=args.role, parent_goal_id=args.parent_goal_id, diff --git a/loopx/cli_commands/start_goal.py b/loopx/cli_commands/start_goal.py index 7c894b9d7..01bbde484 100644 --- a/loopx/cli_commands/start_goal.py +++ b/loopx/cli_commands/start_goal.py @@ -10,6 +10,7 @@ START_GOAL_HOST_SURFACES, build_start_goal_guided_packet, build_start_goal_host_surface_selection_packet, + derive_goal_display_name, render_start_goal_guided_markdown, ) from ._host_thread import current_host_thread_id @@ -51,6 +52,13 @@ def register_start_goal_command(subparsers: argparse._SubParsersAction) -> None: ) start_goal_parser.add_argument("--project", default=".", help="Project directory to inspect.") start_goal_parser.add_argument("--goal-id", help="Goal id. Defaults to -goal.") + start_goal_parser.add_argument( + "--display-name", + help=( + "Public display title for the goal. When omitted, a public-safe title " + "is derived from the goal text; the project name only remains as a fallback." + ), + ) start_goal_parser.add_argument( "--agent-id", help=( @@ -217,6 +225,7 @@ def handle_start_goal_command( } print_payload(payload, args.format, render_start_goal_guided_markdown) return 2 + display_name = args.display_name or derive_goal_display_name(goal_text) if not args.host_surface: payload = build_start_goal_host_surface_selection_packet( project=Path(args.project), @@ -230,6 +239,7 @@ def handle_start_goal_command( capability_route=capability_route, fine_grained=fine_grained, include_command_pack_detail=bool(args.include_command_pack_detail), + display_name=display_name, ) print_payload(payload, args.format, render_start_goal_guided_markdown) return 0 @@ -246,6 +256,7 @@ def handle_start_goal_command( capability_route=capability_route, fine_grained=fine_grained, include_command_pack_detail=bool(args.include_command_pack_detail), + display_name=display_name, ) print_payload(payload, args.format, render_start_goal_guided_markdown) return 0 From bfadfd93c9555de9d11c729ab6a66db791d953f6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=89=9B=E7=91=9E=E5=8D=9A?= <912906590@qq.com> Date: Tue, 25 Aug 2026 17:35:32 +0800 Subject: [PATCH 2/7] fix(goal): project continuation todo_delta instead of unconditional todo authoring MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit When start-goal --guided resolves to an existing agent that already owns an open, unblocked advancement todo, the guided transaction previously always appended plan_ranked_todos and write_ordered_todos, inviting duplicate or overlapping todos during an identity takeover. Inspect the durable active-state todo board for the resolved agent and project an explicit todo_delta (reuse_existing vs add_new): reuse_existing replaces the planning and todo addition steps with a continue_existing_frontier step that continues the agent's runnable todo; add_new keeps the existing planner-order path. - loopx/bootstrap_command_pack.py: add existing_runnable_todo_for_agent (parses active-state agent todos and returns the first open, unblocked todo claimed by the resolved agent), compute todo_delta in build_loopx_bootstrap_command_pack, expose it in the payload and compact projection, and make the guided ordered_steps conditional on it - examples/bootstrap-command-pack-smoke.py: cover reuse_existing frontier continuation, add_new fresh planning, and done-only (no runnable frontier) Closes #3586 Signed-off-by: 牛瑞博 <912906590@qq.com> --- examples/bootstrap-command-pack-smoke.py | 88 +++++++++++++ loopx/bootstrap_command_pack.py | 157 ++++++++++++++++++----- 2 files changed, 210 insertions(+), 35 deletions(-) diff --git a/examples/bootstrap-command-pack-smoke.py b/examples/bootstrap-command-pack-smoke.py index 682dae650..d7889cfe5 100644 --- a/examples/bootstrap-command-pack-smoke.py +++ b/examples/bootstrap-command-pack-smoke.py @@ -797,6 +797,93 @@ def test_start_goal_guided_derives_display_name_from_goal_text() -> None: assert rejected["command_pack"].get("display_name") is None +def test_start_goal_guided_reuses_existing_agent_runnable_frontier() -> None: + with tempfile.TemporaryDirectory() as tmp: + project = Path(tmp) / "reuse-frontier-project" + project.mkdir() + state_file = project / ".codex" / "goals" / "reuse-goal" / "ACTIVE_GOAL_STATE.md" + state_file.parent.mkdir(parents=True, exist_ok=True) + state_file.write_text( + "# Active Goal State\n\n## Agent Todo\n\n" + "- [ ] Repair the scheduler state path coverage regression\n" + " \n", + encoding="utf-8", + ) + registry = project / ".loopx" / "registry.json" + registry.parent.mkdir(parents=True, exist_ok=True) + registry.write_text( + json.dumps( + { + "schema_version": "0.1", + "goals": [ + { + "id": "reuse-goal", + "status": "active", + "repo": str(project), + "state_file": str(state_file.relative_to(project)), + "coordination": { + "agent_model": "peer_v1", + "registered_agents": ["existing-agent"], + }, + } + ], + }, + indent=2, + ) + + "\n", + encoding="utf-8", + ) + + reused = run_json( + "start-goal", + "--guided", + "--project", + str(project), + "--goal-id", + "reuse-goal", + "--agent-id", + "existing-agent", + "--host-surface", + "codex-app-ssh", + "--goal-text", + "take over the existing agent and continue its current work", + ) + assert reused["command_pack"].get("todo_delta") == "reuse_existing" + assert reused["command_pack"].get("existing_runnable_todo_id") == "todo_existing_frontier" + reused_step_ids = [step["id"] for step in reused["guided_transaction"]["ordered_steps"]] + assert "plan_ranked_todos" not in reused_step_ids, reused_step_ids + assert "write_ordered_todos" not in reused_step_ids, reused_step_ids + assert "continue_existing_frontier" in reused_step_ids, reused_step_ids + frontier_step = next( + step + for step in reused["guided_transaction"]["ordered_steps"] + if step["id"] == "continue_existing_frontier" + ) + assert frontier_step.get("decision") == "reuse_existing" + + fresh = run_json( + "start-goal", + "--guided", + "--project", + str(project), + "--goal-id", + "reuse-goal", + "--agent-id", + "fresh-agent", + "--host-surface", + "codex-app-ssh", + "--goal-text", + "start a new auto research lane", + ) + assert fresh["command_pack"].get("todo_delta") == "add_new" + fresh_step_ids = [step["id"] for step in fresh["guided_transaction"]["ordered_steps"]] + assert "plan_ranked_todos" in fresh_step_ids, fresh_step_ids + assert "write_ordered_todos" in fresh_step_ids, fresh_step_ids + assert "continue_existing_frontier" not in fresh_step_ids, fresh_step_ids + + def main() -> int: test_missing_project_stops_before_mutation() test_goal_text_invocation_plans_ranked_todos_before_activation() @@ -806,6 +893,7 @@ def main() -> int: test_linked_git_worktree_reuses_canonical_source_registry() test_skill_slash_fallback_contract() test_start_goal_guided_derives_display_name_from_goal_text() + test_start_goal_guided_reuses_existing_agent_runnable_frontier() print("bootstrap command pack smoke passed") return 0 diff --git a/loopx/bootstrap_command_pack.py b/loopx/bootstrap_command_pack.py index fdd1420a6..26c933932 100644 --- a/loopx/bootstrap_command_pack.py +++ b/loopx/bootstrap_command_pack.py @@ -288,6 +288,8 @@ def _guided_command_pack_projection( "host_loop_activation": command_pack.get("host_loop_activation"), "safety_contract": command_pack.get("safety_contract"), "detail_command": detail_command, + "todo_delta": command_pack.get("todo_delta"), + "existing_runnable_todo_id": command_pack.get("existing_runnable_todo_id"), } projection["packet_summary"] = _build_packet_summary( projection, @@ -660,6 +662,54 @@ def derive_goal_display_name(goal_text: str | None) -> str | None: return public_safe_compact_text(goal_text, limit=132) +def existing_runnable_todo_for_agent( + *, + project: Path, + goal: dict[str, Any], + state_file: str, + agent_id: str | None, +) -> dict[str, Any] | None: + """Return one open, unblocked agent todo claimed by agent_id, if any. + + A guided existing-agent takeover should continue the agent's runnable + frontier instead of unconditionally authoring new todos. This inspects the + durable active-state todo board and returns the first open, unblocked todo + claimed by the resolved agent, or None when the agent has no runnable work + to continue (fresh goal, all todos done, or the frontier is blocked). + """ + if not agent_id: + return None + state_path = Path(state_file) + if not state_path.is_absolute(): + state_path = project / state_path + if not state_path.exists(): + return None + try: + state_text = state_path.read_text(encoding="utf-8") + except OSError: + return None + from .control_plane.todos.active_state_todo_parser import ( + parse_active_state_todos, + ) + from .control_plane.todos.contract import normalize_todo_claimed_by + + parsed = parse_active_state_todos(state_text, goal=goal) + agent_todos = parsed.get("agent_todos") + if not isinstance(agent_todos, dict): + return None + for item in agent_todos.get("items") or []: + if not isinstance(item, dict): + continue + if item.get("done"): + continue + if normalize_todo_claimed_by(item.get("claimed_by")) != agent_id: + continue + if item.get("blocking"): + continue + return item + return None + + def _goal_start_bootstrap_command( *, project: str, @@ -832,6 +882,17 @@ def build_loopx_bootstrap_command_pack( thread_binding_projection = {"status": thread_binding.get("status")} if thread_binding.get("agent_id"): thread_binding_projection["agent_id"] = thread_binding["agent_id"] + existing_runnable_todo = existing_runnable_todo_for_agent( + project=Path(resolved_project), + goal=registry_goal, + state_file=str(inspection.get("state_file") or ""), + agent_id=str(selected_agent_id) if selected_agent_id else None, + ) + todo_delta = ( + "reuse_existing" + if existing_runnable_todo + else "add_new" + ) issue_fix_commands = build_issue_fix_goal_command_templates( cli_bin=cli_bin, goal_id=resolved_goal_id, @@ -960,6 +1021,13 @@ def build_loopx_bootstrap_command_pack( "read_only": True, "goal_text": normalized_goal_text, "display_name": display_name, + "todo_delta": todo_delta, + "existing_runnable_todo_id": ( + str(existing_runnable_todo.get("todo_id")) + if isinstance(existing_runnable_todo, dict) + and existing_runnable_todo.get("todo_id") + else None + ), "project": resolved_project, "goal_id": resolved_goal_id, "agent_id": selected_agent_id, @@ -1531,41 +1599,60 @@ def rerun_start_goal(selected_agent_id: str) -> str: }, *bind_thread_steps, *fine_mode_steps, - { - "id": "plan_ranked_todos", - "kind": "model_checkpoint", - "prompt": commands.get("goal_start_plan_prompt"), - "purpose": ( - "produce one public-safe, small, verifiable checkpoint Todo; keep " - "later options as evidence-linked planning notes" - if fine_grained - else "produce concise public-safe P0/P1/P2 todos before todo writeback" - ), - }, - { - "id": "write_ordered_todos", - "kind": "operator_or_agent_actions", - "command_template": ( - f"{shell_arg(cli_bin)} todo add --goal-id " - f"{shell_arg(str(command_pack.get('goal_id') or ''))} " - "--project . " - "--role agent " - + ( - f"--claimed-by {shell_arg(str(command_pack.get('agent_id') or ''))} " - if command_pack.get("agent_id") - else "--claimed-by " - ) - + "--task-class advancement_task --action-kind " - "[--target-key ] --text '<[P0/P1/P2] ...>'" - ), - "purpose": ( - "write only the current checkpoint Todo; the existing replan path " - "qualifies any successor after completion evidence" - if fine_grained - else "write todos in planner order; capability successors preserve " - "the admitted action_kind and target_key for later quota re-entry" - ), - }, + *( + [ + { + "id": "continue_existing_frontier", + "kind": "conditional_mutation", + "todo_delta": str(command_pack.get("todo_delta") or "add_new"), + "decision": "reuse_existing", + "existing_todo_id": command_pack.get("existing_runnable_todo_id"), + "purpose": ( + "the resolved agent already owns an open, unblocked " + "advancement todo; continue that frontier instead of " + "authoring a duplicate todo" + ), + } + ] + if str(command_pack.get("todo_delta") or "add_new") == "reuse_existing" + else [ + { + "id": "plan_ranked_todos", + "kind": "model_checkpoint", + "prompt": commands.get("goal_start_plan_prompt"), + "purpose": ( + "produce one public-safe, small, verifiable checkpoint Todo; keep " + "later options as evidence-linked planning notes" + if fine_grained + else "produce concise public-safe P0/P1/P2 todos before todo writeback" + ), + }, + { + "id": "write_ordered_todos", + "kind": "operator_or_agent_actions", + "command_template": ( + f"{shell_arg(cli_bin)} todo add --goal-id " + f"{shell_arg(str(command_pack.get('goal_id') or ''))} " + "--project . " + "--role agent " + + ( + f"--claimed-by {shell_arg(str(command_pack.get('agent_id') or ''))} " + if command_pack.get("agent_id") + else "--claimed-by " + ) + + "--task-class advancement_task --action-kind " + "[--target-key ] --text '<[P0/P1/P2] ...>'" + ), + "purpose": ( + "write only the current checkpoint Todo; the existing replan path " + "qualifies any successor after completion evidence" + if fine_grained + else "write todos in planner order; capability successors preserve " + "the admitted action_kind and target_key for later quota re-entry" + ), + }, + ] + ), { "id": "refresh_state", "kind": "state_sync", From 8e25a351904749a80fb21a42318c9a3356660ab2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=89=9B=E7=91=9E=E5=8D=9A?= <912906590@qq.com> Date: Tue, 25 Aug 2026 18:46:15 +0800 Subject: [PATCH 3/7] fix(goal): avoid duplicating derived title in guided output MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: 牛瑞博 <912906590@qq.com> --- examples/bootstrap-command-pack-smoke.py | 24 ++++++++++++++++++++---- loopx/bootstrap.py | 7 +++++++ loopx/bootstrap_command_pack.py | 14 -------------- loopx/cli_commands/bootstrap_connect.py | 7 ++++--- loopx/cli_commands/start_goal.py | 3 +-- 5 files changed, 32 insertions(+), 23 deletions(-) diff --git a/examples/bootstrap-command-pack-smoke.py b/examples/bootstrap-command-pack-smoke.py index d7889cfe5..2f3804eca 100644 --- a/examples/bootstrap-command-pack-smoke.py +++ b/examples/bootstrap-command-pack-smoke.py @@ -746,11 +746,27 @@ def test_start_goal_guided_derives_display_name_from_goal_text() -> None: connect_command = str( derived["command_pack"]["commands"]["goal_start_connect_if_needed"] ) - assert "--display-name '修复 scheduler state path 覆盖问题'" in connect_command, connect_command - assert ( - derived["command_pack"].get("display_name") - == "修复 scheduler state path 覆盖问题" + assert "--display-name" not in connect_command, connect_command + assert derived["command_pack"].get("display_name") is None + + run_json( + "bootstrap", + "--project", + str(project), + "--goal-id", + "derived-display-goal", + "--objective", + "修复 scheduler state path 覆盖问题", + "--no-onboarding-scan", + "--no-global-sync", + ) + registry = json.loads( + (project / ".loopx" / "registry.json").read_text(encoding="utf-8") + ) + registry_goal = next( + goal for goal in registry["goals"] if goal["id"] == "derived-display-goal" ) + assert registry_goal.get("display_name") == "修复 scheduler state path 覆盖问题" explicit = run_json( "start-goal", diff --git a/loopx/bootstrap.py b/loopx/bootstrap.py index 2c7790e38..adacc6180 100644 --- a/loopx/bootstrap.py +++ b/loopx/bootstrap.py @@ -7,6 +7,7 @@ from typing import Any from .control_plane.runtime.time import now_local_iso +from .control_plane.runtime.public_safety import public_safe_compact_text from .control_plane.todos.active_state_editing import ( TODO_SECTION_HEADINGS, insertion_anchor, @@ -76,6 +77,12 @@ def default_goal_id(project: Path) -> str: return f"{slugify_goal_id(project.name)}-goal" +def derive_goal_display_name(goal_text: str | None) -> str | None: + """Derive a public-safe display title from user-supplied goal text.""" + + return public_safe_compact_text(goal_text, limit=132) + + def now_iso() -> str: return now_local_iso() diff --git a/loopx/bootstrap_command_pack.py b/loopx/bootstrap_command_pack.py index 26c933932..6a734d5ee 100644 --- a/loopx/bootstrap_command_pack.py +++ b/loopx/bootstrap_command_pack.py @@ -648,20 +648,6 @@ def _project_command(project: str, command: str) -> str: return "\n".join([f"cd {shell_arg(project)}", command]) -def derive_goal_display_name(goal_text: str | None) -> str | None: - """Derive a public-safe display title from goal text. - - The project name is only a fallback when no title can be derived. Goal text - is user-supplied task prose, so it is run through the public-safe compact - text boundary: whitespace is collapsed, the result is truncated, and any - local-path or credential-like surface makes the title unrevealable - (returns None) instead of leaking private material into a public goal title. - """ - from .control_plane.runtime.public_safety import public_safe_compact_text - - return public_safe_compact_text(goal_text, limit=132) - - def existing_runnable_todo_for_agent( *, project: Path, diff --git a/loopx/cli_commands/bootstrap_connect.py b/loopx/cli_commands/bootstrap_connect.py index 96ccb34b2..5816c9896 100644 --- a/loopx/cli_commands/bootstrap_connect.py +++ b/loopx/cli_commands/bootstrap_connect.py @@ -8,6 +8,7 @@ DEFAULT_DOMAIN, DEFAULT_OBJECTIVE, bootstrap_project, + derive_goal_display_name, render_bootstrap_markdown, ) PrintPayload = Callable[ @@ -32,8 +33,8 @@ def register_bootstrap_connect_command(subparsers: argparse._SubParsersAction) - bootstrap_parser.add_argument( "--display-name", help=( - "Public display title for the goal. When omitted, no title is written " - "and the dashboard projection falls back to the project name." + "Public display title for the goal. When omitted, a public-safe title is " + "derived from the objective; the project name remains the fallback." ), ) bootstrap_parser.add_argument("--domain", default=DEFAULT_DOMAIN, help="Goal domain label.") @@ -202,7 +203,7 @@ def handle_bootstrap_connect_command( runtime_root=runtime_root, goal_id=goal_id, objective=args.objective, - display_name=args.display_name, + display_name=args.display_name or derive_goal_display_name(args.objective), domain=args.domain, role=args.role, parent_goal_id=args.parent_goal_id, diff --git a/loopx/cli_commands/start_goal.py b/loopx/cli_commands/start_goal.py index 01bbde484..2b3843bb4 100644 --- a/loopx/cli_commands/start_goal.py +++ b/loopx/cli_commands/start_goal.py @@ -10,7 +10,6 @@ START_GOAL_HOST_SURFACES, build_start_goal_guided_packet, build_start_goal_host_surface_selection_packet, - derive_goal_display_name, render_start_goal_guided_markdown, ) from ._host_thread import current_host_thread_id @@ -225,7 +224,7 @@ def handle_start_goal_command( } print_payload(payload, args.format, render_start_goal_guided_markdown) return 2 - display_name = args.display_name or derive_goal_display_name(goal_text) + display_name = args.display_name if not args.host_surface: payload = build_start_goal_host_surface_selection_packet( project=Path(args.project), From df8746db728a70aa07ad5164d692a2c40e4655dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=89=9B=E7=91=9E=E5=8D=9A?= <912906590@qq.com> Date: Tue, 25 Aug 2026 19:05:54 +0800 Subject: [PATCH 4/7] refactor(goal): isolate existing agent frontier lookup MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: 牛瑞博 <912906590@qq.com> --- loopx/bootstrap_command_pack.py | 51 ++----------------- .../goals/existing_agent_frontier.py | 39 ++++++++++++++ 2 files changed, 42 insertions(+), 48 deletions(-) create mode 100644 loopx/control_plane/goals/existing_agent_frontier.py diff --git a/loopx/bootstrap_command_pack.py b/loopx/bootstrap_command_pack.py index 6a734d5ee..5e1b3014a 100644 --- a/loopx/bootstrap_command_pack.py +++ b/loopx/bootstrap_command_pack.py @@ -18,6 +18,9 @@ build_goal_start_contract, build_goal_start_prompt, ) +from .control_plane.goals.existing_agent_frontier import ( + existing_runnable_todo_for_agent, +) from .control_plane.scheduler.execution_context import ( GUIDED_START_TURN_RUNTIME_PROFILES, ) @@ -648,54 +651,6 @@ def _project_command(project: str, command: str) -> str: return "\n".join([f"cd {shell_arg(project)}", command]) -def existing_runnable_todo_for_agent( - *, - project: Path, - goal: dict[str, Any], - state_file: str, - agent_id: str | None, -) -> dict[str, Any] | None: - """Return one open, unblocked agent todo claimed by agent_id, if any. - - A guided existing-agent takeover should continue the agent's runnable - frontier instead of unconditionally authoring new todos. This inspects the - durable active-state todo board and returns the first open, unblocked todo - claimed by the resolved agent, or None when the agent has no runnable work - to continue (fresh goal, all todos done, or the frontier is blocked). - """ - if not agent_id: - return None - state_path = Path(state_file) - if not state_path.is_absolute(): - state_path = project / state_path - if not state_path.exists(): - return None - try: - state_text = state_path.read_text(encoding="utf-8") - except OSError: - return None - from .control_plane.todos.active_state_todo_parser import ( - parse_active_state_todos, - ) - from .control_plane.todos.contract import normalize_todo_claimed_by - - parsed = parse_active_state_todos(state_text, goal=goal) - agent_todos = parsed.get("agent_todos") - if not isinstance(agent_todos, dict): - return None - for item in agent_todos.get("items") or []: - if not isinstance(item, dict): - continue - if item.get("done"): - continue - if normalize_todo_claimed_by(item.get("claimed_by")) != agent_id: - continue - if item.get("blocking"): - continue - return item - return None - - def _goal_start_bootstrap_command( *, project: str, diff --git a/loopx/control_plane/goals/existing_agent_frontier.py b/loopx/control_plane/goals/existing_agent_frontier.py new file mode 100644 index 000000000..0acf5dbdb --- /dev/null +++ b/loopx/control_plane/goals/existing_agent_frontier.py @@ -0,0 +1,39 @@ +from __future__ import annotations + +from pathlib import Path +from typing import Any + +from ..todos.active_state_todo_parser import parse_active_state_todos +from ..todos.contract import normalize_todo_claimed_by + + +def existing_runnable_todo_for_agent( + *, + project: Path, + goal: dict[str, Any], + state_file: str, + agent_id: str | None, +) -> dict[str, Any] | None: + """Return one open, unblocked Todo claimed by the selected agent, if any.""" + if not agent_id: + return None + state_path = Path(state_file) + if not state_path.is_absolute(): + state_path = project / state_path + if not state_path.exists(): + return None + try: + state_text = state_path.read_text(encoding="utf-8") + except OSError: + return None + + parsed = parse_active_state_todos(state_text, goal=goal) + agent_todos = parsed.get("agent_todos") + if not isinstance(agent_todos, dict): + return None + for item in agent_todos.get("items") or []: + if not isinstance(item, dict) or item.get("done") or item.get("blocking"): + continue + if normalize_todo_claimed_by(item.get("claimed_by")) == agent_id: + return item + return None From b9fd93075c06e4841a660e3e71a297ca9116367c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=89=9B=E7=91=9E=E5=8D=9A?= <912906590@qq.com> Date: Tue, 25 Aug 2026 19:08:39 +0800 Subject: [PATCH 5/7] refactor(goal): project todo frontier steps outside command pack MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: 牛瑞博 <912906590@qq.com> --- loopx/bootstrap_command_pack.py | 59 ++--------------- .../goals/existing_agent_frontier.py | 65 +++++++++++++++++++ 2 files changed, 71 insertions(+), 53 deletions(-) diff --git a/loopx/bootstrap_command_pack.py b/loopx/bootstrap_command_pack.py index ed97614a2..4bacc1dd5 100644 --- a/loopx/bootstrap_command_pack.py +++ b/loopx/bootstrap_command_pack.py @@ -19,6 +19,7 @@ build_goal_start_prompt, ) from .control_plane.goals.existing_agent_frontier import ( + build_goal_todo_frontier_steps, existing_runnable_todo_for_agent, ) from .control_plane.scheduler.execution_context import ( @@ -1546,59 +1547,11 @@ def rerun_start_goal(selected_agent_id: str) -> str: }, *bind_thread_steps, *fine_mode_steps, - *( - [ - { - "id": "continue_existing_frontier", - "kind": "conditional_mutation", - "todo_delta": str(command_pack.get("todo_delta") or "add_new"), - "decision": "reuse_existing", - "existing_todo_id": command_pack.get("existing_runnable_todo_id"), - "purpose": ( - "the resolved agent already owns an open, unblocked " - "advancement todo; continue that frontier instead of " - "authoring a duplicate todo" - ), - } - ] - if str(command_pack.get("todo_delta") or "add_new") == "reuse_existing" - else [ - { - "id": "plan_ranked_todos", - "kind": "model_checkpoint", - "prompt": commands.get("goal_start_plan_prompt"), - "purpose": ( - "produce one public-safe, small, verifiable checkpoint Todo; keep " - "later options as evidence-linked planning notes" - if fine_grained - else "produce concise public-safe P0/P1/P2 todos before todo writeback" - ), - }, - { - "id": "write_ordered_todos", - "kind": "operator_or_agent_actions", - "command_template": ( - f"{shell_arg(cli_bin)} todo add --goal-id " - f"{shell_arg(str(command_pack.get('goal_id') or ''))} " - "--project . " - "--role agent " - + ( - f"--claimed-by {shell_arg(str(command_pack.get('agent_id') or ''))} " - if command_pack.get("agent_id") - else "--claimed-by " - ) - + "--task-class advancement_task --action-kind " - "[--target-key ] --text '<[P0/P1/P2] ...>'" - ), - "purpose": ( - "write only the current checkpoint Todo; the existing replan path " - "qualifies any successor after completion evidence" - if fine_grained - else "write todos in planner order; capability successors preserve " - "the admitted action_kind and target_key for later quota re-entry" - ), - }, - ] + *build_goal_todo_frontier_steps( + command_pack=command_pack, + commands=commands, + cli_bin=cli_bin, + fine_grained=fine_grained, ), { "id": "refresh_state", diff --git a/loopx/control_plane/goals/existing_agent_frontier.py b/loopx/control_plane/goals/existing_agent_frontier.py index 0acf5dbdb..afe17b9a6 100644 --- a/loopx/control_plane/goals/existing_agent_frontier.py +++ b/loopx/control_plane/goals/existing_agent_frontier.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import Any +from ...project_prompt import shell_arg from ..todos.active_state_todo_parser import parse_active_state_todos from ..todos.contract import normalize_todo_claimed_by @@ -37,3 +38,67 @@ def existing_runnable_todo_for_agent( if normalize_todo_claimed_by(item.get("claimed_by")) == agent_id: return item return None + + +def build_goal_todo_frontier_steps( + *, + command_pack: dict[str, Any], + commands: dict[str, Any], + cli_bin: str, + fine_grained: bool, +) -> list[dict[str, Any]]: + """Project guided steps that either reuse or create the agent frontier.""" + todo_delta = str(command_pack.get("todo_delta") or "add_new") + if todo_delta == "reuse_existing": + return [ + { + "id": "continue_existing_frontier", + "kind": "conditional_mutation", + "todo_delta": todo_delta, + "decision": "reuse_existing", + "existing_todo_id": command_pack.get("existing_runnable_todo_id"), + "purpose": ( + "the resolved agent already owns an open, unblocked " + "advancement todo; continue that frontier instead of " + "authoring a duplicate todo" + ), + } + ] + + claimed_by = ( + f"--claimed-by {shell_arg(str(command_pack.get('agent_id') or ''))} " + if command_pack.get("agent_id") + else "--claimed-by " + ) + return [ + { + "id": "plan_ranked_todos", + "kind": "model_checkpoint", + "prompt": commands.get("goal_start_plan_prompt"), + "purpose": ( + "produce one public-safe, small, verifiable checkpoint Todo; keep " + "later options as evidence-linked planning notes" + if fine_grained + else "produce concise public-safe P0/P1/P2 todos before todo writeback" + ), + }, + { + "id": "write_ordered_todos", + "kind": "operator_or_agent_actions", + "command_template": ( + f"{shell_arg(cli_bin)} todo add --goal-id " + f"{shell_arg(str(command_pack.get('goal_id') or ''))} " + "--project . --role agent " + f"{claimed_by}" + "--task-class advancement_task --action-kind " + "[--target-key ] --text '<[P0/P1/P2] ...>'" + ), + "purpose": ( + "write only the current checkpoint Todo; the existing replan path " + "qualifies any successor after completion evidence" + if fine_grained + else "write todos in planner order; capability successors preserve " + "the admitted action_kind and target_key for later quota re-entry" + ), + }, + ] From 3a6f975eca0e7eb334e8043e3ce180223ea10cec Mon Sep 17 00:00:00 2001 From: cmyk-labs <263870852+cmyk-labs@users.noreply.github.com> Date: Thu, 27 Aug 2026 18:14:20 +0800 Subject: [PATCH 6/7] fix(goal): skip blocked frontier and scan full todo list on reuse Address PR #3603 review (now-ing): - existing_runnable_todo_for_agent filtered on item.get("blocking"), a key the active-state todo parser never emits; blocked todos are modeled as status=blocked, so a blocked todo claimed by the agent could be projected as the runnable frontier. Filter on normalize_todo_status(item.get("status")) == TODO_STATUS_BLOCKED so the docstring promise (one open, unblocked todo) holds. - The frontier lookup inherited the parser default MAX_STATUS_TODOS_PER_ROLE item cap, so a claimed todo beyond the cap silently degraded reuse to add_new. Pass item_limit=None to scan the full agent todo list. - Attach add_new_command_template plus a bounded escape-hatch note to the reuse_existing frontier step so the executing model still has an in-packet path to author a replacement todo when the frontier turns terminal or stale at execution time. Extend examples/bootstrap-command-pack-smoke.py with regressions for the blocked-frontier skip, reuse beyond the default item cap, and the escape-hatch template on the reuse step. Validation: - examples/bootstrap-command-pack-smoke.py (pass; new regressions fail against the pre-fix code) - loopx check on changed files: 0 errors, 0 warnings - tests/test_slash_command_install.py + tests/test_pi_goal_mode.py: 52 passed - tests/control_plane -k "todo or goal": 721 passed Signed-off-by: cmyk-labs <263870852+cmyk-labs@users.noreply.github.com> --- examples/bootstrap-command-pack-smoke.py | 108 ++++++++++++++++++ .../goals/existing_agent_frontier.py | 47 +++++--- 2 files changed, 139 insertions(+), 16 deletions(-) diff --git a/examples/bootstrap-command-pack-smoke.py b/examples/bootstrap-command-pack-smoke.py index 2f3804eca..635fb3e3e 100644 --- a/examples/bootstrap-command-pack-smoke.py +++ b/examples/bootstrap-command-pack-smoke.py @@ -878,6 +878,10 @@ def test_start_goal_guided_reuses_existing_agent_runnable_frontier() -> None: if step["id"] == "continue_existing_frontier" ) assert frontier_step.get("decision") == "reuse_existing" + escape_template = str(frontier_step.get("add_new_command_template") or "") + assert " todo add " in escape_template, escape_template + assert "todo_existing_frontier" not in escape_template, escape_template + assert frontier_step.get("add_new_escape_hatch"), frontier_step fresh = run_json( "start-goal", @@ -900,6 +904,108 @@ def test_start_goal_guided_reuses_existing_agent_runnable_frontier() -> None: assert "continue_existing_frontier" not in fresh_step_ids, fresh_step_ids +def _write_reuse_frontier_project(project: Path, agent_todo_section: str) -> None: + project.mkdir(parents=True) + state_file = project / ".codex" / "goals" / "reuse-goal" / "ACTIVE_GOAL_STATE.md" + state_file.parent.mkdir(parents=True, exist_ok=True) + state_file.write_text( + "# Active Goal State\n\n## Agent Todo\n\n" + agent_todo_section, + encoding="utf-8", + ) + registry = project / ".loopx" / "registry.json" + registry.parent.mkdir(parents=True, exist_ok=True) + registry.write_text( + json.dumps( + { + "schema_version": "0.1", + "goals": [ + { + "id": "reuse-goal", + "status": "active", + "repo": str(project), + "state_file": str(state_file.relative_to(project)), + "coordination": { + "agent_model": "peer_v1", + "registered_agents": ["existing-agent"], + }, + } + ], + }, + indent=2, + ) + + "\n", + encoding="utf-8", + ) + + +def _run_guided_takeover(project: Path, agent_id: str) -> dict[str, object]: + return run_json( + "start-goal", + "--guided", + "--project", + str(project), + "--goal-id", + "reuse-goal", + "--agent-id", + agent_id, + "--host-surface", + "codex-app-ssh", + "--goal-text", + "take over the existing agent and continue its current work", + ) + + +def test_start_goal_guided_skips_blocked_agent_frontier() -> None: + with tempfile.TemporaryDirectory() as tmp: + project = Path(tmp) / "blocked-frontier-project" + _write_reuse_frontier_project( + project, + "- [ ] Wait on the upstream quota window before continuing\n" + " \n", + ) + + blocked = _run_guided_takeover(project, "existing-agent") + assert blocked["command_pack"].get("todo_delta") == "add_new" + assert blocked["command_pack"].get("existing_runnable_todo_id") is None + blocked_step_ids = [ + step["id"] for step in blocked["guided_transaction"]["ordered_steps"] + ] + assert "continue_existing_frontier" not in blocked_step_ids, blocked_step_ids + assert "plan_ranked_todos" in blocked_step_ids, blocked_step_ids + assert "write_ordered_todos" in blocked_step_ids, blocked_step_ids + + +def test_start_goal_guided_reuse_scans_beyond_default_item_cap() -> None: + with tempfile.TemporaryDirectory() as tmp: + project = Path(tmp) / "capped-frontier-project" + filler_todos = "".join( + f"- [ ] Filler open todo {index} owned by another lane\n" + " \n" + for index in range(1, 14) + ) + _write_reuse_frontier_project( + project, + filler_todos + + "- [ ] Continue the frontier beyond the status todo cap\n" + " \n", + ) + + deep = _run_guided_takeover(project, "existing-agent") + assert deep["command_pack"].get("todo_delta") == "reuse_existing" + assert deep["command_pack"].get("existing_runnable_todo_id") == "todo_deep_frontier" + deep_step_ids = [ + step["id"] for step in deep["guided_transaction"]["ordered_steps"] + ] + assert "continue_existing_frontier" in deep_step_ids, deep_step_ids + + def main() -> int: test_missing_project_stops_before_mutation() test_goal_text_invocation_plans_ranked_todos_before_activation() @@ -910,6 +1016,8 @@ def main() -> int: test_skill_slash_fallback_contract() test_start_goal_guided_derives_display_name_from_goal_text() test_start_goal_guided_reuses_existing_agent_runnable_frontier() + test_start_goal_guided_skips_blocked_agent_frontier() + test_start_goal_guided_reuse_scans_beyond_default_item_cap() print("bootstrap command pack smoke passed") return 0 diff --git a/loopx/control_plane/goals/existing_agent_frontier.py b/loopx/control_plane/goals/existing_agent_frontier.py index afe17b9a6..b73ae5580 100644 --- a/loopx/control_plane/goals/existing_agent_frontier.py +++ b/loopx/control_plane/goals/existing_agent_frontier.py @@ -5,7 +5,11 @@ from ...project_prompt import shell_arg from ..todos.active_state_todo_parser import parse_active_state_todos -from ..todos.contract import normalize_todo_claimed_by +from ..todos.contract import ( + TODO_STATUS_BLOCKED, + normalize_todo_claimed_by, + normalize_todo_status, +) def existing_runnable_todo_for_agent( @@ -28,12 +32,14 @@ def existing_runnable_todo_for_agent( except OSError: return None - parsed = parse_active_state_todos(state_text, goal=goal) + parsed = parse_active_state_todos(state_text, goal=goal, item_limit=None) agent_todos = parsed.get("agent_todos") if not isinstance(agent_todos, dict): return None for item in agent_todos.get("items") or []: - if not isinstance(item, dict) or item.get("done") or item.get("blocking"): + if not isinstance(item, dict) or item.get("done"): + continue + if normalize_todo_status(item.get("status")) == TODO_STATUS_BLOCKED: continue if normalize_todo_claimed_by(item.get("claimed_by")) == agent_id: return item @@ -49,6 +55,19 @@ def build_goal_todo_frontier_steps( ) -> list[dict[str, Any]]: """Project guided steps that either reuse or create the agent frontier.""" todo_delta = str(command_pack.get("todo_delta") or "add_new") + claimed_by = ( + f"--claimed-by {shell_arg(str(command_pack.get('agent_id') or ''))} " + if command_pack.get("agent_id") + else "--claimed-by " + ) + add_new_command_template = ( + f"{shell_arg(cli_bin)} todo add --goal-id " + f"{shell_arg(str(command_pack.get('goal_id') or ''))} " + "--project . --role agent " + f"{claimed_by}" + "--task-class advancement_task --action-kind " + "[--target-key ] --text '<[P0/P1/P2] ...>'" + ) if todo_delta == "reuse_existing": return [ { @@ -62,14 +81,17 @@ def build_goal_todo_frontier_steps( "advancement todo; continue that frontier instead of " "authoring a duplicate todo" ), + "add_new_command_template": add_new_command_template, + "add_new_escape_hatch": ( + "bounded fallback only: if the frontier todo is already " + "terminal or no longer covers the requested continuation " + "when the step executes, author one replacement advancement " + "todo with add_new_command_template instead of continuing " + "the stale frontier" + ), } ] - claimed_by = ( - f"--claimed-by {shell_arg(str(command_pack.get('agent_id') or ''))} " - if command_pack.get("agent_id") - else "--claimed-by " - ) return [ { "id": "plan_ranked_todos", @@ -85,14 +107,7 @@ def build_goal_todo_frontier_steps( { "id": "write_ordered_todos", "kind": "operator_or_agent_actions", - "command_template": ( - f"{shell_arg(cli_bin)} todo add --goal-id " - f"{shell_arg(str(command_pack.get('goal_id') or ''))} " - "--project . --role agent " - f"{claimed_by}" - "--task-class advancement_task --action-kind " - "[--target-key ] --text '<[P0/P1/P2] ...>'" - ), + "command_template": add_new_command_template, "purpose": ( "write only the current checkpoint Todo; the existing replan path " "qualifies any successor after completion evidence" From 0bd831c86667950af60c5fca9fbf24df1142547a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=89=9B=E7=91=9E=E5=8D=9A?= <912906590@qq.com> Date: Mon, 31 Aug 2026 12:17:20 +0800 Subject: [PATCH 7/7] fix(goal): exclude monitor todos from reusable frontier MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: 牛瑞博 <912906590@qq.com> --- examples/bootstrap-command-pack-smoke.py | 23 ++++++ loopx/bootstrap_command_pack.py | 78 +++---------------- .../goals/existing_agent_frontier.py | 24 ++++++ loopx/project_prompt.py | 36 +++++++++ 4 files changed, 94 insertions(+), 67 deletions(-) diff --git a/examples/bootstrap-command-pack-smoke.py b/examples/bootstrap-command-pack-smoke.py index 635fb3e3e..e402aa4fa 100644 --- a/examples/bootstrap-command-pack-smoke.py +++ b/examples/bootstrap-command-pack-smoke.py @@ -977,6 +977,28 @@ def test_start_goal_guided_skips_blocked_agent_frontier() -> None: assert "write_ordered_todos" in blocked_step_ids, blocked_step_ids +def test_start_goal_guided_skips_continuous_monitor_frontier() -> None: + with tempfile.TemporaryDirectory() as tmp: + project = Path(tmp) / "monitor-frontier-project" + _write_reuse_frontier_project( + project, + "- [ ] Observe the upstream release window\n" + " \n", + ) + + monitor = _run_guided_takeover(project, "existing-agent") + assert monitor["command_pack"].get("todo_delta") == "add_new" + assert monitor["command_pack"].get("existing_runnable_todo_id") is None + monitor_step_ids = [ + step["id"] for step in monitor["guided_transaction"]["ordered_steps"] + ] + assert "continue_existing_frontier" not in monitor_step_ids, monitor_step_ids + assert "plan_ranked_todos" in monitor_step_ids, monitor_step_ids + assert "write_ordered_todos" in monitor_step_ids, monitor_step_ids + + def test_start_goal_guided_reuse_scans_beyond_default_item_cap() -> None: with tempfile.TemporaryDirectory() as tmp: project = Path(tmp) / "capped-frontier-project" @@ -1017,6 +1039,7 @@ def main() -> int: test_start_goal_guided_derives_display_name_from_goal_text() test_start_goal_guided_reuses_existing_agent_runnable_frontier() test_start_goal_guided_skips_blocked_agent_frontier() + test_start_goal_guided_skips_continuous_monitor_frontier() test_start_goal_guided_reuse_scans_beyond_default_item_cap() print("bootstrap command pack smoke passed") return 0 diff --git a/loopx/bootstrap_command_pack.py b/loopx/bootstrap_command_pack.py index d6606fa32..0174335c7 100644 --- a/loopx/bootstrap_command_pack.py +++ b/loopx/bootstrap_command_pack.py @@ -14,14 +14,11 @@ build_issue_fix_goal_command_templates, ) from .control_plane.effect_program import effect_program_from_ordered_steps +from .control_plane.goals import existing_agent_frontier from .control_plane.goals.start_contract import ( build_goal_start_contract, build_goal_start_prompt, ) -from .control_plane.goals.existing_agent_frontier import ( - build_goal_todo_frontier_steps, - existing_runnable_todo_for_agent, -) from .control_plane.scheduler.execution_context import ( GUIDED_START_TURN_RUNTIME_PROFILES, ) @@ -36,6 +33,8 @@ DEFAULT_HANDOFF_ADAPTER_STATUS, render_available_capability_args, render_cli_command_prefix, + render_goal_start_bootstrap_command, + render_optional_cli_arg, render_quota_guard_command, render_refresh_state_command, shell_arg, @@ -233,11 +232,7 @@ def _start_goal_command( else "" ) + f" --goal-text {shell_arg(goal_text)}" - + ( - f" --display-name {shell_arg(display_name)}" - if display_name - else "" - ) + + render_optional_cli_arg("--display-name", display_name) + (" --include-command-pack-detail" if include_command_pack_detail else "") ) @@ -388,11 +383,7 @@ def build_start_goal_host_surface_selection_packet( else "" ) + f" --goal-text {shell_arg(normalized_goal_text)}" - + ( - f" --display-name {shell_arg(display_name)}" - if display_name - else "" - ) + + render_optional_cli_arg("--display-name", display_name) + (" --include-command-pack-detail" if include_command_pack_detail else "") ) choices.append( @@ -694,36 +685,6 @@ def _project_command(project: str, command: str) -> str: return "\n".join([f"cd {shell_arg(project)}", command]) -def _goal_start_bootstrap_command( - *, - project: str, - goal_id: str, - goal_text: str | None, - cli_bin: str, - runtime_root: str | None, - fine_grained: bool, - display_name: str | None = None, -) -> str: - objective = goal_text or "" - lines = [ - f"cd {shell_arg(project)}", - f"{render_cli_command_prefix(cli_bin=cli_bin, runtime_root=runtime_root)} bootstrap \\", - " --project . \\", - f" --goal-id {shell_arg(goal_id)} \\", - f" --objective {shell_arg(objective)} \\", - f" --adapter-kind {shell_arg(DEFAULT_HANDOFF_ADAPTER_KIND)} \\", - f" --adapter-status {shell_arg(DEFAULT_HANDOFF_ADAPTER_STATUS)} \\", - " --no-onboarding-scan \\", - " --codex-app-heartbeat ask", - ] - if display_name: - lines.insert(-1, f" --display-name {shell_arg(display_name)} \\") - if fine_grained: - lines[-1] += " \\" - lines.append(" --fine-grained") - return "\n".join(lines) - - def _selected_goal_capability_route( capability_route: str | None, ) -> dict[str, Any] | None: @@ -877,17 +838,10 @@ def build_loopx_bootstrap_command_pack( thread_binding_projection = {"status": thread_binding.get("status")} if thread_binding.get("agent_id"): thread_binding_projection["agent_id"] = thread_binding["agent_id"] - existing_runnable_todo = existing_runnable_todo_for_agent( - project=Path(resolved_project), - goal=registry_goal, - state_file=str(inspection.get("state_file") or ""), + todo_frontier = existing_agent_frontier.existing_agent_frontier_projection( + project=Path(resolved_project), goal=registry_goal, inspection=inspection, agent_id=str(selected_agent_id) if selected_agent_id else None, ) - todo_delta = ( - "reuse_existing" - if existing_runnable_todo - else "add_new" - ) issue_fix_commands = build_issue_fix_goal_command_templates( cli_bin=cli_bin, goal_id=resolved_goal_id, @@ -925,7 +879,7 @@ def build_loopx_bootstrap_command_pack( runtime_root=command_runtime_root, ) status_command = _project_command(resolved_project, f"{command_prefix} status") - goal_start_bootstrap_command = _goal_start_bootstrap_command( + goal_start_bootstrap_command = render_goal_start_bootstrap_command( project=resolved_project, goal_id=resolved_goal_id, goal_text=normalized_goal_text, @@ -1013,22 +967,12 @@ def build_loopx_bootstrap_command_pack( if normalized_goal_text else "" ) - + ( - f" --display-name {shell_arg(display_name)}" - if display_name - else "" - ) + + render_optional_cli_arg("--display-name", display_name) ), "read_only": True, "goal_text": normalized_goal_text, "display_name": display_name, - "todo_delta": todo_delta, - "existing_runnable_todo_id": ( - str(existing_runnable_todo.get("todo_id")) - if isinstance(existing_runnable_todo, dict) - and existing_runnable_todo.get("todo_id") - else None - ), + **todo_frontier, "project": resolved_project, "goal_id": resolved_goal_id, "agent_id": selected_agent_id, @@ -1614,7 +1558,7 @@ def rerun_start_goal(selected_agent_id: str) -> str: }, *bind_thread_steps, *fine_mode_steps, - *build_goal_todo_frontier_steps( + *existing_agent_frontier.build_goal_todo_frontier_steps( command_pack=command_pack, commands=commands, cli_bin=cli_bin, diff --git a/loopx/control_plane/goals/existing_agent_frontier.py b/loopx/control_plane/goals/existing_agent_frontier.py index 7a2a62237..8b7b9dc01 100644 --- a/loopx/control_plane/goals/existing_agent_frontier.py +++ b/loopx/control_plane/goals/existing_agent_frontier.py @@ -7,9 +7,11 @@ from ..todos.active_state_todo_parser import parse_active_state_todos from ..todos.contract import ( TODO_STATUS_BLOCKED, + TODO_TASK_CLASS_ADVANCEMENT, normalize_todo_claimed_by, normalize_todo_status, ) +from ..todos.projection import todo_item_task_class def existing_runnable_todo_for_agent( @@ -41,11 +43,33 @@ def existing_runnable_todo_for_agent( continue if normalize_todo_status(item.get("status")) == TODO_STATUS_BLOCKED: continue + if todo_item_task_class(item) != TODO_TASK_CLASS_ADVANCEMENT: + continue if normalize_todo_claimed_by(item.get("claimed_by")) == agent_id: return item return None +def existing_agent_frontier_projection( + *, + project: Path, + goal: dict[str, Any], + inspection: dict[str, Any], + agent_id: str | None, +) -> dict[str, Any]: + todo = existing_runnable_todo_for_agent( + project=project, + goal=goal, + state_file=str(inspection.get("state_file") or ""), + agent_id=agent_id, + ) + todo_id = todo.get("todo_id") if isinstance(todo, dict) else None + return { + "todo_delta": "reuse_existing" if todo else "add_new", + "existing_runnable_todo_id": str(todo_id) if todo_id else None, + } + + def build_goal_todo_frontier_steps( *, command_pack: dict[str, Any], diff --git a/loopx/project_prompt.py b/loopx/project_prompt.py index 1528ed12c..e3f1abf7d 100644 --- a/loopx/project_prompt.py +++ b/loopx/project_prompt.py @@ -31,6 +31,12 @@ def shell_arg(value: str) -> str: return shlex.quote(value) +def render_optional_cli_arg(flag: str, value: str | None) -> str: + if not value: + return "" + return f" {flag} {shell_arg(value)}" + + def render_cli_command_prefix( *, cli_bin: str = "loopx", @@ -42,6 +48,36 @@ def render_cli_command_prefix( return prefix +def render_goal_start_bootstrap_command( + *, + project: str, + goal_id: str, + goal_text: str | None, + cli_bin: str, + runtime_root: str | None, + fine_grained: bool, + display_name: str | None = None, +) -> str: + objective = goal_text or "" + lines = [ + f"cd {shell_arg(project)}", + f"{render_cli_command_prefix(cli_bin=cli_bin, runtime_root=runtime_root)} bootstrap \\", + " --project . \\", + f" --goal-id {shell_arg(goal_id)} \\", + f" --objective {shell_arg(objective)} \\", + f" --adapter-kind {shell_arg(DEFAULT_HANDOFF_ADAPTER_KIND)} \\", + f" --adapter-status {shell_arg(DEFAULT_HANDOFF_ADAPTER_STATUS)} \\", + " --no-onboarding-scan \\", + " --codex-app-heartbeat ask", + ] + if display_name: + lines.insert(-1, f" --display-name {shell_arg(display_name)} \\") + if fine_grained: + lines[-1] += " \\" + lines.append(" --fine-grained") + return "\n".join(lines) + + def render_register_agent_command( goal_id: str, *,