@clawnet/template-minimal 0.0.1
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.
- package/.agents/skills/claude-agent-sdk/.claude-plugin/plugin.json +13 -0
- package/.agents/skills/claude-agent-sdk/SKILL.md +954 -0
- package/.agents/skills/claude-agent-sdk/references/mcp-servers-guide.md +387 -0
- package/.agents/skills/claude-agent-sdk/references/permissions-guide.md +429 -0
- package/.agents/skills/claude-agent-sdk/references/query-api-reference.md +437 -0
- package/.agents/skills/claude-agent-sdk/references/session-management.md +419 -0
- package/.agents/skills/claude-agent-sdk/references/subagents-patterns.md +464 -0
- package/.agents/skills/claude-agent-sdk/references/top-errors.md +503 -0
- package/.agents/skills/claude-agent-sdk/rules/claude-agent-sdk.md +96 -0
- package/.agents/skills/claude-agent-sdk/scripts/check-versions.sh +55 -0
- package/.agents/skills/claude-agent-sdk/templates/basic-query.ts +55 -0
- package/.agents/skills/claude-agent-sdk/templates/custom-mcp-server.ts +161 -0
- package/.agents/skills/claude-agent-sdk/templates/error-handling.ts +283 -0
- package/.agents/skills/claude-agent-sdk/templates/filesystem-settings.ts +211 -0
- package/.agents/skills/claude-agent-sdk/templates/multi-agent-workflow.ts +318 -0
- package/.agents/skills/claude-agent-sdk/templates/package.json +30 -0
- package/.agents/skills/claude-agent-sdk/templates/permission-control.ts +211 -0
- package/.agents/skills/claude-agent-sdk/templates/query-with-tools.ts +54 -0
- package/.agents/skills/claude-agent-sdk/templates/session-management.ts +151 -0
- package/.agents/skills/claude-agent-sdk/templates/subagents-orchestration.ts +166 -0
- package/.agents/skills/claude-agent-sdk/templates/tsconfig.json +22 -0
- package/.claude/settings.local.json +70 -0
- package/.claude/skills/moltbook-example/SKILL.md +79 -0
- package/.claude/skills/post/SKILL.md +130 -0
- package/.env.example +4 -0
- package/.vercel/README.txt +11 -0
- package/.vercel/project.json +1 -0
- package/AGENTS.md +114 -0
- package/CLAUDE.md +532 -0
- package/README.md +44 -0
- package/api/index.ts +3 -0
- package/biome.json +14 -0
- package/clark_avatar.jpeg +0 -0
- package/package.json +21 -0
- package/scripts/wake.ts +38 -0
- package/skills/clawbook/HEARTBEAT.md +142 -0
- package/skills/clawbook/SKILL.md +219 -0
- package/skills/moltbook-example/SKILL.md +79 -0
- package/skills/moltbook-example/bot/index.ts +61 -0
- package/src/agent/prompts.ts +98 -0
- package/src/agent/runner.ts +526 -0
- package/src/agent/tool-definitions.ts +1151 -0
- package/src/agent-options.ts +14 -0
- package/src/bot-identity.ts +41 -0
- package/src/constants.ts +15 -0
- package/src/handlers/heartbeat.ts +21 -0
- package/src/handlers/openai-compat.ts +95 -0
- package/src/handlers/post.ts +21 -0
- package/src/identity.ts +83 -0
- package/src/index.ts +30 -0
- package/src/middleware/cron-auth.ts +53 -0
- package/src/middleware/sigma-auth.ts +147 -0
- package/src/runs.ts +49 -0
- package/tests/agent/prompts.test.ts +172 -0
- package/tests/agent/runner.test.ts +353 -0
- package/tests/agent/tool-definitions.test.ts +171 -0
- package/tests/constants.test.ts +24 -0
- package/tests/handlers/openai-compat.test.ts +128 -0
- package/tests/handlers.test.ts +133 -0
- package/tests/identity.test.ts +66 -0
- package/tests/index.test.ts +108 -0
- package/tests/middleware/cron-auth.test.ts +99 -0
- package/tests/middleware/sigma-auth.test.ts +198 -0
- package/tests/runs.test.ts +56 -0
- package/tests/skill.test.ts +71 -0
- package/tsconfig.json +14 -0
- package/vercel.json +9 -0
|
@@ -0,0 +1,429 @@
|
|
|
1
|
+
# Permissions Guide
|
|
2
|
+
|
|
3
|
+
Complete guide to permission control in Claude Agent SDK.
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## Permission Modes
|
|
8
|
+
|
|
9
|
+
### Overview
|
|
10
|
+
|
|
11
|
+
Three built-in modes:
|
|
12
|
+
|
|
13
|
+
| Mode | Behavior | Use Case |
|
|
14
|
+
|------|----------|----------|
|
|
15
|
+
| `default` | Standard checks | General use, production |
|
|
16
|
+
| `acceptEdits` | Auto-approve file edits | Trusted refactoring |
|
|
17
|
+
| `bypassPermissions` | Skip ALL checks | CI/CD, sandboxed envs |
|
|
18
|
+
|
|
19
|
+
---
|
|
20
|
+
|
|
21
|
+
## Default Mode
|
|
22
|
+
|
|
23
|
+
Standard permission checks.
|
|
24
|
+
|
|
25
|
+
```typescript
|
|
26
|
+
options: {
|
|
27
|
+
permissionMode: "default"
|
|
28
|
+
}
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
**Prompts user for**:
|
|
32
|
+
- File writes/edits
|
|
33
|
+
- Potentially dangerous bash commands
|
|
34
|
+
- Sensitive operations
|
|
35
|
+
|
|
36
|
+
**Auto-allows**:
|
|
37
|
+
- Read operations (Read, Grep, Glob)
|
|
38
|
+
- Safe bash commands
|
|
39
|
+
|
|
40
|
+
---
|
|
41
|
+
|
|
42
|
+
## Accept Edits Mode
|
|
43
|
+
|
|
44
|
+
Automatically approves file modifications.
|
|
45
|
+
|
|
46
|
+
```typescript
|
|
47
|
+
options: {
|
|
48
|
+
permissionMode: "acceptEdits"
|
|
49
|
+
}
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
**Auto-approves**:
|
|
53
|
+
- File edits (Edit)
|
|
54
|
+
- File writes (Write)
|
|
55
|
+
|
|
56
|
+
**Still prompts for**:
|
|
57
|
+
- Dangerous bash commands
|
|
58
|
+
- Sensitive operations
|
|
59
|
+
|
|
60
|
+
**Use when**: Refactoring, code generation workflows
|
|
61
|
+
|
|
62
|
+
---
|
|
63
|
+
|
|
64
|
+
## Bypass Permissions Mode
|
|
65
|
+
|
|
66
|
+
⚠️ **DANGER**: Skips ALL permission checks.
|
|
67
|
+
|
|
68
|
+
```typescript
|
|
69
|
+
options: {
|
|
70
|
+
permissionMode: "bypassPermissions"
|
|
71
|
+
}
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
**Auto-approves EVERYTHING**:
|
|
75
|
+
- All file operations
|
|
76
|
+
- All bash commands
|
|
77
|
+
- All tools
|
|
78
|
+
|
|
79
|
+
**ONLY use in**:
|
|
80
|
+
- CI/CD pipelines
|
|
81
|
+
- Sandboxed containers
|
|
82
|
+
- Docker environments
|
|
83
|
+
- Trusted, isolated contexts
|
|
84
|
+
|
|
85
|
+
**NEVER use in**:
|
|
86
|
+
- Production systems
|
|
87
|
+
- User-facing environments
|
|
88
|
+
- Untrusted inputs
|
|
89
|
+
|
|
90
|
+
---
|
|
91
|
+
|
|
92
|
+
## Custom Permission Logic
|
|
93
|
+
|
|
94
|
+
### canUseTool Callback
|
|
95
|
+
|
|
96
|
+
```typescript
|
|
97
|
+
type CanUseTool = (
|
|
98
|
+
toolName: string,
|
|
99
|
+
input: any
|
|
100
|
+
) => Promise<PermissionDecision>;
|
|
101
|
+
|
|
102
|
+
type PermissionDecision =
|
|
103
|
+
| { behavior: "allow" }
|
|
104
|
+
| { behavior: "deny"; message?: string }
|
|
105
|
+
| { behavior: "ask"; message?: string };
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
### Basic Example
|
|
109
|
+
|
|
110
|
+
```typescript
|
|
111
|
+
options: {
|
|
112
|
+
canUseTool: async (toolName, input) => {
|
|
113
|
+
// Allow read-only
|
|
114
|
+
if (['Read', 'Grep', 'Glob'].includes(toolName)) {
|
|
115
|
+
return { behavior: "allow" };
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
// Deny dangerous bash
|
|
119
|
+
if (toolName === 'Bash' && input.command.includes('rm -rf')) {
|
|
120
|
+
return {
|
|
121
|
+
behavior: "deny",
|
|
122
|
+
message: "Destructive command blocked"
|
|
123
|
+
};
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
// Ask for confirmation
|
|
127
|
+
if (toolName === 'Write') {
|
|
128
|
+
return {
|
|
129
|
+
behavior: "ask",
|
|
130
|
+
message: `Create ${input.file_path}?`
|
|
131
|
+
};
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
return { behavior: "allow" };
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
---
|
|
140
|
+
|
|
141
|
+
## Common Patterns
|
|
142
|
+
|
|
143
|
+
### Pattern 1: Block Destructive Commands
|
|
144
|
+
|
|
145
|
+
```typescript
|
|
146
|
+
canUseTool: async (toolName, input) => {
|
|
147
|
+
if (toolName === 'Bash') {
|
|
148
|
+
const dangerous = [
|
|
149
|
+
'rm -rf',
|
|
150
|
+
'dd if=',
|
|
151
|
+
'mkfs',
|
|
152
|
+
'> /dev/',
|
|
153
|
+
'shutdown',
|
|
154
|
+
'reboot',
|
|
155
|
+
'kill -9',
|
|
156
|
+
'pkill'
|
|
157
|
+
];
|
|
158
|
+
|
|
159
|
+
for (const pattern of dangerous) {
|
|
160
|
+
if (input.command.includes(pattern)) {
|
|
161
|
+
return {
|
|
162
|
+
behavior: "deny",
|
|
163
|
+
message: `Blocked dangerous command: ${pattern}`
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
return { behavior: "allow" };
|
|
170
|
+
}
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
### Pattern 2: Protect Sensitive Files
|
|
174
|
+
|
|
175
|
+
```typescript
|
|
176
|
+
canUseTool: async (toolName, input) => {
|
|
177
|
+
if (toolName === 'Write' || toolName === 'Edit') {
|
|
178
|
+
const sensitivePaths = [
|
|
179
|
+
'/etc/',
|
|
180
|
+
'/root/',
|
|
181
|
+
'.env',
|
|
182
|
+
'credentials',
|
|
183
|
+
'secrets',
|
|
184
|
+
'config/production',
|
|
185
|
+
'.ssh/',
|
|
186
|
+
'private_key'
|
|
187
|
+
];
|
|
188
|
+
|
|
189
|
+
for (const path of sensitivePaths) {
|
|
190
|
+
if (input.file_path?.includes(path)) {
|
|
191
|
+
return {
|
|
192
|
+
behavior: "ask",
|
|
193
|
+
message: `⚠️ Modify sensitive file: ${input.file_path}?`
|
|
194
|
+
};
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
return { behavior: "allow" };
|
|
200
|
+
}
|
|
201
|
+
```
|
|
202
|
+
|
|
203
|
+
### Pattern 3: Environment-Based Permissions
|
|
204
|
+
|
|
205
|
+
```typescript
|
|
206
|
+
const environment = process.env.NODE_ENV; // 'development' | 'staging' | 'production'
|
|
207
|
+
|
|
208
|
+
canUseTool: async (toolName, input) => {
|
|
209
|
+
// Production: require approval for everything
|
|
210
|
+
if (environment === 'production') {
|
|
211
|
+
if (toolName === 'Bash' || toolName === 'Write' || toolName === 'Edit') {
|
|
212
|
+
return {
|
|
213
|
+
behavior: "ask",
|
|
214
|
+
message: `PRODUCTION: Approve ${toolName}?`
|
|
215
|
+
};
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
// Staging: auto-approve edits
|
|
220
|
+
if (environment === 'staging') {
|
|
221
|
+
if (toolName === 'Write' || toolName === 'Edit') {
|
|
222
|
+
return { behavior: "allow" };
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
// Development: allow most things
|
|
227
|
+
if (environment === 'development') {
|
|
228
|
+
return { behavior: "allow" };
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
return { behavior: "allow" };
|
|
232
|
+
}
|
|
233
|
+
```
|
|
234
|
+
|
|
235
|
+
### Pattern 4: Deployment Confirmation
|
|
236
|
+
|
|
237
|
+
```typescript
|
|
238
|
+
canUseTool: async (toolName, input) => {
|
|
239
|
+
if (toolName === 'Bash') {
|
|
240
|
+
const deploymentPatterns = [
|
|
241
|
+
'deploy',
|
|
242
|
+
'kubectl apply',
|
|
243
|
+
'terraform apply',
|
|
244
|
+
'helm install',
|
|
245
|
+
'docker push',
|
|
246
|
+
'npm publish'
|
|
247
|
+
];
|
|
248
|
+
|
|
249
|
+
for (const pattern of deploymentPatterns) {
|
|
250
|
+
if (input.command.includes(pattern)) {
|
|
251
|
+
return {
|
|
252
|
+
behavior: "ask",
|
|
253
|
+
message: `🚀 DEPLOYMENT: ${input.command}\n\nProceed?`
|
|
254
|
+
};
|
|
255
|
+
}
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
return { behavior: "allow" };
|
|
260
|
+
}
|
|
261
|
+
```
|
|
262
|
+
|
|
263
|
+
### Pattern 5: Audit Logging
|
|
264
|
+
|
|
265
|
+
```typescript
|
|
266
|
+
const auditLog: Array<{
|
|
267
|
+
tool: string;
|
|
268
|
+
input: any;
|
|
269
|
+
decision: string;
|
|
270
|
+
timestamp: Date;
|
|
271
|
+
}> = [];
|
|
272
|
+
|
|
273
|
+
canUseTool: async (toolName, input) => {
|
|
274
|
+
// Log everything
|
|
275
|
+
console.log(`[${new Date().toISOString()}] ${toolName}`);
|
|
276
|
+
|
|
277
|
+
const decision = { behavior: "allow" as const };
|
|
278
|
+
|
|
279
|
+
// Store audit log
|
|
280
|
+
auditLog.push({
|
|
281
|
+
tool: toolName,
|
|
282
|
+
input,
|
|
283
|
+
decision: decision.behavior,
|
|
284
|
+
timestamp: new Date()
|
|
285
|
+
});
|
|
286
|
+
|
|
287
|
+
// Could also send to external service
|
|
288
|
+
// await logToDatadog(toolName, input, decision);
|
|
289
|
+
|
|
290
|
+
return decision;
|
|
291
|
+
}
|
|
292
|
+
```
|
|
293
|
+
|
|
294
|
+
---
|
|
295
|
+
|
|
296
|
+
## Combining Modes with Custom Logic
|
|
297
|
+
|
|
298
|
+
```typescript
|
|
299
|
+
options: {
|
|
300
|
+
permissionMode: "acceptEdits", // Auto-approve file edits
|
|
301
|
+
canUseTool: async (toolName, input) => {
|
|
302
|
+
// But still block dangerous bash
|
|
303
|
+
if (toolName === 'Bash' && input.command.includes('rm -rf')) {
|
|
304
|
+
return { behavior: "deny", message: "Blocked" };
|
|
305
|
+
}
|
|
306
|
+
|
|
307
|
+
// Custom logic runs AFTER permission mode
|
|
308
|
+
return { behavior: "allow" };
|
|
309
|
+
}
|
|
310
|
+
}
|
|
311
|
+
```
|
|
312
|
+
|
|
313
|
+
---
|
|
314
|
+
|
|
315
|
+
## Security Best Practices
|
|
316
|
+
|
|
317
|
+
### ✅ Do
|
|
318
|
+
|
|
319
|
+
- Start with `"default"` mode
|
|
320
|
+
- Use `canUseTool` for fine-grained control
|
|
321
|
+
- Block known dangerous patterns
|
|
322
|
+
- Require confirmation for sensitive ops
|
|
323
|
+
- Log all tool usage for auditing
|
|
324
|
+
- Test permission logic thoroughly
|
|
325
|
+
- Use environment-based rules
|
|
326
|
+
- Implement rate limiting if needed
|
|
327
|
+
|
|
328
|
+
### ❌ Don't
|
|
329
|
+
|
|
330
|
+
- Use `"bypassPermissions"` in production
|
|
331
|
+
- Skip permission checks for "trusted" inputs
|
|
332
|
+
- Allow arbitrary bash without filtering
|
|
333
|
+
- Trust file paths without validation
|
|
334
|
+
- Ignore audit logging
|
|
335
|
+
- Assume AI won't make mistakes
|
|
336
|
+
- Give blanket approvals
|
|
337
|
+
|
|
338
|
+
---
|
|
339
|
+
|
|
340
|
+
## Testing Permissions
|
|
341
|
+
|
|
342
|
+
```typescript
|
|
343
|
+
async function testPermissions() {
|
|
344
|
+
const tests = [
|
|
345
|
+
{ tool: "Read", input: { file_path: "/etc/passwd" }, expectAllow: true },
|
|
346
|
+
{ tool: "Bash", input: { command: "rm -rf /" }, expectDeny: true },
|
|
347
|
+
{ tool: "Write", input: { file_path: ".env" }, expectAsk: true }
|
|
348
|
+
];
|
|
349
|
+
|
|
350
|
+
for (const test of tests) {
|
|
351
|
+
const decision = await canUseTool(test.tool, test.input);
|
|
352
|
+
|
|
353
|
+
if (test.expectAllow && decision.behavior !== 'allow') {
|
|
354
|
+
console.error(`FAIL: Expected allow for ${test.tool}`);
|
|
355
|
+
}
|
|
356
|
+
if (test.expectDeny && decision.behavior !== 'deny') {
|
|
357
|
+
console.error(`FAIL: Expected deny for ${test.tool}`);
|
|
358
|
+
}
|
|
359
|
+
if (test.expectAsk && decision.behavior !== 'ask') {
|
|
360
|
+
console.error(`FAIL: Expected ask for ${test.tool}`);
|
|
361
|
+
}
|
|
362
|
+
}
|
|
363
|
+
}
|
|
364
|
+
```
|
|
365
|
+
|
|
366
|
+
---
|
|
367
|
+
|
|
368
|
+
## Common Scenarios
|
|
369
|
+
|
|
370
|
+
### Allow Read-Only
|
|
371
|
+
|
|
372
|
+
```typescript
|
|
373
|
+
canUseTool: async (toolName, input) => {
|
|
374
|
+
if (['Read', 'Grep', 'Glob'].includes(toolName)) {
|
|
375
|
+
return { behavior: "allow" };
|
|
376
|
+
}
|
|
377
|
+
return {
|
|
378
|
+
behavior: "deny",
|
|
379
|
+
message: "Read-only mode"
|
|
380
|
+
};
|
|
381
|
+
}
|
|
382
|
+
```
|
|
383
|
+
|
|
384
|
+
### Require Approval for All
|
|
385
|
+
|
|
386
|
+
```typescript
|
|
387
|
+
canUseTool: async (toolName, input) => {
|
|
388
|
+
return {
|
|
389
|
+
behavior: "ask",
|
|
390
|
+
message: `Approve ${toolName}?`
|
|
391
|
+
};
|
|
392
|
+
}
|
|
393
|
+
```
|
|
394
|
+
|
|
395
|
+
### Block Bash Entirely
|
|
396
|
+
|
|
397
|
+
```typescript
|
|
398
|
+
canUseTool: async (toolName, input) => {
|
|
399
|
+
if (toolName === 'Bash') {
|
|
400
|
+
return {
|
|
401
|
+
behavior: "deny",
|
|
402
|
+
message: "Bash execution disabled"
|
|
403
|
+
};
|
|
404
|
+
}
|
|
405
|
+
return { behavior: "allow" };
|
|
406
|
+
}
|
|
407
|
+
```
|
|
408
|
+
|
|
409
|
+
---
|
|
410
|
+
|
|
411
|
+
## Error Handling
|
|
412
|
+
|
|
413
|
+
Handle permission errors gracefully:
|
|
414
|
+
|
|
415
|
+
```typescript
|
|
416
|
+
for await (const message of response) {
|
|
417
|
+
if (message.type === 'error') {
|
|
418
|
+
if (message.error.type === 'permission_denied') {
|
|
419
|
+
console.log('Permission denied for:', message.error.tool);
|
|
420
|
+
// Continue with fallback or skip
|
|
421
|
+
}
|
|
422
|
+
}
|
|
423
|
+
}
|
|
424
|
+
```
|
|
425
|
+
|
|
426
|
+
---
|
|
427
|
+
|
|
428
|
+
**For more details**: See SKILL.md
|
|
429
|
+
**Template**: templates/permission-control.ts
|