Files
github-spec-kit/src/specify_cli/integrations/opencode/__init__.py
Copilot b4e5a1c3be feat: support SPECKIT_INTEGRATION_<KEY>_EXECUTABLE env var (#2743)
* Initial plan

* feat: support SPECKIT_INTEGRATION_<KEY>_EXECUTABLE env var override

Adds `IntegrationBase._resolve_executable()` which reads
`SPECKIT_INTEGRATION_<KEY>_EXECUTABLE` (hyphens→underscores, uppercased)
and falls back to `self.key` when unset or whitespace-only.

All concrete `build_exec_args()` implementations now call
`self._resolve_executable()` instead of hard-coding `self.key` or
`"agy"` as the first argv token:
- MarkdownIntegration, TomlIntegration, SkillsIntegration (base classes)
- CodexIntegration, DevinIntegration, OpencodeIntegration, HermesIntegration, AgyIntegration
- CopilotIntegration (overrides `_resolve_executable()` to fall back to
  the platform-specific `_copilot_executable()` default; also updates
  `dispatch_command()` to use `_resolve_executable()`)

Tests added to tests/integrations/test_extra_args.py covering:
- default (unset) falls back to key
- env var replaces first argv token
- whitespace-only env var is a no-op
- key hyphen→underscore normalisation
- cross-integration scoping (wrong key ignored)
- all override integrations (Codex, Devin, Opencode, Copilot)
- Copilot dispatch_command path
- EXECUTABLE and EXTRA_ARGS can be set simultaneously

See issue #2596."

* fix: complete docstring sentence in _resolve_executable

* test: generalize extra-args test comments for override coverage

* Fix stale Codex executable comment

---------

Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
2026-05-29 10:19:31 -05:00

52 lines
1.5 KiB
Python

"""opencode integration."""
from ..base import MarkdownIntegration
class OpencodeIntegration(MarkdownIntegration):
key = "opencode"
config = {
"name": "opencode",
"folder": ".opencode/",
"commands_subdir": "commands",
"install_url": "https://opencode.ai",
"requires_cli": True,
}
registrar_config = {
"dir": ".opencode/commands",
"legacy_dir": ".opencode/command",
"format": "markdown",
"args": "$ARGUMENTS",
"extension": ".md",
}
context_file = "AGENTS.md"
def build_exec_args(
self,
prompt: str,
*,
model: str | None = None,
output_json: bool = True,
) -> list[str] | None:
args = [self._resolve_executable(), "run"]
# Apply operator-injected extra args before the prompt-derived
# --command and the canonical --format/-m flags so Spec Kit's
# later appends remain authoritative under repeated-flag CLI
# semantics.
self._apply_extra_args_env_var(args)
message = prompt
if prompt.startswith("/"):
command, _, remainder = prompt[1:].partition(" ")
if command:
args.extend(["--command", command])
message = remainder
if model:
args.extend(["-m", model])
if output_json:
args.extend(["--format", "json"])
if message:
args.append(message)
return args