Connect MCP servers
Give the agent the tools of any MCP server, local over stdio or remote over HTTP with OAuth, using elelem-mcp.
At the end of this guide elelem will start your MCP servers, list their
tools next to its own, and sign in to remote servers that need OAuth. The
Model Context Protocol (MCP) is a standard way for a program to offer tools
to an agent. elelem-mcp is the client side.
Before you start #
- elelem and
elelem-builtinsinstalled, with a working provider. See your first session. - An MCP server to connect. This guide uses Playwright’s, which needs
Node.js for
npx.
1. Install and load elelem-mcp #
gem install elelem-mcpelelem does not load integration gems on its own. Add a one-line plugin file that requires it:
mkdir -p ~/.agents/plugins
echo 'require "elelem/mcp"' > ~/.agents/plugins/mcp.rbEvery session now loads elelem-mcp. To use it in one project only, put
the file in that project’s .agents/plugins/ instead.
2. Add a stdio server #
Most MCP servers are programs that talk JSON-RPC over stdin and stdout.
elelem reads servers from ~/.agents/mcp.json and .agents/mcp.json in
the current directory. Both are read and merged; when both define a server
with the same name, the project file wins.
Create .agents/mcp.json:
{
"mcpServers": {
"playwright": {
"command": "npx",
"args": ["@playwright/mcp@latest"]
}
}
}Each entry under mcpServers is a name and how to start the server:
commandis the program to run.argsis its argument list.envis an optional hash of extra environment variables. A value can refer to your environment as${NAME}.
{
"mcpServers": {
"github": {
"command": "github-mcp-server",
"args": ["stdio"],
"env": { "GITHUB_PERSONAL_ACCESS_TOKEN": "${GITHUB_TOKEN}" }
}
}
}If GITHUB_TOKEN is not set, the server does not start and elelem prints
MCP failed: Missing environment variable: GITHUB_TOKEN.
Note: Stdio entries accept only
command,args, andenv. Do not add"type": "stdio", which some other clients use.elelem-mcp0.2.0 rejects it, and the server fails withunknown keyword: :type.
3. Check the tools #
elelem chat -p ollama> /toolsMCP tools are named SERVER_TOOL: the Playwright server’s browser_navigate
becomes playwright_browser_navigate. If a name collides with a tool that
is already registered, the existing tool wins.
elelem starts the servers in the background so the prompt appears right
away. If /tools does not list them yet, wait a moment and run it again.
Servers are stopped when elelem exits.
Ask for something that needs the server:
> open https://example.com and tell me the page titleWhen a server reports an error, the model gets it as a failed tool result.
Structured results (structuredContent) are passed through as-is;
otherwise the text parts of the result are joined.
4. Add a remote server over HTTP #
For a server reachable by URL, set type to http:
{
"mcpServers": {
"docs": {
"type": "http",
"url": "https://mcp.example.com/mcp",
"headers": { "Authorization": "Bearer ${DOCS_TOKEN}" }
}
}
}headers is optional and supports ${NAME} like env does. elelem sends
JSON-RPC requests as POST to url, accepts JSON or server-sent event
replies, and keeps the Mcp-Session-Id the server returns.
5. Sign in with OAuth #
If an HTTP server answers 401 Unauthorized, elelem runs the OAuth flow
and retries once. Leave headers out for these servers.
- It reads
/.well-known/oauth-protected-resourcefrom the server’s host to find the authorization server, then that server’s/.well-known/oauth-authorization-server. - It registers itself as a client named
elelem. The authorization server must support dynamic client registration. - It opens the sign-in page with
xdg-open,open, orstart. If none works, it printsOpen this URL in your browser: .... - It waits up to 120 seconds for the redirect on
http://127.0.0.1:18273/callback, then exchanges the code using PKCE.
Tokens and the client registration are saved in
~/.config/elelem/tokens/, readable only by you. Expired tokens are
refreshed on their own; if the refresh fails, elelem asks you to sign in
again. To force a fresh sign-in, delete the files in that directory.
Limitations #
- If one server fails to start, elelem prints
MCP failed: ...and adds no MCP tools from any server for that session. - Servers load in the background. In a one-shot
elelem ask, the first model call can happen before the MCP tools are registered. - OAuth discovery uses the server’s scheme and host only. A server on a non-default port has to serve the metadata on the default port.
- Only MCP tools are supported, not resources or prompts.
What you built #
elelem now starts the servers listed in mcp.json, adds their tools to
the agent, fills secrets from your environment, and signs in to OAuth
servers in your browser.
Next steps #
- Use agent skills for instructions the model loads on demand.
- Write a tool plugin when the tool you want is 10 lines of Ruby.
- Read the elelem-mcp page.