TermCraft SSH

SSH for AI agents through a native Mac app. You set per host what the agent may do, and production always asks.

Documentation

TermCraft MCP

You decide what agents can touch.

TermCraft is a native SSH client for macOS 26 and later, available in the Mac App Store. It has a built-in MCP server, so Claude Code, Codex, Cursor, VS Code and Claude Desktop can work with the hosts you saved in TermCraft. For each host you choose whether agents can't see it, have to ask first, or may run commands on their own. Commands on production hosts and commands that look destructive always wait for you, and approving them takes Touch ID or your Mac password. Every tool call lands in an activity log on your Mac.

This repository holds the setup guide, a Claude Code plugin with a skill, and the metadata that MCP directories need. There is no app code in it. The files here are MIT-licensed; the TermCraft app itself is proprietary.

How it works

flowchart LR
    A["AI agent<br/>Claude Code, Codex, Cursor, ..."] -- "HTTP to 127.0.0.1:47823<br/>with bearer token" --> S["MCP server<br/>inside TermCraft"]
    S --> P{"Host access level<br/>and pause switch"}
    P -- "approval needed" --> U["Approval card in TermCraft<br/>Touch ID for production<br/>and destructive commands"]
    P -- "Full access" --> C["SSH connection<br/>keys from Keychain or Secure Enclave"]
    U -- "approved" --> C
    C --> H[("Your host")]
    S -. "every call" .-> L["Activity log<br/>stays on this Mac"]
    S -- "exit code, stdout, stderr" --> A

The agent's client sends requests to TermCraft over HTTP on 127.0.0.1. TermCraft checks the host's access level and asks you when the rules say so. Then it opens the SSH connection itself, with keys from your Keychain or Secure Enclave, and returns the command's output to the agent. The connection and the keys stay inside TermCraft.

Access control

The server is off until you switch it on in Settings › AI Agents. It listens only on 127.0.0.1, port 47823 by default (you can change the port). Every request needs the access token, 256 random bits kept in the Keychain. If you generate a new token, every connected agent loses access immediately. Requests with a foreign Origin or Host header get 403, so web pages open in your browser can't reach the server.

Each host has one of three levels:

LevelWhat agents can do
No accessNothing. The host is invisible to every tool. Hosts you add or import start here.
With approvalAgents can propose commands. Each command runs only after you approve it in TermCraft.
Full accessCommands run without asking. They are still logged.

Even at Full access, TermCraft always asks first for:

  • any command on a host whose environment is set to Production
  • commands caught by the destructive-command check, for example rm -rf, mkfs, dd of=, shutdown, DROP TABLE, kubectl delete, terraform destroy or git push --force
  • deleting a host, and changing a host's address, port, user, key or environment (if you let agents change the library at all)

Production needs your fingerprint

To approve anything in that list, you confirm with Touch ID or your Mac password. The approval card shows the client's name, the host, the command and the one-sentence reason the agent gave.

Other controls

  • Allow for 10 minutes: for a normal command you can let the same client run more commands on the same host without asking for 10 minutes. TermCraft doesn't offer this for production hosts or destructive commands, and destructive commands still ask while a grant is active.
  • Timeout: if you don't answer an approval within two minutes, TermCraft treats it as denied.
  • Pause: AI Agents › Pause AI Agents (⌥⌘.) blocks every tool call, denies pending approvals and ends all 10-minute grants. The server keeps running, so agents get an error that says they are paused.
  • Library changes: a separate setting (Not allowed, With approval, Allowed; With approval by default) decides whether agents may create and change hosts and snippets and generate keys. Deleting a host always asks.
  • Retargeting: when a host's address, port, user or key changes, TermCraft sets the host back to With approval, deletes its stored password and ends its 10-minute grants.
  • Your terminal: after you approve or deny a command, TermCraft prints the command and up to 20 lines of its output, or the denial, above the prompt of an open session to that host. These lines are only shown on your Mac and are never sent to the host.
  • Activity log: TermCraft logs every tool call with time, client name, tool, host, command, outcome, exit code, duration and whether you approved it. The log stays on this Mac, is never synced and can be exported as CSV.

Where the design has limits

  • The destructive-command check is a heuristic. It removes quotes before matching and covers common forms, but it can miss a command. Use With approval for hosts where any mistake matters.
  • Client names come from the clients themselves. Anyone who has the token is trusted equally, and 10-minute grants are tied to a host and a client name.

What agents can see and what they can't

Agents only see hosts that are not set to No access. For those hosts they can read:

  • name, address, port, user, group, environment, access level, and whether the host logs in with a password or a key
  • with get_host: port forwards, startup command, whether agent forwarding is on, time of the last connection, and the name of the jump host if that jump host is shared as well
  • every snippet (name, command, notes) and every group name
  • SSH keys that no host uses or that a shared host uses: name, type, fingerprint, public key, storage, and whether the key works on this Mac
  • the result of each command they run: exit code, stdout and stderr (up to 256 KB each), and duration

Agents never receive:

  • passwords, private keys, key passphrases or the access token
  • host notes
  • hosts set to No access, or keys that only those hosts use. If a connection fails on a jump host without agent access, the agent gets a generic error.

Agents can't change access levels, set passwords or trust a host key. Agent connections only reach hosts whose host key you trusted yourself in TermCraft.

Anything a command prints reaches the agent. If an agent runs cat .env and you allow it, the agent reads the file. Snippets and startup commands are visible too, so keep secrets out of them. Your agent client usually sends tool results on to its model provider.

Tools

Kind is the MCP annotation TermCraft sends with each tool (readOnlyHint, destructiveHint).

ToolKindWhat it doesWhen TermCraft asks you
list_hostsread-onlyLists the hosts shared with agents, filtered by query or group. Without Pro it adds a note when other hosts are inactivenever
get_hostread-onlyShows one host with port forwards, jump host, startup command and whether agent forwarding is onnever
list_groupsread-onlyLists host groupsnever
list_snippetsread-onlyLists saved snippets with command and notesnever
list_keysread-onlyLists SSH keys with type, fingerprint, public key and the shared hosts that use themnever
run_commanddestructiveRuns a non-interactive command and returns exit code, stdout, stderr and duration. Takes an optional reason and timeout_seconds (default 60, maximum 600)With approval hosts; always for production hosts and destructive commands
run_snippetdestructiveRuns a saved snippet, with an optional reasonsame as run_command
create_hostwritesAdds a host. It starts at With approval (without Pro at No access, when another host already has agent access), and agents can't give it a passwordLibrary changes setting
update_hostwritesChanges name, address, port, user, key or environmentLibrary changes setting; always for address, port, user, key and environment
delete_hostdestructiveDeletes a hostalways, with Touch ID
create_snippetwritesSaves a snippetLibrary changes setting
generate_keywritesCreates an Ed25519, ECDSA (P-256, P-384) or RSA 4096 key in TermCraft and returns the public keyLibrary changes setting
open_sessionwritesOpens a terminal tab for you. Works only for hosts whose host key you confirmedWith approval hosts and production hosts

Results come back as structuredContent and as a text block. Errors the agent can act on, such as an unknown host, a validation problem, a denial or an SSH failure, are tool results with isError: true.

Setup

1. Turn on the server in TermCraft

  1. Open Settings (⌘,) › AI Agents and turn on Allow agent access.
  2. Copy the access token. The same page shows copy-ready snippets for the clients below, with your port and token already filled in.
  3. On the Agent Access page, set the hosts you want to share to With approval or Full access. All other hosts stay at No access.

The free version gives agents access to one host. Pro, a one-time purchase, removes that limit.

To check that the server is running:

curl -s -o /dev/null -w "%{http_code}\n" http://127.0.0.1:47823/mcp

401 means the server is running and wants a token. 000 means nothing is listening, so the server is off or uses another port.

In the examples below, replace YOUR_TOKEN with your token and 47823 with your port if you changed it.

Claude Code

claude mcp add --transport http --scope user termcraft http://127.0.0.1:47823/mcp --header "Authorization: Bearer YOUR_TOKEN"

With --scope user, TermCraft is available in all your projects. Leave the option out to add it to the current project only.

Claude Code plugin

The plugin sets up the same connection and adds a skill that tells the agent how to work with TermCraft: list hosts first, give a reason with each command, wait for approval, and leave secrets alone.

/plugin marketplace add marlonlng/termcraft-mcp
/plugin install termcraft@termcraft-mcp

Claude Code asks for the server URL (the default is http://127.0.0.1:47823/mcp) and the access token. It keeps the token in your system's secure credential store, not in settings.json. If you already added TermCraft with claude mcp add, remove that entry so the server isn't connected twice.

After you generate a new token in TermCraft, copy it and run:

printf '{"access_token":"%s"}' "$(pbpaste)" | claude plugin configure termcraft@termcraft-mcp --values-stdin

Only Claude Code connects to TermCraft through the plugin. On claude.ai and in Cowork, the plugin loads the skill only.

Claude Desktop

Claude Desktop connects through mcp-remote, which needs Node.js. Add this to ~/Library/Application Support/Claude/claude_desktop_config.json and restart Claude Desktop:

{
  "mcpServers": {
    "termcraft": {
      "command": "npx",
      "args": ["-y", "mcp-remote", "http://127.0.0.1:47823/mcp", "--header", "Authorization: Bearer YOUR_TOKEN"]
    }
  }
}

Cursor

Add TermCraft to Cursor

The button installs the entry with the placeholder YOUR_TOKEN. Afterwards, open Cursor's MCP settings, edit the termcraft entry and paste your token. To set it up by hand, add this to ~/.cursor/mcp.json:

{
  "mcpServers": {
    "termcraft": {
      "url": "http://127.0.0.1:47823/mcp",
      "headers": { "Authorization": "Bearer YOUR_TOKEN" }
    }
  }
}

VS Code

Add this to .vscode/mcp.json. VS Code asks for the token when the server starts for the first time, so the token doesn't end up in a file you might commit.

{
  "inputs": [
    {
      "type": "promptString",
      "id": "termcraft-token",
      "description": "TermCraft access token",
      "password": true
    }
  ],
  "servers": {
    "termcraft": {
      "type": "http",
      "url": "http://127.0.0.1:47823/mcp",
      "headers": { "Authorization": "Bearer ${input:termcraft-token}" }
    }
  }
}

Codex CLI

Add this to ~/.codex/config.toml:

[mcp_servers.termcraft]
url = "http://127.0.0.1:47823/mcp"
http_headers = { "Authorization" = "Bearer YOUR_TOKEN" }
tool_timeout_sec = 300

By default, Codex stops waiting for a tool after 60 seconds. An approval can take up to two minutes, which is why the example raises tool_timeout_sec.

Other clients

Any client that supports Streamable HTTP and custom headers works. TermCraft speaks the stateless MCP revision 2026-07-28 and the initialize-based revisions 2025-03-26, 2025-06-18 and 2025-11-25. If your client gives up on tool calls after a fixed time, allow at least two minutes so you have time to approve.

FAQ

Why is the app closed source?

TermCraft is a commercial app by one independent developer, Marlon Lange, and its source code is not public. This repository is the public part. It describes what the MCP server does in enough detail that you can compare it with what you observe: lsof -nP -iTCP:47823 -sTCP:LISTEN shows the server bound to 127.0.0.1 only, a request without a token gets 401, and the activity log lists every call an agent made.

Why does the server only listen on localhost?

Your keys and your approvals are on your Mac, so the server runs there as well. Other devices on your network can't reach it, and the Origin and Host checks block web pages in your browser. The agent therefore has to run on the same Mac. Cloud agents such as claude.ai on the web can't connect, and MCP registries that require a public HTTPS address can't list TermCraft as a remote server.

Does anything leave my Mac?

TermCraft connects only to the hosts you add and, if you turn on sync, to your private iCloud database. It has no analytics and no server of its own, and the MCP server only answers requests from this Mac. What an agent receives (host details, command output) goes to its client, which usually sends it on to its model provider under that provider's terms.

What is free and what is Pro?

TermCraft is free, with every feature, including agent access for one host. Pro is a one-time in-app purchase for 5,99 € / $5.99 and unlocks agent access for any number of hosts. There is no subscription and no account.

Privacy

TermCraft collects no personal data and contains no analytics, tracking or ads. Your library is stored encrypted on your Mac and, if you turn on sync, end-to-end encrypted in your private iCloud database. Passwords and private keys stay in the macOS Keychain and sync only through iCloud Keychain. The activity log never leaves the Mac. Full privacy policy: https://termcraft.app/app-privacy/

The Claude Code plugin in this repository runs no scripts and downloads nothing. It connects Claude Code to the server URL you enter (by default http://127.0.0.1:47823/mcp) and sends your access token only there.

Reporting security issues

Please report vulnerabilities privately to marlonlange@live.de and don't open public issues for them. Use the issue tracker of this repository for problems with the setup guide, the plugin or the skill.

License

The files in this repository are released under the MIT License. The TermCraft app is proprietary software, and all rights are reserved.