Repository navigation
Run OpenBot's server, app and worker from the published server image - #851
Merged
Merged
Conversation
The server image already carries the API and the built app. Add worker/src and its node_modules (the isolated install's link to @openbot/shared), so the same published image can run the worker with `bun ../worker/src/index.ts`. Nothing uses it yet; this is step 1 of running OpenBot Desktop's server, app and worker as containers instead of building them on the customer's machine.
OpenBot's own server (the API and the built app it serves) and the routines worker, from the published server image, behind an `openbot` profile so scripts/start.sh and a plain `docker compose up -d` keep running them on the host as before. The server reads the same .env a host server does, with every address overridden to a service on the compose network, PORT and SERVER_PORT both pinned to 3001 (the server refuses to start when they disagree), NODE_ENV cleared so a local OpenBot may still reach private addresses, and the app and server host ports both mapped to it on loopback. The worker gets its three settings and sits on the data network only. Bots keep their host.docker.internal tool URL by default; whoever starts the server service points them at server:3001.
The runtime sends the browser the gateway's /client socket in /info, and the browser opens it itself. A server in a container reaches local Intelligence at host.docker.internal, which the browser on the host cannot resolve, while the browser's localhost is the container from inside it. INTELLIGENCE_BROWSER_GATEWAY_WS_URL, when set, is the address /info (and a trajectory grant) gives the browser; the server's own runner and channel sockets stay on INTELLIGENCE_GATEWAY_WS_URL. The compose server service sets it to the deployment's own gateway URL and reads its container address from INTELLIGENCE_CONTAINER_GATEWAY_WS_URL.
A Google or xAI sign-in leaves .openbot/model-oauth.json on the host, and the server reads and renews it itself (temp file plus rename, and a .lock folder beside it), so the folder is bind-mounted rather than the file. Not created by Compose, which would make it root-owned on Linux. The user is settable so the Linux desktop can run the server as the host user who owns that 0600 file.
dustywusty
marked this pull request as ready for review
October 27, 2026 18:39
dustywusty
requested review from
MikeRyanDev,
davidmckayv,
guidovizoso,
mxmzb and
tylerslaton
as code owners
October 27, 2026 18:39
Codex Review SummaryThis comment shows the latest Codex review activity on this pull request.
ℹ️ About Codex in GitHubYour team has set up Codex to review pull requests in this repo. Reviews are triggered when you
Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings. |
guidovizoso
approved these changes
Oct 27, 2026
guidovizoso
left a comment
Collaborator
There was a problem hiding this comment.
Groundwork for #852, and nothing changes until something starts the new services. Approving so we can cut a release with the worker in the image.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Lets OpenBot run its own server, app and worker from the published server image, so a first install of OpenBot Desktop needs only Docker. Nothing changes for anyone until something starts the new services. The desktop half is a separate draft stacked on #832.
Today and proposed
Bun is still installed on first use of the self-hosted Intelligence sign-in, the one host script left.
Why
Today the desktop downloads OpenBot's source, downloads Bun, runs
bun install, builds the web app with Vite and runs the server, app and worker as host processes. On a fresh Windows 11 VM,bun installwas still running 20+ minutes in, and the run timed out at 30 minutes. Every release already publishesghcr.io/copilotkit/openbot-serverwith the API and the built app inside it (APP_DIST_DIR). The desktop never used it for those processes, and the worker was missing from it.What
server/Dockerfile: shipsworker/src,worker/package.jsonandworker/node_modules. The last one holds the isolated install's link to@openbot/shared; without it the worker's first import fails. The image still starts the API by default, andbun ../worker/src/index.tsruns the worker.docker-compose.yml: newserverandworkerservices from that image, behind anopenbotprofile.scripts/start.shand a plaindocker compose up -ddon't start them, so developers keep their host server..enva host server reads. Every address is overridden with a service name (postgres,agent-computer,supervisor,agent-langgraph,agent-harness).PORTandSERVER_PORTare both pinned to 3001..envcarries the host port, and the server refuses to start when the two disagree.NODE_ENVis cleared, as it is for a host server: production refusesAGENT_COMPUTER_ALLOW_PRIVATE_HOSTS, which a local OpenBot needs.APP_PORTandSERVER_PORTare both published to container 3001, loopback only. The desktop's host-access broker callsSERVER_PORT.OPENBOT_DESKTOP_HOST_TOKENgoes to the server only../.openbotis bind-mounted for the Google and xAI sign-in file, which the server renews itself (temp file plus rename).datanetwork only.INTELLIGENCE_BROWSER_GATEWAY_WS_URL(server, toolkit): the browser opens the Intelligence gateway itself, at the URL/infogives it. A server in a container reaches local Intelligence athost.docker.internal, which the browser on the host can't resolve. When this setting is set,/infogives the browser this URL instead; the server's runner and channel sockets stay onINTELLIGENCE_GATEWAY_WS_URL. Unset, nothing changes.The Bots keep
host.docker.internalas their default tool URL, becausestart.sh's server is on the host. Whoever startsserversetsOPENBOT_TOOL_URL=http://server:3001/api/agent-tools/call.Verification
bunx biome check,bun run typecheck: clean.intelligence-browser-gateway.test.ts. Serverconfig.test.ts143/143.SERVER_PORTpin is removed./applayout from the Dockerfile's COPY list and ranbun ../worker/src/index.ts. The sweep loop started. Withworker/node_modulesremoved it failed withCannot find module '@openbot/shared/work-owner'.TEST_DATABASE_URLunset, network guard, live providers).Not verified locally (Docker isn't available on the machine this was written on). CI needs to cover:
docker compose configtest intests/compose.test.ts(addresses the server's Bots and endpoints from inside the network), which checks the:+and container-address interpolation../.openbotdoesn't trip Compose for other services.