[client] Route agent-network through the daemon and shape env per provider

Two field-test findings drive this change: the direct-dial path needed
sudo (the profile's WireGuard key is root-owned), and a single flat
ANTHROPIC_* export set is wrong for providers that speak other API
shapes.

Relay the setup request through the daemon instead: a new
GetAgentNetworkSetup daemon RPC forwards to management over the
engine's existing peer connection, so unprivileged callers get the
caller-scoped answer the same way 'netbird status' works — no sudo,
and the key never leaves the daemon. The daemon's JSON gateway exposes
the RPC for the desktop UI for free.

Teach 'agent-network env' the per-provider environment contracts,
mirroring Claude Code's LLM-gateway configuration:
- anthropic flavor: ANTHROPIC_BASE_URL / ANTHROPIC_AUTH_TOKEN /
  ANTHROPIC_MODEL
- bedrock_api: CLAUDE_CODE_USE_BEDROCK, ANTHROPIC_BEDROCK_BASE_URL,
  CLAUDE_CODE_SKIP_BEDROCK_AUTH (the proxy injects AWS credentials)
- vertex_ai_api: CLAUDE_CODE_USE_VERTEX, ANTHROPIC_VERTEX_BASE_URL,
  CLAUDE_CODE_SKIP_VERTEX_AUTH, plus comments for the admin-supplied
  ANTHROPIC_VERTEX_PROJECT_ID and CLOUD_ML_REGION (the proxy forwards
  the URL path, so those values must be the operator's real ones)
- openai flavor: OPENAI_BASE_URL / OPENAI_API_KEY
- anything else: comment lines only — no guessed variables

Selection stays explicit: --provider picks by operator label or
catalog id and is required when several providers are authorized;
--model is validated against the provider's allowed set and required
when several models are allowed. Ambiguity renders as shell comments,
never as exports.

Linear: NET-1399
This commit is contained in:
mlsmaycon
2026-08-04 09:10:01 +00:00
parent ba3db38932
commit e193e59c6a
8 changed files with 883 additions and 251 deletions
+13
View File
@@ -2200,6 +2200,19 @@ func (e *Engine) GetExposeManager() *expose.Manager {
return e.exposeManager
}
// GetAgentNetworkSetup asks the management server for the Agent Network
// connection info this peer's groups authorize, over the engine's
// existing management connection.
func (e *Engine) GetAgentNetworkSetup(ctx context.Context) (*mgmProto.AgentNetworkSetupResponse, error) {
e.syncMsgMux.Lock()
mgmClient := e.mgmClient
e.syncMsgMux.Unlock()
if mgmClient == nil {
return nil, errors.New("management client not available")
}
return mgmClient.GetAgentNetworkSetup(ctx)
}
// IsBlockInbound returns whether inbound connections are blocked.
func (e *Engine) IsBlockInbound() bool {
return e.config.BlockInbound