mirror of
https://github.com/github/spec-kit.git
synced 2026-07-05 21:49:47 +08:00
fix: show 'forge' binary name in user-facing messages for forgecode
Addresses Copilot PR feedback: Users should see the actual executable name 'forge' in status and error messages, not the agent key 'forgecode'. Changes: - Added 'cli_binary' field to forgecode AGENT_CONFIG (set to 'forge') - Updated check_tool() to accept optional display_key parameter - Updated check_tool() to use cli_binary from AGENT_CONFIG when available - Updated check() command to display cli_binary in StepTracker - Updated init() error message to show cli_binary instead of agent key UX improvements: - 'specify check' now shows: '● forge (available/not found)' - 'specify init --ai forgecode' error shows: 'forge not found' (instead of confusing 'forgecode not found') This makes it clear to users that they need to install the 'forge' binary, even though they selected the 'forgecode' agent.
This commit is contained in:
@@ -308,6 +308,7 @@ AGENT_CONFIG = {
|
||||
"commands_subdir": "commands",
|
||||
"install_url": "https://forgecode.dev/docs/",
|
||||
"requires_cli": True,
|
||||
"cli_binary": "forge", # The actual executable users must install
|
||||
},
|
||||
"generic": {
|
||||
"name": "Generic (bring your own agent)",
|
||||
@@ -603,16 +604,20 @@ def run_command(cmd: list[str], check_return: bool = True, capture: bool = False
|
||||
raise
|
||||
return None
|
||||
|
||||
def check_tool(tool: str, tracker: StepTracker = None) -> bool:
|
||||
def check_tool(tool: str, tracker: StepTracker = None, display_key: str = None) -> bool:
|
||||
"""Check if a tool is installed. Optionally update tracker.
|
||||
|
||||
Args:
|
||||
tool: Name of the tool to check
|
||||
tool: Name of the tool to check (agent key from AGENT_CONFIG)
|
||||
tracker: Optional StepTracker to update with results
|
||||
display_key: Optional key to use for tracker display (defaults to tool)
|
||||
|
||||
Returns:
|
||||
True if tool is found, False otherwise
|
||||
"""
|
||||
# Use display_key for tracker if provided, otherwise use tool
|
||||
tracker_key = display_key if display_key else tool
|
||||
|
||||
# Special handling for Claude CLI local installs
|
||||
# See: https://github.com/github/spec-kit/issues/123
|
||||
# See: https://github.com/github/spec-kit/issues/550
|
||||
@@ -623,24 +628,25 @@ def check_tool(tool: str, tracker: StepTracker = None) -> bool:
|
||||
if tool == "claude":
|
||||
if CLAUDE_LOCAL_PATH.is_file() or CLAUDE_NPM_LOCAL_PATH.is_file():
|
||||
if tracker:
|
||||
tracker.complete(tool, "available")
|
||||
tracker.complete(tracker_key, "available")
|
||||
return True
|
||||
|
||||
if tool == "kiro-cli":
|
||||
# Kiro currently supports both executable names. Prefer kiro-cli and
|
||||
# accept kiro as a compatibility fallback.
|
||||
found = shutil.which("kiro-cli") is not None or shutil.which("kiro") is not None
|
||||
elif tool == "forgecode":
|
||||
# The forgecode agent key is 'forgecode' but the CLI binary is 'forge'.
|
||||
found = shutil.which("forge") is not None
|
||||
else:
|
||||
found = shutil.which(tool) is not None
|
||||
# Check if this tool has a custom cli_binary name in AGENT_CONFIG
|
||||
cli_binary = tool
|
||||
if tool in AGENT_CONFIG and "cli_binary" in AGENT_CONFIG[tool]:
|
||||
cli_binary = AGENT_CONFIG[tool]["cli_binary"]
|
||||
found = shutil.which(cli_binary) is not None
|
||||
|
||||
if tracker:
|
||||
if found:
|
||||
tracker.complete(tool, "available")
|
||||
tracker.complete(tracker_key, "available")
|
||||
else:
|
||||
tracker.error(tool, "not found")
|
||||
tracker.error(tracker_key, "not found")
|
||||
|
||||
return found
|
||||
|
||||
@@ -2009,9 +2015,10 @@ def init(
|
||||
agent_config = AGENT_CONFIG.get(selected_ai)
|
||||
if agent_config and agent_config["requires_cli"]:
|
||||
install_url = agent_config["install_url"]
|
||||
cli_binary = agent_config.get("cli_binary", selected_ai)
|
||||
if not check_tool(selected_ai):
|
||||
error_panel = Panel(
|
||||
f"[cyan]{selected_ai}[/cyan] not found\n"
|
||||
f"[cyan]{cli_binary}[/cyan] not found\n"
|
||||
f"Install from: [cyan]{install_url}[/cyan]\n"
|
||||
f"{agent_config['name']} is required to continue with this project type.\n\n"
|
||||
"Tip: Use [cyan]--ignore-agent-tools[/cyan] to skip this check",
|
||||
@@ -2410,14 +2417,17 @@ def check():
|
||||
continue # Generic is not a real agent to check
|
||||
agent_name = agent_config["name"]
|
||||
requires_cli = agent_config["requires_cli"]
|
||||
|
||||
# Use cli_binary for display if specified, otherwise use agent_key
|
||||
display_key = agent_config.get("cli_binary", agent_key)
|
||||
|
||||
tracker.add(agent_key, agent_name)
|
||||
tracker.add(display_key, agent_name)
|
||||
|
||||
if requires_cli:
|
||||
agent_results[agent_key] = check_tool(agent_key, tracker=tracker)
|
||||
agent_results[agent_key] = check_tool(agent_key, tracker=tracker, display_key=display_key)
|
||||
else:
|
||||
# IDE-based agent - skip CLI check and mark as optional
|
||||
tracker.skip(agent_key, "IDE-based, no CLI check")
|
||||
tracker.skip(display_key, "IDE-based, no CLI check")
|
||||
agent_results[agent_key] = False # Don't count IDE agents as "found"
|
||||
|
||||
# Check VS Code variants (not in agent config)
|
||||
|
||||
Reference in New Issue
Block a user