teamver-agent-sdk 0.6.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- teamver_agent_sdk-0.6.1/.gitignore +50 -0
- teamver_agent_sdk-0.6.1/CHANGELOG.md +82 -0
- teamver_agent_sdk-0.6.1/LICENSE +21 -0
- teamver_agent_sdk-0.6.1/PKG-INFO +115 -0
- teamver_agent_sdk-0.6.1/README.md +82 -0
- teamver_agent_sdk-0.6.1/docs/11_1_agent_sdk_Drive_DM_/352/265/254/355/230/204/354/204/244/352/263/204.md +119 -0
- teamver_agent_sdk-0.6.1/docs/11_2_agent_sdk_Drive_DM_/352/265/254/355/230/204/355/230/204/355/231/251.md +70 -0
- teamver_agent_sdk-0.6.1/docs/11_agent_sdk_Drive_DM_/355/231/225/354/236/245_/354/203/201/354/234/204/354/204/244/352/263/204.md +145 -0
- teamver_agent_sdk-0.6.1/docs/teamver_agent_sdk_AI_AGENT_GUIDE.md +277 -0
- teamver_agent_sdk-0.6.1/docs/teamver_agent_sdk_API_QUICKREF.md +154 -0
- teamver_agent_sdk-0.6.1/docs/teamver_agent_sdk_DESIGN.md +97 -0
- teamver_agent_sdk-0.6.1/examples/unified_worker.py +23 -0
- teamver_agent_sdk-0.6.1/pyproject.toml +73 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/__init__.py +93 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/agent.py +166 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/channel.py +122 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/checkpoint.py +87 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/config.py +115 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/decision.py +115 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/dm.py +143 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/drive.py +225 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/errors.py +56 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/events.py +117 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/http.py +142 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/intent_runtime.py +110 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/job_intent.py +250 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/jobs.py +221 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/mail.py +45 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/openclaw/__init__.py +20 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/openclaw/adapter.py +8 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/openclaw/tools.py +8 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/report.py +41 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/runtime.py +83 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/sync.py +30 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/tools/__init__.py +21 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/tools/adapter.py +227 -0
- teamver_agent_sdk-0.6.1/teamver_agent_sdk/tools/catalog.py +267 -0
- teamver_agent_sdk-0.6.1/tests/test_agent_tools.py +101 -0
- teamver_agent_sdk-0.6.1/tests/test_checkpoint.py +57 -0
- teamver_agent_sdk-0.6.1/tests/test_config.py +47 -0
- teamver_agent_sdk-0.6.1/tests/test_decision.py +103 -0
- teamver_agent_sdk-0.6.1/tests/test_dm_client.py +88 -0
- teamver_agent_sdk-0.6.1/tests/test_drive_client.py +161 -0
- teamver_agent_sdk-0.6.1/tests/test_errors.py +20 -0
- teamver_agent_sdk-0.6.1/tests/test_intent_runtime.py +108 -0
- teamver_agent_sdk-0.6.1/tests/test_job_intent_golden.py +108 -0
- teamver_agent_sdk-0.6.1/tests/test_jobs_client.py +29 -0
- teamver_agent_sdk-0.6.1/tests/test_report.py +90 -0
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
|
|
2
|
+
|
|
3
|
+
# dependencies
|
|
4
|
+
/node_modules
|
|
5
|
+
node_modules/
|
|
6
|
+
/.pnp
|
|
7
|
+
.pnp.js
|
|
8
|
+
|
|
9
|
+
# testing
|
|
10
|
+
/coverage
|
|
11
|
+
|
|
12
|
+
# next.js
|
|
13
|
+
/.next/
|
|
14
|
+
.next/
|
|
15
|
+
/out/
|
|
16
|
+
out/
|
|
17
|
+
|
|
18
|
+
# production
|
|
19
|
+
/build
|
|
20
|
+
|
|
21
|
+
# misc
|
|
22
|
+
.DS_Store
|
|
23
|
+
*.pem
|
|
24
|
+
|
|
25
|
+
# debug
|
|
26
|
+
npm-debug.log*
|
|
27
|
+
yarn-debug.log*
|
|
28
|
+
yarn-error.log*
|
|
29
|
+
|
|
30
|
+
# local env files
|
|
31
|
+
.env*.local
|
|
32
|
+
.env
|
|
33
|
+
|
|
34
|
+
# vercel
|
|
35
|
+
.vercel
|
|
36
|
+
|
|
37
|
+
# typescript
|
|
38
|
+
*.tsbuildinfo
|
|
39
|
+
next-env.d.ts
|
|
40
|
+
dist/
|
|
41
|
+
|
|
42
|
+
# vite build output
|
|
43
|
+
examples/react-ai-app/dist/
|
|
44
|
+
|
|
45
|
+
# python
|
|
46
|
+
__pycache__/
|
|
47
|
+
*.py[cod]
|
|
48
|
+
.venv/
|
|
49
|
+
*.egg-info/
|
|
50
|
+
.pytest_cache/
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
# Changelog — teamver-agent-sdk
|
|
2
|
+
|
|
3
|
+
Format loosely follows [Keep a Changelog](https://keepachangelog.com/).
|
|
4
|
+
|
|
5
|
+
## [0.6.1] - 2026-08-02
|
|
6
|
+
|
|
7
|
+
### Changed (OpenClaw → agent 용어)
|
|
8
|
+
- Prefer `teamver_agent_sdk.tools` / `AgentToolAdapter` (function-calling).
|
|
9
|
+
- `OpenClawAdapter` · `teamver_agent_sdk.openclaw` 는 하위 호환 alias/shim.
|
|
10
|
+
- Docs·examples·publish 스크립트: `docs_reference/agent`, `examples/python-docker-agent`,
|
|
11
|
+
`scripts/publish-agent-pypi.sh`, `.github/workflows/publish-agent-pypi.yml`.
|
|
12
|
+
|
|
13
|
+
## [0.6.0] - 2026-08-02
|
|
14
|
+
|
|
15
|
+
### Added (Drive / DM for agent runtimes)
|
|
16
|
+
- `DmClient` — workspace DM list/open/read/post (`/api/v2/workspace/{ws}/dm/*`).
|
|
17
|
+
- `DriveClient` — shared-drive list, file list, download-url, local download, presigned 3-step upload.
|
|
18
|
+
- Agent tools: `teamver_channel_read` / `react`, `teamver_dm_*` (4), `teamver_drive_*` (5).
|
|
19
|
+
Catalog **13 → 24**.
|
|
20
|
+
- Docs: `docs/11_agent_sdk_Drive_DM_확장_상위설계.md` + 구현설계·현황.
|
|
21
|
+
- Tests: `test_dm_client.py`, `test_drive_client.py`; adapter catalog assertions.
|
|
22
|
+
|
|
23
|
+
## [0.5.0] - 2026-07-23
|
|
24
|
+
|
|
25
|
+
### Added (15-1 §07.2-E — Engine 런타임 결선)
|
|
26
|
+
- `intent_runtime.py` — `JobIntentClassifier`: 주입된 `chat_fn`(동기/비동기)으로 판단 루프
|
|
27
|
+
수행(규칙 선필터 → 구조화 출력 LLM → 계약 검증 → 선택적 apply). 잘못된 LLM 출력은 안전
|
|
28
|
+
CLARIFY 로 폴백. `ChatCompletionFn` Protocol. 모델·프레임워크 무관(테스트는 가짜 chat_fn).
|
|
29
|
+
- `classify_and_apply()` — 판단 후 `AgentToolAdapter` 로 create/attach/NO_JOB 라우팅.
|
|
30
|
+
- 신규 export + `tests/test_intent_runtime.py`(5). 49 passed.
|
|
31
|
+
|
|
32
|
+
## [0.4.0] - 2026-07-23
|
|
33
|
+
|
|
34
|
+
### Added (15-1 §07.2 판단 위치·Engine 연동)
|
|
35
|
+
- `job_intent.py` — Job 의도 판단을 **Engine LLM** 이 하도록 돕는 계약/프롬프트:
|
|
36
|
+
`JobCandidate`/`InboundMessage`/`JobDecisionContext`, `SYSTEM_PROMPT`+`FEW_SHOTS`,
|
|
37
|
+
`render_context`/`build_job_decision_messages`(모델 무관), `job_decision_response_schema`
|
|
38
|
+
(구조화 출력), `rule_prefilter`(명백한 잡담→NONE, LLM 생략).
|
|
39
|
+
- `AgentToolAdapter.build_job_decision_request()`(messages+schema+선필터) /
|
|
40
|
+
`apply_job_decision()`(검증된 decision → create/attach/NO_JOB 라우팅).
|
|
41
|
+
- `jobs.create()` + `JobsCreateArgs` 에 `request_intent`/`related_job_id`/`link_type`/
|
|
42
|
+
`confidence` 추가(서버 링크·SUPERSEDE 종료·confidence 가드 연동).
|
|
43
|
+
- 신규 export + `tests/test_job_intent_golden.py`(10). 44 passed.
|
|
44
|
+
|
|
45
|
+
## [0.3.0] - 2026-07-23
|
|
46
|
+
|
|
47
|
+
### Added (15-1 §07.1 요청 의도 분류 / Request Intent Classification)
|
|
48
|
+
- `AgentJobDecision` 확장: `request_intent`(AMEND/SUPERSEDE/FOLLOW_UP/NEW/NONE/
|
|
49
|
+
CLARIFY), `related_job_id`, `link_type`(follow_up|supersedes), `clarification`.
|
|
50
|
+
- `effective_intent` — `request_intent` 미지정 시 `action` 에서 유도(ATTACH→AMEND,
|
|
51
|
+
CREATE→NEW, NO_JOB→NONE).
|
|
52
|
+
- 검증 규칙: AMEND→existing_job_id, SUPERSEDE/FOLLOW_UP→related_job_id,
|
|
53
|
+
link_type→related_job_id 정합. `contracts/schemas/job-decision.schema.json` 동기.
|
|
54
|
+
- 신규 export: `RequestIntent`, `LinkType`, `Clarification`.
|
|
55
|
+
|
|
56
|
+
## [0.2.0] - 2026-07-23
|
|
57
|
+
|
|
58
|
+
### Changed (16-1 §7, §13, §17)
|
|
59
|
+
- **BREAKING**: HTTP transport (channel/events/jobs/runtime) now delegates to
|
|
60
|
+
`teamver-sdk-core` (`TeamverAsyncTransport`). Per-surface retry/error loops
|
|
61
|
+
removed (§17). `AgentHTTP` builds the transport per request so a swapped
|
|
62
|
+
underlying client is honored (test injection).
|
|
63
|
+
- Errors unified onto the core tree: `TeamverAgentError`→`TeamverSDKError`,
|
|
64
|
+
`TeamverAgentConfigError`→`ConfigurationError`, `TeamverAgentAPIError`→root.
|
|
65
|
+
|
|
66
|
+
### Added
|
|
67
|
+
- **Agent Tool Adapter** (§8): `teamver_agent_sdk.tools` (`AgentToolAdapter`;
|
|
68
|
+
legacy `openclaw`/`OpenClawAdapter` alias) with `ToolSpec`,
|
|
69
|
+
`build_tool_specs`, `tool_json_schemas` (validate args → route to agent surface).
|
|
70
|
+
13 tools; JSON Schema generated from Pydantic models.
|
|
71
|
+
- **Job decision** (§9): `AgentJobDecision` model + `JobsClient.decide()` — a
|
|
72
|
+
local schema validator (no server decide API); conditional required fields for
|
|
73
|
+
CREATE_JOB / ATTACH_JOB.
|
|
74
|
+
- `teamver-sdk-core>=0.1.0` dependency; bumped `teamver-mail-agent>=0.3.0`.
|
|
75
|
+
|
|
76
|
+
## [0.1.0] - previous
|
|
77
|
+
|
|
78
|
+
### Added
|
|
79
|
+
- Unified Teamver SDK for agent runtimes: channel reporting, event receive
|
|
80
|
+
loop, and mail integration.
|
|
81
|
+
- Event checkpoint stores (`InMemoryCheckpointStore`, `FileCheckpointStore`) and
|
|
82
|
+
`dedup_key` helper for idempotent event processing (15-1 §04).
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) Neural Studio
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: teamver-agent-sdk
|
|
3
|
+
Version: 0.6.1
|
|
4
|
+
Summary: Unified Teamver SDK for agent runtimes (channel, DM, drive, events, jobs, mail, agent tools)
|
|
5
|
+
Project-URL: Homepage, https://teamver.com
|
|
6
|
+
Project-URL: Documentation, https://github.com/NeuralStudioKr/ns-teamver-packages/tree/main/packages/python/teamver-agent-sdk-python
|
|
7
|
+
Project-URL: Repository, https://github.com/NeuralStudioKr/ns-teamver-packages
|
|
8
|
+
Project-URL: Issues, https://github.com/NeuralStudioKr/ns-teamver-packages/issues
|
|
9
|
+
Project-URL: Changelog, https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/CHANGELOG.md
|
|
10
|
+
Author-email: Teamver <dev@teamver.com>
|
|
11
|
+
Maintainer-email: Teamver <dev@teamver.com>
|
|
12
|
+
License: MIT
|
|
13
|
+
License-File: LICENSE
|
|
14
|
+
Keywords: agent,agent-tools,channel,dm,drive,mail,sdk,teamver
|
|
15
|
+
Classifier: Development Status :: 4 - Beta
|
|
16
|
+
Classifier: Intended Audience :: Developers
|
|
17
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
18
|
+
Classifier: Operating System :: OS Independent
|
|
19
|
+
Classifier: Programming Language :: Python :: 3
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
23
|
+
Classifier: Typing :: Typed
|
|
24
|
+
Requires-Python: >=3.11
|
|
25
|
+
Requires-Dist: httpx<0.28,>=0.27.0
|
|
26
|
+
Requires-Dist: pydantic<3,>=2.0
|
|
27
|
+
Requires-Dist: teamver-mail-agent>=0.3.0
|
|
28
|
+
Requires-Dist: teamver-sdk-core>=0.1.0
|
|
29
|
+
Provides-Extra: dev
|
|
30
|
+
Requires-Dist: pytest-asyncio>=0.24; extra == 'dev'
|
|
31
|
+
Requires-Dist: pytest>=8.0; extra == 'dev'
|
|
32
|
+
Description-Content-Type: text/markdown
|
|
33
|
+
|
|
34
|
+
# teamver-agent-sdk
|
|
35
|
+
|
|
36
|
+
Official **Teamver Agent SDK** for agent runtimes (e.g. OpenClaw, Hermes).
|
|
37
|
+
|
|
38
|
+
One facade (`TeamverAgent` + `AgentToolAdapter`) for:
|
|
39
|
+
|
|
40
|
+
- **Channels** — list / post / read / react
|
|
41
|
+
- **DM** — threads open / read / post
|
|
42
|
+
- **Drive** — list / download / upload (presigned)
|
|
43
|
+
- **Mail** — via `teamver-mail-agent`
|
|
44
|
+
- **Jobs · heartbeat · SSE events**
|
|
45
|
+
- **agent tools** — `adapter.list_tools()` / `adapter.dispatch(...)`
|
|
46
|
+
|
|
47
|
+
## Install
|
|
48
|
+
|
|
49
|
+
```bash
|
|
50
|
+
pip install teamver-agent-sdk
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
Pulls in `teamver-mail-agent` and `teamver-sdk-core`. Python **≥ 3.11**.
|
|
54
|
+
|
|
55
|
+
## Environment
|
|
56
|
+
|
|
57
|
+
| env | purpose |
|
|
58
|
+
|-----|---------|
|
|
59
|
+
| `TEAMVER_WORKSPACE_ID` | workspace id (`WS-…`) |
|
|
60
|
+
| `TEAMVER_AGENT_ID` | agent id (`AGT-…`) |
|
|
61
|
+
| `TEAMVER_CHANNEL_API_BASE` | Main API host (`https://api.teamver.com`, **no** `/api`) |
|
|
62
|
+
| `TEAMVER_AGENT_TOKEN` | channel/DM/drive grant (`tv_ak_*`) |
|
|
63
|
+
| `TEAMVER_AGENT_API_BASE` | Agents BE host (jobs / heartbeat) |
|
|
64
|
+
| `TEAMVER_MAIL_API_BASE` | Mail API host (**no** `/v1`) |
|
|
65
|
+
| `TEAMVER_MAIL_AGENT_TOKEN` | mail agent token (`tv_agent_*`) |
|
|
66
|
+
|
|
67
|
+
Do **not** put user passwords or `TEAMVER_INTERNAL_API_KEY` in the agent runtime.
|
|
68
|
+
|
|
69
|
+
## Quick start
|
|
70
|
+
|
|
71
|
+
```python
|
|
72
|
+
import asyncio
|
|
73
|
+
from teamver_agent_sdk import TeamverAgent, AgentToolAdapter
|
|
74
|
+
|
|
75
|
+
async def main():
|
|
76
|
+
agent = TeamverAgent() # from env
|
|
77
|
+
adapter = AgentToolAdapter(agent)
|
|
78
|
+
|
|
79
|
+
# agent function-calling schemas
|
|
80
|
+
tools = adapter.list_tools()
|
|
81
|
+
|
|
82
|
+
await agent.report(text="Deploy finished ✅", channel_id="CH-…")
|
|
83
|
+
files = await agent.drive.list_files(drive_id="personal", limit=20)
|
|
84
|
+
threads = await agent.dm.list_threads(limit=10)
|
|
85
|
+
|
|
86
|
+
# Tool dispatch example
|
|
87
|
+
await adapter.dispatch(
|
|
88
|
+
"teamver_channel_post",
|
|
89
|
+
{"channel_id": "CH-…", "text": "hello", "idempotency_key": "k1"},
|
|
90
|
+
)
|
|
91
|
+
|
|
92
|
+
await agent.aclose()
|
|
93
|
+
|
|
94
|
+
asyncio.run(main())
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
Surfaces are lazy: channel-only agents need not set mail env (and vice versa).
|
|
98
|
+
|
|
99
|
+
## Documentation
|
|
100
|
+
|
|
101
|
+
- [AI Agent Guide](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/docs/teamver_agent_sdk_AI_AGENT_GUIDE.md)
|
|
102
|
+
- [API Quickref](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/docs/teamver_agent_sdk_API_QUICKREF.md)
|
|
103
|
+
- [Drive/DM design](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/docs/11_agent_sdk_Drive_DM_확장_상위설계.md)
|
|
104
|
+
- [agent ops guide](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/docs_reference/agent/README.md)
|
|
105
|
+
|
|
106
|
+
## Development
|
|
107
|
+
|
|
108
|
+
```bash
|
|
109
|
+
pip install -e ".[dev]"
|
|
110
|
+
pytest
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
## License
|
|
114
|
+
|
|
115
|
+
MIT — see [LICENSE](./LICENSE).
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
# teamver-agent-sdk
|
|
2
|
+
|
|
3
|
+
Official **Teamver Agent SDK** for agent runtimes (e.g. OpenClaw, Hermes).
|
|
4
|
+
|
|
5
|
+
One facade (`TeamverAgent` + `AgentToolAdapter`) for:
|
|
6
|
+
|
|
7
|
+
- **Channels** — list / post / read / react
|
|
8
|
+
- **DM** — threads open / read / post
|
|
9
|
+
- **Drive** — list / download / upload (presigned)
|
|
10
|
+
- **Mail** — via `teamver-mail-agent`
|
|
11
|
+
- **Jobs · heartbeat · SSE events**
|
|
12
|
+
- **agent tools** — `adapter.list_tools()` / `adapter.dispatch(...)`
|
|
13
|
+
|
|
14
|
+
## Install
|
|
15
|
+
|
|
16
|
+
```bash
|
|
17
|
+
pip install teamver-agent-sdk
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
Pulls in `teamver-mail-agent` and `teamver-sdk-core`. Python **≥ 3.11**.
|
|
21
|
+
|
|
22
|
+
## Environment
|
|
23
|
+
|
|
24
|
+
| env | purpose |
|
|
25
|
+
|-----|---------|
|
|
26
|
+
| `TEAMVER_WORKSPACE_ID` | workspace id (`WS-…`) |
|
|
27
|
+
| `TEAMVER_AGENT_ID` | agent id (`AGT-…`) |
|
|
28
|
+
| `TEAMVER_CHANNEL_API_BASE` | Main API host (`https://api.teamver.com`, **no** `/api`) |
|
|
29
|
+
| `TEAMVER_AGENT_TOKEN` | channel/DM/drive grant (`tv_ak_*`) |
|
|
30
|
+
| `TEAMVER_AGENT_API_BASE` | Agents BE host (jobs / heartbeat) |
|
|
31
|
+
| `TEAMVER_MAIL_API_BASE` | Mail API host (**no** `/v1`) |
|
|
32
|
+
| `TEAMVER_MAIL_AGENT_TOKEN` | mail agent token (`tv_agent_*`) |
|
|
33
|
+
|
|
34
|
+
Do **not** put user passwords or `TEAMVER_INTERNAL_API_KEY` in the agent runtime.
|
|
35
|
+
|
|
36
|
+
## Quick start
|
|
37
|
+
|
|
38
|
+
```python
|
|
39
|
+
import asyncio
|
|
40
|
+
from teamver_agent_sdk import TeamverAgent, AgentToolAdapter
|
|
41
|
+
|
|
42
|
+
async def main():
|
|
43
|
+
agent = TeamverAgent() # from env
|
|
44
|
+
adapter = AgentToolAdapter(agent)
|
|
45
|
+
|
|
46
|
+
# agent function-calling schemas
|
|
47
|
+
tools = adapter.list_tools()
|
|
48
|
+
|
|
49
|
+
await agent.report(text="Deploy finished ✅", channel_id="CH-…")
|
|
50
|
+
files = await agent.drive.list_files(drive_id="personal", limit=20)
|
|
51
|
+
threads = await agent.dm.list_threads(limit=10)
|
|
52
|
+
|
|
53
|
+
# Tool dispatch example
|
|
54
|
+
await adapter.dispatch(
|
|
55
|
+
"teamver_channel_post",
|
|
56
|
+
{"channel_id": "CH-…", "text": "hello", "idempotency_key": "k1"},
|
|
57
|
+
)
|
|
58
|
+
|
|
59
|
+
await agent.aclose()
|
|
60
|
+
|
|
61
|
+
asyncio.run(main())
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
Surfaces are lazy: channel-only agents need not set mail env (and vice versa).
|
|
65
|
+
|
|
66
|
+
## Documentation
|
|
67
|
+
|
|
68
|
+
- [AI Agent Guide](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/docs/teamver_agent_sdk_AI_AGENT_GUIDE.md)
|
|
69
|
+
- [API Quickref](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/docs/teamver_agent_sdk_API_QUICKREF.md)
|
|
70
|
+
- [Drive/DM design](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/packages/python/teamver-agent-sdk-python/docs/11_agent_sdk_Drive_DM_확장_상위설계.md)
|
|
71
|
+
- [agent ops guide](https://github.com/NeuralStudioKr/ns-teamver-packages/blob/main/docs_reference/agent/README.md)
|
|
72
|
+
|
|
73
|
+
## Development
|
|
74
|
+
|
|
75
|
+
```bash
|
|
76
|
+
pip install -e ".[dev]"
|
|
77
|
+
pytest
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
## License
|
|
81
|
+
|
|
82
|
+
MIT — see [LICENSE](./LICENSE).
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
# teamver-agent-sdk — Drive / DM 구현설계 (루프)
|
|
2
|
+
|
|
3
|
+
## 변경 이력
|
|
4
|
+
|
|
5
|
+
| 일시 (KST) | 변경 내용 |
|
|
6
|
+
|---|-----|
|
|
7
|
+
| 2026-08-02 15:55 | Phase 4 — 0.6.0 · CHANGELOG · agent smoke 동기화 |
|
|
8
|
+
| 2026-08-02 15:50 | Phase 3 — DriveClient + agent drive tools |
|
|
9
|
+
| 2026-08-02 15:45 | Phase 2 — DmClient + agent DM tools |
|
|
10
|
+
| 2026-08-02 15:42 | Phase 1 — channel read/react tool 구현 반영 |
|
|
11
|
+
| 2026-08-02 15:40 | Phase 0 — 상위설계 반영, Phase 1~4 상세 초안 |
|
|
12
|
+
|
|
13
|
+
**SSOT 상위:** [11_agent_sdk_Drive_DM_확장_상위설계.md](./11_agent_sdk_Drive_DM_확장_상위설계.md)
|
|
14
|
+
**현황:** [11_2_agent_sdk_Drive_DM_구현현황.md](./11_2_agent_sdk_Drive_DM_구현현황.md)
|
|
15
|
+
|
|
16
|
+
---
|
|
17
|
+
|
|
18
|
+
## Phase 0 — 문서 (완료 기준)
|
|
19
|
+
|
|
20
|
+
- [x] 상위설계 문서
|
|
21
|
+
- [x] 본 구현설계 · 현황 문서 골격
|
|
22
|
+
|
|
23
|
+
---
|
|
24
|
+
|
|
25
|
+
## Phase 1 — Channel agent tools ✅
|
|
26
|
+
|
|
27
|
+
### 설계
|
|
28
|
+
|
|
29
|
+
기존 `ChannelClient.read_messages` / `react` 를 tool로 노출.
|
|
30
|
+
|
|
31
|
+
| 항목 | 내용 |
|
|
32
|
+
|------|------|
|
|
33
|
+
| Args | `ChannelReadArgs(channel_id, limit=50, cursor?)`, `ChannelReactArgs(channel_id, message_id, emoji)` |
|
|
34
|
+
| tools | `teamver_channel_read`, `teamver_channel_react` |
|
|
35
|
+
| adapter | `_invoke`에 `channel.read_messages`, `channel.react` |
|
|
36
|
+
| tests | catalog **15**, fake channel dispatch |
|
|
37
|
+
|
|
38
|
+
### 파일
|
|
39
|
+
|
|
40
|
+
- `teamver_agent_sdk/tools/catalog.py`
|
|
41
|
+
- `teamver_agent_sdk/tools/adapter.py`
|
|
42
|
+
- `tests/test_agent_tools.py`
|
|
43
|
+
- (하위 호환) `teamver_agent_sdk/openclaw/*` → `tools` re-export
|
|
44
|
+
|
|
45
|
+
---
|
|
46
|
+
|
|
47
|
+
## Phase 2 — DM surface ✅
|
|
48
|
+
|
|
49
|
+
### 설계
|
|
50
|
+
|
|
51
|
+
`teamver_agent_sdk/dm.py` — `DmClient` (AgentHTTP, base=`…/api/v2`).
|
|
52
|
+
|
|
53
|
+
```python
|
|
54
|
+
class DmClient:
|
|
55
|
+
async def list_threads(self, *, limit=50, cursor=None) -> dict
|
|
56
|
+
async def open_thread(self, peer_user_id: str, *, idempotency_key=None) -> dict
|
|
57
|
+
async def read_messages(self, thread_id, *, limit=50, cursor=None) -> dict
|
|
58
|
+
async def post_message(self, thread_id, text, *, reply_to_message_id=None, idempotency_key=None) -> dict
|
|
59
|
+
async def aclose(self) -> None
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
Paths:
|
|
63
|
+
|
|
64
|
+
- `GET /workspace/{ws}/dm/threads`
|
|
65
|
+
- `POST /workspace/{ws}/dm/threads` JSON `{"peer_user_id": "…"}`
|
|
66
|
+
- `GET /workspace/{ws}/dm/threads/{thread_id}/messages`
|
|
67
|
+
- `POST /workspace/{ws}/dm/threads/{thread_id}/messages` JSON `{"text": "…"}`
|
|
68
|
+
|
|
69
|
+
`TeamverAgent.dm` lazy property; `aclose`에 포함.
|
|
70
|
+
|
|
71
|
+
agent tools 4개 (§상위설계 §4).
|
|
72
|
+
|
|
73
|
+
---
|
|
74
|
+
|
|
75
|
+
## Phase 3 — Drive surface ✅
|
|
76
|
+
|
|
77
|
+
### 설계
|
|
78
|
+
|
|
79
|
+
`teamver_agent_sdk/drive.py` — `DriveClient`.
|
|
80
|
+
|
|
81
|
+
- `_http_v1`: AgentHTTP base `{channel_api_base}/api`
|
|
82
|
+
- `_http_v2`: AgentHTTP base `{channel_api_base}/api/v2` (또는 channel과 공유 가능하나 생명주기 단순화를 위해 Drive 전용 v2 client)
|
|
83
|
+
|
|
84
|
+
```python
|
|
85
|
+
class DriveClient:
|
|
86
|
+
async def list_shared_drives(self) -> dict
|
|
87
|
+
async def list_files(self, *, drive_id="personal", limit=50, folder_id=None) -> dict
|
|
88
|
+
async def download_url(self, asset_id, *, drive_id="personal") -> dict # {download_url,…}
|
|
89
|
+
async def download(self, asset_id, dest_path, *, drive_id="personal") -> dict # {path, bytes}
|
|
90
|
+
async def upload(self, *, local_path, filename=None, drive_id="personal", folder_id=None, content_type=None) -> dict
|
|
91
|
+
async def aclose(self) -> None
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
Upload:
|
|
95
|
+
|
|
96
|
+
1. POST `/drive/upload-request`
|
|
97
|
+
2. PUT `upload_url` with file body
|
|
98
|
+
3. POST `/drive/upload-confirm` `{asset_id}`
|
|
99
|
+
|
|
100
|
+
agent tools 5개. `drive.download` / `upload`는 **로컬 path** 필수(컨테이너/VM 가정).
|
|
101
|
+
|
|
102
|
+
---
|
|
103
|
+
|
|
104
|
+
## Phase 4 — 마무리 ✅
|
|
105
|
+
|
|
106
|
+
- `__version__` / `pyproject` → **0.6.0**
|
|
107
|
+
- CHANGELOG, API_QUICKREF, AI_AGENT_GUIDE, DESIGN, README
|
|
108
|
+
- `docs_reference/agent/01·02` tool·버전 갱신
|
|
109
|
+
- `examples/python-docker-agent/agent_smoke.py` dm/drive 섹션
|
|
110
|
+
- export `DmClient` / `DriveClient`
|
|
111
|
+
|
|
112
|
+
---
|
|
113
|
+
|
|
114
|
+
## 공통 규칙
|
|
115
|
+
|
|
116
|
+
- docstring 한국어 모듈 목적 (repo rule)
|
|
117
|
+
- 토큰 로그 금지
|
|
118
|
+
- 기존 channel/mail/jobs 동작 회귀 금지
|
|
119
|
+
- main 직접 push, PR/CI 없음
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
# teamver-agent-sdk — Drive / DM 구현현황
|
|
2
|
+
|
|
3
|
+
## 변경 이력
|
|
4
|
+
|
|
5
|
+
| 일시 (KST) | 변경 내용 |
|
|
6
|
+
|---|-----|
|
|
7
|
+
| 2026-08-02 15:55 | Phase 4 완료 — 0.6.0 릴리스 위생 · 문서/smoke 동기화 |
|
|
8
|
+
| 2026-08-02 15:50 | Phase 3 완료 — DriveClient + drive tools 5종 |
|
|
9
|
+
| 2026-08-02 15:45 | Phase 2 완료 — DmClient + DM tools 4종 |
|
|
10
|
+
| 2026-08-02 15:42 | Phase 1 완료 — channel read/react agent tools |
|
|
11
|
+
| 2026-08-02 15:40 | Phase 0 문서 착수 — 구현 전 baseline |
|
|
12
|
+
|
|
13
|
+
**상위설계:** [11_agent_sdk_Drive_DM_확장_상위설계.md](./11_agent_sdk_Drive_DM_확장_상위설계.md)
|
|
14
|
+
**구현설계:** [11_1_agent_sdk_Drive_DM_구현설계.md](./11_1_agent_sdk_Drive_DM_구현설계.md)
|
|
15
|
+
|
|
16
|
+
---
|
|
17
|
+
|
|
18
|
+
## 진행 요약
|
|
19
|
+
|
|
20
|
+
| Phase | 상태 | 메모 |
|
|
21
|
+
|-------|------|------|
|
|
22
|
+
| 0 상위·구현설계 문서 | ✅ | 본 세트 작성 |
|
|
23
|
+
| 1 Channel read/react tools | ✅ | tools 13→15 |
|
|
24
|
+
| 2 DmClient + tools | ✅ | tools 15→19 · `dm.py` |
|
|
25
|
+
| 3 DriveClient + tools | ✅ | tools 19→24 · `drive.py` |
|
|
26
|
+
| 4 0.6.0 · 문서/smoke 동기화 | ✅ | version 0.6.0 |
|
|
27
|
+
|
|
28
|
+
---
|
|
29
|
+
|
|
30
|
+
## Baseline (0.5.0)
|
|
31
|
+
|
|
32
|
+
- agent tools: **13**
|
|
33
|
+
- Channel: list/post (+ read/react 클라이언트만)
|
|
34
|
+
- DM / Drive: 없음
|
|
35
|
+
|
|
36
|
+
---
|
|
37
|
+
|
|
38
|
+
## Phase별 로그
|
|
39
|
+
|
|
40
|
+
### Phase 0 — 2026-08-02 15:40 KST
|
|
41
|
+
|
|
42
|
+
- 추가: `docs/11_*.md` 3종
|
|
43
|
+
- 코드 변경 없음
|
|
44
|
+
|
|
45
|
+
### Phase 1 — 2026-08-02 15:42 KST
|
|
46
|
+
|
|
47
|
+
- `teamver_channel_read` / `teamver_channel_react` 도구 + adapter 라우팅
|
|
48
|
+
- `tests/test_agent_tools.py` catalog=24, fake dispatch 검증
|
|
49
|
+
- agent tools 총 **15**
|
|
50
|
+
|
|
51
|
+
### Phase 2 — 2026-08-02 15:45 KST
|
|
52
|
+
|
|
53
|
+
- `DmClient`: list_threads / open_thread / read_messages / post_message
|
|
54
|
+
- `TeamverAgent.dm` lazy + aclose
|
|
55
|
+
- tools: `teamver_dm_*` 4종 · `tests/test_dm_client.py`
|
|
56
|
+
- agent tools 총 **19**
|
|
57
|
+
|
|
58
|
+
### Phase 3 — 2026-08-02 15:50 KST
|
|
59
|
+
|
|
60
|
+
- `DriveClient`: list_shared_drives / list_files / download_url / download / upload(3-step)
|
|
61
|
+
- `TeamverAgent.drive` lazy + aclose
|
|
62
|
+
- tools: `teamver_drive_*` 5종 · `tests/test_drive_client.py`
|
|
63
|
+
- agent tools 총 **24**
|
|
64
|
+
|
|
65
|
+
### Phase 4 — 2026-08-02 15:55 KST
|
|
66
|
+
|
|
67
|
+
- `teamver-agent-sdk` **0.6.0** (pyproject / `__version__` / User-Agent)
|
|
68
|
+
- CHANGELOG · DESIGN · API_QUICKREF · AI_AGENT_GUIDE · README
|
|
69
|
+
- `docs_reference/agent` + Docker smoke dm/drive 단계
|
|
70
|
+
- 단위 테스트 전부 통과 (구현 시점 54+)
|
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
# teamver-agent-sdk — Drive / DM 확장 상위설계
|
|
2
|
+
|
|
3
|
+
## 변경 이력
|
|
4
|
+
|
|
5
|
+
| 일시 (KST) | 변경 내용 |
|
|
6
|
+
|---|-----|
|
|
7
|
+
| 2026-08-02 15:40 | v0.1 초안 — agent 런타임용 channel 보강 · DM · Drive surface/tool |
|
|
8
|
+
|
|
9
|
+
**목표:** agent 런타임(예: OpenClaw·Hermes 등)이 Teamver **채널 읽기·쓰기**, **DM 읽기·쓰기**, **Drive 목록·다운로드·업로드**를 `teamver-agent-sdk` 한 파사드(+ agent tools)로 수행한다.
|
|
10
|
+
**대상 패키지:** `packages/python/teamver-agent-sdk-python` (배포명 `teamver-agent-sdk`)
|
|
11
|
+
**인증:** 기존과 동일 — Main Bearer **`tv_ak_*`** + `TEAMVER_CHANNEL_API_BASE` / `TEAMVER_WORKSPACE_ID` (별도 Drive/DM 토큰 없음).
|
|
12
|
+
**비목표:** 사용자 login/signup, Mail M2M, WebSocket, `TEAMVER_INTERNAL_API_KEY`.
|
|
13
|
+
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
## 1. 배경 · Gap
|
|
17
|
+
|
|
18
|
+
| 요구 | 0.5.x 상태 |
|
|
19
|
+
|------|------------|
|
|
20
|
+
| 채널 쓰기 · 목록 | ✅ + agent tool |
|
|
21
|
+
| 채널 읽기 · react | △ 클라이언트만 / tool 없음 |
|
|
22
|
+
| DM | ❌ |
|
|
23
|
+
| Drive | ❌ (DESIGN non-goal이었음) |
|
|
24
|
+
|
|
25
|
+
상위 agent 제품 요구로 Drive/DM이 **in-scope**로 승격된다. 전체 Main 카탈로그(`teamver-be-sdk`)를 끌어오지 않고, agent에 필요한 **최소 surface**만 추가한다.
|
|
26
|
+
|
|
27
|
+
---
|
|
28
|
+
|
|
29
|
+
## 2. 아키텍처
|
|
30
|
+
|
|
31
|
+
```text
|
|
32
|
+
TeamverAgent
|
|
33
|
+
├─ channel (기존 + tool 보강)
|
|
34
|
+
├─ dm (신규 DmClient) ← /api/v2/workspace/{ws}/dm/*
|
|
35
|
+
├─ drive (신규 DriveClient) ← /api/drive/* + /api/v2/shared-drive|drive/*
|
|
36
|
+
├─ events / mail / jobs / runtime (기존)
|
|
37
|
+
└─ AgentToolAdapter.dispatch(tool) (tools 카탈로그 확장)
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
| Surface | HTTP base | Auth |
|
|
41
|
+
|---------|-----------|------|
|
|
42
|
+
| channel / dm / events | `{CHANNEL_API_BASE}/api/v2` | `tv_ak_*` |
|
|
43
|
+
| drive v1 (list/upload/download-url) | `{CHANNEL_API_BASE}/api` | `tv_ak_*` |
|
|
44
|
+
| drive v2 (shared-drive, home/recent) | `{CHANNEL_API_BASE}/api/v2` | `tv_ak_*` |
|
|
45
|
+
|
|
46
|
+
`drive_enabled` / `dm_enabled` ≡ `channel_enabled` (동일 base+token).
|
|
47
|
+
공유 드라이브는 `X-Shared-Drive-Id` 또는 query `shared_drive_id` (BE 호환: 헤더 우선, 예시는 host-wheels와 동일).
|
|
48
|
+
|
|
49
|
+
---
|
|
50
|
+
|
|
51
|
+
## 3. API 매핑 (agent 최소 집합)
|
|
52
|
+
|
|
53
|
+
### 3.1 Channel (보강)
|
|
54
|
+
|
|
55
|
+
| SDK | HTTP |
|
|
56
|
+
|-----|------|
|
|
57
|
+
| `read_messages(channel_id, limit, cursor)` | GET `…/channels/{id}/messages` |
|
|
58
|
+
| `react(channel_id, message_id, emoji)` | POST `…/messages/{id}/reactions` |
|
|
59
|
+
|
|
60
|
+
(이미 `channel.py` 존재 — **agent tool만 추가**해도 Phase 1 완료 가능.)
|
|
61
|
+
|
|
62
|
+
### 3.2 DM (신규)
|
|
63
|
+
|
|
64
|
+
레포 확인 경로: `GET /api/v2/workspace/{ws}/dm/threads` (`api_perf_monitor`).
|
|
65
|
+
메시지 경로는 채널과 대칭으로 둔다 (BE 불일치 시 escape `request`).
|
|
66
|
+
|
|
67
|
+
| SDK | HTTP (가정·대칭) |
|
|
68
|
+
|-----|------------------|
|
|
69
|
+
| `list_threads(limit, cursor)` | GET `/workspace/{ws}/dm/threads` |
|
|
70
|
+
| `open_thread(peer_user_id)` | POST `/workspace/{ws}/dm/threads` body `{peer_user_id}` |
|
|
71
|
+
| `read_messages(thread_id, limit, cursor)` | GET `…/dm/threads/{id}/messages` |
|
|
72
|
+
| `post_message(thread_id, text, …)` | POST `…/dm/threads/{id}/messages` |
|
|
73
|
+
|
|
74
|
+
### 3.3 Drive (신규)
|
|
75
|
+
|
|
76
|
+
| SDK | HTTP |
|
|
77
|
+
|-----|------|
|
|
78
|
+
| `list_shared_drives()` | GET `/api/v2/shared-drive` |
|
|
79
|
+
| `list_files(drive_id?, limit, folder_id?)` | GET `/api/drive/list` (+ personal/shared 헤더) |
|
|
80
|
+
| `download_url(asset_id, drive_id?)` | GET `/api/drive/asset/{id}/download-url` |
|
|
81
|
+
| `download(asset_id, dest_path, …)` | download-url → httpx GET → 파일 저장 |
|
|
82
|
+
| `upload(path\|bytes, filename, …)` | upload-request → PUT presign → upload-confirm |
|
|
83
|
+
|
|
84
|
+
업로드는 be-sdk / host-wheels 와 동일한 **3-step presigned** 계약.
|
|
85
|
+
|
|
86
|
+
---
|
|
87
|
+
|
|
88
|
+
## 4. agent tools (추가)
|
|
89
|
+
|
|
90
|
+
| tool | handler |
|
|
91
|
+
|------|---------|
|
|
92
|
+
| `teamver_channel_read` | `channel.read_messages` |
|
|
93
|
+
| `teamver_channel_react` | `channel.react` |
|
|
94
|
+
| `teamver_dm_list_threads` | `dm.list_threads` |
|
|
95
|
+
| `teamver_dm_open_thread` | `dm.open_thread` |
|
|
96
|
+
| `teamver_dm_read_messages` | `dm.read_messages` |
|
|
97
|
+
| `teamver_dm_post_message` | `dm.post_message` |
|
|
98
|
+
| `teamver_drive_list_drives` | `drive.list_shared_drives` |
|
|
99
|
+
| `teamver_drive_list_files` | `drive.list_files` |
|
|
100
|
+
| `teamver_drive_download_url` | `drive.download_url` |
|
|
101
|
+
| `teamver_drive_download` | `drive.download` (dest_path) |
|
|
102
|
+
| `teamver_drive_upload` | `drive.upload` (local path) |
|
|
103
|
+
|
|
104
|
+
대용량 바이너리는 tool 결과에 넣지 않는다 — **경로·URL·asset_id 메타만** 반환.
|
|
105
|
+
|
|
106
|
+
---
|
|
107
|
+
|
|
108
|
+
## 5. 구현 루프 (Phase)
|
|
109
|
+
|
|
110
|
+
| Phase | 내용 | 산출 |
|
|
111
|
+
|-------|------|------|
|
|
112
|
+
| **0** | 본 상위설계 + 현황 문서 | docs |
|
|
113
|
+
| **1** | Channel read/react agent tools + 테스트 | tools/adapter/tests |
|
|
114
|
+
| **2** | `DmClient` + facade + tools + 테스트 | `dm.py` |
|
|
115
|
+
| **3** | `DriveClient` + facade + tools + 테스트 | `drive.py` |
|
|
116
|
+
| **4** | 버전 0.6.0 · CHANGELOG · smoke/example · docs_reference/agent 동기화 | release hygiene |
|
|
117
|
+
|
|
118
|
+
각 Phase마다 **구현설계 절 갱신 · 구현현황 문서 갱신 · main push**.
|
|
119
|
+
|
|
120
|
+
---
|
|
121
|
+
|
|
122
|
+
## 6. 테스트 전략
|
|
123
|
+
|
|
124
|
+
- httpx `MockTransport` 또는 Fake surface (기존 `test_agent_tools` 패턴).
|
|
125
|
+
- Drive upload: request/confirm mock + PUT용 ASGI/MockTransport.
|
|
126
|
+
- DM path는 mock으로 계약 고정; live는 opt-in 아님(이 루프에서는 mock만).
|
|
127
|
+
|
|
128
|
+
---
|
|
129
|
+
|
|
130
|
+
## 7. 리스크
|
|
131
|
+
|
|
132
|
+
| 리스크 | 완화 |
|
|
133
|
+
|--------|------|
|
|
134
|
+
| DM POST body 필드명 BE와 불일치 | `open_thread`/`post_message`에 raw `body` escape; 문서에 가정 명시 |
|
|
135
|
+
| Agent 토큰에 drive/dm 스코프 부족 | 403 → 명확한 APIError; Console 스코프 문서화 |
|
|
136
|
+
| 업로드 메모리 | 파일 path 스트리밍 PUT 권장 |
|
|
137
|
+
|
|
138
|
+
---
|
|
139
|
+
|
|
140
|
+
## 8. 관련 문서
|
|
141
|
+
|
|
142
|
+
- 구현설계(루프): [11_1_agent_sdk_Drive_DM_구현설계.md](./11_1_agent_sdk_Drive_DM_구현설계.md)
|
|
143
|
+
- 구현현황: [11_2_agent_sdk_Drive_DM_구현현황.md](./11_2_agent_sdk_Drive_DM_구현현황.md)
|
|
144
|
+
- 기존: [teamver_agent_sdk_DESIGN.md](./teamver_agent_sdk_DESIGN.md)
|
|
145
|
+
- 예시 패턴: `examples/python-docker-host-wheels/download_drive_file.py`
|