stacklok / stacklok/toolhive

Decouple transport from runtime

Open
#2,429 0 comments 0 reactions 1 assignee View on GitHub

@blkt is already working on this.

Since Nov 2, 2025.

enhancement go proxy
Dominant language
Go
Stars
2.2k
Forks
300
Avg merge
1d 15h
Merged PRs (30d)
184

Description

As currently implemented, pkg/transport is tightly coupled with the underlying runtime.

Specifically, transport implementations are aware of the fact that they're wrapping a container workload and even use rt.Deployer to stop and, in the case of STDIO transport, restart the workload.

We propose refactoring pkg/transport and pkg/runner to obtain the following split in responsibilities

  • pkg/runner is responsible for starting, restarting, and stopping workloads
  • pkg/transport is responsible for exposing an MCP-compatible Transport to the Client

Here are some facts worth keeping in mind during refactoring

  • HTTP Proxy only needs an URI to connect to the workload
  • HTTP Proxy dynamically reconnects to upstream MCP server
    • It relies on HTTP mechanics (502 Bad Gateway) to handle reconnections
  • HTTP Proxy does not try to restart the workload if it exits
  • HTTP Proxy does not create the container in case of remote MCPs
  • STDIO Proxy only needs a STDIN/STDOUT pair to function
  • STDIO Proxy tries to restart the workload when provided STDIN/STDOUT file descriptors are closed
    • it checks for io.EOF errors

It's evident from the previous list that decoupling workload creation and restart from the transport layer requires transport implementations to dynamically reconnect to the proxied workload. As stated, this is straightforward for HTTP Proxy, which relies on 502 Bad Gateway and basic TCP to handle that, but it's not as straightforward for STDIO Proxy, which will require some other component to provide a new pair of file descriptors.

My personal suggestion is to implement it in a functional fashion, by which I do not mean the unnecessarily zealous "no side effects" interpretation, but rather that the transport layer should provide its creator with a single function allowing dynamic reconfiguration which it is responsible for calling when it detects relevant changes in the workload.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.