Skip to content

feat(opencode): add MCP server + Agent Skill for opencode CLI - #29

Open
namana843-bit wants to merge 1 commit into
suitedaces:mainfrom
namana843-bit:opencode-mcp-skill
Open

namana843-bit wants to merge 1 commit into
suitedaces:mainfrom
namana843-bit:opencode-mcp-skill

Conversation

@namana843-bit

Copy link
Copy Markdown

Summary

Makes computer-agent (taskhomie) runnable headless from opencode CLI via MCP server + Agent Skill - no Tauri window needed. Reuses the same Rust tool surface (computer.rs, �rowser.rs, �ash.rs, �gent.rs) over MCP stdio.

What's added

1. MCP server mcp-server/ (Node, @modelcontextprotocol/sdk)

  • Tools exposed (14 total, names match Rust mirrors):
    • computer_screenshot -> ComputerControl::take_screenshot (base64 PNG, AI 1280x800, via screenshot-desktop)
    • computer_click x,y,button,double -> left_click/
      ight_click/double_click (AI coords mapped to real screen)
    • computer_drag rom_x,from_y,to_x,to_y -> left_click_drag
    • computer_type ext -> ype, computer_key combo -> key/hold_key, computer_scroll/computer_move
    • �ash_run command,timeout_ms -> BashExecutor::execute (blocked
      m -rf /, mkfs, dd if= etc, truncated 8000 chars)
    • �rowser_snapshot �erbose -> BrowserClient::take_snapshot (via CDP http://127.0.0.1:9222), �rowser_navigate url|action, �rowser_tabs -> list_pages, �rowser_click/�rowser_type stubs with fallback guidance (full a11y tree via taskhomie Background Mode)
  • mcp-server/src/index.ts stdio server, ListTools + CallTool handlers, zod validation
  • @nut/nut-js optional for mouse/keyboard (degrades gracefully, screenshots work without it)
  • Build:
    pm install && npm run build -> mcp-server/dist/index.js

2. Agent Skill skills/computer-agent/SKILL.md

  • Frontmatter
    ame: computer-agent compatibility: opencode (https://opencode.ai/docs/skills)
  • Installed via
    px skills add suitedaces/computer-agent -g -a opencode -y -> ~/.config/opencode/skills + ~/.agents/skills (opencode discovery)
  • Verified on Windows 11:
    px skills ls -g -a opencode shows computer-agent

3. Opencode config

  • opencode.json.example:
    json { "mcp": { "computer-agent": { "type": "local", "command": ["node", "mcp-server/dist/index.js"] } } }
  • Works with opencode.json:11 prior �rowsermcp example - just add second entry

4. Docs

  • README.md:24 New Use with opencode CLI section (skill install, MCP build, opencode.json snippet, prompt examples)
  • mcp-server/README.md tool table + permissions (macOS Accessibility)
  • .gitignore:5 !mcp-server/dist/ so built MCP ships in repo

Verification

`�ash

skill

npx skills add ./skills/computer-agent -g -a opencode -y
npx skills ls -g -a opencode --json | grep computer-agent

MCP

cd mcp-server && npm install && npm run build
node dist/index.js # stdio -> "computer-agent MCP server running"

in opencode, add mcp to opencode.json and prompt:

"use computer-agent to take a screenshot and click at 600,400"

`

Tauri desktop flow unchanged (
pm run tauri dev still works).

Testing

pm --prefix mcp-server run build passes (TS strict, @nut/nut-js optional)

  • Skill discovery verified on win32 (~/.agents/skills + ~/.config/opencode/skills)

Closes headless/opencode gap - lets any opencode agent (local or remote) drive the desktop without the Tauri UI.

- mcp-server: Node MCP (stdio) exposing computer_screenshot/click/drag/type/key/scroll/move, bash_run (blocked rm -rf /, mkfs etc), browser_snapshot/navigate/tabs/click/type via CDP http://127.0.0.1:9222 - mirrors src-tauri/src/computer.rs, browser.rs, bash.rs, agent.rs; AI space 1280x800
- skills/computer-agent/SKILL.md: opencode-compatible skill (name: computer-agent) installed via npx skills add suitedaces/computer-agent -g -a opencode
- opencode.json.example: mcp config for opencode
- README: new Use with opencode CLI section
- .gitignore: allow mcp-server/dist
- verified: npx skills add ./skills -g -a opencode works, MCP builds and runs via node mcp-server/dist/index.js

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 9c6b4e426f

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +19 to +21
const img = await screenshot({ format: "png" });
// img is Buffer, convert to base64
const b64 = (img as Buffer).toString("base64");

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Resize screenshots before using AI-space coordinates

When computer_screenshot runs on any display that is not exactly 1280x800, this returns the native-size screenshot while the mouse tools still interpret inputs as 1280x800 AI coordinates. A coordinate read from the returned image is then scaled a second time by mapFromAI (for example, x=960 from a 1920-wide screenshot maps to x=1440), so clicks and drags land in the wrong place for the primary workflow of screenshot-then-act. The MCP path needs to resize like the Rust ComputerControl::take_screenshot implementation or expose/use native coordinates consistently.

Useful? React with 👍 / 👎.

Comment thread mcp-server/package.json
Comment on lines +20 to +22
"optionalDependencies": {
"@nut/nut-js": "^4.0.0"
},

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Regenerate the lockfile for nut-js

Adding @nut/nut-js here without resolving it in mcp-server/package-lock.json makes clean installs fail before anything is installed: I checked npm --prefix mcp-server ci --omit=optional --ignore-scripts, and npm reports Missing: @nut/nut-js@ from lock file. Any CI or reproducible setup that uses npm ci cannot build the new MCP server until the lockfile is regenerated from this package.json.

Useful? React with 👍 / 👎.

// Use CDP Page.navigate via websocket would be ideal; use http fallback via fetch to chrome's /json/new?url
if (url) {
// open new tab via /json/new
const r = await fetch(`${CDP_HOST}/json/new?${encodeURIComponent(url)}`);

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Use PUT when opening CDP tabs

When browser_navigate is called with a URL, this fetch defaults to GET, but Chrome's remote-debugging /json/new endpoint only accepts PUT for creating a tab. In a normal Chrome --remote-debugging-port=9222 session this returns 405, so the advertised URL navigation path never opens the page; pass method: "PUT" here or drive Page.navigate over the websocket.

Useful? React with 👍 / 👎.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant