mirror of
https://github.com/github/spec-kit.git
synced 2026-08-03 06:26:30 +08:00
feat(integrations): add Grok Build skills-based integration (#3535)
* feat(integrations): add Grok Build skills-based integration Add first-class support for xAI Grok Build via SkillsIntegration, installing speckit skills under .grok/skills and wiring init/invocation/catalog surfaces. Assisted-by: Grok Build (model: grok-4, supervised) * test+docs: address Copilot review on Grok multi-install and next steps Assert init next-steps guidance for Grok (.grok/skills, /speckit-*) and clarify that multi-install safety is path/manifest isolation, not agent-context defaults such as shared AGENTS.md. * fix(integrations): Grok headless --always-approve and isolation paths Document Grok multi-install isolation as .grok/skills and .grok/rules. Override build_exec_args to pass --always-approve so non-interactive dispatch is not blocked at tool permission gates. * docs(integrations): list only managed .grok/skills for Grok isolation Multi-install isolation documents Spec Kit-managed paths; Grok only writes .grok/skills, so drop the read-only .grok/rules entry. * fix(integrations): always-slash Grok hooks and refresh catalog date Move grok to ALWAYS_SLASH_AGENTS so hooks never emit /speckit.plan when ai_skills is missing/false. Update slash-format tests, persist ai_skills on init, and bump catalog updated_at for the Grok entry. --------- Co-authored-by: Nate Chadwick <1232206+natechadwick@users.noreply.github.com> Co-authored-by: test <test@example.com>
This commit is contained in:
@@ -12,7 +12,7 @@ from __future__ import annotations
|
||||
DOLLAR_SKILLS_AGENTS: frozenset[str] = frozenset({"codex", "zcode"})
|
||||
|
||||
# Agents that always render /speckit-<name>, regardless of ai_skills.
|
||||
ALWAYS_SLASH_AGENTS: frozenset[str] = frozenset({"devin", "trae", "zed"})
|
||||
ALWAYS_SLASH_AGENTS: frozenset[str] = frozenset({"devin", "grok", "trae", "zed"})
|
||||
|
||||
# Agents that render /speckit-<name> only when ai_skills is enabled.
|
||||
CONDITIONAL_SLASH_AGENTS: frozenset[str] = frozenset(
|
||||
|
||||
@@ -701,6 +701,7 @@ def register(app: typer.Typer) -> None:
|
||||
copilot_skill_mode = selected_ai == "copilot" and _is_skills_integration
|
||||
devin_skill_mode = selected_ai == "devin"
|
||||
zed_skill_mode = selected_ai == "zed" and _is_skills_integration
|
||||
grok_skill_mode = selected_ai == "grok" and _is_skills_integration
|
||||
cline_skill_mode = selected_ai == "cline"
|
||||
native_skill_mode = (
|
||||
codex_skill_mode
|
||||
@@ -713,6 +714,7 @@ def register(app: typer.Typer) -> None:
|
||||
or copilot_skill_mode
|
||||
or devin_skill_mode
|
||||
or zed_skill_mode
|
||||
or grok_skill_mode
|
||||
)
|
||||
|
||||
if codex_skill_mode:
|
||||
@@ -745,6 +747,11 @@ def register(app: typer.Typer) -> None:
|
||||
f"{step_num}. Start Zed in this project directory; spec-kit skills were installed to [cyan].agents/skills[/cyan]"
|
||||
)
|
||||
step_num += 1
|
||||
if grok_skill_mode:
|
||||
steps_lines.append(
|
||||
f"{step_num}. Start Grok Build in this project directory; spec-kit skills were installed to [cyan].grok/skills[/cyan]"
|
||||
)
|
||||
step_num += 1
|
||||
usage_label = "skills" if native_skill_mode else "slash commands"
|
||||
|
||||
from .._invocation_style import (
|
||||
|
||||
@@ -63,6 +63,7 @@ def _register_builtins() -> None:
|
||||
from .gemini import GeminiIntegration
|
||||
from .generic import GenericIntegration
|
||||
from .goose import GooseIntegration
|
||||
from .grok import GrokIntegration
|
||||
from .hermes import HermesIntegration
|
||||
from .junie import JunieIntegration
|
||||
from .kilocode import KilocodeIntegration
|
||||
@@ -99,6 +100,7 @@ def _register_builtins() -> None:
|
||||
_register(GeminiIntegration())
|
||||
_register(GenericIntegration())
|
||||
_register(GooseIntegration())
|
||||
_register(GrokIntegration())
|
||||
_register(HermesIntegration())
|
||||
_register(JunieIntegration())
|
||||
_register(KilocodeIntegration())
|
||||
|
||||
60
src/specify_cli/integrations/grok/__init__.py
Normal file
60
src/specify_cli/integrations/grok/__init__.py
Normal file
@@ -0,0 +1,60 @@
|
||||
"""Grok Build integration — skills-based agent.
|
||||
|
||||
Grok Build discovers project skills from ``.grok/skills/speckit-<name>/SKILL.md``
|
||||
(and also scans ``.agents/skills/``). Spec Kit installs into the native
|
||||
``.grok/skills`` tree so skills take highest local priority.
|
||||
"""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from ..base import SkillsIntegration
|
||||
|
||||
|
||||
class GrokIntegration(SkillsIntegration):
|
||||
"""Integration for xAI Grok Build CLI."""
|
||||
|
||||
key = "grok"
|
||||
config = {
|
||||
"name": "Grok Build",
|
||||
"folder": ".grok/",
|
||||
"commands_subdir": "skills",
|
||||
"install_url": "https://docs.x.ai/build/overview",
|
||||
"requires_cli": True,
|
||||
}
|
||||
registrar_config = {
|
||||
"dir": ".grok/skills",
|
||||
"format": "markdown",
|
||||
"args": "$ARGUMENTS",
|
||||
"extension": "/SKILL.md",
|
||||
}
|
||||
multi_install_safe = True
|
||||
|
||||
def build_exec_args(
|
||||
self,
|
||||
prompt: str,
|
||||
*,
|
||||
model: str | None = None,
|
||||
output_json: bool = True,
|
||||
) -> list[str] | None:
|
||||
"""Build CLI arguments for non-interactive ``grok`` execution.
|
||||
|
||||
Mandatory headless flag:
|
||||
|
||||
* ``--always-approve`` — auto-approve tool executions so workflow
|
||||
dispatch and ``dispatch_command()`` are not blocked at permission
|
||||
gates (same role as Cursor's ``--force`` / Copilot's ``--yolo``).
|
||||
"""
|
||||
if not self.config or not self.config.get("requires_cli"):
|
||||
return None
|
||||
args = [
|
||||
self._resolve_executable(),
|
||||
"-p",
|
||||
prompt,
|
||||
"--always-approve",
|
||||
]
|
||||
self._apply_extra_args_env_var(args)
|
||||
if model:
|
||||
args.extend(["--model", model])
|
||||
if output_json:
|
||||
args.extend(["--output-format", "json"])
|
||||
return args
|
||||
Reference in New Issue
Block a user