Microservice exec sessions
Interactive exec into microservice containers uses a multi-session model on Controller v3.8.0. Each session has its own id, WebSocket attach path, and runtime exec process.
Controller REST POST/DELETE .../exec on microservices is removed. Open exec via WebSocket only. Legacy single-session Agent paths are not supported on Controller v3.8.
Overview
| Concern | Controller-initiated exec | Local edgelet ms exec |
|---|---|---|
| Who opens the session | Pot user / EdgeOps Console via Controller | Operator CLI on the Edgelet node |
| Session discovery | Field agent polls GET /api/v3/agent/exec/sessions | POST /v1/ms/{id}/exec/sessions |
| Attach transport | WebSocket .../agent/exec/microservice/{uuid}/{sessionId} | GET /v1/ms/{id}/exec/sessions/{sessionId}:attach |
| Concurrent limit | 5 per microservice (Controller quota) | Unlimited (node resources only) |
| Reported in status | Yes - execSessionIds[] on agent status | No - local sessions are excluded from Controller status |
Exec sessions work like log sessions: poll a session list, attach per sessionId, reconcile when rows disappear.
Local exec (edgelet ms exec)
edgelet ms exec <uuid|namespace.name>
edgelet ms exec <uuid> -- /bin/sh -c 'ps aux'
Flow:
- CLI calls
POST /v1/ms/{id}/exec/sessionswith the remote command (default interactive shell). - EdgeletAPI waits up to 15 seconds for the shell to start before returning.
- CLI attaches over WebSocket and streams stdin/stdout/stderr until the remote command exits.
Multiple local sessions on the same microservice can run concurrently. Each session gets a unique runtime exec id so local CLI exec does not collide with Controller sessions.
Start timeout
If the shell does not become ready within 15 seconds, the API returns HTTP 504 with code EXEC_START_TIMEOUT. The CLI surfaces:
Error[EXEC_START_TIMEOUT]: Interactive shell did not start within 15 seconds. Retry `edgelet ms exec`; if the problem persists, check microservice and engine logs.
Common causes: container not running, image missing /bin/sh, engine overload, or stale containerd exec state after a prior crash.
Controller-initiated exec
When a user opens exec from Pot or EdgeOps Console:
- Controller creates a session row and sets
execSessions: trueon the nextconfig/changes. - The field agent polls the session list and opens one agent WebSocket per pending row.
- MessagePack relay frames use
execId=sessionId(not containerd runtime ids). - When the session row disappears from the poll, the agent tears down that attachment only.
Attach path on the Edgelet node:
WS .../agent/exec/microservice/{uuid}/{sessionId}
The legacy single-session path (WS /agent/exec/{microserviceUuid} with init MessagePack pairing) is removed in Edgelet v1.0.0+.
Concurrent session limit
Controller v3.8.0 allows up to 5 concurrent exec sessions per microservice. When the quota is full, new session requests fail until an existing session closes.
Status reporting
Agent status includes Controller attachment session ids per microservice:
"execSessionIds": ["session-uuid-1", "session-uuid-2"]
Values are Controller session ids for attachments this Edgelet node holds. They are not containerd exec process names and not local CLI sessions.
execEnabled (deprecated)
Edgelet no longer uses the microservice execEnabled flag to open or keep exec sessions. Controller drives exec via session poll (execSessions: true).
Operators do not need to toggle execEnabled for exec to work.
Related operations
- Control plane restart stops interactive exec on the controller microservice before bounce. See Control plane on node.
- Health checks use a separate short-lived exec path and are not part of the interactive session registry.
Troubleshooting
See Troubleshooting - Microservice exec for timeout, orphan session, and concurrent-session scenarios.
See also
- EdgeletAPI v1 - local exec and WebSocket routes
- Microservice logs - log streaming over WebSocket
- Migrating to v3.8.0 - exec breaking changes