AgentStack
Browse Sign in
Browse Why AgentStack Sell Docs
Sign in
MCP unreviewed MIT Self-run

Platter

mcp-scriptsmith-platter · by hadriangateway

MCP server exposing Read, Write, Edit, Bash, Glob, Grep, and JS tools over stdio.

No reviews yet
0 installs
34 views
0.0% view→install

Install

$ agentstack add mcp-scriptsmith-platter

Open-source listing, not yet scanned by AgentStack. Follow the source repository for install instructions.

Security review

⚠ Flagged

1 finding(s); flagged for manual review. · v2.0.2-rc1 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures
  • high Destructive filesystem operation.

What it can access

  • Network access Used
  • Filesystem access No
  • Shell / process execution Used
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v2.0.2-rc1. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

View the full security report →

Reliability & compatibility

Not yet reviewed
0 installs to date
no reviews yet
3mo ago

Declared compatibility

Claude CodeClaude DesktopCursorWindsurf

Compatibility is declared by the source manifest. End-to-end runtime verification is coming, see below.

Preview Execution monitoring

We're building live execution health for every listing: tool-call success rate, median latency, uptime, and last-checked timestamps, measured, not self-reported. It isn't live yet, so we don't show numbers we can't stand behind.

How agent discovery & health will work →
Are you the author of Platter? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

platter

Your computer, served on a platter.

MCP server that exposes Read, Write, Edit, Bash, Glob, Grep, and JS tools over Stdio and StreamableHTTP transports. Built with Bun, compiles to standalone executables.

Designed to be used by browser-based (or any MCP-compatible) agents, like Hadrian, to control a computer.

Tools

| Tool | Description | |------|-------------| | read | Read file contents with pagination (offset/limit). Detects image files (JPEG, PNG, GIF, WebP) and returns metadata. Truncates text to 2000 lines or 50KB. | | write | Create or overwrite files. Auto-creates parent directories. | | edit | Find-and-replace with exact or fuzzy matching (normalizes smart quotes, dashes, and Unicode whitespace). Requires a unique match, or use replace_all for every occurrence (exact matches only). Returns a unified diff. | | bash | Execute shell commands with optional timeout. Output truncated to last 2000 lines or 50KB. | | glob | Fast file pattern matching. Returns up to 500 paths matching a glob pattern (e.g. **/*.ts). | | grep | Search file contents using ripgrep. Supports regex, file filtering, context lines, and multiple output modes. Requires rg to be installed. | | js | Evaluate JavaScript/TypeScript in a persistent Node.js vm context. State persists across calls within a session. Supports await, console.log, and loading packages from unpkg.com via await load("package"). Auto-returns the last expression. Not a security sandbox — see [Security](#security) below. |

Quick start

From a release binary

Download the latest binary for your platform from Releases, or grab it with curl:

# Download (replace the filename for your platform)
# Available: platter-linux-x64, platter-linux-arm64, platter-darwin-x64, platter-darwin-arm64
curl -fsSL https://github.com/hadriangateway/platter/releases/latest/download/platter-linux-x64 -o platter
chmod +x platter

./platter          # stdio mode
./platter -t http  # HTTP mode on :3100

Docker

docker run --rm -i ghcr.io/hadriangateway/platter                                   # stdio mode
docker run --rm -p 3100:3100 ghcr.io/hadriangateway/platter -t http --host 0.0.0.0  # HTTP mode

See [Docker](#docker-1) below for mounting paths, networking, installing extra software, and building custom images.

From source

bun install
bun run dev      # run directly from TypeScript
bun run compile  # build standalone binary for current platform

Usage

platter v1.x.x

Your computer, served on a platter.

Usage: platter [options]

Options:
  -t, --transport    Transport mode (default: stdio)
      --tray                     Run the HTTP server with a Linux system tray
                                 (implies --transport=http, persists state
                                 across restarts in ~/.config/platter)
  -p, --port             HTTP port (default: 3100)
      --host            HTTP bind address (default: 127.0.0.1)
      --cwd                Working directory for tools (default: current directory)
      --cors-origin      Allowed CORS origin (default: *)
      --auth               Auth mode: oauth, bearer, jwks, none (default: oauth)
      --auth-token        Bearer token for HTTP auth (auto-generated if omitted)
      --tls-cert           TLS certificate file (PEM) — enables HTTPS
      --tls-key            TLS private key file (PEM)

External JWKS / OIDC (--auth jwks — verify tokens from an external IdP):
      --oauth-issuer        Issuer URL; OIDC-discovers the JWKS endpoint
      --jwks-url            Explicit JWKS endpoint (overrides discovery)
      --oauth-audience      Expected token audience (strongly recommended)
      --jwks-scope-grants        Map tools: token scopes to tool access
                                 (fail closed: a token with no tools:
                                 scopes is granted no tools)

Process management:
      --max-processes    Max concurrent bash processes per session (default: 20)
      --max-sessions     Max concurrent HTTP sessions (default: unlimited)

Restrictions:
      --tools              Comma-separated tools to enable (default: all)
                                 Valid: read, write, edit, bash, glob, grep, js
      --allow-path         Restrict read/write/edit/glob/grep to this path (repeatable)
                                 Does not restrict bash or js
      --allow-command     Allow bash commands matching this pattern (repeatable)
                                 Pattern must match the entire command string
                                 Applies to bash only; does not restrict js

Sandbox (applies to bash only; the js tool is never sandboxed):
      --sandbox                  Use just-bash sandbox instead of native bash
      --sandbox-fs         Filesystem backend: memory, overlay, readwrite (default: readwrite)
      --sandbox-allow-url   Allow network access to URL prefix (repeatable)

  -h, --help                     Show this help message
  -v, --version                  Show version number

Restrictions

You can limit which tools are registered, which filesystem paths file tools can access, and which commands the bash tool can execute.

Tool selection

Only register specific tools. Unregistered tools are completely hidden from MCP clients:

platter --tools read,glob,grep    # read-only server
platter --tools read,write,edit   # no bash/search/js
Path restrictions

Restrict file-accessing tools (read, write, edit, glob, grep) to one or more directory trees. Paths are resolved to absolute form and symlinks are resolved via realpath to prevent escaping:

platter --allow-path /home/user/project
platter --allow-path /home/user/project --allow-path /tmp
Command restrictions

Only allow bash commands whose entire command string matches at least one regex pattern:

platter --allow-command "git( .*)?"                             # git only
platter --allow-command "git( .*)?" --allow-command "npm( .*)?" # git or npm
platter --allow-command "ls( .*)?" --allow-command "cat .*"     # ls or cat

Patterns are anchored: --allow-command "git( .*)?" compiles to ^(?:git( .*)?)$, so git status matches but rm -rf / && git status does not.

Combined example
# Locked-down: read-only tools, scoped to one directory
platter --tools read,glob,grep --allow-path /home/user/project

# Full tools, but bash restricted to git/npm, files restricted to project
platter --allow-path ./my-project --allow-command "git( .*)?" --allow-command "npm( .*)?"

Active restrictions are logged to stderr at startup.

Authentication

Controlled by --auth :

| Mode | Description | |------|-------------| | oauth (default) | OAuth 2.1 Authorization Code + PKCE, with a static bearer token as fallback | | bearer | Static bearer token only | | jwks | Resource-server mode: verifies JWT access tokens issued by an external OAuth/OIDC issuer (Auth0, Keycloak, Okta, Entra) via JWKS | | none | No authentication |

OAuth 2.1 (--auth oauth)

MCP clients that support RFC 9728 (Protected Resource Metadata) can discover platter's OAuth endpoints automatically and authenticate without manual token copying.

The flow:

  1. Client discovers /.well-known/oauth-authorization-server and /.well-known/oauth-protected-resource/mcp
  2. Client registers via POST /register (RFC 7591 dynamic client registration)
  3. Client initiates Authorization Code + PKCE flow via /authorize
  4. A confirmation code is displayed out-of-band (printed to stderr, or shown as a desktop notification in tray mode)
  5. User sees a consent page, enters the confirmation code, selects which tools to grant, and approves or denies the request
  6. Client exchanges the authorization code for tokens at /token
  7. Subsequent requests use Authorization: Bearer

The confirmation code proves that the person approving the request has access to the platter process — a remote attacker who can reach the consent page cannot approve without it. Codes are single-use and expire after 5 minutes, with a maximum of 5 attempts.

Access tokens expire after 1 hour and can be refreshed. Client registrations are persisted to ~/.config/platter/clients.json. A static bearer token is also accepted as a fallback for clients that don't support OAuth.

Bearer token (--auth bearer)

A random bearer token is generated at startup and printed to stderr (or stored in the system keyring in tray mode). Every request must include Authorization: Bearer . You can provide your own:

platter -t http --auth bearer --auth-token my-secret-token
No authentication (--auth none)

Disable authentication entirely (e.g. behind a reverse proxy that handles auth):

platter -t http --auth none
External JWKS / OIDC (--auth jwks)

In jwks mode platter acts as a pure resource server: it does not mint its own tokens. Instead it verifies JWT access tokens issued by an external OAuth/OIDC authorization server (Auth0, Keycloak, Okta, Microsoft Entra) — validating the signature against the issuer's JWKS, plus the iss, aud, and exp claims. This lets you put platter behind your existing IdP without a reverse proxy.

# Auth0 (root issuer)
platter -t http --auth jwks \
  --oauth-issuer https://YOUR_TENANT.auth0.com/ \
  --oauth-audience https://platter.example.com/mcp

# Keycloak (realm issuer)
platter -t http --auth jwks \
  --oauth-issuer https://kc.example.com/realms/myrealm \
  --oauth-audience platter-api

# Skip discovery / point at a JWKS endpoint directly
platter -t http --auth jwks \
  --jwks-url https://idp.example.com/.well-known/jwks.json \
  --oauth-audience platter-api

Audience validation (strongly recommended). Set --oauth-audience to the API identifier configured in your IdP. If you omit it, platter accepts any valid token from the issuer — including tokens minted for a different resource server (a confused-deputy risk). platter prints a warning at startup when audience validation is disabled.

Discovery. With --oauth-issuer, platter fetches the issuer's /.well-known/openid-configuration (falling back to /.well-known/oauth-authorization-server) at startup to find the jwks_uri and re-advertise the authorization server to RFC 9728-capable MCP clients (at /.well-known/oauth-protected-resource/mcp). Pass --jwks-url to skip discovery, or if the IdP isn't reachable at startup. If discovery fails but --jwks-url is set, token verification still works — only the RFC 9728 auto-advertisement is skipped.

Authorization (what a token can do). By default a verified token gets admin-level access, bounded only by the operator's CLI restrictions (--tools, --allow-path, --allow-command, --sandbox) — the IdP controls who gets in, the CLI flags control what they can do. Pass --jwks-scope-grants to additionally honor tools: scopes in the token (e.g. tools:read tools:bash), which further narrow the granted tools (they can only narrow, never widen the operator's ceiling). The scope claim and Entra-style scp claim are both supported. In this mode access is fail closed: a token carrying no tools:* scope is granted no tools at all, so a token must explicitly request the tools it needs.

No static fallback. Unlike oauth mode, jwks mode accepts only externally-issued JWTs — --auth-token is rejected.

> Note: MCP_DANGEROUSLY_ALLOW_INSECURE_ISSUER_URL is unrelated to this mode. It only concerns platter serving its own issuer over http in --auth oauth mode. An external https issuer needs no such flag. If you point --auth jwks at a plain-http issuer (e.g. a localhost Keycloak), platter warns and skips RFC 9728 metadata advertisement, but token verification still works.

TLS (HTTPS)

To serve over HTTPS, provide a PEM-encoded certificate and private key:

platter -t http --tls-cert cert.pem --tls-key key.pem

Both --tls-cert and --tls-key are required together. When provided, the server listens over HTTPS instead of plain HTTP.

To generate a self-signed certificate for development or trusted internal use:

openssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 365 -nodes -subj '/CN=myserver'
platter -t http --tls-cert cert.pem --tls-key key.pem

Stdio mode

For use with Claude Desktop, Cursor, and other MCP clients that spawn a subprocess:

{
  "mcpServers": {
    "platter": {
      "command": "/path/to/platter"
    }
  }
}

HTTP mode (StreamableHTTP)

For browser-based agents and remote connections:

platter -t http -p 3100

The server exposes a single endpoint at /mcp that handles:

  • POST /mcp - JSON-RPC messages (initialize, tool calls)
  • GET /mcp - SSE notification stream
  • DELETE /mcp - session teardown

CORS is enabled for all origins by default (reflects the request Origin). To restrict to a specific origin:

platter -t http --cors-origin https://myapp.example.com

Sessions are managed via the Mcp-Session-Id header per the StreamableHTTP spec.

The server validates the Host header to prevent DNS rebinding attacks. When --cors-origin is set, the Origin header is also validated server-side (not just via CORS response headers).

Tray mode (Linux)

Run platter as a persistent background service with a system tray icon:

platter --tray

This implies --transport=http and adds:

  • System tray icon via DBus (StatusNotifierItem protocol), compatible with KDE, GNOME (with AppIndicator extension), and other desktop environments.
  • Persistent configuration in ~/.config/platter/config.json — auth token, enabled tools, port, host, and working directory survive restarts.
  • Dynamic tool toggling — enable or disable individual tools at runtime from the tray menu. Changes are persisted and take effect immediately.
  • Auth token management — copy the server URL or auth token to clipboard, or regenerate the token. Tokens are stored in the system keyring when available, falling back to the config file.
  • Server controls — start, stop, and restart the HTTP server from the tray menu.
Linux installer

The linux/install.sh script performs a user-level install (no sudo required):

./linux/install.sh                  # install
./linux/install.sh --uninstall      # remove

This installs:

  • ~/.local/bin/platter — the binary
  • ~/.local/share/applications/platter.desktop — desktop launcher entry
  • ~/.local/share/icons/hicolor/scalable/apps/platter.svg — application icon
  • ~/.config/systemd/user/platter.service — systemd user unit for autostart

Security

Network (HTTP mode)

  • TLS (HTTPS) - optional transport encryption via --tls-cert and --tls-key. Uses Node.js https module with PEM-encoded certificate and key files.
  • OAuth 2.1 + PKCE (--auth oauth, default) - MCP clients authenticate via Authorization Code flow with PKCE (RFC 7636). Supports dynamic client registration (RFC 7591) and token revocation (RFC 7009).
  • External JWKS / OIDC (--auth jwks) - resource-server mode: platter verifies JWT access tokens from an external issuer (Auth0, Keycloak, Okta, Entra) against the issuer's JWKS, validating signature, iss, aud, and exp. Asymmetric algorithms only (alg: none and

Source & license

This open-source MCP server is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet, be the first.

Versions

  • v2.0.2-rc1 Imported from the upstream source.