@blockrun/clawrouter 0.4.7 → 0.5.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/LICENSE +21 -0
- package/README.md +139 -17
- package/dist/index.d.ts +188 -1
- package/dist/index.js +865 -88
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 BlockRunAI
|
|
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.
|
package/README.md
CHANGED
|
@@ -1,8 +1,6 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
# ClawRouter
|
|
1
|
+

|
|
4
2
|
|
|
5
|
-
|
|
3
|
+
<div align="center">
|
|
6
4
|
|
|
7
5
|
Route every request to the cheapest model that can handle it.
|
|
8
6
|
One wallet, 30+ models, zero API keys.
|
|
@@ -28,7 +26,7 @@ One wallet, 30+ models, zero API keys.
|
|
|
28
26
|
|
|
29
27
|
## Why ClawRouter?
|
|
30
28
|
|
|
31
|
-
- **100% local routing** —
|
|
29
|
+
- **100% local routing** — 15-dimension weighted scoring runs on your machine in <1ms
|
|
32
30
|
- **Zero external calls** — no API calls for routing decisions, ever
|
|
33
31
|
- **30+ models** — OpenAI, Anthropic, Google, DeepSeek, xAI, Moonshot through one wallet
|
|
34
32
|
- **x402 micropayments** — pay per request with USDC on Base, no API keys
|
|
@@ -94,14 +92,14 @@ Request → Weighted Scorer (14 dimensions)
|
|
|
94
92
|
|
|
95
93
|
No external classifier calls. Ambiguous queries default to the MEDIUM tier (DeepSeek/GPT-4o-mini) — fast, cheap, and good enough for most tasks.
|
|
96
94
|
|
|
97
|
-
###
|
|
95
|
+
### 15-Dimension Weighted Scoring
|
|
98
96
|
|
|
99
97
|
| Dimension | Weight | What It Detects |
|
|
100
98
|
| -------------------- | ------ | ---------------------------------------- |
|
|
101
99
|
| Reasoning markers | 0.18 | "prove", "theorem", "step by step" |
|
|
102
100
|
| Code presence | 0.15 | "function", "async", "import", "```" |
|
|
103
|
-
| Simple indicators | 0.12 | "what is", "define", "translate" |
|
|
104
101
|
| Multi-step patterns | 0.12 | "first...then", "step 1", numbered lists |
|
|
102
|
+
| **Agentic task** | 0.10 | "run", "test", "fix", "deploy", "edit" |
|
|
105
103
|
| Technical terms | 0.10 | "algorithm", "kubernetes", "distributed" |
|
|
106
104
|
| Token count | 0.08 | short (<50) vs long (>500) prompts |
|
|
107
105
|
| Creative markers | 0.05 | "story", "poem", "brainstorm" |
|
|
@@ -109,6 +107,7 @@ No external classifier calls. Ambiguous queries default to the MEDIUM tier (Deep
|
|
|
109
107
|
| Constraint count | 0.04 | "at most", "O(n)", "maximum" |
|
|
110
108
|
| Imperative verbs | 0.03 | "build", "create", "implement" |
|
|
111
109
|
| Output format | 0.03 | "json", "yaml", "schema" |
|
|
110
|
+
| Simple indicators | 0.02 | "what is", "define", "translate" |
|
|
112
111
|
| Domain specificity | 0.02 | "quantum", "fpga", "genomics" |
|
|
113
112
|
| Reference complexity | 0.02 | "the docs", "the api", "above" |
|
|
114
113
|
| Negation complexity | 0.01 | "don't", "avoid", "without" |
|
|
@@ -131,15 +130,93 @@ Mixed-language prompts are supported — keywords from all languages are checked
|
|
|
131
130
|
|
|
132
131
|
### Tier → Model Mapping
|
|
133
132
|
|
|
134
|
-
| Tier | Primary Model
|
|
135
|
-
| --------- |
|
|
136
|
-
| SIMPLE | gemini-2.5-flash
|
|
137
|
-
| MEDIUM |
|
|
138
|
-
| COMPLEX |
|
|
139
|
-
| REASONING |
|
|
133
|
+
| Tier | Primary Model | Cost/M | Savings vs Opus |
|
|
134
|
+
| --------- | ---------------------- | ------ | --------------- |
|
|
135
|
+
| SIMPLE | gemini-2.5-flash | $0.60 | **99.2%** |
|
|
136
|
+
| MEDIUM | grok-code-fast-1 | $1.50 | **98.0%** |
|
|
137
|
+
| COMPLEX | gemini-2.5-pro | $10.00 | **86.7%** |
|
|
138
|
+
| REASONING | grok-4-fast-reasoning | $0.50 | **99.3%** |
|
|
140
139
|
|
|
141
140
|
Special rule: 2+ reasoning markers → REASONING at 0.97 confidence.
|
|
142
141
|
|
|
142
|
+
### Agentic Auto-Detection
|
|
143
|
+
|
|
144
|
+
ClawRouter automatically detects multi-step agentic tasks and routes to models optimized for autonomous execution:
|
|
145
|
+
|
|
146
|
+
```
|
|
147
|
+
"what is 2+2" → gemini-flash (standard)
|
|
148
|
+
"build the project then run tests" → kimi-k2.5 (auto-agentic)
|
|
149
|
+
"fix the bug and make sure it works" → kimi-k2.5 (auto-agentic)
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
**How it works:**
|
|
153
|
+
- Detects agentic keywords: file ops ("read", "edit"), execution ("run", "test", "deploy"), iteration ("fix", "debug", "verify")
|
|
154
|
+
- Threshold: 2+ signals triggers auto-switch to agentic tiers
|
|
155
|
+
- No config needed — works automatically
|
|
156
|
+
|
|
157
|
+
**Agentic tier models** (optimized for multi-step autonomy):
|
|
158
|
+
|
|
159
|
+
| Tier | Agentic Model | Why |
|
|
160
|
+
| --------- | -------------------- | -------------------------------------- |
|
|
161
|
+
| SIMPLE | claude-haiku-4.5 | Fast + reliable tool use |
|
|
162
|
+
| MEDIUM | kimi-k2.5 | 200+ tool chains, 76% cheaper |
|
|
163
|
+
| COMPLEX | claude-sonnet-4 | Best balance for complex tasks |
|
|
164
|
+
| REASONING | kimi-k2.5 | Extended reasoning + execution |
|
|
165
|
+
|
|
166
|
+
You can also force agentic mode via config:
|
|
167
|
+
|
|
168
|
+
```yaml
|
|
169
|
+
# openclaw.yaml
|
|
170
|
+
plugins:
|
|
171
|
+
- id: "@blockrun/clawrouter"
|
|
172
|
+
config:
|
|
173
|
+
routing:
|
|
174
|
+
overrides:
|
|
175
|
+
agenticMode: true # Always use agentic tiers
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
### Tool Detection (v0.5)
|
|
179
|
+
|
|
180
|
+
When your request includes a `tools` array (function calling), ClawRouter automatically switches to agentic tiers:
|
|
181
|
+
|
|
182
|
+
```typescript
|
|
183
|
+
// Request with tools → auto-agentic mode
|
|
184
|
+
{
|
|
185
|
+
model: "blockrun/auto",
|
|
186
|
+
messages: [{ role: "user", content: "Check the weather" }],
|
|
187
|
+
tools: [{ type: "function", function: { name: "get_weather", ... } }]
|
|
188
|
+
}
|
|
189
|
+
// → Routes to claude-haiku-4.5 (excellent tool use)
|
|
190
|
+
// → Instead of gemini-flash (may produce malformed tool calls)
|
|
191
|
+
```
|
|
192
|
+
|
|
193
|
+
**Why this matters:** Some models (like `deepseek-reasoner`) are optimized for chain-of-thought reasoning but can generate malformed tool calls. Tool detection ensures requests with functions go to models proven to handle tool use correctly.
|
|
194
|
+
|
|
195
|
+
### Context-Length-Aware Routing (v0.5)
|
|
196
|
+
|
|
197
|
+
ClawRouter automatically filters out models that can't handle your context size:
|
|
198
|
+
|
|
199
|
+
```
|
|
200
|
+
150K token request:
|
|
201
|
+
Full chain: [grok-4-fast (131K), deepseek (128K), kimi (262K), gemini (1M)]
|
|
202
|
+
Filtered: [kimi (262K), gemini (1M)]
|
|
203
|
+
→ Skips models that would fail with "context too long" errors
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
This prevents wasted API calls and faster fallback to capable models.
|
|
207
|
+
|
|
208
|
+
### Session Persistence (v0.5)
|
|
209
|
+
|
|
210
|
+
For multi-turn conversations, ClawRouter pins the model to prevent mid-task switching:
|
|
211
|
+
|
|
212
|
+
```
|
|
213
|
+
Turn 1: "Build a React component" → claude-sonnet-4
|
|
214
|
+
Turn 2: "Add dark mode support" → claude-sonnet-4 (pinned)
|
|
215
|
+
Turn 3: "Now add tests" → claude-sonnet-4 (pinned)
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
Sessions are identified by conversation ID and persist for 1 hour of inactivity.
|
|
219
|
+
|
|
143
220
|
### Cost Savings (Real Numbers)
|
|
144
221
|
|
|
145
222
|
| Tier | % of Traffic | Cost/M |
|
|
@@ -179,8 +256,13 @@ Compared to **$75/M** for Claude Opus = **96% savings** on a typical workload.
|
|
|
179
256
|
| **xAI** | | | | |
|
|
180
257
|
| grok-3 | $3.00 | $15.00 | 131K | \* |
|
|
181
258
|
| grok-3-mini | $0.30 | $0.50 | 131K | |
|
|
259
|
+
| grok-4-fast-reasoning | $0.20 | $0.50 | 131K | \* |
|
|
260
|
+
| grok-4-fast | $0.20 | $0.50 | 131K | |
|
|
261
|
+
| grok-code-fast-1 | $0.20 | $1.50 | 131K | |
|
|
182
262
|
| **Moonshot** | | | | |
|
|
183
|
-
| kimi-k2.5 | $0.50 | $2.40 |
|
|
263
|
+
| kimi-k2.5 | $0.50 | $2.40 | 262K | \* |
|
|
264
|
+
| **NVIDIA** | | | | |
|
|
265
|
+
| gpt-oss-120b | **FREE** | **FREE** | 128K | |
|
|
184
266
|
|
|
185
267
|
Full list: [`src/models.ts`](src/models.ts)
|
|
186
268
|
|
|
@@ -446,6 +528,38 @@ console.log(decision);
|
|
|
446
528
|
|
|
447
529
|
---
|
|
448
530
|
|
|
531
|
+
## Cost Tracking with /stats (v0.5)
|
|
532
|
+
|
|
533
|
+
Track your savings in real-time:
|
|
534
|
+
|
|
535
|
+
```bash
|
|
536
|
+
# In any OpenClaw conversation
|
|
537
|
+
/stats
|
|
538
|
+
```
|
|
539
|
+
|
|
540
|
+
Output:
|
|
541
|
+
```
|
|
542
|
+
╔════════════════════════════════════════════════════════════╗
|
|
543
|
+
║ ClawRouter Usage Statistics ║
|
|
544
|
+
╠════════════════════════════════════════════════════════════╣
|
|
545
|
+
║ Period: last 7 days ║
|
|
546
|
+
║ Total Requests: 442 ║
|
|
547
|
+
║ Total Cost: $1.73 ║
|
|
548
|
+
║ Baseline Cost (Opus): $20.13 ║
|
|
549
|
+
║ 💰 Total Saved: $18.40 (91.4%) ║
|
|
550
|
+
╠════════════════════════════════════════════════════════════╣
|
|
551
|
+
║ Routing by Tier: ║
|
|
552
|
+
║ SIMPLE ███████████ 55.0% (243) ║
|
|
553
|
+
║ MEDIUM ██████ 30.8% (136) ║
|
|
554
|
+
║ COMPLEX █ 7.2% (32) ║
|
|
555
|
+
║ REASONING █ 7.0% (31) ║
|
|
556
|
+
╚════════════════════════════════════════════════════════════╝
|
|
557
|
+
```
|
|
558
|
+
|
|
559
|
+
Stats are stored locally at `~/.openclaw/blockrun/logs/` and aggregated on demand.
|
|
560
|
+
|
|
561
|
+
---
|
|
562
|
+
|
|
449
563
|
## Why Not OpenRouter / LiteLLM?
|
|
450
564
|
|
|
451
565
|
They're built for developers. ClawRouter is built for **agents**.
|
|
@@ -468,7 +582,7 @@ Agents shouldn't need a human to paste API keys. They should generate a wallet,
|
|
|
468
582
|
### Quick Checklist
|
|
469
583
|
|
|
470
584
|
```bash
|
|
471
|
-
# 1. Check your version (should be 0.
|
|
585
|
+
# 1. Check your version (should be 0.5.0+)
|
|
472
586
|
cat ~/.openclaw/extensions/clawrouter/package.json | grep version
|
|
473
587
|
|
|
474
588
|
# 2. Check proxy is running
|
|
@@ -477,6 +591,9 @@ curl http://localhost:8402/health
|
|
|
477
591
|
# 3. Watch routing in action
|
|
478
592
|
openclaw logs --follow
|
|
479
593
|
# Should see: gemini-2.5-flash $0.0012 (saved 99%)
|
|
594
|
+
|
|
595
|
+
# 4. View cost savings
|
|
596
|
+
/stats
|
|
480
597
|
```
|
|
481
598
|
|
|
482
599
|
### "Unknown model: blockrun/auto" or "Unknown model: auto"
|
|
@@ -586,14 +703,19 @@ BLOCKRUN_WALLET_KEY=0x... npx tsx test-e2e.ts
|
|
|
586
703
|
|
|
587
704
|
## Roadmap
|
|
588
705
|
|
|
589
|
-
- [x] Smart routing —
|
|
706
|
+
- [x] Smart routing — 15-dimension weighted scoring, 4-tier model selection
|
|
590
707
|
- [x] x402 payments — per-request USDC micropayments, non-custodial
|
|
591
708
|
- [x] Response dedup — prevents double-charge on retries
|
|
592
709
|
- [x] Payment pre-auth — skips 402 round trip
|
|
593
710
|
- [x] SSE heartbeat — prevents upstream timeouts
|
|
711
|
+
- [x] Agentic auto-detect — auto-switch to agentic models for multi-step tasks
|
|
712
|
+
- [x] Tool detection — auto-switch to agentic mode when tools array present
|
|
713
|
+
- [x] Context-aware routing — filter out models that can't handle context size
|
|
714
|
+
- [x] Session persistence — pin model for multi-turn conversations
|
|
715
|
+
- [x] Cost tracking — /stats command with savings dashboard
|
|
594
716
|
- [ ] Cascade routing — try cheap model first, escalate on low quality
|
|
595
717
|
- [ ] Spend controls — daily/monthly budgets
|
|
596
|
-
- [ ]
|
|
718
|
+
- [ ] Remote analytics — cost tracking at blockrun.ai
|
|
597
719
|
|
|
598
720
|
---
|
|
599
721
|
|
package/dist/index.d.ts
CHANGED
|
@@ -168,6 +168,7 @@ type ScoringConfig = {
|
|
|
168
168
|
referenceKeywords: string[];
|
|
169
169
|
negationKeywords: string[];
|
|
170
170
|
domainSpecificKeywords: string[];
|
|
171
|
+
agenticTaskKeywords: string[];
|
|
171
172
|
dimensionWeights: Record<string, number>;
|
|
172
173
|
tierBoundaries: {
|
|
173
174
|
simpleMedium: number;
|
|
@@ -188,12 +189,20 @@ type OverridesConfig = {
|
|
|
188
189
|
maxTokensForceComplex: number;
|
|
189
190
|
structuredOutputMinTier: Tier;
|
|
190
191
|
ambiguousDefaultTier: Tier;
|
|
192
|
+
/**
|
|
193
|
+
* When enabled, prefer models optimized for agentic workflows.
|
|
194
|
+
* Agentic models continue autonomously with multi-step tasks
|
|
195
|
+
* instead of stopping and waiting for user input.
|
|
196
|
+
*/
|
|
197
|
+
agenticMode?: boolean;
|
|
191
198
|
};
|
|
192
199
|
type RoutingConfig = {
|
|
193
200
|
version: string;
|
|
194
201
|
classifier: ClassifierConfig;
|
|
195
202
|
scoring: ScoringConfig;
|
|
196
203
|
tiers: Record<Tier, TierConfig>;
|
|
204
|
+
/** Tier configs for agentic mode - models that excel at multi-step tasks */
|
|
205
|
+
agenticTiers?: Record<Tier, TierConfig>;
|
|
197
206
|
overrides: OverridesConfig;
|
|
198
207
|
};
|
|
199
208
|
|
|
@@ -208,6 +217,21 @@ type ModelPricing = {
|
|
|
208
217
|
inputPrice: number;
|
|
209
218
|
outputPrice: number;
|
|
210
219
|
};
|
|
220
|
+
/**
|
|
221
|
+
* Get the ordered fallback chain for a tier: [primary, ...fallbacks].
|
|
222
|
+
*/
|
|
223
|
+
declare function getFallbackChain(tier: Tier, tierConfigs: Record<Tier, TierConfig>): string[];
|
|
224
|
+
/**
|
|
225
|
+
* Get the fallback chain filtered by context length.
|
|
226
|
+
* Only returns models that can handle the estimated total context.
|
|
227
|
+
*
|
|
228
|
+
* @param tier - The tier to get fallback chain for
|
|
229
|
+
* @param tierConfigs - Tier configurations
|
|
230
|
+
* @param estimatedTotalTokens - Estimated total context (input + output)
|
|
231
|
+
* @param getContextWindow - Function to get context window for a model ID
|
|
232
|
+
* @returns Filtered list of models that can handle the context
|
|
233
|
+
*/
|
|
234
|
+
declare function getFallbackChainFiltered(tier: Tier, tierConfigs: Record<Tier, TierConfig>, estimatedTotalTokens: number, getContextWindow: (modelId: string) => number | undefined): string[];
|
|
211
235
|
|
|
212
236
|
/**
|
|
213
237
|
* Default Routing Config
|
|
@@ -340,6 +364,82 @@ declare class BalanceMonitor {
|
|
|
340
364
|
private buildInfo;
|
|
341
365
|
}
|
|
342
366
|
|
|
367
|
+
/**
|
|
368
|
+
* Session Persistence Store
|
|
369
|
+
*
|
|
370
|
+
* Tracks model selections per session to prevent model switching mid-task.
|
|
371
|
+
* When a session is active, the router will continue using the same model
|
|
372
|
+
* instead of re-routing each request.
|
|
373
|
+
*/
|
|
374
|
+
type SessionEntry = {
|
|
375
|
+
model: string;
|
|
376
|
+
tier: string;
|
|
377
|
+
createdAt: number;
|
|
378
|
+
lastUsedAt: number;
|
|
379
|
+
requestCount: number;
|
|
380
|
+
};
|
|
381
|
+
type SessionConfig = {
|
|
382
|
+
/** Enable session persistence (default: false) */
|
|
383
|
+
enabled: boolean;
|
|
384
|
+
/** Session timeout in ms (default: 30 minutes) */
|
|
385
|
+
timeoutMs: number;
|
|
386
|
+
/** Header name for session ID (default: X-Session-ID) */
|
|
387
|
+
headerName: string;
|
|
388
|
+
};
|
|
389
|
+
declare const DEFAULT_SESSION_CONFIG: SessionConfig;
|
|
390
|
+
/**
|
|
391
|
+
* Session persistence store for maintaining model selections.
|
|
392
|
+
*/
|
|
393
|
+
declare class SessionStore {
|
|
394
|
+
private sessions;
|
|
395
|
+
private config;
|
|
396
|
+
private cleanupInterval;
|
|
397
|
+
constructor(config?: Partial<SessionConfig>);
|
|
398
|
+
/**
|
|
399
|
+
* Get the pinned model for a session, if any.
|
|
400
|
+
*/
|
|
401
|
+
getSession(sessionId: string): SessionEntry | undefined;
|
|
402
|
+
/**
|
|
403
|
+
* Pin a model to a session.
|
|
404
|
+
*/
|
|
405
|
+
setSession(sessionId: string, model: string, tier: string): void;
|
|
406
|
+
/**
|
|
407
|
+
* Touch a session to extend its timeout.
|
|
408
|
+
*/
|
|
409
|
+
touchSession(sessionId: string): void;
|
|
410
|
+
/**
|
|
411
|
+
* Clear a specific session.
|
|
412
|
+
*/
|
|
413
|
+
clearSession(sessionId: string): void;
|
|
414
|
+
/**
|
|
415
|
+
* Clear all sessions.
|
|
416
|
+
*/
|
|
417
|
+
clearAll(): void;
|
|
418
|
+
/**
|
|
419
|
+
* Get session stats for debugging.
|
|
420
|
+
*/
|
|
421
|
+
getStats(): {
|
|
422
|
+
count: number;
|
|
423
|
+
sessions: Array<{
|
|
424
|
+
id: string;
|
|
425
|
+
model: string;
|
|
426
|
+
age: number;
|
|
427
|
+
}>;
|
|
428
|
+
};
|
|
429
|
+
/**
|
|
430
|
+
* Clean up expired sessions.
|
|
431
|
+
*/
|
|
432
|
+
private cleanup;
|
|
433
|
+
/**
|
|
434
|
+
* Stop the cleanup interval.
|
|
435
|
+
*/
|
|
436
|
+
close(): void;
|
|
437
|
+
}
|
|
438
|
+
/**
|
|
439
|
+
* Generate a session ID from request headers or create a default.
|
|
440
|
+
*/
|
|
441
|
+
declare function getSessionId(headers: Record<string, string | string[] | undefined>, headerName?: string): string | undefined;
|
|
442
|
+
|
|
343
443
|
/**
|
|
344
444
|
* Local x402 Proxy Server
|
|
345
445
|
*
|
|
@@ -388,6 +488,11 @@ type ProxyOptions = {
|
|
|
388
488
|
requestTimeoutMs?: number;
|
|
389
489
|
/** Skip balance checks (for testing only). Default: false */
|
|
390
490
|
skipBalanceCheck?: boolean;
|
|
491
|
+
/**
|
|
492
|
+
* Session persistence config. When enabled, maintains model selection
|
|
493
|
+
* across requests within a session to prevent mid-task model switching.
|
|
494
|
+
*/
|
|
495
|
+
sessionConfig?: Partial<SessionConfig>;
|
|
391
496
|
onReady?: (port: number) => void;
|
|
392
497
|
onError?: (error: Error) => void;
|
|
393
498
|
onPayment?: (info: {
|
|
@@ -441,6 +546,16 @@ declare const blockrunProvider: ProviderPlugin;
|
|
|
441
546
|
* they set their own markup when reselling to end users (Phase 2).
|
|
442
547
|
*/
|
|
443
548
|
|
|
549
|
+
/**
|
|
550
|
+
* Model aliases for convenient shorthand access.
|
|
551
|
+
* Users can type `/model claude` instead of `/model blockrun/anthropic/claude-sonnet-4`.
|
|
552
|
+
*/
|
|
553
|
+
declare const MODEL_ALIASES: Record<string, string>;
|
|
554
|
+
/**
|
|
555
|
+
* Resolve a model alias to its full model ID.
|
|
556
|
+
* Returns the original model if not an alias.
|
|
557
|
+
*/
|
|
558
|
+
declare function resolveModelAlias(model: string): string;
|
|
444
559
|
type BlockRunModel = {
|
|
445
560
|
id: string;
|
|
446
561
|
name: string;
|
|
@@ -450,6 +565,8 @@ type BlockRunModel = {
|
|
|
450
565
|
maxOutput: number;
|
|
451
566
|
reasoning?: boolean;
|
|
452
567
|
vision?: boolean;
|
|
568
|
+
/** Models optimized for agentic workflows (multi-step autonomous tasks) */
|
|
569
|
+
agentic?: boolean;
|
|
453
570
|
};
|
|
454
571
|
declare const BLOCKRUN_MODELS: BlockRunModel[];
|
|
455
572
|
/**
|
|
@@ -462,6 +579,21 @@ declare const OPENCLAW_MODELS: ModelDefinitionConfig[];
|
|
|
462
579
|
* @param baseUrl - The proxy's local base URL (e.g., "http://127.0.0.1:12345")
|
|
463
580
|
*/
|
|
464
581
|
declare function buildProviderModels(baseUrl: string): ModelProviderConfig;
|
|
582
|
+
/**
|
|
583
|
+
* Check if a model is optimized for agentic workflows.
|
|
584
|
+
* Agentic models continue autonomously with multi-step tasks
|
|
585
|
+
* instead of stopping and waiting for user input.
|
|
586
|
+
*/
|
|
587
|
+
declare function isAgenticModel(modelId: string): boolean;
|
|
588
|
+
/**
|
|
589
|
+
* Get all agentic-capable models.
|
|
590
|
+
*/
|
|
591
|
+
declare function getAgenticModels(): string[];
|
|
592
|
+
/**
|
|
593
|
+
* Get context window size for a model.
|
|
594
|
+
* Returns undefined if model not found.
|
|
595
|
+
*/
|
|
596
|
+
declare function getModelContextWindow(modelId: string): number | undefined;
|
|
465
597
|
|
|
466
598
|
/**
|
|
467
599
|
* Usage Logger
|
|
@@ -475,7 +607,10 @@ declare function buildProviderModels(baseUrl: string): ModelProviderConfig;
|
|
|
475
607
|
type UsageEntry = {
|
|
476
608
|
timestamp: string;
|
|
477
609
|
model: string;
|
|
610
|
+
tier: string;
|
|
478
611
|
cost: number;
|
|
612
|
+
baselineCost: number;
|
|
613
|
+
savings: number;
|
|
479
614
|
latencyMs: number;
|
|
480
615
|
};
|
|
481
616
|
/**
|
|
@@ -674,6 +809,58 @@ declare function fetchWithRetry(fetchFn: (url: string, init?: RequestInit) => Pr
|
|
|
674
809
|
*/
|
|
675
810
|
declare function isRetryable(errorOrResponse: Error | Response, config?: Partial<RetryConfig>): boolean;
|
|
676
811
|
|
|
812
|
+
/**
|
|
813
|
+
* Usage Statistics Aggregator
|
|
814
|
+
*
|
|
815
|
+
* Reads usage log files and aggregates statistics for terminal display.
|
|
816
|
+
* Supports filtering by date range and provides multiple aggregation views.
|
|
817
|
+
*/
|
|
818
|
+
type DailyStats = {
|
|
819
|
+
date: string;
|
|
820
|
+
totalRequests: number;
|
|
821
|
+
totalCost: number;
|
|
822
|
+
totalBaselineCost: number;
|
|
823
|
+
totalSavings: number;
|
|
824
|
+
avgLatencyMs: number;
|
|
825
|
+
byTier: Record<string, {
|
|
826
|
+
count: number;
|
|
827
|
+
cost: number;
|
|
828
|
+
}>;
|
|
829
|
+
byModel: Record<string, {
|
|
830
|
+
count: number;
|
|
831
|
+
cost: number;
|
|
832
|
+
}>;
|
|
833
|
+
};
|
|
834
|
+
type AggregatedStats = {
|
|
835
|
+
period: string;
|
|
836
|
+
totalRequests: number;
|
|
837
|
+
totalCost: number;
|
|
838
|
+
totalBaselineCost: number;
|
|
839
|
+
totalSavings: number;
|
|
840
|
+
savingsPercentage: number;
|
|
841
|
+
avgLatencyMs: number;
|
|
842
|
+
avgCostPerRequest: number;
|
|
843
|
+
byTier: Record<string, {
|
|
844
|
+
count: number;
|
|
845
|
+
cost: number;
|
|
846
|
+
percentage: number;
|
|
847
|
+
}>;
|
|
848
|
+
byModel: Record<string, {
|
|
849
|
+
count: number;
|
|
850
|
+
cost: number;
|
|
851
|
+
percentage: number;
|
|
852
|
+
}>;
|
|
853
|
+
dailyBreakdown: DailyStats[];
|
|
854
|
+
};
|
|
855
|
+
/**
|
|
856
|
+
* Get aggregated statistics for the last N days.
|
|
857
|
+
*/
|
|
858
|
+
declare function getStats(days?: number): Promise<AggregatedStats>;
|
|
859
|
+
/**
|
|
860
|
+
* Format stats as ASCII table for terminal display.
|
|
861
|
+
*/
|
|
862
|
+
declare function formatStatsAscii(stats: AggregatedStats): string;
|
|
863
|
+
|
|
677
864
|
/**
|
|
678
865
|
* @blockrun/clawrouter
|
|
679
866
|
*
|
|
@@ -695,4 +882,4 @@ declare function isRetryable(errorOrResponse: Error | Response, config?: Partial
|
|
|
695
882
|
|
|
696
883
|
declare const plugin: OpenClawPluginDefinition;
|
|
697
884
|
|
|
698
|
-
export { BALANCE_THRESHOLDS, BLOCKRUN_MODELS, type BalanceInfo, BalanceMonitor, type CachedPaymentParams, type CachedResponse, DEFAULT_RETRY_CONFIG, DEFAULT_ROUTING_CONFIG, EmptyWalletError, InsufficientFundsError, type InsufficientFundsInfo, type LowBalanceInfo, OPENCLAW_MODELS, PaymentCache, type PaymentFetchResult, type PreAuthParams, type ProxyHandle, type ProxyOptions, RequestDeduplicator, type RetryConfig, type RoutingConfig, type RoutingDecision, RpcError, type SufficiencyResult, type Tier, type UsageEntry, blockrunProvider, buildProviderModels, createPaymentFetch, plugin as default, fetchWithRetry, getProxyPort, isBalanceError, isEmptyWalletError, isInsufficientFundsError, isRetryable, isRpcError, logUsage, route, startProxy };
|
|
885
|
+
export { type AggregatedStats, BALANCE_THRESHOLDS, BLOCKRUN_MODELS, type BalanceInfo, BalanceMonitor, type CachedPaymentParams, type CachedResponse, DEFAULT_RETRY_CONFIG, DEFAULT_ROUTING_CONFIG, DEFAULT_SESSION_CONFIG, type DailyStats, EmptyWalletError, InsufficientFundsError, type InsufficientFundsInfo, type LowBalanceInfo, MODEL_ALIASES, OPENCLAW_MODELS, PaymentCache, type PaymentFetchResult, type PreAuthParams, type ProxyHandle, type ProxyOptions, RequestDeduplicator, type RetryConfig, type RoutingConfig, type RoutingDecision, RpcError, type SessionConfig, type SessionEntry, SessionStore, type SufficiencyResult, type Tier, type UsageEntry, blockrunProvider, buildProviderModels, createPaymentFetch, plugin as default, fetchWithRetry, formatStatsAscii, getAgenticModels, getFallbackChain, getFallbackChainFiltered, getModelContextWindow, getProxyPort, getSessionId, getStats, isAgenticModel, isBalanceError, isEmptyWalletError, isInsufficientFundsError, isRetryable, isRpcError, logUsage, resolveModelAlias, route, startProxy };
|