-
Notifications
You must be signed in to change notification settings - Fork 1
Description
问题描述
agentrun.sandbox.template.Template 的字段 sandbox_ttlin_seconds 在通过 from_inner_object() 从阿里云 API 响应解析时,始终为 None,即使 API 实际返回了有效的 TTL 值。
根因分析
1. API 返回的 JSON key
阿里云 API(alibabacloud_agentrun20250910)的 _template.py 中,to_map() 方法将 TTL 字段序列化为:
result['sandboxTTLInSeconds'] = self.sandbox_ttlin_seconds即 API 响应中的 key 为 sandboxTTLInSeconds(注意 TTL 是大写)。
2. agentrun SDK 的 alias 生成
agentrun/utils/model.py 中的 BaseModel 使用了自动 alias 生成器:
def to_camel_case(field_name: str) -> str:
if "_" not in field_name:
return field_name
parts = field_name.split("_")
return parts[0] + "".join(word.capitalize() for word in parts[1:])对于字段 sandbox_ttlin_seconds,生成的 alias 为:
sandbox_ttlin_seconds → sandboxTtlinSeconds
3. 不匹配
| 来源 | Key |
|---|---|
| API 实际返回 | sandboxTTLInSeconds |
| Pydantic alias 生成 | sandboxTtlinSeconds |
由于 BaseModel 配置了 validate_by_alias=False,model_validate(d, by_alias=True) 时用 alias 做 key 匹配。sandboxTTLInSeconds 无法匹配到 sandboxTtlinSeconds,因此该值落入 model_extra(因为配置了 extra="allow"),而 sandbox_ttlin_seconds 字段始终为 None。
4. 为什么 idle_timeout 正常?
sandbox_idle_timeout_in_seconds 的 alias 为 sandboxIdleTimeoutInSeconds,与 API 返回的 key 完全一致,因此可以正常解析。
关键区别在于:TTL 是连续大写缩写词,to_camel_case 无法正确处理这种 case。按当前逻辑,ttlin 被视为一个单词,首字母大写变成 Ttlin,而 API 期望的是 TTLIn。
复现步骤
from agentrun.sandbox.template import Template
# 模拟 API 返回的数据(经 alibabacloud SDK to_map 转换后的格式)
api_data = {
'templateName': 'code-interpreter-01',
'sandboxIdleTimeoutInSeconds': 900,
'sandboxTTLInSeconds': 3600,
}
t = Template.model_validate(api_data, by_alias=True)
print(t.sandbox_idle_timeout_in_seconds) # 900 ✅
print(t.sandbox_ttlin_seconds) # None ❌(应为 3600)
print(t.model_extra) # {'sandboxTTLInSeconds': 3600}期望行为
template.sandbox_ttlin_seconds 应正确解析为 API 返回的 sandboxTTLInSeconds 值。
建议修复方案
方案 A:为该字段添加显式 alias(推荐)
在 agentrun/sandbox/template.py 中:
from pydantic import Field
sandbox_ttlin_seconds: Optional[int] = Field(None, alias="sandboxTTLInSeconds")这样 Pydantic 会优先使用显式 alias,覆盖自动生成的错误 alias。
方案 B:修正字段命名
将字段重命名为 sandbox_ttl_in_seconds,使 to_camel_case 能正确生成 sandboxTtlInSeconds...但这仍然无法匹配 sandboxTTLInSeconds(API 返回全大写 TTL)。所以此方案仍需搭配显式 alias。
方案 C:改进 to_camel_case 函数
使其能识别常见缩写词(如 TTL、URL、API 等),但通用性和维护成本较高。
影响范围
agentrun.sandbox.template.Template.sandbox_ttlin_seconds— 永远为 None- 所有通过
Sandbox.get_template()/Sandbox.list_templates()获取模版 TTL 的代码 - 下游依赖此值的业务逻辑(如同步模版配置到数据库)
环境信息
- agentrun-sdk 版本:0.0.17(已确认 0.0.21 最新版仍存在此问题)
- alibabacloud-agentrun20250910 版本:随 SDK 安装
- Python 版本:3.12
- Pydantic 版本:2.x
临时 Workaround
在业务代码中从 model_extra 回退读取:
def get_template_ttl_sec(template) -> int | None:
val = getattr(template, "sandbox_ttlin_seconds", None)
if val is not None:
return int(val)
extra = getattr(template, "model_extra", None) or {}
raw = extra.get("sandboxTTLInSeconds")
if raw is not None and raw != "":
return int(raw)
return None