# Agents over MCP Fluksio exposes flow tools over MCP. An agent can inspect, edit, publish, and run flows with the permissions of the user who authorizes it. ## Connect an agent Set `MCP_ENABLED=true` in the engine's environment and restart it, under `environment` in `compose.override.yml` for the Docker container. It defaults to off. Configure your MCP client with an HTTP endpoint: - Docker container: `http://localhost:8080/mcp` - Deployment: `https:///mcp` The endpoint has to be the address in `FRONTEND_HOST`, which is also the issuer of the client's tokens. It speaks the streamable HTTP transport without sessions and answers clients of the MCP revisions 2025-03-26 to 2026-07-28. The client registers, opens browser authorization, and receives an OAuth token after you approve access. The issuer and browser redirects use `FRONTEND_HOST` and `ENVIRONMENT`, so configure those for the addresses your client and browser can reach. Manage registered clients under **Admin → Agents**. Revoking a client invalidates its access. MCP uses a separate signing key at `OAUTH_PRIVATE_KEY_FILE`; rotating that key invalidates all MCP tokens. An instance connected to a [portal](../interface/portal.md) also answers through the portal's API address, for example `https://portal.example.com/i//mcp`. The portal forwards MCP and OAuth requests; the instance checks the agent's token as it does locally. Open the instance from the portal first so the browser can show its consent page. ## Available tools | Task | Tools | |---|---| | Inspect flows | `list_flows`, `get_flow`, `get_node_source`, `list_node_types`, `get_graph`, `list_shared_nodes` | | Inspect values | `get_flow_state`, `get_message_history` | | Inspect the instance | `list_secrets` (names only), `get_modules`, `get_health`, `get_metrics`, `list_failures`, `list_runs` (live cascades) | | Inspect devices | `list_devices`, `get_device` | | Edit flows | `create_flow`, `save_flow`, `save_node_source`, `validate_flow`, `publish_flow`, `discard_draft`, `delete_flow` | | Operate flows | `run_flow`, `trigger_node`, `start_flow`, `stop_flow`, `pause_flow`, `resume_flow`, `cancel_node` | | Install node packages | `apply_modules` | Tools call the same API as the browser. Drafts, validation, version checks, and superuser restrictions apply. Secrets cannot be read back. A tool's `flow` argument is the flow's id or its key, resolved from the flows the agent's user can list, as the [CLI does](cli.md#naming-a-flow). When a name could mean two flows, a reading tool uses the id and adds a `warning` to its answer, and a tool that changes something refuses until the agent writes `id:` or `key:`. `create_flow` makes a new flow, under an id the server issues. `save_flow` only changes an existing one and cannot change its key. A useful workflow: ask the agent to inspect the flow, save a draft, and validate it. Review the draft before asking it to publish. The agent has a publish tool, so make your intent explicit. ## The assistant A superuser configures an OpenAI-compatible provider under **Settings → Assistant**, with a base URL, API key, and model. This enables the dashboard's Assistant entry for signed-in users. The assistant uses the same tools with your own permissions. Draft edits appear in the editor. Each answer streams in as the model writes it and renders as markdown with a tool trace. Conversations are stored per user on the instance; the bin button clears yours. `MCP_ENABLED` is only needed for external clients, so the built-in assistant works without it. In both tabs, chips above the input offer quick prompts: the messages you send most often in this browser, then a few starters. A tap puts the text in the input to edit and send. Double-clicking, or double-tapping, one of your own messages does the same. ## Control A live [Wren](../reference/node-types.md#wren) or [Assistant](../reference/node-types.md#assistant) node with its `prompt` and a `reply` or `actions` wired adds a **Control** tab to the chat. Wren uses its local model, the Assistant node the provider above. Choose a conversation and type a command. It goes out on the node's prompt, which is where a `stt` node writes what a device heard, so typed and spoken commands are one conversation: the words heard so far, the command, each reply, and the reported actions with their target message, value and whether each was applied. A node whose prompt is another's `unhandled` answers in that node's conversation. Wren's `apply`, `min_confidence` and `targets` settings decide whether it writes to its targets. Control conversations stay in the browser and clear on reload.