Principle:OpenHands OpenHands Nested Server Configuration
| Knowledge Sources | |
|---|---|
| Domains | Distributed_Systems, Conversation_Management |
| Last Updated | 2026-02-11 21:00 GMT |
Overview
Nested server configuration is the pattern of pushing application settings, provider credentials, and secrets to a subordinate runtime server via HTTP API calls after the runtime has been provisioned.
Description
In a nested architecture, the orchestrator (outer server) provisions a runtime container that runs its own HTTP server (inner/nested server). The nested server starts in an unconfigured state and must receive its configuration from the orchestrator before it can serve agent conversations. This configuration injection happens over the nested server's REST API, not through environment variables or mounted files, because:
- Late binding -- The configuration may not be known at container creation time (e.g., tokens are refreshed after provisioning).
- Security -- Secrets are transmitted over an authenticated HTTP channel rather than baked into container images or orchestration manifests.
- Modularity -- The nested server's configuration API is the same regardless of how it was provisioned (Kubernetes, Docker, bare metal).
The configuration injection typically involves multiple sequential HTTP POST requests:
- Settings -- Push general application settings (agent name, LLM model, sandbox parameters).
- Git providers -- Register Git provider configurations (GitHub, GitLab) with their OAuth tokens.
- Secrets -- Inject any additional secrets (custom API keys, webhook tokens) the agent may need.
Usage
Use nested server configuration whenever:
- A new runtime has been provisioned and needs to be made operational.
- Settings have changed mid-conversation and need to be propagated to the nested server.
- Provider credentials have been refreshed and the nested server must receive the updated tokens.
Theoretical Basis
This pattern is an instance of configuration injection via service API from the microservices architecture domain. The orchestrator treats the nested server as a black box that exposes a configuration contract.
Pseudocode:
function configure_nested_server(runtime, settings, provider_tokens, secrets):
api_url = runtime.api_url
client = create_http_client(base_url=api_url, timeout=CONFIG_TIMEOUT)
# Step 1: Push application settings
response = client.post("/api/settings", json=settings.to_dict())
assert response.status_code == 200
# Step 2: Register Git providers
for provider_name, token in provider_tokens.items():
payload = {
"provider": provider_name,
"token": token.get_secret_value(),
}
response = client.post("/api/add-git-providers", json=payload)
assert response.status_code == 200
# Step 3: Inject secrets
for secret_name, secret_value in secrets.items():
payload = {"name": secret_name, "value": secret_value.get_secret_value()}
response = client.post("/api/secrets", json=payload)
assert response.status_code == 200
return True
Key invariants:
- Order dependency -- Settings must be pushed before Git providers, because provider registration may depend on settings (e.g., which Git host is configured).
- Idempotency -- Each POST endpoint must be idempotent: calling it twice with the same payload produces the same result as calling it once.
- Failure atomicity -- If any configuration step fails, the orchestrator should not proceed to start the conversation; the runtime is in a partially configured state and must be torn down or retried.