Skip to content

Add --command/--arg/--env flags to connect stdio servers without a config file #163

@jirispilka

Description

@jirispilka

Problem

mcpc is useful for developing MCP servers. The loop is: change code, rebuild, mcpc @stdio restart, run tools-list or tools-call, check the result. Faster and more scriptable than going through a full client like Claude Desktop or Cursor.

Right now this loop needs a config file:

mcpc connect ./.mcp.json:stdio @stdio

Fine for one stable setup. During feature work you often want to change what gets spawned:

  • different tool sets to test
  • two variants in parallel without maintaining two config entries

Every variant means editing a JSON file. In sandboxed or agent-supervised setups, writing a file often triggers an approval.

The transport already accepts {command, args, env} directly (createTransportFromConfig in src/core/transports.ts:141). There's just no CLI path to it without a file.

Proposal

Add flags to mcpc connect:

mcpc connect --command <binary> [--arg <value>...] [--env KEY=VAL...] @session

Example:

mcpc connect --command node --arg dist/stdio.js --env APIFY_TOKEN=xxx @stdio
mcpc @stdio tools-list

Rules

  1. Argv form only. --command is the binary, --arg is repeatable. No shell string, no --shell, no --eval.
  2. No ${VAR} substitution in flag values. The shell already expands $VAR before mcpc sees it.
  3. --command cannot be combined with a URL server arg, --header, --profile, or --x402.
  4. If @session is omitted, derive it from the binary basename (e.g. dist/stdio.js@stdio).
  5. Print Launching: <command> <args...> on stderr at connect time. Already logged at debug in transports.ts:49 — promote to info for inline invocations.

Session reuse

For the --command path only: compare the new ServerConfig to the stored SessionData.server.

  • Same name, same {command, args, env}, bridge live → reuse.
  • Same name, different config → stop the old bridge, spawn a new one.

Today's lookup is name-only (sessions.ts:253-282). This is a small semantic change, scoped to inline connects. HTTP and config-file paths are unchanged.

Security

mcpc already spawns arbitrary processes from config files. This feature is a CLI shortcut to the same ServerConfig shape. No new attack surface.

  • Shell injection: not possible. Argv form, no shell string.
  • ${VAR} env exfil: not possible. Config file substitutes ${VAR} (config.ts:147); flag values don't.
  • Social engineering ("run this mcpc command"): same risk as today. The user trusts the command they type.

Peer tools accept inline command+args for the same reason:

  • npx @modelcontextprotocol/inspector node dist/stdio.js
  • claude mcp add <name> -- node dist/stdio.js
  • Cursor, Windsurf CLIs

Complexity

Two files.

Change File ~LOC
Add --command/--arg/--env options, mutual-exclusivity checks src/cli/index.ts (connect command) ~20
Build ServerConfig from flags, skip parseServerArg src/cli/index.ts action handler ~15
Config-diff check on session reuse (scoped) src/cli/commands/sessions.ts ~15
Session-name auto-gen from binary basename src/cli/commands/sessions.ts ~5
Help text, README examples src/cli/index.ts, README.md ~30
Tests test/ ~100

No changes to transports, bridge, session storage schema, reconnection, or auth.

Out of scope

  • Applying the config-diff check to HTTP or config-file paths. Defensible as a separate PR, but behavior change for existing users.
  • Stdin-config (echo '{...}' | mcpc connect -). Same use case, worse ergonomics.
  • Any shell-string variant of --command.

Open questions

  • Should the spawn echo be always on, or suppressible with --quiet?
  • If --command derives @stdio and an existing @stdio was created from a different path, fall back to a numeric suffix or error out?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions