dashclaw 2.1.5 → 2.2.0
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/README.md +60 -27
- package/dashclaw.js +61 -0
- package/legacy/index-v1.cjs +4 -4
- package/package.json +49 -49
package/README.md
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
# DashClaw SDK (v2.
|
|
1
|
+
# DashClaw SDK (v2.2.0)
|
|
2
2
|
|
|
3
3
|
**Minimal governance runtime for AI agents.**
|
|
4
4
|
|
|
@@ -25,7 +25,7 @@ DashClaw v2 is designed around a single 4-step loop.
|
|
|
25
25
|
import { DashClaw } from 'dashclaw';
|
|
26
26
|
|
|
27
27
|
const claw = new DashClaw({
|
|
28
|
-
baseUrl:
|
|
28
|
+
baseUrl: process.env.DASHCLAW_BASE_URL,
|
|
29
29
|
apiKey: process.env.DASHCLAW_API_KEY,
|
|
30
30
|
agentId: 'my-agent'
|
|
31
31
|
});
|
|
@@ -45,11 +45,12 @@ await claw.updateOutcome(action_id, { status: 'completed' });
|
|
|
45
45
|
|
|
46
46
|
### Python
|
|
47
47
|
```python
|
|
48
|
+
import os
|
|
48
49
|
from dashclaw import DashClaw
|
|
49
50
|
|
|
50
51
|
claw = DashClaw(
|
|
51
|
-
base_url=
|
|
52
|
-
api_key="
|
|
52
|
+
base_url=os.environ["DASHCLAW_BASE_URL"],
|
|
53
|
+
api_key=os.environ["DASHCLAW_API_KEY"],
|
|
53
54
|
agent_id="my-agent"
|
|
54
55
|
)
|
|
55
56
|
|
|
@@ -69,38 +70,40 @@ claw.update_outcome(action_id, status="completed")
|
|
|
69
70
|
|
|
70
71
|
---
|
|
71
72
|
|
|
72
|
-
## SDK Surface Area (v2.1.
|
|
73
|
+
## SDK Surface Area (v2.1.5)
|
|
73
74
|
|
|
74
|
-
The v2.1.
|
|
75
|
+
The v2.1.5 SDK is optimized for stability and zero-overhead governance:
|
|
75
76
|
|
|
76
77
|
### Core Runtime
|
|
77
|
-
- `guard(context)`
|
|
78
|
-
- `createAction(action)`
|
|
79
|
-
- `updateOutcome(id, outcome)`
|
|
80
|
-
- `recordAssumption(assumption)`
|
|
81
|
-
- `waitForApproval(id)`
|
|
78
|
+
- `guard(context)` -- Policy evaluation ("Can I do X?")
|
|
79
|
+
- `createAction(action)` -- Lifecycle tracking ("I am doing X")
|
|
80
|
+
- `updateOutcome(id, outcome)` -- Result recording ("X finished with Y")
|
|
81
|
+
- `recordAssumption(assumption)` -- Integrity tracking ("I believe Z while doing X")
|
|
82
|
+
- `waitForApproval(id)` -- Polling helper for human-in-the-loop approvals
|
|
83
|
+
- `approveAction(id, decision, reasoning?)` -- Submit approval decisions from code
|
|
84
|
+
- `getPendingApprovals()` -- List actions awaiting human review
|
|
82
85
|
|
|
83
86
|
### Decision Integrity
|
|
84
|
-
- `registerOpenLoop(actionId, type, desc)`
|
|
85
|
-
- `resolveOpenLoop(loopId, status, res)`
|
|
86
|
-
- `getSignals()`
|
|
87
|
+
- `registerOpenLoop(actionId, type, desc)` -- Register unresolved dependencies.
|
|
88
|
+
- `resolveOpenLoop(loopId, status, res)` -- Resolve pending loops.
|
|
89
|
+
- `getSignals()` -- Get current risk signals across all agents.
|
|
87
90
|
|
|
88
91
|
### Swarm & Connectivity
|
|
89
|
-
- `heartbeat(status, metadata)`
|
|
90
|
-
- `reportConnections(connections)`
|
|
92
|
+
- `heartbeat(status, metadata)` -- Report agent presence and health.
|
|
93
|
+
- `reportConnections(connections)` -- Report active provider connections.
|
|
91
94
|
|
|
92
95
|
### Learning & Optimization
|
|
93
|
-
- `getLearningVelocity()`
|
|
94
|
-
- `getLearningCurves()`
|
|
95
|
-
- `renderPrompt(context)`
|
|
96
|
+
- `getLearningVelocity()` -- Track agent improvement rate.
|
|
97
|
+
- `getLearningCurves()` -- Measure efficiency gains per action type.
|
|
98
|
+
- `renderPrompt(context)` -- Fetch rendered prompt templates from DashClaw.
|
|
96
99
|
|
|
97
100
|
### Compliance & Audit
|
|
98
|
-
- `createScorer(name, type, config)`
|
|
99
|
-
- `createScoringProfile(profile)`
|
|
100
|
-
- `mapCompliance(framework)`
|
|
101
|
-
- `getProofReport(format)`
|
|
102
|
-
- `getActivityLogs(filters)`
|
|
103
|
-
- `createWebhook(url, events)`
|
|
101
|
+
- `createScorer(name, type, config)` -- Define automated evaluations.
|
|
102
|
+
- `createScoringProfile(profile)` -- Weighted quality scoring.
|
|
103
|
+
- `mapCompliance(framework)` -- Map behavior to regulatory controls.
|
|
104
|
+
- `getProofReport(format)` -- Generate audit-ready evidence exports.
|
|
105
|
+
- `getActivityLogs(filters)` -- Query the immutable audit trail.
|
|
106
|
+
- `createWebhook(url, events)` -- Real-time event exfiltration.
|
|
104
107
|
|
|
105
108
|
---
|
|
106
109
|
|
|
@@ -108,8 +111,38 @@ The v2.1.2 SDK is optimized for stability and zero-overhead governance:
|
|
|
108
111
|
|
|
109
112
|
DashClaw uses standard HTTP status codes and custom error classes:
|
|
110
113
|
|
|
111
|
-
- `GuardBlockedError`
|
|
112
|
-
- `ApprovalDeniedError`
|
|
114
|
+
- `GuardBlockedError` -- Thrown when `claw.guard()` returns a `block` decision.
|
|
115
|
+
- `ApprovalDeniedError` -- Thrown when an operator denies an action during `waitForApproval()`.
|
|
116
|
+
|
|
117
|
+
---
|
|
118
|
+
|
|
119
|
+
## CLI Approval Channel
|
|
120
|
+
|
|
121
|
+
Install the DashClaw CLI to approve agent actions from the terminal:
|
|
122
|
+
|
|
123
|
+
```bash
|
|
124
|
+
npm install -g @dashclaw/cli
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
```bash
|
|
128
|
+
dashclaw approvals # interactive approval inbox
|
|
129
|
+
dashclaw approve <actionId> # approve a specific action
|
|
130
|
+
dashclaw deny <actionId> # deny a specific action
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
When an agent calls `waitForApproval()`, it prints the action ID and replay link to stdout. Approve from any terminal or the dashboard, and the agent unblocks instantly.
|
|
134
|
+
|
|
135
|
+
## Claude Code Hooks
|
|
136
|
+
|
|
137
|
+
Govern Claude Code tool calls without any SDK instrumentation. Copy two files from the `hooks/` directory in the repo into your `.claude/hooks/` folder:
|
|
138
|
+
|
|
139
|
+
```bash
|
|
140
|
+
# In your project directory
|
|
141
|
+
cp path/to/DashClaw/hooks/dashclaw_pretool.py .claude/hooks/
|
|
142
|
+
cp path/to/DashClaw/hooks/dashclaw_posttool.py .claude/hooks/
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
Then merge the hooks block from `hooks/settings.json` into your `.claude/settings.json`. Set `DASHCLAW_BASE_URL`, `DASHCLAW_API_KEY`, and optionally `DASHCLAW_HOOK_MODE=enforce`.
|
|
113
146
|
|
|
114
147
|
---
|
|
115
148
|
|
package/dashclaw.js
CHANGED
|
@@ -101,6 +101,36 @@ class DashClaw {
|
|
|
101
101
|
});
|
|
102
102
|
}
|
|
103
103
|
|
|
104
|
+
/**
|
|
105
|
+
* GET /api/actions/:id — Fetch a single action by ID.
|
|
106
|
+
*/
|
|
107
|
+
async getAction(actionId) {
|
|
108
|
+
return this._request(`/api/actions/${actionId}`, 'GET');
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
/**
|
|
112
|
+
* GET /api/actions?status=pending_approval — List actions awaiting approval.
|
|
113
|
+
*/
|
|
114
|
+
async getPendingApprovals(limit = 20, offset = 0) {
|
|
115
|
+
return this._request('/api/actions', 'GET', null, {
|
|
116
|
+
status: 'pending_approval',
|
|
117
|
+
limit,
|
|
118
|
+
offset,
|
|
119
|
+
});
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
/**
|
|
123
|
+
* POST /api/actions/:id/approve — Approve or deny an action.
|
|
124
|
+
* @param {string} actionId
|
|
125
|
+
* @param {'allow'|'deny'} decision
|
|
126
|
+
* @param {string} [reasoning]
|
|
127
|
+
*/
|
|
128
|
+
async approveAction(actionId, decision, reasoning) {
|
|
129
|
+
const body = { decision };
|
|
130
|
+
if (reasoning) body.reasoning = reasoning;
|
|
131
|
+
return this._request(`/api/actions/${actionId}/approve`, 'POST', body);
|
|
132
|
+
}
|
|
133
|
+
|
|
104
134
|
/**
|
|
105
135
|
* POST /api/assumptions — "I believe Z is true while doing X."
|
|
106
136
|
*/
|
|
@@ -114,9 +144,40 @@ class DashClaw {
|
|
|
114
144
|
async waitForApproval(actionId, { timeout = 300000, interval = 5000 } = {}) {
|
|
115
145
|
const startTime = Date.now();
|
|
116
146
|
let wasPending = false;
|
|
147
|
+
let printedBlock = false;
|
|
117
148
|
|
|
118
149
|
while (Date.now() - startTime < timeout) {
|
|
119
150
|
const { action } = await this._request(`/api/actions/${actionId}`, 'GET');
|
|
151
|
+
|
|
152
|
+
// Print structured approval block on first fetch
|
|
153
|
+
if (!printedBlock) {
|
|
154
|
+
printedBlock = true;
|
|
155
|
+
try {
|
|
156
|
+
const actionType = action.action_type || 'unknown';
|
|
157
|
+
const riskScore = action.risk_score != null ? String(action.risk_score) : '-';
|
|
158
|
+
const goal = action.declared_goal || '-';
|
|
159
|
+
const agent = action.agent_id || this.agentId;
|
|
160
|
+
const replayUrl = `${this.baseUrl}/replay/${actionId}`;
|
|
161
|
+
|
|
162
|
+
const lines = [
|
|
163
|
+
'\u2554\u2550\u2550 DashClaw Approval Required \u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2557',
|
|
164
|
+
` Action ID: ${actionId}`,
|
|
165
|
+
` Agent: ${agent}`,
|
|
166
|
+
` Action: ${actionType}`,
|
|
167
|
+
' Policy: require_approval',
|
|
168
|
+
` Risk Score: ${riskScore}`,
|
|
169
|
+
` Goal: ${goal}`,
|
|
170
|
+
'',
|
|
171
|
+
` Replay: ${replayUrl}`,
|
|
172
|
+
'',
|
|
173
|
+
' Waiting for approval... (Ctrl+C to abort)',
|
|
174
|
+
'\u255a\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u255d',
|
|
175
|
+
];
|
|
176
|
+
process.stdout.write('\n' + lines.join('\n') + '\n\n');
|
|
177
|
+
} catch (_) {
|
|
178
|
+
// Rendering failure must not prevent the wait from proceeding
|
|
179
|
+
}
|
|
180
|
+
}
|
|
120
181
|
|
|
121
182
|
if (action.status === 'pending_approval') {
|
|
122
183
|
wasPending = true;
|
package/legacy/index-v1.cjs
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* DashClaw SDK: CommonJS compatibility wrapper.
|
|
3
|
-
* For ESM: import { DashClaw } from 'dashclaw'
|
|
4
|
-
* For CJS: const { DashClaw } = require('dashclaw')
|
|
2
|
+
* DashClaw SDK v1 (Legacy): CommonJS compatibility wrapper.
|
|
3
|
+
* For ESM: import { DashClaw } from 'dashclaw/legacy'
|
|
4
|
+
* For CJS: const { DashClaw } = require('dashclaw/legacy')
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
7
|
let _module;
|
|
8
8
|
|
|
9
9
|
async function loadModule() {
|
|
10
10
|
if (!_module) {
|
|
11
|
-
_module = await import('./dashclaw.js');
|
|
11
|
+
_module = await import('./dashclaw-v1.js');
|
|
12
12
|
}
|
|
13
13
|
return _module;
|
|
14
14
|
}
|
package/package.json
CHANGED
|
@@ -1,49 +1,49 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "dashclaw",
|
|
3
|
-
"version": "2.
|
|
4
|
-
"description": "Minimal governance runtime for AI agents. Intercept, govern, and verify agent actions.",
|
|
5
|
-
"type": "module",
|
|
6
|
-
"publishConfig": {
|
|
7
|
-
"access": "public"
|
|
8
|
-
},
|
|
9
|
-
"main": "./index.cjs",
|
|
10
|
-
"module": "./dashclaw.js",
|
|
11
|
-
"exports": {
|
|
12
|
-
".": {
|
|
13
|
-
"import": "./dashclaw.js",
|
|
14
|
-
"require": "./index.cjs"
|
|
15
|
-
},
|
|
16
|
-
"./legacy": {
|
|
17
|
-
"import": "./legacy/dashclaw-v1.js",
|
|
18
|
-
"require": "./legacy/index-v1.cjs"
|
|
19
|
-
}
|
|
20
|
-
},
|
|
21
|
-
"files": [
|
|
22
|
-
"dashclaw.js",
|
|
23
|
-
"index.cjs",
|
|
24
|
-
"LICENSE",
|
|
25
|
-
"README.md",
|
|
26
|
-
"legacy/"
|
|
27
|
-
],
|
|
28
|
-
"keywords": [
|
|
29
|
-
"ai-agent",
|
|
30
|
-
"decision-infrastructure",
|
|
31
|
-
"agent-governance",
|
|
32
|
-
"guardrails",
|
|
33
|
-
"dashclaw"
|
|
34
|
-
],
|
|
35
|
-
"author": "DashClaw",
|
|
36
|
-
"license": "MIT",
|
|
37
|
-
"repository": {
|
|
38
|
-
"type": "git",
|
|
39
|
-
"url": "git+https://github.com/ucsandman/DashClaw.git",
|
|
40
|
-
"directory": "sdk"
|
|
41
|
-
},
|
|
42
|
-
"engines": {
|
|
43
|
-
"node": ">=18.0.0"
|
|
44
|
-
},
|
|
45
|
-
"dependencies": {},
|
|
46
|
-
"devDependencies": {},
|
|
47
|
-
"scripts": {},
|
|
48
|
-
"sideEffects": false
|
|
49
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "dashclaw",
|
|
3
|
+
"version": "2.2.0",
|
|
4
|
+
"description": "Minimal governance runtime for AI agents. Intercept, govern, and verify agent actions.",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"publishConfig": {
|
|
7
|
+
"access": "public"
|
|
8
|
+
},
|
|
9
|
+
"main": "./index.cjs",
|
|
10
|
+
"module": "./dashclaw.js",
|
|
11
|
+
"exports": {
|
|
12
|
+
".": {
|
|
13
|
+
"import": "./dashclaw.js",
|
|
14
|
+
"require": "./index.cjs"
|
|
15
|
+
},
|
|
16
|
+
"./legacy": {
|
|
17
|
+
"import": "./legacy/dashclaw-v1.js",
|
|
18
|
+
"require": "./legacy/index-v1.cjs"
|
|
19
|
+
}
|
|
20
|
+
},
|
|
21
|
+
"files": [
|
|
22
|
+
"dashclaw.js",
|
|
23
|
+
"index.cjs",
|
|
24
|
+
"LICENSE",
|
|
25
|
+
"README.md",
|
|
26
|
+
"legacy/"
|
|
27
|
+
],
|
|
28
|
+
"keywords": [
|
|
29
|
+
"ai-agent",
|
|
30
|
+
"decision-infrastructure",
|
|
31
|
+
"agent-governance",
|
|
32
|
+
"guardrails",
|
|
33
|
+
"dashclaw"
|
|
34
|
+
],
|
|
35
|
+
"author": "DashClaw",
|
|
36
|
+
"license": "MIT",
|
|
37
|
+
"repository": {
|
|
38
|
+
"type": "git",
|
|
39
|
+
"url": "git+https://github.com/ucsandman/DashClaw.git",
|
|
40
|
+
"directory": "sdk"
|
|
41
|
+
},
|
|
42
|
+
"engines": {
|
|
43
|
+
"node": ">=18.0.0"
|
|
44
|
+
},
|
|
45
|
+
"dependencies": {},
|
|
46
|
+
"devDependencies": {},
|
|
47
|
+
"scripts": {},
|
|
48
|
+
"sideEffects": false
|
|
49
|
+
}
|