Skip to content

Commit 1f91f54

Browse files
feat(adk/backend): implement Agentkit Sandbox and Local filesystem backend adapters (#651)
Introduces two new backend implementations for the adk/backend filesystem interface to support flexible file operations in different execution environments: a remote Agentkit Sandbox backend for secure isolated execution and a local backend for direct filesystem access. **Agentkit Sandbox Backend ** - Implements filesystem.Backend interface to integrate with Volcengine's Agentkit Sandbox API - Provides secure remote code execution with request signing using HMAC-SHA256 - Manages session lifecycle with automatic token refresh and expiration handling - Supports all core filesystem operations: LsInfo, Read, Write, Edit, GrepRaw, GlobInfo - Includes Python code templates for sandbox execution with proper error handling - Defines comprehensive API types for request/response structures **Local Backend (local)** - Implements filesystem.Backend interface for direct local filesystem operations - Supports directory listing (LsInfo) with configurable depth and ignore patterns - Provides file reading (Read) with line-based pagination (offset/limit support) - Enables file writing (Write) with automatic directory creation - Implements content search (GrepRaw) with regex pattern matching - Supports glob pattern matching (GlobInfo) for file discovery - Includes robust input validation (absolute path enforcement, permission checks) **Testing & Documentation** - Adds comprehensive unit tests for both backends (323 lines for agentkit, 700 lines for local) - Provides detailed README documentation with usage examples and API references - Includes example implementations demonstrating backend and middleware integration - Updates dependency management (go.mod/go.sum) with required packages **Technical Details** - Total additions: 4,216 lines across 16 files - Both backends implement the same filesystem.Backend interface for consistency - Error handling follows Go conventions with wrapped errors for context - Middleware examples demonstrate authentication and logging patterns
1 parent 25c5d51 commit 1f91f54

File tree

16 files changed

+4169
-0
lines changed

16 files changed

+4169
-0
lines changed

adk/backend/agentkit/README.md

Lines changed: 288 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,288 @@
1+
# Ark Sandbox Backend
2+
3+
A secure filesystem backend for EINO ADK that executes operations in Volcengine's isolated Ark Sandbox environment.
4+
5+
## Quick Start
6+
7+
### Installation
8+
9+
```bash
10+
go get github.com/cloudwego/eino-ext/adk/backend/arksandbox
11+
```
12+
13+
### Basic Usage
14+
15+
```go
16+
import (
17+
"context"
18+
"os"
19+
"time"
20+
21+
"github.com/cloudwego/eino-ext/adk/backend/arksandbox"
22+
"github.com/cloudwego/eino/adk/middlewares/filesystem"
23+
)
24+
25+
// Configure with credentials
26+
config := &arksandbox.Config{
27+
AccessKeyID: os.Getenv("VOLC_ACCESS_KEY_ID"),
28+
SecretAccessKey: os.Getenv("VOLC_SECRET_ACCESS_KEY"),
29+
ToolID: os.Getenv("VOLC_TOOL_ID"),
30+
UserSessionID: "session-" + time.Now().Format("20060102-150405"),
31+
Region: arksandbox.RegionOfBeijing,
32+
}
33+
34+
// Initialize backend
35+
backend, err := arksandbox.NewArkSandboxBackend(config)
36+
if err != nil {
37+
panic(err)
38+
}
39+
40+
// Use the backend
41+
backend.Write(ctx, &filesystem.WriteRequest{
42+
FilePath: "/home/gem/file.txt",
43+
Content: "Hello, Sandbox!",
44+
})
45+
```
46+
47+
## Features
48+
49+
- **Secure Execution** - All operations run in isolated sandbox environment
50+
- **Session Management** - Supports session isolation with configurable TTL
51+
- **Full Backend Implementation** - Supports all `filesystem.Backend` operations
52+
- **Request Signing** - Automatic AK/SK authentication with Volcengine
53+
- **Remote Execution** - Python-based sandbox operations with result streaming
54+
55+
## Configuration
56+
57+
```go
58+
type Config struct {
59+
// Required: Volcengine credentials
60+
AccessKeyID string
61+
SecretAccessKey string
62+
ToolID string // Sandbox tool ID from Volcengine console
63+
UserSessionID string // Unique session ID for isolation
64+
65+
// Optional: Defaults provided
66+
Region Region // Default: RegionOfBeijing
67+
SessionTTL int // Default: 1800 seconds (30 min)
68+
ExecutionTimeout int
69+
Timeout time.Duration // HTTP client timeout
70+
}
71+
```
72+
73+
### Environment Setup
74+
75+
```bash
76+
# Set credentials as environment variables
77+
export VOLC_ACCESS_KEY_ID="your_access_key"
78+
export VOLC_SECRET_ACCESS_KEY="your_secret_key"
79+
export VOLC_TOOL_ID="your_tool_id"
80+
```
81+
82+
**Get Credentials:**
83+
1. Log in to [Volcengine Console](https://console.volcengine.com/)
84+
2. Navigate to IAM → Access Keys
85+
3. Create Ark Sandbox tool in Ark Platform
86+
4. Copy credentials and tool ID
87+
88+
## Examples
89+
90+
### Example 1: File Operations
91+
92+
Basic file operations in the sandbox environment.
93+
94+
```go
95+
package main
96+
97+
import (
98+
"context"
99+
"fmt"
100+
"log"
101+
"os"
102+
"time"
103+
104+
"github.com/cloudwego/eino-ext/adk/backend/arksandbox"
105+
"github.com/cloudwego/eino/adk/middlewares/filesystem"
106+
)
107+
108+
func main() {
109+
ctx := context.Background()
110+
111+
// Initialize backend
112+
backend, err := arksandbox.NewArkSandboxBackend(&arksandbox.Config{
113+
AccessKeyID: os.Getenv("VOLC_ACCESS_KEY_ID"),
114+
SecretAccessKey: os.Getenv("VOLC_SECRET_ACCESS_KEY"),
115+
ToolID: os.Getenv("VOLC_TOOL_ID"),
116+
UserSessionID: "example-" + time.Now().Format("20060102-150405"),
117+
Region: arksandbox.RegionOfBeijing,
118+
})
119+
if err != nil {
120+
log.Fatal(err)
121+
}
122+
123+
// Write file
124+
backend.Write(ctx, &filesystem.WriteRequest{
125+
FilePath: "/home/gem/test.txt",
126+
Content: "Hello from Ark Sandbox!",
127+
})
128+
129+
// Read file
130+
content, _ := backend.Read(ctx, &filesystem.ReadRequest{
131+
FilePath: "/home/gem/test.txt",
132+
})
133+
fmt.Println("Content:", content)
134+
135+
// List directory
136+
files, _ := backend.LsInfo(ctx, &filesystem.LsInfoRequest{
137+
Path: "/home/gem",
138+
})
139+
fmt.Printf("Found %d files\n", len(files))
140+
}
141+
```
142+
143+
**Output:**
144+
```
145+
Content: 1 Hello from Ark Sandbox!
146+
Found 1 files
147+
```
148+
149+
### Example 2: Search Operations
150+
151+
Search and pattern matching in sandbox files.
152+
153+
```go
154+
// Search for pattern
155+
matches, _ := backend.GrepRaw(ctx, &filesystem.GrepRequest{
156+
Path: "/home/gem",
157+
Pattern: "Sandbox",
158+
Glob: "*.txt",
159+
})
160+
161+
for _, match := range matches {
162+
fmt.Printf("%s:%d - %s\n", match.Path, match.Line, match.Content)
163+
}
164+
165+
// Find files by pattern
166+
files, _ := backend.GlobInfo(ctx, &filesystem.GlobInfoRequest{
167+
Path: "/home/gem",
168+
Pattern: "**/*.txt",
169+
})
170+
171+
fmt.Printf("Found %d .txt files\n", len(files))
172+
```
173+
174+
**Output:**
175+
```
176+
/home/gem/test.txt:1 - Hello from Ark Sandbox!
177+
Found 1 .txt files
178+
```
179+
180+
### Example 3: Agent Integration
181+
182+
Build AI-powered filesystem assistant with sandbox backend.
183+
184+
```go
185+
import (
186+
"github.com/cloudwego/eino/adk"
187+
"github.com/cloudwego/eino/components/model/openai"
188+
)
189+
190+
// Create backend
191+
backend, _ := arksandbox.NewArkSandboxBackend(config)
192+
193+
// Create middleware
194+
middleware, _ := filesystem.NewMiddleware(ctx, &filesystem.Config{
195+
Backend: backend,
196+
})
197+
198+
// Create agent with ChatModel
199+
chatModel, _ := openai.NewChatModel(ctx, &openai.ChatModelConfig{
200+
APIKey: os.Getenv("OPENAI_API_KEY"),
201+
Model: "gpt-4",
202+
})
203+
204+
agent, _ := adk.NewChatModelAgent(ctx, &adk.ChatModelAgentConfig{
205+
Name: "SandboxAgent",
206+
Description: "AI agent for secure filesystem operations",
207+
Model: chatModel,
208+
Middlewares: []adk.AgentMiddleware{middleware},
209+
})
210+
211+
// Execute user query
212+
input := &adk.AgentInput{
213+
Messages: []*schema.Message{
214+
schema.UserMessage("List all files in /home/gem and show their details"),
215+
},
216+
}
217+
218+
for event := range agent.Run(ctx, input) {
219+
// Process agent events
220+
}
221+
```
222+
223+
## API Reference
224+
225+
### Core Methods
226+
227+
- **`LsInfo(ctx, req)`** - List directory contents
228+
- **`Read(ctx, req)`** - Read file with optional line offset/limit
229+
- **`Write(ctx, req)`** - Create new file (fails if exists)
230+
- **`Edit(ctx, req)`** - Search and replace in file
231+
- **`GrepRaw(ctx, req)`** - Search pattern in files
232+
- **`GlobInfo(ctx, req)`** - Find files by glob pattern
233+
234+
**Note:** Use `/home/gem` directory for file operations. The default `gem` user has limited permissions on system paths.
235+
236+
## Security
237+
238+
### Best Practices
239+
240+
- ✅ Store credentials in environment variables, never in code
241+
- ✅ Use unique session IDs for each execution context
242+
- ✅ Set appropriate timeouts to prevent resource exhaustion
243+
- ✅ Monitor sandbox resource usage in production
244+
- ✅ Implement proper error handling and retry logic
245+
246+
### Session Isolation
247+
248+
```go
249+
// Each user/context should have unique session ID
250+
config := &arksandbox.Config{
251+
UserSessionID: fmt.Sprintf("user-%s-%d", userID, time.Now().Unix()),
252+
SessionTTL: 3600, // 1 hour
253+
}
254+
```
255+
256+
## Troubleshooting
257+
258+
**File Already Exists**
259+
- `Write()` fails if file exists (safety feature)
260+
- Delete file first or use unique filenames
261+
262+
**Authentication Errors**
263+
- Verify credentials are correct
264+
- Check environment variables are set
265+
- Ensure Volcengine account has Ark Sandbox access
266+
267+
**Timeout Errors**
268+
- Increase `Timeout` or `ExecutionTimeout` in config
269+
- Check network connectivity
270+
- Verify Ark Sandbox service availability
271+
272+
## FAQ
273+
274+
**Q: What's the difference from Local backend?**
275+
A: Ark Sandbox executes in isolated remote environment (secure, sandboxed). Local backend accesses local filesystem directly (fast, simple).
276+
277+
**Q: Can I use this in production?**
278+
A: Yes. Ensure proper error handling, timeouts, unique session IDs, and resource monitoring.
279+
280+
**Q: What are the rate limits?**
281+
A: Limits depend on your Volcengine account tier. Check Volcengine documentation for details.
282+
283+
**Q: How long do sessions last?**
284+
A: Default is 30 minutes (1800 seconds). Configure with `SessionTTL` (range: 60-86400 seconds).
285+
286+
## License
287+
288+
Licensed under the Apache License, Version 2.0. See the [LICENSE](../../LICENSE) file for details.

0 commit comments

Comments
 (0)