agent-cache-optimizer 0.1.1 → 0.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 +5 -12
- package/README.zh-CN.md +2 -2
- package/bin/aco +168 -0
- package/package.json +5 -2
- package/skills/cache-status/SKILL.md +0 -81
package/README.md
CHANGED
|
@@ -84,16 +84,9 @@ tail -f ~/.cache/opencode/agent-cache-optimizer/diag.log
|
|
|
84
84
|
|
|
85
85
|
### Status dashboard
|
|
86
86
|
|
|
87
|
-
Inside OpenCode:
|
|
88
|
-
|
|
89
|
-
```
|
|
90
|
-
/cache-status
|
|
91
|
-
```
|
|
92
|
-
|
|
93
|
-
Or terminal:
|
|
94
|
-
|
|
95
87
|
```bash
|
|
96
|
-
|
|
88
|
+
aco status # text dashboard
|
|
89
|
+
aco status --json # JSON for scripts
|
|
97
90
|
```
|
|
98
91
|
|
|
99
92
|
### Output
|
|
@@ -216,11 +209,11 @@ agent-cache-optimizer/
|
|
|
216
209
|
│ └── types.ts # TypeScript types
|
|
217
210
|
├── adapters/
|
|
218
211
|
│ └── claude-code.md # Claude Code optimization guide
|
|
212
|
+
├── bin/
|
|
213
|
+
│ └── aco # CLI: aco status
|
|
219
214
|
├── scripts/
|
|
220
|
-
│ ├── cache-status.sh # Status dashboard
|
|
215
|
+
│ ├── cache-status.sh # Status dashboard (legacy)
|
|
221
216
|
│ └── check-cache-friendly.sh # Config audit tool
|
|
222
|
-
├── skills/
|
|
223
|
-
│ └── cache-status/ # /cache-status slash command
|
|
224
217
|
├── docs/
|
|
225
218
|
│ ├── cross-cli.md # Cross-CLI architecture
|
|
226
219
|
│ └── upstream.md # Upstream fix recommendations
|
package/README.zh-CN.md
CHANGED
package/bin/aco
ADDED
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# aco — agent-cache-optimizer CLI
|
|
3
|
+
# Usage: aco status [--json]
|
|
4
|
+
set -euo pipefail
|
|
5
|
+
|
|
6
|
+
CACHE_DIR="${HOME}/.cache/opencode/agent-cache-optimizer"
|
|
7
|
+
CMD="${1:-help}"
|
|
8
|
+
|
|
9
|
+
# ── Colors ────────────────────────────────────────────────────────
|
|
10
|
+
BOLD='\033[1m'; GREEN='\033[0;32m'; YELLOW='\033[1;33m'; RED='\033[0;31m'; CYAN='\033[0;36m'; NC='\033[0m'
|
|
11
|
+
|
|
12
|
+
# ── status ────────────────────────────────────────────────────────
|
|
13
|
+
status_json() {
|
|
14
|
+
local agents_json="{}"
|
|
15
|
+
for db in "$CACHE_DIR"/stability-*.json; do
|
|
16
|
+
[[ -f "$db" ]] || continue
|
|
17
|
+
local agent
|
|
18
|
+
agent=$(basename "$db" .json | sed 's/^stability-//')
|
|
19
|
+
local obs
|
|
20
|
+
obs=$(python3 -c "import json; d=json.load(open('$db')); print(d.get('observations', 0))" 2>/dev/null || echo 0)
|
|
21
|
+
local pos_count
|
|
22
|
+
pos_count=$(python3 -c "import json; d=json.load(open('$db')); print(len(d.get('positions', {})))" 2>/dev/null || echo 0)
|
|
23
|
+
local avg_score
|
|
24
|
+
avg_score=$(python3 -c "
|
|
25
|
+
import json
|
|
26
|
+
d=json.load(open('$db'))
|
|
27
|
+
scores=list(d.get('scores',{}).values())
|
|
28
|
+
stable=sum(1 for s in scores if s>=0.7)
|
|
29
|
+
total=len(scores)
|
|
30
|
+
print(f'{stable}/{total}')" 2>/dev/null || echo "0/0")
|
|
31
|
+
agents_json=$(echo "$agents_json" | python3 -c "
|
|
32
|
+
import json,sys
|
|
33
|
+
agents=json.load(sys.stdin)
|
|
34
|
+
agents['$agent']={'observations':$obs,'positions':$pos_count,'stable':'$avg_score'}
|
|
35
|
+
print(json.dumps(agents))" 2>/dev/null || echo "$agents_json")
|
|
36
|
+
done
|
|
37
|
+
|
|
38
|
+
local diag_entries=0
|
|
39
|
+
[[ -f "$CACHE_DIR/diag.log" ]] && diag_entries=$(wc -l < "$CACHE_DIR/diag.log" | tr -d ' ')
|
|
40
|
+
|
|
41
|
+
local total_obs=0
|
|
42
|
+
for db in "$CACHE_DIR"/stability-*.json; do
|
|
43
|
+
[[ -f "$db" ]] || continue
|
|
44
|
+
local o
|
|
45
|
+
o=$(python3 -c "import json; d=json.load(open('$db')); print(d.get('observations', 0))" 2>/dev/null || echo 0)
|
|
46
|
+
total_obs=$((total_obs + o))
|
|
47
|
+
done
|
|
48
|
+
|
|
49
|
+
local status="no_data"
|
|
50
|
+
[[ $diag_entries -gt 0 ]] && status="active"
|
|
51
|
+
|
|
52
|
+
python3 -c "
|
|
53
|
+
import json
|
|
54
|
+
print(json.dumps({
|
|
55
|
+
'status': '$status',
|
|
56
|
+
'diag_entries': $diag_entries,
|
|
57
|
+
'total_observations': $total_obs,
|
|
58
|
+
'agents': $agents_json
|
|
59
|
+
}, indent=2))"
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
status_text() {
|
|
63
|
+
# Check if any data exists
|
|
64
|
+
if [[ ! -d "$CACHE_DIR" ]] || [[ -z "$(ls "$CACHE_DIR"/stability-*.json 2>/dev/null)" ]]; then
|
|
65
|
+
echo ""
|
|
66
|
+
echo -e "${BOLD}╔══════════════════════════════════════════════════════╗${NC}"
|
|
67
|
+
echo -e "${BOLD}║ agent-cache-optimizer Status ║${NC}"
|
|
68
|
+
echo -e "${BOLD}╠══════════════════════════════════════════════════════╣${NC}"
|
|
69
|
+
echo -e "║ ${YELLOW}Status: NO DATA${NC} ║"
|
|
70
|
+
echo -e "║ ║"
|
|
71
|
+
echo -e "║ Plugin has not been invoked yet. Make a request first. ║"
|
|
72
|
+
echo -e "${BOLD}╚══════════════════════════════════════════════════════╝${NC}"
|
|
73
|
+
echo ""
|
|
74
|
+
return
|
|
75
|
+
fi
|
|
76
|
+
|
|
77
|
+
# Count agents
|
|
78
|
+
local agent_count=0
|
|
79
|
+
for db in "$CACHE_DIR"/stability-*.json; do [[ -f "$db" ]] && agent_count=$((agent_count + 1)); done
|
|
80
|
+
|
|
81
|
+
# Diag entries
|
|
82
|
+
local diag_entries=0 first_ts="" last_ts=""
|
|
83
|
+
if [[ -f "$CACHE_DIR/diag.log" ]]; then
|
|
84
|
+
diag_entries=$(wc -l < "$CACHE_DIR/diag.log" | tr -d ' ')
|
|
85
|
+
first_ts=$(head -1 "$CACHE_DIR/diag.log" | grep -oP '^\[[^\]]+\]' | tr -d '[]' 2>/dev/null || echo "?")
|
|
86
|
+
last_ts=$(tail -1 "$CACHE_DIR/diag.log" | grep -oP '^\[[^\]]+\]' | tr -d '[]' 2>/dev/null || echo "?")
|
|
87
|
+
fi
|
|
88
|
+
|
|
89
|
+
echo ""
|
|
90
|
+
echo -e "${BOLD}╔══════════════════════════════════════════════════════╗${NC}"
|
|
91
|
+
echo -e "${BOLD}║ agent-cache-optimizer Status ║${NC}"
|
|
92
|
+
echo -e "${BOLD}╠══════════════════════════════════════════════════════╣${NC}"
|
|
93
|
+
|
|
94
|
+
if [[ $diag_entries -gt 0 ]]; then
|
|
95
|
+
echo -e "║ ${GREEN}Status: ACTIVE${NC} ║"
|
|
96
|
+
printf "║ Uptime: %-46s ║\n" "$first_ts → $last_ts"
|
|
97
|
+
else
|
|
98
|
+
echo -e "║ ${YELLOW}Status: LOADED (no activity yet)${NC} ║"
|
|
99
|
+
fi
|
|
100
|
+
|
|
101
|
+
echo -e "${BOLD}╠══════════════════════════════════════════════════════╣${NC}"
|
|
102
|
+
|
|
103
|
+
if [[ $agent_count -eq 0 ]]; then
|
|
104
|
+
echo -e "║ ${YELLOW}No per-agent data yet${NC} ║"
|
|
105
|
+
else
|
|
106
|
+
printf "║ ${CYAN}%-22s %5s %8s %9s${NC} ║\n" "Agent" "Obs" "Pos" "Stable"
|
|
107
|
+
for db in "$CACHE_DIR"/stability-*.json; do
|
|
108
|
+
[[ -f "$db" ]] || continue
|
|
109
|
+
local agent obs pos stable
|
|
110
|
+
agent=$(basename "$db" .json | sed 's/^stability-//')
|
|
111
|
+
obs=$(python3 -c "import json; d=json.load(open('$db')); print(d.get('observations', 0))" 2>/dev/null || echo 0)
|
|
112
|
+
pos=$(python3 -c "import json; d=json.load(open('$db')); print(len(d.get('positions', {})))" 2>/dev/null || echo 0)
|
|
113
|
+
stable=$(python3 -c "
|
|
114
|
+
import json
|
|
115
|
+
d=json.load(open('$db'))
|
|
116
|
+
scores=list(d.get('scores',{}).values())
|
|
117
|
+
if scores:
|
|
118
|
+
s=sum(1 for v in scores if v>=0.7)
|
|
119
|
+
print(f'{s}/{len(scores)}')
|
|
120
|
+
else:
|
|
121
|
+
print('0/0')" 2>/dev/null || echo "0/0")
|
|
122
|
+
printf "║ %-22s %5s %8s %9s ║\n" "$agent" "$obs" "$pos" "$stable"
|
|
123
|
+
done
|
|
124
|
+
fi
|
|
125
|
+
|
|
126
|
+
echo -e "${BOLD}╠══════════════════════════════════════════════════════╣${NC}"
|
|
127
|
+
|
|
128
|
+
if [[ $diag_entries -gt 0 ]]; then
|
|
129
|
+
echo -e "║ ${CYAN}Last reorder:${NC} ║"
|
|
130
|
+
tail -1 "$CACHE_DIR/diag.log" 2>/dev/null | while IFS= read -r line; do
|
|
131
|
+
printf "║ %-52s ║\n" "${line:0:52}"
|
|
132
|
+
done
|
|
133
|
+
fi
|
|
134
|
+
|
|
135
|
+
echo -e "${BOLD}╚══════════════════════════════════════════════════════╝${NC}"
|
|
136
|
+
echo ""
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
# ── help ───────────────────────────────────────────────────────────
|
|
140
|
+
help_text() {
|
|
141
|
+
echo "agent-cache-optimizer (aco) — KV cache optimizer for LLM CLI agents"
|
|
142
|
+
echo ""
|
|
143
|
+
echo "Usage: aco <command>"
|
|
144
|
+
echo ""
|
|
145
|
+
echo "Commands:"
|
|
146
|
+
echo " status Show cache optimizer status"
|
|
147
|
+
echo " status --json Show status in JSON format"
|
|
148
|
+
echo " help Show this help"
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
# ── Main ───────────────────────────────────────────────────────────
|
|
152
|
+
case "$CMD" in
|
|
153
|
+
status)
|
|
154
|
+
if [[ "${2:-}" == "--json" ]]; then
|
|
155
|
+
status_json
|
|
156
|
+
else
|
|
157
|
+
status_text
|
|
158
|
+
fi
|
|
159
|
+
;;
|
|
160
|
+
help|--help|-h)
|
|
161
|
+
help_text
|
|
162
|
+
;;
|
|
163
|
+
*)
|
|
164
|
+
echo "Unknown command: $CMD"
|
|
165
|
+
help_text
|
|
166
|
+
exit 1
|
|
167
|
+
;;
|
|
168
|
+
esac
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "agent-cache-optimizer",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.2.0",
|
|
4
4
|
"description": "Content-agnostic KV cache optimizer for LLM CLI agents — boosts prompt cache hit rate by 40-88% through automatic stability tracking and block reordering",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"kv-cache",
|
|
@@ -25,6 +25,9 @@
|
|
|
25
25
|
},
|
|
26
26
|
"type": "module",
|
|
27
27
|
"main": "./src/index.ts",
|
|
28
|
+
"bin": {
|
|
29
|
+
"aco": "./bin/aco"
|
|
30
|
+
},
|
|
28
31
|
"exports": {
|
|
29
32
|
".": "./src/index.ts",
|
|
30
33
|
"./core": "./src/core.ts",
|
|
@@ -32,10 +35,10 @@
|
|
|
32
35
|
"./splitting": "./src/splitting.ts"
|
|
33
36
|
},
|
|
34
37
|
"files": [
|
|
38
|
+
"bin/",
|
|
35
39
|
"src/",
|
|
36
40
|
"adapters/",
|
|
37
41
|
"scripts/",
|
|
38
|
-
"skills/",
|
|
39
42
|
"docs/",
|
|
40
43
|
"README.md",
|
|
41
44
|
"README.zh-CN.md",
|
|
@@ -1,81 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: cache-status
|
|
3
|
-
description: Show KV cache optimizer status — stability DBs, reordering stats, diagnostics. Trigger: /cache-status
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
# KV Cache Optimizer Status
|
|
7
|
-
|
|
8
|
-
Show the current state of the KV cache optimizer plugin (agent-cache-optimizer.ts).
|
|
9
|
-
|
|
10
|
-
## Data Locations
|
|
11
|
-
|
|
12
|
-
- Stability DBs: `~/.cache/opencode/agent-cache-optimizer/stability-*.json`
|
|
13
|
-
- Diagnostic log: `~/.cache/opencode/agent-cache-optimizer/diag.log`
|
|
14
|
-
|
|
15
|
-
## Display Format
|
|
16
|
-
|
|
17
|
-
Read all `stability-*.json` files and `diag.log`, then present:
|
|
18
|
-
|
|
19
|
-
```
|
|
20
|
-
╔══════════════════════════════════════════════════════════════╗
|
|
21
|
-
║ KV Cache Optimizer Status ║
|
|
22
|
-
╠══════════════════════════════════════════════════════════════╣
|
|
23
|
-
║ Status: ACTIVE / NO DATA / ERROR ║
|
|
24
|
-
║ Mode: COLD START (heuristics) / WARM (hash-based) ║
|
|
25
|
-
║ Uptime: first_seen → last_seen ║
|
|
26
|
-
╠══════════════════════════════════════════════════════════════╣
|
|
27
|
-
║ Per-Agent Breakdown: ║
|
|
28
|
-
║ orchestrator: 12 obs, 88% cacheable ║
|
|
29
|
-
║ oracle: 5 obs, 75% cacheable ║
|
|
30
|
-
║ fixer: 3 obs, 90% cacheable ║
|
|
31
|
-
║ ... ║
|
|
32
|
-
╠══════════════════════════════════════════════════════════════╣
|
|
33
|
-
║ Last 5 reorders (from diag.log): ║
|
|
34
|
-
║ [time] [agent] S:X U:Y D:Z T:N obs:M ║
|
|
35
|
-
║ ... ║
|
|
36
|
-
╠══════════════════════════════════════════════════════════════╣
|
|
37
|
-
║ Estimated savings: XX KB / session ║
|
|
38
|
-
╚══════════════════════════════════════════════════════════════╝
|
|
39
|
-
```
|
|
40
|
-
|
|
41
|
-
## Key Metrics
|
|
42
|
-
|
|
43
|
-
From each `stability-{agent}.json`:
|
|
44
|
-
- `observations`: number of calls tracked
|
|
45
|
-
- `positions`: number of distinct block positions
|
|
46
|
-
- Average `scores` per block → classification quality
|
|
47
|
-
- Ratio of stable vs dynamic blocks
|
|
48
|
-
|
|
49
|
-
From `diag.log`:
|
|
50
|
-
- Last N reorder operations
|
|
51
|
-
- Confirm plugin is being invoked
|
|
52
|
-
|
|
53
|
-
## Interpretation
|
|
54
|
-
|
|
55
|
-
- **NO DATA**: Plugin hasn't been invoked yet. Restart OpenCode after adding the plugin to `opencode.json`.
|
|
56
|
-
- **COLD START**: First 2 sessions per agent — using position/size heuristics.
|
|
57
|
-
- **WARM**: 3+ sessions — using hash-based stability tracking. More accurate.
|
|
58
|
-
- **High stable %**: Good cache reuse across sessions.
|
|
59
|
-
- **High unknown %**: Heuristics can't classify some blocks → will improve with more observations.
|
|
60
|
-
|
|
61
|
-
## If Plugin Not Working
|
|
62
|
-
|
|
63
|
-
1. Check `opencode.json` has `"file:///home/chris/.config/opencode/plugins/agent-cache-optimizer.ts"` in `plugin` array
|
|
64
|
-
2. Check `diag.log` exists and has entries
|
|
65
|
-
3. If no diag.log: the `experimental.chat.system.transform` hook may not be firing → fall back to `chat.params` diagnostic
|
|
66
|
-
4. Run `opencode debug agent orchestrator` to verify plugin config
|
|
67
|
-
|
|
68
|
-
## Quick Health Check
|
|
69
|
-
|
|
70
|
-
```bash
|
|
71
|
-
# Check if plugin is loaded
|
|
72
|
-
ls ~/.cache/opencode/agent-cache-optimizer/
|
|
73
|
-
|
|
74
|
-
# View last reorder
|
|
75
|
-
tail -5 ~/.cache/opencode/agent-cache-optimizer/diag.log
|
|
76
|
-
|
|
77
|
-
# Count observations per agent
|
|
78
|
-
for f in ~/.cache/opencode/agent-cache-optimizer/stability-*.json; do
|
|
79
|
-
echo "$(basename $f .json): $(python3 -c "import json; d=json.load(open('$f')); print(d['observations'])") obs"
|
|
80
|
-
done
|
|
81
|
-
```
|