feat: add Grok Build CLI as a built-in agent - #103
Open
Shxiao101 wants to merge 14 commits into
Open
Conversation
Register grok as a first-class CLI agent with native TOML MCP inject (project .grok/config.toml, HTTP + bearer), Windows launchers that find %USERPROFILE%\.grok\bin, identity mapping to base grok, official grok.com favicon avatar, and tests for the launch/inject path.
Stop silently trusting Grok project folders. Keep the instance token in AGENTCHATTR_MCP_TOKEN instead of writing it into project .grok/config.toml. Use an explicit grok_toml inject mode so generic settings_file stays format-neutral. Document that Grok launchers are Windows-only.
Merge mcp_servers.agentchattr via tomlkit so spaced/quoted table headers replace instead of duplicating. Invalid existing files raise instead of being overwritten. Trust coverage is a launch-path behavior check; remove the Unix-launcher absence test.
Avoid a shared config.toml.tmp so concurrent Grok instances cannot FileNotFoundError on replace. Drop the leftover deleted-trust-helper call from the launch behavior test.
Reuse the existing settings_file path for Grok. mcp_settings_format is json by default and grok_toml for Grok; unknown formats error. Instance tokens stay in AGENTCHATTR_MCP_TOKEN. Document Windows-only adapter limits.
Reject explicit empty/false format instead of coercing to JSON. Barrier the concurrent unique-temp test so a shared config.toml.tmp fails reliably.
Drop the extra grok.svg request and .avatar-fill CSS. Keep tomlkit in requirements.txt because grok_toml merge lives in shared wrapper.py.
If mcp_servers is present but not a TOML table, raise ValueError and leave the file unchanged. Only create a table when the field is missing.
Every built-in agent ships both launchers; Grok was Windows-only. The wrapper's grok_toml inject already works under the Mac/Linux tmux path, so add start_grok.sh / start_grok_yolo.sh (mirroring start_qwen.sh, with a grok pre-flight check) and drop the Windows-only wording from README.md and config.toml. Also document Grok in the Manual MCP registration section and add its color to the chat_set_hat context.
Mirror 5403338 (start_antigravity.sh) for Grok: the installer puts the binary in $GROK_BIN_DIR (default ~/.grok/bin) and wires it into PATH via the shell profile, so a launcher run from a non-login shell — or one opened before the profile was re-sourced — reports 'grok not found' even though the CLI is installed. Best-effort prepend the resolved install dir when grok actually lives there, skipping a dir already on PATH; the pre-flight check still catches a truly missing CLI.
The Grok avatar filled the whole circle with the favicon's dark field, which needed overflow: hidden on .avatar and .agent-name-avatar — the only global-rendering change in the branch. Kilo (#f7f677, the same light-color problem) needs no container change: a static dark glyph on the brand-colored circle. Give Grok the same treatment: drop the favicon's background tile, flip the glyph paths to #050505, remove the full-bleed inline style so .avatar svg sizing applies, and revert both overflow: hidden additions. Cache-bust chat.js and style.css.
Follow-up to the kilo-style revert: on the dark UI, grok's #e5e5e5 brand circle reads as a plain white avatar, and the bare glyph rendered ~22% small (it spans 400/512 of the favicon viewBox). Draw the favicon properly instead: the SVG carries its own #050505 disc (r=256 inscribed in the viewBox, square corners transparent) sized inline to fill the avatar circle, so the shared overflow: hidden is still not needed. The glyph group scales 0.84 to keep the slash tips (283 units from center untransformed) inside the disc. Cache-bust chat.js.
…olor style.css is byte-identical to main again after the overflow revert, so ?v=255 was diff noise — back to main's v=251; chat.js 268 -> 273 is the only legitimate bump left. Also make the Grok avatar comment state that the dark disc intentionally paints over the agent-color container: #e5e5e5 remains visible only in the sender name, pill, and @mentions.
# Conflicts: # requirements.txt # static/index.html
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds Grok Build (xAI's
grokCLI) as a built-in agent, following the same pattern as the CodeBuddy / Copilot / Antigravity additions:config.tomlentry, built-in wrapper defaults, brand avatar, identity mapping, README coverage, launchers for both platforms, and tests.Grok is a config-format adapter on the existing
settings_fileinject path — not a new agent lifecycle. It reads MCP servers from the project's.grok/config.toml(native TOML, not JSON) and authenticates throughbearer_token_env_var, so no live token is ever written to the config file.Why
tomlkit(new runtime dependency).grok/config.tomlis a user-owned file that may already hold their other Grok settings, usually with comments. The adapter must merge an[mcp_servers.agentchattr]block into that file without damaging the rest:tomllib(3.11+) is read-only — it can parse TOML but cannot serialize it, so it cannot perform the merge-and-write.tomllibparse) would drop comments, reorder keys, or append a duplicate table when the file already contains anmcp_serverssection.tomlkitround-trips the document (comments, whitespace, and dotted/quoted table headers survive). The write path is defensive: invalid TOML is refused rather than treated as empty, a present-but-non-tablemcp_serversis refused rather than replaced, the dump is re-parsed and validated before replacing the original, and the write goes through a unique temp file. It is imported at module scope inwrapper.pyon every platform, so it is a global dependency inrequirements.txt(documented in the README's dependency section).What's included
config.toml—[agents.grok]block with install commands for both platformswrapper.py—_BUILTIN_DEFAULTS["grok"](mcp_settings_format = "grok_toml"),_write_grok_mcp_tomlmerge helper,AGENTCHATTR_MCP_TOKENenv-var authstatic/chat.js— Grok avatar from the official favicon: self-clipped dark disc + light glyph, inline-sized to the avatar circle (no shared CSS changes; the disc intentionally covers the brand-color container —#e5e5e5remains the pill/mention/name accent)mcp_bridge.py— identity mapping + Grok color in thechat_set_hatcolor contextwindows/start_grok.bat/start_grok_yolo.bat(CRLF, PATH hardening for%USERPROFILE%\.grok\bin) andmacos-linux/start_grok.sh/start_grok_yolo.sh(LF, 100755, PATH hardening for$GROK_BIN_DIR/~/.grok/binin the5403338style, pre-flight check with the officialinstall.shhint)@grokmentions in both quickstarts, Grok adapter notes, Manual MCP registration entry, dependency notetests/test_wrapper_mcp_config.py(+331) andtests/test_identity_contract.py(+89) covering merge semantics, invalid-TOML refusal, non-tablemcp_serversrefusal, and temp-file handlingTesting
python -m unittest discover -s tests— 100 tests, all greengit diff --checkclean;.batlaunchers are CRLF,.shlaunchers are LF with the executable bit sethttps://x.ai/cli/install.sh(bash installer, darwin/linux targets,BIN_DIR="${GROK_BIN_DIR:-$HOME/.grok/bin}") and the PowerShell installer for the launcher hintsstart_qwen.sh/start_antigravity.sh, and thegrok_tomlinject lives in the shared wrapper path, but no live macOS/Linux run was performed