What happened:
The Python SDK documents and sends a ttl field (seconds) when creating a CodeInterpreter session via POST /v1/code-interpreter. The Workload Manager API type CreateSandboxRequest only defines kind, name, and namespace. Gin's ShouldBindJSON silently drops the extra ttl field.
Session expiry is always derived from the CodeInterpreter CRD spec.maxSessionDuration (or internal defaults), not from the SDK ttl argument.
I reproduced this on a live cluster:
- CodeInterpreter CR
my-interpreter has maxSessionDuration: 8h.
- Created a session with request body
"ttl": 60 (1 minute).
- Redis key
session:<session_id> shows expiresAt ~8 hours in the future, not ~60 seconds.
Concrete repro output:
POST http://localhost:8080/v1/code-interpreter
payload: {"name": "my-interpreter", "namespace": "default", "ttl": 60, "metadata": {}}
session_id: ff70326a-6411-4281-98fd-65195c22b3d3
expiresAt: 2026-06-19T15:13:40+00:00
remaining_seconds: 28779.2 (~8h, not 60s)
request_ttl_seconds: 60
crd maxSessionDuration: 8h
bug_indicator: LIKELY_BUG
What you expected to happen:
When CodeInterpreterClient(ttl=60) or ControlPlaneClient.create_session(ttl=60) is used, the created session should expire approximately 60 seconds after creation (or be capped by the CRD maxSessionDuration if lower).
How to reproduce it (as minimally and precisely as possible):
Static confirmation (no cluster):
cd agentcube
Select-String -Path sdk-python\agentcube\clients\control_plane.py -Pattern '"ttl"'
# -> line 97: "ttl": ttl
Select-String -Path pkg\common\types\sandbox.go -Pattern "CreateSandboxRequest" -Context 0,5
# -> struct has Kind, Name, Namespace only (no ttl field)
Runtime confirmation (cluster required):
Prerequisites:
- AgentCube deployed (
kubectl get pods -n agentcube)
- Port-forward:
kubectl port-forward -n agentcube svc/workloadmanager 8080:8080
- CodeInterpreter CR
my-interpreter in default with maxSessionDuration: 8h
- Token:
kubectl create token e2e-test -n agentcube --duration=24h
$env:WORKLOAD_MANAGER_URL = "http://localhost:8080"
$env:API_TOKEN = kubectl create token e2e-test -n agentcube --duration=24h
# Create session with ttl=60
python -c "
import os, requests, json
r = requests.post(
os.environ['WORKLOAD_MANAGER_URL'] + '/v1/code-interpreter',
json={'name':'my-interpreter','namespace':'default','ttl':60,'metadata':{}},
headers={'Authorization':'Bearer '+os.environ['API_TOKEN']},
timeout=120)
r.raise_for_status()
print('session_id:', r.json()['sessionId'])
"
# Inspect Redis expiry (replace SESSION_ID)
kubectl exec -n agentcube deploy/redis -- redis-cli GET session:SESSION_ID
kubectl exec -n agentcube deploy/redis -- redis-cli ZSCORE session:expiry SESSION_ID
Compare expiresAt in the JSON to wall clock: it reflects CRD max (~8h), not request ttl (60s).
A step-by-step repro kit is available in the repo at hack/contributor/repro-bug1-ttl/ (for contributors working from a fork).
Affected code:
| Layer |
File |
SDK sends ttl |
sdk-python/agentcube/clients/control_plane.py (lines 81, 97-98) |
SDK documents ttl |
sdk-python/agentcube/code_interpreter.py (lines 55, 71) |
API ignores ttl |
pkg/common/types/sandbox.go (CreateSandboxRequest) |
| Handler |
pkg/workloadmanager/handlers.go (handleSandboxCreate) |
| TTL from CRD only |
pkg/workloadmanager/workload_builder.go |
Related ignored field: SDK also sends metadata in the same payload; it is dropped for the same reason. This issue focuses on ttl.
Proposed fix (for discussion):
- (A) Add optional
ttl to CreateSandboxRequest, validate ttl > 0, cap by CRD maxSessionDuration, wire through buildSandboxByCodeInterpreter / buildSandboxByAgentRuntime to ShutdownTime and store ExpiresAt.
- (B) Remove or deprecate
ttl from the Python SDK and document that session lifetime is CRD-controlled only.
I am happy to submit a PR after maintainers confirm the preferred approach. Please advise whether (A) or (B) is desired.
Anything else we need to know?:
- This is not the same as #303 (AgentRuntime default max TTL policy) or warm-pool placeholder expiry fixes.
- GitHub search for
"Python SDK ttl" / "sdk ttl parameter" returned 0 existing issues as of 2026-06-18.
- Router
session_manager.go also omits ttl when creating sandboxes; SDK users hitting Workload Manager directly are affected today.
Environment:
- agentcube version:
ghcr.io/volcano-sh/workloadmanager:latest (local dev cluster)
- Kubernetes version: v1.29.2
- OS: Windows 11
- Python SDK:
sdk-python from main branch
- CodeInterpreter:
my-interpreter in namespace default, maxSessionDuration: 8h
What happened:
The Python SDK documents and sends a
ttlfield (seconds) when creating a CodeInterpreter session viaPOST /v1/code-interpreter. The Workload Manager API typeCreateSandboxRequestonly defineskind,name, andnamespace. Gin'sShouldBindJSONsilently drops the extrattlfield.Session expiry is always derived from the CodeInterpreter CRD
spec.maxSessionDuration(or internal defaults), not from the SDKttlargument.I reproduced this on a live cluster:
my-interpreterhasmaxSessionDuration: 8h."ttl": 60(1 minute).session:<session_id>showsexpiresAt~8 hours in the future, not ~60 seconds.Concrete repro output:
What you expected to happen:
When
CodeInterpreterClient(ttl=60)orControlPlaneClient.create_session(ttl=60)is used, the created session should expire approximately 60 seconds after creation (or be capped by the CRDmaxSessionDurationif lower).How to reproduce it (as minimally and precisely as possible):
Static confirmation (no cluster):
Runtime confirmation (cluster required):
Prerequisites:
kubectl get pods -n agentcube)kubectl port-forward -n agentcube svc/workloadmanager 8080:8080my-interpreterindefaultwithmaxSessionDuration: 8hkubectl create token e2e-test -n agentcube --duration=24hCompare
expiresAtin the JSON to wall clock: it reflects CRD max (~8h), not request ttl (60s).A step-by-step repro kit is available in the repo at
hack/contributor/repro-bug1-ttl/(for contributors working from a fork).Affected code:
ttlsdk-python/agentcube/clients/control_plane.py(lines 81, 97-98)ttlsdk-python/agentcube/code_interpreter.py(lines 55, 71)ttlpkg/common/types/sandbox.go(CreateSandboxRequest)pkg/workloadmanager/handlers.go(handleSandboxCreate)pkg/workloadmanager/workload_builder.goRelated ignored field: SDK also sends
metadatain the same payload; it is dropped for the same reason. This issue focuses onttl.Proposed fix (for discussion):
ttltoCreateSandboxRequest, validatettl > 0, cap by CRDmaxSessionDuration, wire throughbuildSandboxByCodeInterpreter/buildSandboxByAgentRuntimetoShutdownTimeand storeExpiresAt.ttlfrom the Python SDK and document that session lifetime is CRD-controlled only.I am happy to submit a PR after maintainers confirm the preferred approach. Please advise whether (A) or (B) is desired.
Anything else we need to know?:
"Python SDK ttl"/"sdk ttl parameter"returned 0 existing issues as of 2026-06-18.session_manager.goalso omitsttlwhen creating sandboxes; SDK users hitting Workload Manager directly are affected today.Environment:
ghcr.io/volcano-sh/workloadmanager:latest(local dev cluster)sdk-pythonfrommainbranchmy-interpreterin namespacedefault,maxSessionDuration: 8h