ni.agentkit 0.7.0__tar.gz → 0.7.2__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.
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/PKG-INFO +4 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/README.md +3 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/__init__.py +1 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/docs/Architecture.md +2 -2
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/docs/QuickStart.md +66 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/docs/README.md +1 -2
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/docs/Reference.md +15 -2
- ni_agentkit-0.7.2/docs/TestReport.md +61 -0
- ni_agentkit-0.7.2/examples/Skill.md +41 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/01_basic_chat.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/02_tool_calling.py +2 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/03_skill_usage.py +2 -5
- ni_agentkit-0.7.2/examples/ollama/03b_skill_tools_entry.py +45 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/04_multi_agent.py +6 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/05_guardrail.py +2 -5
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/05_human_in_the_loop.py +2 -5
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/06_orchestration.py +9 -15
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/07_sync_async_stream.py +2 -9
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/08_memory.py +3 -12
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/08a_memory_simple_provider.py +3 -8
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/08b_memory_mem0_provider.py +2 -9
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/08c_memory_file_provider.py +2 -6
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/09a_structured_data_sql.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/09b_structured_data_graph.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/09c_nebula_graph_tool.py +0 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/10_skill_lifecycle.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/11_orchestration_enhancement.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/13_human_in_the_loop.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/14_event_standardization.py +8 -9
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/15_multi_tenant_isolation.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/16_lifecycle_hooks.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/17_checkpoint_handoff_resume.py +0 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/18_model_cosplay.py +9 -9
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/19_hitl_deterministic.py +0 -2
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/README.md +24 -10
- ni_agentkit-0.7.2/examples/ollama/model_config.py +61 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/quickstart.py +2 -4
- ni_agentkit-0.7.2/examples/skills/weather-tools-entry/SKILL.md +25 -0
- ni_agentkit-0.7.2/examples/skills/weather-tools-entry/tools/weather_tools.py +12 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/01_basic_chat.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/02_tool_calling.py +2 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/03_skill_usage.py +2 -5
- ni_agentkit-0.7.2/examples/standard/03b_skill_tools_entry.py +44 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/04_multi_agent.py +6 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/05_guardrail.py +2 -5
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/06_orchestration.py +9 -11
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/07_sync_async_stream.py +2 -9
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/08_memory.py +3 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/08a_memory_simple_provider.py +2 -5
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/08b_memory_mem0_provider.py +5 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/08c_memory_file_provider.py +2 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/09a_structured_data_sql.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/09b_structured_data_graph.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/09c_nebula_graph_tool.py +0 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/10_skill_lifecycle.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/11_orchestration_enhancement.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/13_human_in_the_loop.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/14_event_standardization.py +8 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/15_multi_tenant_isolation.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/16_lifecycle_hooks.py +2 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/17_checkpoint_handoff_resume.py +0 -4
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/18_model_cosplay.py +8 -9
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/README.md +7 -0
- ni_agentkit-0.7.2/examples/standard/model_config.py +53 -0
- ni_agentkit-0.7.2/examples/test_standard.py +50 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/ni.agentkit.egg-info/PKG-INFO +4 -7
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/ni.agentkit.egg-info/SOURCES.txt +17 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/ni.agentkit.egg-info/requires.txt +0 -3
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/pyproject.toml +1 -2
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/runner/context_store.py +0 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/safety/permissions.py +1 -1
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/skills/loader.py +1 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/skills/models.py +75 -0
- ni_agentkit-0.7.2/tests/test_skill_frontmatter.py +135 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/skill_toolset.py +116 -2
- ni_agentkit-0.7.0/docs/TestReport.md +0 -92
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/LICENSE +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/_cli.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/agents/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/agents/agent.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/agents/base_agent.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/agents/orchestrators.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/12_run_context_serialization.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/ollama/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/12_run_context_serialization.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/standard/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/examples/test_ollama.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/adapters/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/adapters/anthropic_adapter.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/adapters/google_adapter.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/adapters/ollama_adapter.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/adapters/openai_adapter.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/adapters/openai_compatible.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/base.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/cache.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/middleware.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/registry.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/llm/types.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/memory/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/memory/base.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/memory/mem0_provider.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/ni.agentkit.egg-info/dependency_links.txt +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/ni.agentkit.egg-info/entry_points.txt +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/ni.agentkit.egg-info/top_level.txt +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/runner/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/runner/context.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/runner/events.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/runner/runner.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/safety/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/safety/guardrails.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/setup.cfg +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/skills/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/skills/registry.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tests/test_after_callback.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tests/test_graph_repository.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tests/test_quickstart_core.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tests/test_runner_checkpoint_resume.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/base_tool.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/function_tool.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/nebula_tool.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/sqlite_tool.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/tools/structured_data.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/utils/__init__.py +0 -0
- {ni_agentkit-0.7.0 → ni_agentkit-0.7.2}/utils/schema.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: ni.agentkit
|
|
3
|
-
Version: 0.7.
|
|
3
|
+
Version: 0.7.2
|
|
4
4
|
Summary: A Python-native Agent framework with first-class Skill support and multi-LLM adapter
|
|
5
5
|
Author-email: Krix Tam <krix.tam@qq.com>
|
|
6
6
|
License: MIT
|
|
@@ -31,8 +31,6 @@ Provides-Extra: google
|
|
|
31
31
|
Requires-Dist: google-genai>=1.0.0; extra == "google"
|
|
32
32
|
Provides-Extra: memory
|
|
33
33
|
Requires-Dist: mem0ai>=0.1.0; extra == "memory"
|
|
34
|
-
Provides-Extra: docker
|
|
35
|
-
Requires-Dist: docker>=7.0.0; extra == "docker"
|
|
36
34
|
Provides-Extra: all
|
|
37
35
|
Requires-Dist: openai>=1.0.0; extra == "all"
|
|
38
36
|
Requires-Dist: anthropic>=0.30.0; extra == "all"
|
|
@@ -71,7 +69,6 @@ pip install "ni.agentkit[openai]"
|
|
|
71
69
|
pip install "ni.agentkit[anthropic]"
|
|
72
70
|
pip install "ni.agentkit[google]"
|
|
73
71
|
pip install "ni.agentkit[memory]"
|
|
74
|
-
pip install "ni.agentkit[docker]"
|
|
75
72
|
pip install "ni.agentkit[all]"
|
|
76
73
|
```
|
|
77
74
|
|
|
@@ -119,7 +116,7 @@ print(agentkit.get_examples_dir()) # 示例目录路径
|
|
|
119
116
|
|
|
120
117
|
## 🧪 示例
|
|
121
118
|
|
|
122
|
-
|
|
119
|
+
安装包内含可运行示例(标准版 24 个 + Ollama 本地版 26 个):
|
|
123
120
|
|
|
124
121
|
```bash
|
|
125
122
|
# Ollama 本地版(无需 API Key)
|
|
@@ -153,8 +150,8 @@ python "$(python -c "import agentkit, os; print(os.path.join(agentkit.get_exampl
|
|
|
153
150
|
|
|
154
151
|
```bash
|
|
155
152
|
dist/
|
|
156
|
-
├── ni_agentkit-0.7.
|
|
157
|
-
└── ni_agentkit-0.7.
|
|
153
|
+
├── ni_agentkit-0.7.2-py3-none-any.whl # pip install 用这个
|
|
154
|
+
└── ni_agentkit-0.7.2.tar.gz # 源码分发
|
|
158
155
|
```
|
|
159
156
|
|
|
160
157
|
## 📄 License
|
|
@@ -29,7 +29,6 @@ pip install "ni.agentkit[openai]"
|
|
|
29
29
|
pip install "ni.agentkit[anthropic]"
|
|
30
30
|
pip install "ni.agentkit[google]"
|
|
31
31
|
pip install "ni.agentkit[memory]"
|
|
32
|
-
pip install "ni.agentkit[docker]"
|
|
33
32
|
pip install "ni.agentkit[all]"
|
|
34
33
|
```
|
|
35
34
|
|
|
@@ -77,7 +76,7 @@ print(agentkit.get_examples_dir()) # 示例目录路径
|
|
|
77
76
|
|
|
78
77
|
## 🧪 示例
|
|
79
78
|
|
|
80
|
-
|
|
79
|
+
安装包内含可运行示例(标准版 24 个 + Ollama 本地版 26 个):
|
|
81
80
|
|
|
82
81
|
```bash
|
|
83
82
|
# Ollama 本地版(无需 API Key)
|
|
@@ -111,8 +110,8 @@ python "$(python -c "import agentkit, os; print(os.path.join(agentkit.get_exampl
|
|
|
111
110
|
|
|
112
111
|
```bash
|
|
113
112
|
dist/
|
|
114
|
-
├── ni_agentkit-0.7.
|
|
115
|
-
└── ni_agentkit-0.7.
|
|
113
|
+
├── ni_agentkit-0.7.2-py3-none-any.whl # pip install 用这个
|
|
114
|
+
└── ni_agentkit-0.7.2.tar.gz # 源码分发
|
|
116
115
|
```
|
|
117
116
|
|
|
118
117
|
## 📄 License
|
|
@@ -31,7 +31,7 @@ from .tools.function_tool import FunctionTool, function_tool
|
|
|
31
31
|
from .tools.structured_data import ResultFormatter, StructuredDataTool
|
|
32
32
|
from .tools.sqlite_tool import SQLiteTool, SQLiteResultFormatter
|
|
33
33
|
|
|
34
|
-
__version__ = "0.7.
|
|
34
|
+
__version__ = "0.7.2"
|
|
35
35
|
|
|
36
36
|
|
|
37
37
|
def get_docs_dir() -> str:
|
|
@@ -620,8 +620,8 @@ agentkit/
|
|
|
620
620
|
│ └── schema.py # 函数签名 → JSON Schema
|
|
621
621
|
│
|
|
622
622
|
├── examples/ # 示例
|
|
623
|
-
│ ├── standard/ # 标准版示例(01-18,含 8A/8B/8C、9A/9B/9C)
|
|
624
|
-
│ ├── ollama/ # Ollama 版示例(01-19,含 8A/8B/8C、9A/9B/9C)
|
|
623
|
+
│ ├── standard/ # 标准版示例(24 个:01-18 + 03B,含 8A/8B/8C、9A/9B/9C)
|
|
624
|
+
│ ├── ollama/ # Ollama 版示例(26 个:01-19 + 03B + 05_human_in_the_loop,含 8A/8B/8C、9A/9B/9C)
|
|
625
625
|
│ ├── quickstart.py
|
|
626
626
|
│ └── test_ollama.py
|
|
627
627
|
│
|
|
@@ -308,6 +308,66 @@ agent = Agent(
|
|
|
308
308
|
)
|
|
309
309
|
```
|
|
310
310
|
|
|
311
|
+
### 方式 C:通过 `SKILL.md` 的 `tools.entry` 动态注册工具
|
|
312
|
+
|
|
313
|
+
当 Skill 需要自带工具实现时,可以在 `tools` 字段中声明 `entry`。Skill 激活后,AgentKit 会按 `entry` 自动发现并注册工具。
|
|
314
|
+
|
|
315
|
+
Skill 目录结构:
|
|
316
|
+
|
|
317
|
+
```text
|
|
318
|
+
skills/weather-tools-entry/
|
|
319
|
+
├── SKILL.md
|
|
320
|
+
└── tools/
|
|
321
|
+
└── weather_tools.py
|
|
322
|
+
```
|
|
323
|
+
|
|
324
|
+
`SKILL.md`(关键片段):
|
|
325
|
+
|
|
326
|
+
```yaml
|
|
327
|
+
---
|
|
328
|
+
name: weather-tools-entry
|
|
329
|
+
description: 通过 SKILL.md 的 tools.entry 动态注册天气查询工具
|
|
330
|
+
tools:
|
|
331
|
+
- name: weather_lookup
|
|
332
|
+
description: 查询城市天气并给出简要信息
|
|
333
|
+
entry: tools/weather_tools.py:weather_lookup
|
|
334
|
+
parameters:
|
|
335
|
+
city: { type: string, description: "城市名称,如北京/上海/深圳" }
|
|
336
|
+
---
|
|
337
|
+
```
|
|
338
|
+
|
|
339
|
+
`tools/weather_tools.py`:
|
|
340
|
+
|
|
341
|
+
```python
|
|
342
|
+
def weather_lookup(city: str) -> str:
|
|
343
|
+
data = {"北京": "晴,25°C", "深圳": "阵雨,28°C"}
|
|
344
|
+
return data.get(city, f"{city}:暂无数据")
|
|
345
|
+
```
|
|
346
|
+
|
|
347
|
+
加载并使用(无需手动把 `weather_lookup` 放入 `Agent.tools`):
|
|
348
|
+
|
|
349
|
+
```python
|
|
350
|
+
from pathlib import Path
|
|
351
|
+
from agentkit import Agent, Runner, load_skill_from_dir
|
|
352
|
+
|
|
353
|
+
skill_dir = Path("./skills/weather-tools-entry")
|
|
354
|
+
skill = load_skill_from_dir(skill_dir)
|
|
355
|
+
|
|
356
|
+
agent = Agent(
|
|
357
|
+
name="skill-tools-entry-agent",
|
|
358
|
+
instructions="你是天气助手。遇到天气问题优先加载并使用 weather-tools-entry Skill。",
|
|
359
|
+
model="ollama/qwen3.5:cloud",
|
|
360
|
+
skills=[skill],
|
|
361
|
+
)
|
|
362
|
+
|
|
363
|
+
result = Runner.run_sync(agent, input="深圳今天适合穿什么?")
|
|
364
|
+
print(result.final_output)
|
|
365
|
+
```
|
|
366
|
+
|
|
367
|
+
> 可运行示例:
|
|
368
|
+
> - `examples/standard/03b_skill_tools_entry.py`
|
|
369
|
+
> - `examples/ollama/03b_skill_tools_entry.py`
|
|
370
|
+
|
|
311
371
|
### Skill 三级加载机制
|
|
312
372
|
|
|
313
373
|
AgentKit 的 Skill 采用三级渐进式加载,避免浪费 token:
|
|
@@ -1234,10 +1294,12 @@ agent = Agent(name="assistant", instructions="...")
|
|
|
1234
1294
|
| [`01_basic_chat.py`](../examples/standard/01_basic_chat.py) | 示例 1:最简 Agent |
|
|
1235
1295
|
| [`02_tool_calling.py`](../examples/standard/02_tool_calling.py) | 示例 2:工具调用 |
|
|
1236
1296
|
| [`03_skill_usage.py`](../examples/standard/03_skill_usage.py) | 示例 3:Skill 使用 |
|
|
1297
|
+
| [`03b_skill_tools_entry.py`](../examples/standard/03b_skill_tools_entry.py) | 示例 3B:Skill tools.entry 动态注册/发现 |
|
|
1237
1298
|
| [`04_multi_agent.py`](../examples/standard/04_multi_agent.py) | 示例 4:多 Agent 协作 |
|
|
1238
1299
|
| [`05_guardrail.py`](../examples/standard/05_guardrail.py) | 示例 5:安全护栏 |
|
|
1239
1300
|
| [`06_orchestration.py`](../examples/standard/06_orchestration.py) | 示例 6:编排 Agent |
|
|
1240
1301
|
| [`07_sync_async_stream.py`](../examples/standard/07_sync_async_stream.py) | 示例 7:同步/异步/流式运行 |
|
|
1302
|
+
| [`08_memory.py`](../examples/standard/08_memory.py) | 示例 8:记忆系统(综合) |
|
|
1241
1303
|
| [`08a_memory_simple_provider.py`](../examples/standard/08a_memory_simple_provider.py) | 示例 8A:记忆系统(SimpleMemory) |
|
|
1242
1304
|
| [`08b_memory_mem0_provider.py`](../examples/standard/08b_memory_mem0_provider.py) | 示例 8B:记忆系统(Mem0Provider) |
|
|
1243
1305
|
| [`08c_memory_file_provider.py`](../examples/standard/08c_memory_file_provider.py) | 示例 8C:记忆系统(文件持久化) |
|
|
@@ -1261,10 +1323,13 @@ agent = Agent(name="assistant", instructions="...")
|
|
|
1261
1323
|
| [`01_basic_chat.py`](../examples/ollama/01_basic_chat.py) | 示例 1:最简 Agent |
|
|
1262
1324
|
| [`02_tool_calling.py`](../examples/ollama/02_tool_calling.py) | 示例 2:工具调用 |
|
|
1263
1325
|
| [`03_skill_usage.py`](../examples/ollama/03_skill_usage.py) | 示例 3:Skill 使用 |
|
|
1326
|
+
| [`03b_skill_tools_entry.py`](../examples/ollama/03b_skill_tools_entry.py) | 示例 3B:Skill tools.entry 动态注册/发现 |
|
|
1264
1327
|
| [`04_multi_agent.py`](../examples/ollama/04_multi_agent.py) | 示例 4:多 Agent 协作 |
|
|
1265
1328
|
| [`05_guardrail.py`](../examples/ollama/05_guardrail.py) | 示例 5:安全护栏 |
|
|
1329
|
+
| [`05_human_in_the_loop.py`](../examples/ollama/05_human_in_the_loop.py) | 扩展示例:HITL 工具触发(Playground) |
|
|
1266
1330
|
| [`06_orchestration.py`](../examples/ollama/06_orchestration.py) | 示例 6:编排 Agent |
|
|
1267
1331
|
| [`07_sync_async_stream.py`](../examples/ollama/07_sync_async_stream.py) | 示例 7:同步/异步/流式运行 |
|
|
1332
|
+
| [`08_memory.py`](../examples/ollama/08_memory.py) | 示例 8:记忆系统(综合) |
|
|
1268
1333
|
| [`08a_memory_simple_provider.py`](../examples/ollama/08a_memory_simple_provider.py) | 示例 8A:记忆系统(SimpleMemory) |
|
|
1269
1334
|
| [`08b_memory_mem0_provider.py`](../examples/ollama/08b_memory_mem0_provider.py) | 示例 8B:记忆系统(Mem0Provider) |
|
|
1270
1335
|
| [`08c_memory_file_provider.py`](../examples/ollama/08c_memory_file_provider.py) | 示例 8C:记忆系统(文件持久化) |
|
|
@@ -1280,6 +1345,7 @@ agent = Agent(name="assistant", instructions="...")
|
|
|
1280
1345
|
| [`16_lifecycle_hooks.py`](../examples/ollama/16_lifecycle_hooks.py) | 示例 16:生命周期 Hooks 与 Callbacks |
|
|
1281
1346
|
| [`17_checkpoint_handoff_resume.py`](../examples/ollama/17_checkpoint_handoff_resume.py) | 示例 17:Checkpoint 深度恢复(Handoff + Resume) |
|
|
1282
1347
|
| [`18_model_cosplay.py`](../examples/ollama/18_model_cosplay.py) | 示例 18:ModelCosplay(运行时改写预设模型) |
|
|
1348
|
+
| [`19_hitl_deterministic.py`](../examples/ollama/19_hitl_deterministic.py) | 示例 19:HITL 确定性触发 |
|
|
1283
1349
|
|
|
1284
1350
|
---
|
|
1285
1351
|
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
> Python 原生的 Agent 开发框架,内置一等公民级别的 Skill 支持和自研多模型适配层。
|
|
4
4
|
|
|
5
5
|
[](https://python.org)
|
|
6
|
-
[]()
|
|
7
7
|
[]()
|
|
8
8
|
|
|
9
9
|
---
|
|
@@ -35,7 +35,6 @@ pip install "ni.agentkit[openai]" # OpenAI + 国内兼容厂商
|
|
|
35
35
|
pip install "ni.agentkit[anthropic]" # Anthropic Claude
|
|
36
36
|
pip install "ni.agentkit[google]" # Google Gemini
|
|
37
37
|
pip install "ni.agentkit[memory]" # 记忆系统 (mem0)
|
|
38
|
-
pip install "ni.agentkit[docker]" # 预留:SandboxExecutor Docker 扩展依赖
|
|
39
38
|
pip install "ni.agentkit[all]" # 安装所有可选依赖
|
|
40
39
|
```
|
|
41
40
|
|
|
@@ -505,7 +505,7 @@ from agentkit import Skill, SkillFrontmatter, SkillResources
|
|
|
505
505
|
| `on_load_hook` | `Callable \| None` | **生命周期钩子**:在 Agent 执行前加载资源 |
|
|
506
506
|
| `on_unload_hook` | `Callable \| None` | **生命周期钩子**:在 Agent 执行后释放资源 |
|
|
507
507
|
|
|
508
|
-
**便捷属性**:`skill.name`、`skill.description`、`skill.additional_tools`、`skill.llm_config`
|
|
508
|
+
**便捷属性**:`skill.name`、`skill.description`、`skill.additional_tools`、`skill.triggers`、`skill.dependencies`、`skill.tools`、`skill.tool_specs`、`skill.llm_config`
|
|
509
509
|
|
|
510
510
|
---
|
|
511
511
|
|
|
@@ -516,7 +516,20 @@ from agentkit import Skill, SkillFrontmatter, SkillResources
|
|
|
516
516
|
| `name` | `str` | kebab-case 标识符(≤64 字符) |
|
|
517
517
|
| `description` | `str` | 描述(≤1024 字符) |
|
|
518
518
|
| `license` | `str \| None` | 许可证 |
|
|
519
|
-
| `
|
|
519
|
+
| `compatibility` | `str \| None` | 可选兼容性标记(版本/平台约束) |
|
|
520
|
+
| `triggers` | `list[str]` | 触发关键词列表,用于描述 Skill 的适用场景 |
|
|
521
|
+
| `dependencies` | `list[str]` | Skill 运行依赖声明(如三方包/外部能力) |
|
|
522
|
+
| `tools` | `list[SkillToolSpec]` | Skill 声明的工具列表;支持字符串简写和对象写法,最终归一化为 `SkillToolSpec` |
|
|
523
|
+
| `metadata` | `dict` | 扩展元数据,可含 `additional_tools`(兼容旧写法)和 `llm_config` |
|
|
524
|
+
|
|
525
|
+
`SkillToolSpec` 字段:
|
|
526
|
+
|
|
527
|
+
| 字段 | 类型 | 说明 |
|
|
528
|
+
|------|------|------|
|
|
529
|
+
| `name` | `str` | 工具名称(必填) |
|
|
530
|
+
| `description` | `str \| None` | 工具描述 |
|
|
531
|
+
| `entry` | `str \| None` | 动态加载入口,格式 `module:attr` 或相对 Skill 目录的 `path.py:attr` |
|
|
532
|
+
| `parameters` | `dict[str, Any]` | 参数 Schema 片段,用于构建工具 JSON Schema |
|
|
520
533
|
|
|
521
534
|
---
|
|
522
535
|
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
# AgentKit 示例测试报告
|
|
2
|
+
|
|
3
|
+
> 测试时间:`2026-05-05`
|
|
4
|
+
> 测试环境:`macOS (Apple Silicon)`
|
|
5
|
+
> 模型:`qwen/qwen3.5-flash` (DashScope)
|
|
6
|
+
> AgentKit 版本:v0.7.2
|
|
7
|
+
> Thinking 模式:开启(默认)
|
|
8
|
+
> LLM 调用模式:非流式(默认)
|
|
9
|
+
> 缓存:开启(默认)
|
|
10
|
+
> 执行脚本:`examples/test_standard.py`
|
|
11
|
+
|
|
12
|
+
---
|
|
13
|
+
|
|
14
|
+
## 测试结果
|
|
15
|
+
|
|
16
|
+
| # | 示例 | 文件 | 耗时 | 状态 | 说明 |
|
|
17
|
+
|---|------|------|-----:|:----:|------|
|
|
18
|
+
| 1 | 基础对话 | `01_basic_chat.py` | 11.89s | ✅ | 运行通过 |
|
|
19
|
+
| 2 | 工具调用 | `02_tool_calling.py` | 5.47s | ✅ | 运行通过 |
|
|
20
|
+
| 3 | Skill 使用 | `03_skill_usage.py` | 8.80s | ✅ | 运行通过 |
|
|
21
|
+
| 3B | Skill tools.entry 动态注册/发现 | `03b_skill_tools_entry.py` | 5.83s | ✅ | 运行通过 |
|
|
22
|
+
| 4 | 多 Agent 协作 | `04_multi_agent.py` | 34.73s | ✅ | 运行通过 |
|
|
23
|
+
| 5 | 安全护栏 | `05_guardrail.py` | 4.80s | ✅ | 运行通过 |
|
|
24
|
+
| 6 | 编排 Agent | `06_orchestration.py` | 84.79s | ✅ | 运行通过 |
|
|
25
|
+
| 7 | 同步/异步/流式 | `07_sync_async_stream.py` | 5.88s | ✅ | 运行通过 |
|
|
26
|
+
| 8 | 记忆系统(综合) | `08_memory.py` | 77.63s | ✅ | 运行通过 |
|
|
27
|
+
| 8A | SimpleMemory | `08a_memory_simple_provider.py` | 13.58s | ✅ | 运行通过 |
|
|
28
|
+
| 8B | Mem0Provider | `08b_memory_mem0_provider.py` | 0.21s | ✅ | 未配置 OPENAI_API_KEY,自动跳过 |
|
|
29
|
+
| 8C | 文件持久化 Memory | `08c_memory_file_provider.py` | 19.65s | ✅ | 运行通过 |
|
|
30
|
+
| 9A | 结构化数据(SQL) | `09a_structured_data_sql.py` | 2.41s | ✅ | 运行通过 |
|
|
31
|
+
| 9B | 结构化数据(图) | `09b_structured_data_graph.py` | 2.48s | ✅ | 运行通过 |
|
|
32
|
+
| 9C | NebulaGraphTool(直调) | `09c_nebula_graph_tool.py` | 0.32s | ✅ | 运行通过 |
|
|
33
|
+
| 10 | Skill 生命周期 | `10_skill_lifecycle.py` | 1.53s | ✅ | 运行通过 |
|
|
34
|
+
| 11 | 编排增强 | `11_orchestration_enhancement.py` | 17.11s | ✅ | 运行通过 |
|
|
35
|
+
| 12 | 序列化协议 | `12_run_context_serialization.py` | 0.31s | ✅ | 运行通过 |
|
|
36
|
+
| 13 | Human in the Loop | `13_human_in_the_loop.py` | 4.39s | ✅ | 运行通过 |
|
|
37
|
+
| 14 | Event 标准化 | `14_event_standardization.py` | 5.13s | ✅ | 运行通过 |
|
|
38
|
+
| 15 | 多租户隔离 | `15_multi_tenant_isolation.py` | 4.58s | ✅ | 运行通过 |
|
|
39
|
+
| 16 | 生命周期 Hooks | `16_lifecycle_hooks.py` | 4.74s | ✅ | 运行通过 |
|
|
40
|
+
| 17 | Checkpoint + Handoff + Resume | `17_checkpoint_handoff_resume.py` | 0.17s | ✅ | 运行通过 |
|
|
41
|
+
| 18 | ModelCosplay | `18_model_cosplay.py` | 0.18s | ✅ | 运行通过 |
|
|
42
|
+
| | **合计** | | **316.61s** | **24/24** | |
|
|
43
|
+
|
|
44
|
+
## 耗时分析
|
|
45
|
+
|
|
46
|
+
- **最快示例**:17 Checkpoint + Handoff + Resume (0.17s)
|
|
47
|
+
- **最慢示例**:06 编排 Agent (84.79s)
|
|
48
|
+
- **性能改进**:相比 Ollama 运行,DashScope 接口响应更快,且在大规模编排和记忆检索场景下稳定性更好。
|
|
49
|
+
|
|
50
|
+
## 已知问题
|
|
51
|
+
|
|
52
|
+
| 问题 | 严重程度 | 说明 |
|
|
53
|
+
|------|:--------:|------|
|
|
54
|
+
| 运行异常 | - | 无,24 个示例全部通过 |
|
|
55
|
+
|
|
56
|
+
## 运行方式
|
|
57
|
+
|
|
58
|
+
```bash
|
|
59
|
+
# 在 agentkit 目录执行
|
|
60
|
+
python examples/test_standard.py
|
|
61
|
+
```
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: "skill_name"
|
|
3
|
+
version: "1.0.0"
|
|
4
|
+
description: "一句话说明技能用途"
|
|
5
|
+
author: "your_name"
|
|
6
|
+
license: "MIT"
|
|
7
|
+
triggers:
|
|
8
|
+
- "触发词1"
|
|
9
|
+
- "触发词2"
|
|
10
|
+
dependencies:
|
|
11
|
+
- package1>=1.0
|
|
12
|
+
- package2
|
|
13
|
+
tools:
|
|
14
|
+
- name: "tool_name"
|
|
15
|
+
description: "工具功能简述"
|
|
16
|
+
entry: "tools/tool_module.py:tool_function"
|
|
17
|
+
parameters:
|
|
18
|
+
param1: { type: string, description: "参数说明" }
|
|
19
|
+
param2: { type: integer, default: 10, description: "可选参数" }
|
|
20
|
+
metadata:
|
|
21
|
+
additional_tools:
|
|
22
|
+
- "extra_tool_name"
|
|
23
|
+
sandbox_required: true
|
|
24
|
+
timeout: 30
|
|
25
|
+
---
|
|
26
|
+
|
|
27
|
+
# 🛠️ 技能名称
|
|
28
|
+
|
|
29
|
+
## 🎯 能力边界
|
|
30
|
+
- ✅ 支持:...
|
|
31
|
+
- ❌ 不支持:...
|
|
32
|
+
- ⚠️ 限制:...
|
|
33
|
+
|
|
34
|
+
## 💡 调用示例
|
|
35
|
+
**用户**: "请执行 XX 操作"
|
|
36
|
+
**Agent**:
|
|
37
|
+
```json
|
|
38
|
+
{
|
|
39
|
+
"tool": "tool_name",
|
|
40
|
+
"arguments": { "param1": "value", "param2": 5 }
|
|
41
|
+
}
|
|
@@ -12,12 +12,13 @@ import sys, os
|
|
|
12
12
|
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
|
|
13
13
|
|
|
14
14
|
from agentkit import Agent, Runner
|
|
15
|
+
from model_config import resolve_model
|
|
15
16
|
|
|
16
17
|
# 创建最简 Agent —— 使用本地 Ollama 模型
|
|
17
18
|
agent = Agent(
|
|
18
19
|
name="assistant",
|
|
19
20
|
instructions="你是一个有帮助的中文助手。回答尽量简洁。",
|
|
20
|
-
model="
|
|
21
|
+
model=resolve_model("qwen3.5:cloud"), # 本地 Ollama 模型,无需 API Key
|
|
21
22
|
)
|
|
22
23
|
|
|
23
24
|
# 同步运行
|
|
@@ -14,7 +14,7 @@ import sys, os
|
|
|
14
14
|
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
|
|
15
15
|
|
|
16
16
|
from agentkit import Agent, Runner, function_tool
|
|
17
|
-
|
|
17
|
+
from model_config import resolve_model
|
|
18
18
|
|
|
19
19
|
# ===== 定义工具 =====
|
|
20
20
|
|
|
@@ -38,17 +38,15 @@ def get_weather(city: str) -> str:
|
|
|
38
38
|
}
|
|
39
39
|
return weather_data.get(city, f"{city}:暂无数据")
|
|
40
40
|
|
|
41
|
-
|
|
42
41
|
# ===== 创建 Agent =====
|
|
43
42
|
|
|
44
43
|
agent = Agent(
|
|
45
44
|
name="smart-assistant",
|
|
46
45
|
instructions="你是一个全能助手。可以做数学计算和查天气。根据用户需求选择合适的工具。回答简洁。",
|
|
47
|
-
model="
|
|
46
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
48
47
|
tools=[add, multiply, get_weather],
|
|
49
48
|
)
|
|
50
49
|
|
|
51
|
-
|
|
52
50
|
# ===== 运行测试 =====
|
|
53
51
|
|
|
54
52
|
queries = [
|
|
@@ -14,7 +14,7 @@ import sys, os
|
|
|
14
14
|
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
|
|
15
15
|
|
|
16
16
|
from agentkit import Agent, Runner, Skill, SkillFrontmatter, function_tool
|
|
17
|
-
|
|
17
|
+
from model_config import resolve_model
|
|
18
18
|
|
|
19
19
|
# ===== 定义工具 =====
|
|
20
20
|
|
|
@@ -30,7 +30,6 @@ def get_weather(city: str) -> str:
|
|
|
30
30
|
}
|
|
31
31
|
return weather_data.get(city, f"{city}:暂无数据")
|
|
32
32
|
|
|
33
|
-
|
|
34
33
|
# ===== 定义 Skill =====
|
|
35
34
|
|
|
36
35
|
weather_skill = Skill(
|
|
@@ -49,18 +48,16 @@ weather_skill = Skill(
|
|
|
49
48
|
4. 用简洁的中文回复用户""",
|
|
50
49
|
)
|
|
51
50
|
|
|
52
|
-
|
|
53
51
|
# ===== 创建带 Skill 的 Agent =====
|
|
54
52
|
|
|
55
53
|
agent = Agent(
|
|
56
54
|
name="skill-agent",
|
|
57
55
|
instructions="你是一个智能助手,可以使用专业技能来完成任务。",
|
|
58
|
-
model="
|
|
56
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
59
57
|
skills=[weather_skill],
|
|
60
58
|
tools=[get_weather],
|
|
61
59
|
)
|
|
62
60
|
|
|
63
|
-
|
|
64
61
|
# ===== 运行测试 =====
|
|
65
62
|
|
|
66
63
|
queries = [
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
"""
|
|
2
|
+
示例 3B:SKILL.md tools.entry 动态工具注册/发现(Ollama 版)
|
|
3
|
+
|
|
4
|
+
运行前请确保:
|
|
5
|
+
ollama serve
|
|
6
|
+
ollama pull qwen3.5:cloud
|
|
7
|
+
|
|
8
|
+
运行:
|
|
9
|
+
python examples/ollama/03b_skill_tools_entry.py
|
|
10
|
+
"""
|
|
11
|
+
import os
|
|
12
|
+
import sys
|
|
13
|
+
from pathlib import Path
|
|
14
|
+
|
|
15
|
+
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
|
|
16
|
+
|
|
17
|
+
from agentkit import Agent, Runner, load_skill_from_dir
|
|
18
|
+
from model_config import resolve_model
|
|
19
|
+
|
|
20
|
+
skill_dir = Path(__file__).resolve().parents[1] / "skills" / "weather-tools-entry"
|
|
21
|
+
weather_skill = load_skill_from_dir(skill_dir)
|
|
22
|
+
|
|
23
|
+
agent = Agent(
|
|
24
|
+
name="skill-tools-entry-agent",
|
|
25
|
+
instructions="你是天气助手。遇到天气问题优先加载并使用 weather-tools-entry Skill。",
|
|
26
|
+
model=resolve_model(),
|
|
27
|
+
skills=[weather_skill],
|
|
28
|
+
)
|
|
29
|
+
|
|
30
|
+
queries = [
|
|
31
|
+
"深圳今天适合穿什么?",
|
|
32
|
+
"广州今天需要带伞吗?",
|
|
33
|
+
]
|
|
34
|
+
|
|
35
|
+
for q in queries:
|
|
36
|
+
print(f"\n用户: {q}")
|
|
37
|
+
result = Runner.run_sync(agent, input=q)
|
|
38
|
+
if result.success:
|
|
39
|
+
print(f"助手: {result.final_output}")
|
|
40
|
+
else:
|
|
41
|
+
print(f"❌ 错误: {result.error}")
|
|
42
|
+
|
|
43
|
+
for event in result.events:
|
|
44
|
+
if event.type == "tool_result":
|
|
45
|
+
print(f" 🔧 {event.data.get('tool')}: {event.data.get('result')}")
|
|
@@ -14,7 +14,7 @@ import sys, os
|
|
|
14
14
|
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
|
|
15
15
|
|
|
16
16
|
from agentkit import Agent, Runner
|
|
17
|
-
|
|
17
|
+
from model_config import resolve_model
|
|
18
18
|
|
|
19
19
|
# ============================================================
|
|
20
20
|
# 模式 A:as_tool(委派)
|
|
@@ -27,13 +27,13 @@ print("=" * 50)
|
|
|
27
27
|
researcher = Agent(
|
|
28
28
|
name="researcher",
|
|
29
29
|
instructions="你是一个研究助手。收到问题后,给出简短的研究结论(不超过 3 句话)。",
|
|
30
|
-
model="
|
|
30
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
31
31
|
)
|
|
32
32
|
|
|
33
33
|
manager = Agent(
|
|
34
34
|
name="manager",
|
|
35
35
|
instructions="你是项目经理。需要研究信息时调用 research 工具。综合研究结果给出你的建议。",
|
|
36
|
-
model="
|
|
36
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
37
37
|
tools=[
|
|
38
38
|
researcher.as_tool("research", "调用研究助手获取研究信息"),
|
|
39
39
|
],
|
|
@@ -49,7 +49,6 @@ for event in result.events:
|
|
|
49
49
|
if event.type == "tool_result":
|
|
50
50
|
print(f" 🔧 研究员返回: {str(event.data)[:100]}")
|
|
51
51
|
|
|
52
|
-
|
|
53
52
|
# ============================================================
|
|
54
53
|
# 模式 B:Handoff(转介)
|
|
55
54
|
# ============================================================
|
|
@@ -61,19 +60,19 @@ print("=" * 50)
|
|
|
61
60
|
billing_agent = Agent(
|
|
62
61
|
name="billing",
|
|
63
62
|
instructions="你是账单专家。处理所有账单相关的问题,给出专业的解答。",
|
|
64
|
-
model="
|
|
63
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
65
64
|
)
|
|
66
65
|
|
|
67
66
|
tech_agent = Agent(
|
|
68
67
|
name="tech",
|
|
69
68
|
instructions="你是技术支持专家。处理所有技术相关的问题。",
|
|
70
|
-
model="
|
|
69
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
71
70
|
)
|
|
72
71
|
|
|
73
72
|
triage_agent = Agent(
|
|
74
73
|
name="triage",
|
|
75
74
|
instructions="你是客服分诊员。根据用户问题类型,转交给合适的专家:账单问题转给 billing,技术问题转给 tech。",
|
|
76
|
-
model="
|
|
75
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
77
76
|
handoffs=[billing_agent, tech_agent],
|
|
78
77
|
)
|
|
79
78
|
|
|
@@ -18,7 +18,7 @@ from agentkit import (
|
|
|
18
18
|
input_guardrail, output_guardrail, GuardrailResult,
|
|
19
19
|
PermissionPolicy,
|
|
20
20
|
)
|
|
21
|
-
|
|
21
|
+
from model_config import resolve_model
|
|
22
22
|
|
|
23
23
|
# ===== 定义工具 =====
|
|
24
24
|
|
|
@@ -32,7 +32,6 @@ def delete_file(filename: str) -> str:
|
|
|
32
32
|
"""删除文件"""
|
|
33
33
|
return f"[模拟] 已删除文件 {filename}"
|
|
34
34
|
|
|
35
|
-
|
|
36
35
|
# ===== 定义护栏 =====
|
|
37
36
|
|
|
38
37
|
@input_guardrail
|
|
@@ -54,13 +53,12 @@ async def check_output_safety(ctx, output):
|
|
|
54
53
|
return GuardrailResult(triggered=True, reason=f"输出包含危险内容: {word}")
|
|
55
54
|
return GuardrailResult(triggered=False)
|
|
56
55
|
|
|
57
|
-
|
|
58
56
|
# ===== 创建带安全护栏的 Agent =====
|
|
59
57
|
|
|
60
58
|
agent = Agent(
|
|
61
59
|
name="safe-agent",
|
|
62
60
|
instructions="你是一个安全的助手。可以帮用户读取文件,但不能删除文件。",
|
|
63
|
-
model="
|
|
61
|
+
model=resolve_model("qwen3.5:cloud"),
|
|
64
62
|
tools=[read_file, delete_file],
|
|
65
63
|
input_guardrails=[block_sensitive_words],
|
|
66
64
|
output_guardrails=[check_output_safety],
|
|
@@ -70,7 +68,6 @@ agent = Agent(
|
|
|
70
68
|
),
|
|
71
69
|
)
|
|
72
70
|
|
|
73
|
-
|
|
74
71
|
# ===== 运行测试 =====
|
|
75
72
|
|
|
76
73
|
print("=" * 50)
|
|
@@ -13,22 +13,19 @@ sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
|
|
|
13
13
|
from agentkit import Agent
|
|
14
14
|
from agentkit.tools.base_tool import request_human_input
|
|
15
15
|
from agentkit.tools.function_tool import FunctionTool
|
|
16
|
-
|
|
16
|
+
from model_config import resolve_model
|
|
17
17
|
|
|
18
18
|
def confirm_action(action: str) -> str:
|
|
19
19
|
"""敏感操作执行前请求人工确认。"""
|
|
20
20
|
request_human_input(f"即将执行敏感操作: {action},请确认 (approve/reject)")
|
|
21
21
|
|
|
22
|
-
|
|
23
22
|
def execute_action(action: str) -> str:
|
|
24
23
|
"""执行操作(示例返回)。"""
|
|
25
24
|
return f"操作 '{action}' 已执行。"
|
|
26
25
|
|
|
27
|
-
|
|
28
26
|
confirm_tool = FunctionTool.from_function(confirm_action)
|
|
29
27
|
execute_tool = FunctionTool.from_function(execute_action)
|
|
30
28
|
|
|
31
|
-
|
|
32
29
|
agent = Agent(
|
|
33
30
|
name="hitl-agent",
|
|
34
31
|
instructions=(
|
|
@@ -37,6 +34,6 @@ agent = Agent(
|
|
|
37
34
|
"收到确认后再调用 execute_action。"
|
|
38
35
|
),
|
|
39
36
|
# 使用纯本地模型,避免 cloud 变体在未鉴权/网络抖动时触发远端 502。
|
|
40
|
-
model=
|
|
37
|
+
model=resolve_model(),
|
|
41
38
|
tools=[confirm_tool, execute_tool],
|
|
42
39
|
)
|