cc-proficiency 0.1.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/.claude-plugin/plugin.json +11 -0
- package/LICENSE +201 -0
- package/README.md +345 -0
- package/README.zh-CN.md +284 -0
- package/dist/cli.d.ts +3 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +543 -0
- package/dist/cli.js.map +1 -0
- package/dist/gist/uploader.d.ts +26 -0
- package/dist/gist/uploader.d.ts.map +1 -0
- package/dist/gist/uploader.js +99 -0
- package/dist/gist/uploader.js.map +1 -0
- package/dist/hooks/session-end.js +64 -0
- package/dist/i18n/locales.d.ts +30 -0
- package/dist/i18n/locales.d.ts.map +1 -0
- package/dist/i18n/locales.js +64 -0
- package/dist/i18n/locales.js.map +1 -0
- package/dist/index.d.ts +12 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +38 -0
- package/dist/index.js.map +1 -0
- package/dist/parsers/config-parser.d.ts +25 -0
- package/dist/parsers/config-parser.d.ts.map +1 -0
- package/dist/parsers/config-parser.js +262 -0
- package/dist/parsers/config-parser.js.map +1 -0
- package/dist/parsers/history-parser.d.ts +13 -0
- package/dist/parsers/history-parser.d.ts.map +1 -0
- package/dist/parsers/history-parser.js +50 -0
- package/dist/parsers/history-parser.js.map +1 -0
- package/dist/parsers/normalizer.d.ts +8 -0
- package/dist/parsers/normalizer.d.ts.map +1 -0
- package/dist/parsers/normalizer.js +105 -0
- package/dist/parsers/normalizer.js.map +1 -0
- package/dist/parsers/transcript-parser.d.ts +23 -0
- package/dist/parsers/transcript-parser.d.ts.map +1 -0
- package/dist/parsers/transcript-parser.js +112 -0
- package/dist/parsers/transcript-parser.js.map +1 -0
- package/dist/renderer/svg.d.ts +10 -0
- package/dist/renderer/svg.d.ts.map +1 -0
- package/dist/renderer/svg.js +209 -0
- package/dist/renderer/svg.js.map +1 -0
- package/dist/scoring/curves.d.ts +34 -0
- package/dist/scoring/curves.d.ts.map +1 -0
- package/dist/scoring/curves.js +60 -0
- package/dist/scoring/curves.js.map +1 -0
- package/dist/scoring/engine.d.ts +16 -0
- package/dist/scoring/engine.d.ts.map +1 -0
- package/dist/scoring/engine.js +137 -0
- package/dist/scoring/engine.js.map +1 -0
- package/dist/scoring/rule-engine.d.ts +30 -0
- package/dist/scoring/rule-engine.d.ts.map +1 -0
- package/dist/scoring/rule-engine.js +151 -0
- package/dist/scoring/rule-engine.js.map +1 -0
- package/dist/scoring/rules.d.ts +32 -0
- package/dist/scoring/rules.d.ts.map +1 -0
- package/dist/scoring/rules.js +443 -0
- package/dist/scoring/rules.js.map +1 -0
- package/dist/scoring/signals.d.ts +7 -0
- package/dist/scoring/signals.d.ts.map +1 -0
- package/dist/scoring/signals.js +245 -0
- package/dist/scoring/signals.js.map +1 -0
- package/dist/store/local-store.d.ts +12 -0
- package/dist/store/local-store.d.ts.map +1 -0
- package/dist/store/local-store.js +107 -0
- package/dist/store/local-store.js.map +1 -0
- package/dist/store/queue.d.ts +24 -0
- package/dist/store/queue.d.ts.map +1 -0
- package/dist/store/queue.js +105 -0
- package/dist/store/queue.js.map +1 -0
- package/dist/types.d.ts +264 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +4 -0
- package/dist/types.js.map +1 -0
- package/dist/utils/ci-detect.d.ts +6 -0
- package/dist/utils/ci-detect.d.ts.map +1 -0
- package/dist/utils/ci-detect.js +19 -0
- package/dist/utils/ci-detect.js.map +1 -0
- package/hooks/hooks.json +15 -0
- package/hooks/session-end.ts +71 -0
- package/hooks/tsconfig.json +13 -0
- package/package.json +43 -0
- package/skills/proficiency/SKILL.md +15 -0
|
@@ -0,0 +1,245 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.extractSignals = extractSignals;
|
|
4
|
+
const transcript_parser_js_1 = require("../parsers/transcript-parser.js");
|
|
5
|
+
/**
|
|
6
|
+
* Extract all signals from parsed sessions + config.
|
|
7
|
+
*/
|
|
8
|
+
function extractSignals(sessions, config) {
|
|
9
|
+
const allEvents = sessions.flatMap((s) => s.events);
|
|
10
|
+
return {
|
|
11
|
+
ccMastery: extractCCMasterySignals(allEvents, config),
|
|
12
|
+
toolMcp: extractToolMcpSignals(allEvents, config),
|
|
13
|
+
agentic: extractAgenticSignals(allEvents, sessions),
|
|
14
|
+
promptCraft: extractPromptCraftSignals(allEvents),
|
|
15
|
+
contextMgmt: extractContextMgmtSignals(sessions, config),
|
|
16
|
+
outcomes: extractOutcomeSignals(allEvents),
|
|
17
|
+
};
|
|
18
|
+
}
|
|
19
|
+
function extractCCMasterySignals(events, config) {
|
|
20
|
+
const toolCalls = events.filter((e) => e.kind === "tool_call");
|
|
21
|
+
// Check which plugins were actually used in transcripts
|
|
22
|
+
const toolNames = new Set(toolCalls.map((tc) => tc.toolName));
|
|
23
|
+
const pluginToolPrefixes = config.pluginNames.map((name) => {
|
|
24
|
+
const parts = name.split("@");
|
|
25
|
+
return parts[0];
|
|
26
|
+
});
|
|
27
|
+
let pluginsUsed = 0;
|
|
28
|
+
for (const prefix of pluginToolPrefixes) {
|
|
29
|
+
if ([...toolNames].some((t) => t.toLowerCase().includes(prefix.toLowerCase()))) {
|
|
30
|
+
pluginsUsed++;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
// Unique skills
|
|
34
|
+
const skillCalls = toolCalls.filter((tc) => tc.toolName === "Skill");
|
|
35
|
+
const uniqueSkills = new Set(skillCalls.map((tc) => String(tc.input?.skill ?? "")));
|
|
36
|
+
// Plan mode
|
|
37
|
+
const userPrompts = events.filter((e) => e.kind === "user_prompt");
|
|
38
|
+
const usedPlanMode = userPrompts.some((p) => p.permissionMode === "plan");
|
|
39
|
+
return {
|
|
40
|
+
hasGlobalClaudeMd: config.hasGlobalClaudeMd,
|
|
41
|
+
globalClaudeMdHasImports: config.globalClaudeMdHasImports,
|
|
42
|
+
projectClaudeMdCount: config.projectClaudeMdCount,
|
|
43
|
+
hasCustomHooks: config.hasCustomHooks,
|
|
44
|
+
hookWithMatcherCount: config.hookWithMatcherCount,
|
|
45
|
+
pluginCount: config.pluginCount,
|
|
46
|
+
pluginsUsedInTranscripts: pluginsUsed,
|
|
47
|
+
uniqueSkillsUsed: uniqueSkills.size,
|
|
48
|
+
usedPlanMode,
|
|
49
|
+
hasRulesFiles: config.hasRulesFiles,
|
|
50
|
+
};
|
|
51
|
+
}
|
|
52
|
+
function extractToolMcpSignals(events, config) {
|
|
53
|
+
const toolCalls = events.filter((e) => e.kind === "tool_call");
|
|
54
|
+
const uniqueTools = new Set(toolCalls.map((tc) => tc.toolName));
|
|
55
|
+
// MCP servers — tools prefixed with mcp__
|
|
56
|
+
const mcpTools = toolCalls.filter((tc) => tc.toolName.startsWith("mcp__"));
|
|
57
|
+
const mcpServers = new Set(mcpTools.map((tc) => {
|
|
58
|
+
// mcp__serverName__toolName → serverName
|
|
59
|
+
const parts = tc.toolName.split("__");
|
|
60
|
+
return parts.length >= 2 ? parts[1] : tc.toolName;
|
|
61
|
+
}));
|
|
62
|
+
// LSP tool calls
|
|
63
|
+
const lspCalls = toolCalls.filter((tc) => tc.toolName === "LSP");
|
|
64
|
+
// Edit success rate: edits NOT followed by another edit within 2 tool calls
|
|
65
|
+
const editCalls = toolCalls.filter((tc) => tc.toolName === "Edit" || tc.toolName === "Write");
|
|
66
|
+
let successfulEdits = 0;
|
|
67
|
+
for (let i = 0; i < editCalls.length; i++) {
|
|
68
|
+
const editIdx = toolCalls.indexOf(editCalls[i]);
|
|
69
|
+
const next1 = toolCalls[editIdx + 1];
|
|
70
|
+
const next2 = toolCalls[editIdx + 2];
|
|
71
|
+
const isCorrectiveReEdit = (next1?.toolName === "Edit" || next1?.toolName === "Write") ||
|
|
72
|
+
(next2?.toolName === "Edit" && next1?.toolName === "Read");
|
|
73
|
+
if (!isCorrectiveReEdit) {
|
|
74
|
+
successfulEdits++;
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
return {
|
|
78
|
+
uniqueToolsUsed: uniqueTools.size,
|
|
79
|
+
uniqueMcpServersUsed: mcpServers.size,
|
|
80
|
+
lspToolCallCount: lspCalls.length,
|
|
81
|
+
deliberateWorkflowCount: (0, transcript_parser_js_1.countDeliberateWorkflows)(events),
|
|
82
|
+
editSuccessRate: editCalls.length > 0 ? successfulEdits / editCalls.length : 0.5, // neutral when no data
|
|
83
|
+
totalToolCalls: toolCalls.length,
|
|
84
|
+
};
|
|
85
|
+
}
|
|
86
|
+
function extractAgenticSignals(events, sessions) {
|
|
87
|
+
const toolCalls = events.filter((e) => e.kind === "tool_call");
|
|
88
|
+
// Subagents
|
|
89
|
+
const agentCalls = toolCalls.filter((tc) => tc.toolName === "Agent");
|
|
90
|
+
const subagentTypes = new Set(agentCalls.map((tc) => String(tc.input?.subagent_type ?? "general-purpose")));
|
|
91
|
+
// Worktree
|
|
92
|
+
const usedWorktree = toolCalls.some((tc) => tc.toolName === "EnterWorktree" || tc.toolName === "ExitWorktree");
|
|
93
|
+
// Task management
|
|
94
|
+
const usedTaskMgmt = toolCalls.some((tc) => tc.toolName === "TaskCreate" || tc.toolName === "TaskUpdate");
|
|
95
|
+
// Multi-session projects
|
|
96
|
+
const projectSessions = new Map();
|
|
97
|
+
for (const session of sessions) {
|
|
98
|
+
const existing = projectSessions.get(session.project) ?? new Set();
|
|
99
|
+
existing.add(session.sessionId);
|
|
100
|
+
projectSessions.set(session.project, existing);
|
|
101
|
+
}
|
|
102
|
+
const multiSessionProjects = [...projectSessions.values()].filter((s) => s.size > 1).length;
|
|
103
|
+
return {
|
|
104
|
+
uniqueSubagentTypes: subagentTypes.size,
|
|
105
|
+
totalSubagentCalls: agentCalls.length,
|
|
106
|
+
parallelToolCallCount: (0, transcript_parser_js_1.countParallelToolCalls)(events),
|
|
107
|
+
usedWorktree,
|
|
108
|
+
multiSessionProjectCount: multiSessionProjects,
|
|
109
|
+
usedTaskManagement: usedTaskMgmt,
|
|
110
|
+
};
|
|
111
|
+
}
|
|
112
|
+
function extractPromptCraftSignals(events) {
|
|
113
|
+
const userPrompts = events.filter((e) => e.kind === "user_prompt");
|
|
114
|
+
// Structured prompts (contain markdown indicators)
|
|
115
|
+
const structuredCount = userPrompts.filter((p) => {
|
|
116
|
+
const c = p.content;
|
|
117
|
+
return (c.includes("- ") ||
|
|
118
|
+
c.includes("* ") ||
|
|
119
|
+
c.includes("1. ") ||
|
|
120
|
+
c.includes("## ") ||
|
|
121
|
+
c.includes("```") ||
|
|
122
|
+
c.includes("| "));
|
|
123
|
+
}).length;
|
|
124
|
+
// Iterative refinement: consecutive prompts in same session that refine
|
|
125
|
+
// (not just any consecutive prompt — look for refinement patterns)
|
|
126
|
+
let refinementCount = 0;
|
|
127
|
+
for (let i = 1; i < userPrompts.length; i++) {
|
|
128
|
+
const prev = userPrompts[i - 1];
|
|
129
|
+
const curr = userPrompts[i];
|
|
130
|
+
if (curr.sessionId !== prev.sessionId)
|
|
131
|
+
continue;
|
|
132
|
+
// Refinement indicators: references to prior work, corrections, adjustments
|
|
133
|
+
const c = curr.content.toLowerCase();
|
|
134
|
+
const isRefinement = c.includes("instead") ||
|
|
135
|
+
c.includes("actually") ||
|
|
136
|
+
c.includes("change") ||
|
|
137
|
+
c.includes("also") ||
|
|
138
|
+
c.includes("but ") ||
|
|
139
|
+
c.includes("wait") ||
|
|
140
|
+
c.includes("no,") ||
|
|
141
|
+
c.includes("not that") ||
|
|
142
|
+
c.includes("update") ||
|
|
143
|
+
c.includes("fix") ||
|
|
144
|
+
c.includes("modify");
|
|
145
|
+
if (isRefinement)
|
|
146
|
+
refinementCount++;
|
|
147
|
+
}
|
|
148
|
+
// Unique commands (from prompt content starting with /)
|
|
149
|
+
const commands = new Set();
|
|
150
|
+
for (const p of userPrompts) {
|
|
151
|
+
if (p.content.startsWith("/")) {
|
|
152
|
+
const cmd = p.content.split(" ")[0];
|
|
153
|
+
commands.add(cmd);
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
// Context provision: prompts with code blocks, file references, or error traces
|
|
157
|
+
// (not just long prompts — look for actual context signals)
|
|
158
|
+
const contextCount = userPrompts.filter((p) => {
|
|
159
|
+
const c = p.content;
|
|
160
|
+
const hasCodeBlock = c.includes("```");
|
|
161
|
+
const hasFilePath = /[\w/\\]+\.\w{1,4}/.test(c) && (c.includes("/") || c.includes("\\"));
|
|
162
|
+
const hasErrorTrace = c.includes("Error:") || c.includes("error:") || c.includes("at ") && c.includes("(");
|
|
163
|
+
// Require at least one concrete context signal, not just length
|
|
164
|
+
return hasCodeBlock || hasFilePath || hasErrorTrace;
|
|
165
|
+
}).length;
|
|
166
|
+
return {
|
|
167
|
+
structuredPromptRatio: userPrompts.length > 0 ? structuredCount / userPrompts.length : 0,
|
|
168
|
+
iterativeRefinementCount: refinementCount,
|
|
169
|
+
uniqueCommandsUsed: commands.size,
|
|
170
|
+
contextProvisionCount: contextCount,
|
|
171
|
+
totalPrompts: userPrompts.length,
|
|
172
|
+
};
|
|
173
|
+
}
|
|
174
|
+
function extractContextMgmtSignals(sessions, config) {
|
|
175
|
+
const projects = new Set(sessions.map((s) => s.project));
|
|
176
|
+
// Session durations in minutes
|
|
177
|
+
const durations = sessions
|
|
178
|
+
.map((s) => {
|
|
179
|
+
const start = new Date(s.startTime).getTime();
|
|
180
|
+
const end = new Date(s.endTime).getTime();
|
|
181
|
+
if (isNaN(start) || isNaN(end))
|
|
182
|
+
return 0;
|
|
183
|
+
return (end - start) / 60000;
|
|
184
|
+
})
|
|
185
|
+
.filter((d) => d > 0);
|
|
186
|
+
return {
|
|
187
|
+
memoryFileCount: config.memoryFileCount,
|
|
188
|
+
activeMemoryFiles: config.activeMemoryFileCount,
|
|
189
|
+
projectCount: projects.size,
|
|
190
|
+
sessionCount: sessions.length,
|
|
191
|
+
sessionDurations: durations,
|
|
192
|
+
};
|
|
193
|
+
}
|
|
194
|
+
function extractOutcomeSignals(events) {
|
|
195
|
+
const toolCalls = events.filter((e) => e.kind === "tool_call");
|
|
196
|
+
const toolResults = events.filter((e) => e.kind === "tool_result");
|
|
197
|
+
// Edit acceptance rate
|
|
198
|
+
const editCalls = toolCalls.filter((tc) => tc.toolName === "Edit" || tc.toolName === "Write");
|
|
199
|
+
let cleanEdits = 0;
|
|
200
|
+
for (let i = 0; i < editCalls.length; i++) {
|
|
201
|
+
const editIdx = toolCalls.indexOf(editCalls[i]);
|
|
202
|
+
const next = toolCalls[editIdx + 1];
|
|
203
|
+
if (!next || (next.toolName !== "Edit" && next.toolName !== "Write")) {
|
|
204
|
+
cleanEdits++;
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
const editAcceptanceRate = editCalls.length > 0 ? cleanEdits / editCalls.length : 0.5; // neutral when no data
|
|
208
|
+
// Error recovery: errors followed by non-error results
|
|
209
|
+
const errors = toolResults.filter((r) => r.kind === "tool_result" && r.isError);
|
|
210
|
+
let recoveries = 0;
|
|
211
|
+
for (const err of errors) {
|
|
212
|
+
const errIdx = events.indexOf(err);
|
|
213
|
+
// Look ahead for successful operations
|
|
214
|
+
for (let j = errIdx + 1; j < Math.min(errIdx + 5, events.length); j++) {
|
|
215
|
+
if (events[j]?.kind === "tool_result" && !events[j].isError) {
|
|
216
|
+
recoveries++;
|
|
217
|
+
break;
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
}
|
|
221
|
+
const errorRecoveryRate = errors.length > 0 ? recoveries / errors.length : 0.5; // neutral when no data
|
|
222
|
+
// Permission mode progression
|
|
223
|
+
const userPrompts = events.filter((e) => e.kind === "user_prompt");
|
|
224
|
+
const modes = userPrompts
|
|
225
|
+
.map((p) => p.permissionMode)
|
|
226
|
+
.filter(Boolean);
|
|
227
|
+
let progression = 0;
|
|
228
|
+
if (modes.length > 1) {
|
|
229
|
+
const hasBypass = modes.includes("bypassPermissions");
|
|
230
|
+
const hasDefault = modes.some((m) => m !== "bypassPermissions" && m !== "plan");
|
|
231
|
+
if (hasBypass && hasDefault)
|
|
232
|
+
progression = 0.5; // mixed usage
|
|
233
|
+
if (hasBypass && !hasDefault)
|
|
234
|
+
progression = -0.5; // always bypass
|
|
235
|
+
if (!hasBypass)
|
|
236
|
+
progression = 1; // responsible defaults
|
|
237
|
+
}
|
|
238
|
+
return {
|
|
239
|
+
editAcceptanceRate,
|
|
240
|
+
permissionModeProgression: progression,
|
|
241
|
+
errorRecoveryRate,
|
|
242
|
+
repeatFailureRate: 0, // TODO: implement pattern detection
|
|
243
|
+
};
|
|
244
|
+
}
|
|
245
|
+
//# sourceMappingURL=signals.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"signals.js","sourceRoot":"","sources":["../../src/scoring/signals.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { LocalStore, SessionSnapshot, CCProficiencyConfig } from "../types.js";
|
|
2
|
+
export declare function loadStore(): LocalStore;
|
|
3
|
+
export declare function saveStore(store: LocalStore): void;
|
|
4
|
+
export declare function isSessionProcessed(store: LocalStore, sessionId: string): boolean;
|
|
5
|
+
export declare function addSnapshot(store: LocalStore, snapshot: SessionSnapshot): void;
|
|
6
|
+
export declare function loadConfig(): CCProficiencyConfig;
|
|
7
|
+
export declare function saveConfig(config: CCProficiencyConfig): void;
|
|
8
|
+
export declare function saveBadge(svg: string): string;
|
|
9
|
+
export declare function getBadgePath(): string;
|
|
10
|
+
export declare function logError(message: string): void;
|
|
11
|
+
export declare function getStoreDir(): string;
|
|
12
|
+
//# sourceMappingURL=local-store.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local-store.d.ts","sourceRoot":"","sources":["../../src/store/local-store.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,UAAU,EAAE,eAAe,EAAqB,mBAAmB,EAAE,MAAM,aAAa,CAAC;AAoBvG,wBAAgB,SAAS,IAAI,UAAU,CAStC;AAED,wBAAgB,SAAS,CAAC,KAAK,EAAE,UAAU,GAAG,IAAI,CAcjD;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAEhF;AAED,wBAAgB,WAAW,CAAC,KAAK,EAAE,UAAU,EAAE,QAAQ,EAAE,eAAe,GAAG,IAAI,CAG9E;AAED,wBAAgB,UAAU,IAAI,mBAAmB,CAUhD;AAED,wBAAgB,UAAU,CAAC,MAAM,EAAE,mBAAmB,GAAG,IAAI,CAG5D;AAED,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAI7C;AAED,wBAAgB,YAAY,IAAI,MAAM,CAErC;AAED,wBAAgB,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAe9C;AAED,wBAAgB,WAAW,IAAI,MAAM,CAEpC"}
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.loadStore = loadStore;
|
|
4
|
+
exports.saveStore = saveStore;
|
|
5
|
+
exports.isSessionProcessed = isSessionProcessed;
|
|
6
|
+
exports.addSnapshot = addSnapshot;
|
|
7
|
+
exports.loadConfig = loadConfig;
|
|
8
|
+
exports.saveConfig = saveConfig;
|
|
9
|
+
exports.saveBadge = saveBadge;
|
|
10
|
+
exports.getBadgePath = getBadgePath;
|
|
11
|
+
exports.logError = logError;
|
|
12
|
+
exports.getStoreDir = getStoreDir;
|
|
13
|
+
const node_fs_1 = require("node:fs");
|
|
14
|
+
const node_path_1 = require("node:path");
|
|
15
|
+
const node_os_1 = require("node:os");
|
|
16
|
+
const queue_js_1 = require("./queue.js");
|
|
17
|
+
const STORE_DIR = (0, node_path_1.join)((0, node_os_1.homedir)(), ".cc-proficiency");
|
|
18
|
+
const STORE_FILE = (0, node_path_1.join)(STORE_DIR, "store.json");
|
|
19
|
+
const CONFIG_FILE = (0, node_path_1.join)(STORE_DIR, "config.json");
|
|
20
|
+
const BADGE_FILE = (0, node_path_1.join)(STORE_DIR, "cc-proficiency.svg");
|
|
21
|
+
const ERROR_LOG = (0, node_path_1.join)(STORE_DIR, "error.log");
|
|
22
|
+
const MAX_ERROR_LOG_SIZE = 1_000_000; // 1MB
|
|
23
|
+
const RETENTION_DAYS = 90;
|
|
24
|
+
function emptyStore() {
|
|
25
|
+
return {
|
|
26
|
+
processedSessionIds: [],
|
|
27
|
+
snapshots: [],
|
|
28
|
+
lastResult: undefined,
|
|
29
|
+
lastUpdated: undefined,
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
function loadStore() {
|
|
33
|
+
(0, queue_js_1.ensureStoreDir)();
|
|
34
|
+
if (!(0, node_fs_1.existsSync)(STORE_FILE))
|
|
35
|
+
return emptyStore();
|
|
36
|
+
try {
|
|
37
|
+
return JSON.parse((0, node_fs_1.readFileSync)(STORE_FILE, "utf-8"));
|
|
38
|
+
}
|
|
39
|
+
catch {
|
|
40
|
+
return emptyStore();
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
function saveStore(store) {
|
|
44
|
+
(0, queue_js_1.ensureStoreDir)();
|
|
45
|
+
store.lastUpdated = new Date().toISOString();
|
|
46
|
+
// Prune old snapshots (>90 days)
|
|
47
|
+
const cutoff = Date.now() - RETENTION_DAYS * 24 * 60 * 60 * 1000;
|
|
48
|
+
store.snapshots = store.snapshots.filter((s) => {
|
|
49
|
+
const ts = new Date(s.timestamp).getTime();
|
|
50
|
+
return !isNaN(ts) && ts > cutoff;
|
|
51
|
+
});
|
|
52
|
+
const tmpFile = (0, node_path_1.join)(STORE_DIR, ".store.json.tmp");
|
|
53
|
+
(0, node_fs_1.writeFileSync)(tmpFile, JSON.stringify(store, null, 2), "utf-8");
|
|
54
|
+
(0, node_fs_1.renameSync)(tmpFile, STORE_FILE);
|
|
55
|
+
}
|
|
56
|
+
function isSessionProcessed(store, sessionId) {
|
|
57
|
+
return store.processedSessionIds.includes(sessionId);
|
|
58
|
+
}
|
|
59
|
+
function addSnapshot(store, snapshot) {
|
|
60
|
+
store.processedSessionIds.push(snapshot.sessionId);
|
|
61
|
+
store.snapshots.push(snapshot);
|
|
62
|
+
}
|
|
63
|
+
function loadConfig() {
|
|
64
|
+
(0, queue_js_1.ensureStoreDir)();
|
|
65
|
+
if (!(0, node_fs_1.existsSync)(CONFIG_FILE)) {
|
|
66
|
+
return { autoUpload: true, public: false };
|
|
67
|
+
}
|
|
68
|
+
try {
|
|
69
|
+
return JSON.parse((0, node_fs_1.readFileSync)(CONFIG_FILE, "utf-8"));
|
|
70
|
+
}
|
|
71
|
+
catch {
|
|
72
|
+
return { autoUpload: true, public: false };
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
function saveConfig(config) {
|
|
76
|
+
(0, queue_js_1.ensureStoreDir)();
|
|
77
|
+
(0, node_fs_1.writeFileSync)(CONFIG_FILE, JSON.stringify(config, null, 2), "utf-8");
|
|
78
|
+
}
|
|
79
|
+
function saveBadge(svg) {
|
|
80
|
+
(0, queue_js_1.ensureStoreDir)();
|
|
81
|
+
(0, node_fs_1.writeFileSync)(BADGE_FILE, svg, "utf-8");
|
|
82
|
+
return BADGE_FILE;
|
|
83
|
+
}
|
|
84
|
+
function getBadgePath() {
|
|
85
|
+
return BADGE_FILE;
|
|
86
|
+
}
|
|
87
|
+
function logError(message) {
|
|
88
|
+
(0, queue_js_1.ensureStoreDir)();
|
|
89
|
+
try {
|
|
90
|
+
// Check size and rotate if needed
|
|
91
|
+
if ((0, node_fs_1.existsSync)(ERROR_LOG)) {
|
|
92
|
+
const stat = (0, node_fs_1.statSync)(ERROR_LOG);
|
|
93
|
+
if (stat.size > MAX_ERROR_LOG_SIZE) {
|
|
94
|
+
(0, node_fs_1.writeFileSync)(ERROR_LOG, "", "utf-8"); // truncate
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
const timestamp = new Date().toISOString();
|
|
98
|
+
(0, node_fs_1.appendFileSync)(ERROR_LOG, `[${timestamp}] ${message}\n`, "utf-8");
|
|
99
|
+
}
|
|
100
|
+
catch {
|
|
101
|
+
// can't log — silently fail
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
function getStoreDir() {
|
|
105
|
+
return STORE_DIR;
|
|
106
|
+
}
|
|
107
|
+
//# sourceMappingURL=local-store.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local-store.js","sourceRoot":"","sources":["../../src/store/local-store.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import type { QueueEntry } from "../types.js";
|
|
2
|
+
export declare function ensureStoreDir(): void;
|
|
3
|
+
/**
|
|
4
|
+
* Append a queue entry (called by the hook, must be fast).
|
|
5
|
+
*/
|
|
6
|
+
export declare function enqueue(entry: QueueEntry): void;
|
|
7
|
+
/**
|
|
8
|
+
* Read all queue entries.
|
|
9
|
+
*/
|
|
10
|
+
export declare function readQueue(): QueueEntry[];
|
|
11
|
+
/**
|
|
12
|
+
* Atomically replace queue with remaining entries.
|
|
13
|
+
* Re-reads queue to merge any entries appended during processing (race-safe).
|
|
14
|
+
*/
|
|
15
|
+
export declare function writeQueue(processedIds: Set<string>): void;
|
|
16
|
+
/**
|
|
17
|
+
* Acquire queue lock. Returns true if acquired, false if held by another process.
|
|
18
|
+
*/
|
|
19
|
+
export declare function acquireLock(): boolean;
|
|
20
|
+
/**
|
|
21
|
+
* Release queue lock.
|
|
22
|
+
*/
|
|
23
|
+
export declare function releaseLock(): void;
|
|
24
|
+
//# sourceMappingURL=queue.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"queue.d.ts","sourceRoot":"","sources":["../../src/store/queue.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAO9C,wBAAgB,cAAc,IAAI,IAAI,CAIrC;AAED;;GAEG;AACH,wBAAgB,OAAO,CAAC,KAAK,EAAE,UAAU,GAAG,IAAI,CAG/C;AAED;;GAEG;AACH,wBAAgB,SAAS,IAAI,UAAU,EAAE,CAcxC;AAED;;;GAGG;AACH,wBAAgB,UAAU,CAAC,YAAY,EAAE,GAAG,CAAC,MAAM,CAAC,GAAG,IAAI,CAS1D;AAED;;GAEG;AACH,wBAAgB,WAAW,IAAI,OAAO,CAyBrC;AAED;;GAEG;AACH,wBAAgB,WAAW,IAAI,IAAI,CAMlC"}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ensureStoreDir = ensureStoreDir;
|
|
4
|
+
exports.enqueue = enqueue;
|
|
5
|
+
exports.readQueue = readQueue;
|
|
6
|
+
exports.writeQueue = writeQueue;
|
|
7
|
+
exports.acquireLock = acquireLock;
|
|
8
|
+
exports.releaseLock = releaseLock;
|
|
9
|
+
const node_fs_1 = require("node:fs");
|
|
10
|
+
const node_path_1 = require("node:path");
|
|
11
|
+
const node_os_1 = require("node:os");
|
|
12
|
+
const STORE_DIR = (0, node_path_1.join)((0, node_os_1.homedir)(), ".cc-proficiency");
|
|
13
|
+
const QUEUE_FILE = (0, node_path_1.join)(STORE_DIR, "queue.jsonl");
|
|
14
|
+
const QUEUE_LOCK = (0, node_path_1.join)(STORE_DIR, "queue.lock");
|
|
15
|
+
const LOCK_STALE_MS = 60_000; // 60 seconds
|
|
16
|
+
function ensureStoreDir() {
|
|
17
|
+
if (!(0, node_fs_1.existsSync)(STORE_DIR)) {
|
|
18
|
+
(0, node_fs_1.mkdirSync)(STORE_DIR, { recursive: true });
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Append a queue entry (called by the hook, must be fast).
|
|
23
|
+
*/
|
|
24
|
+
function enqueue(entry) {
|
|
25
|
+
ensureStoreDir();
|
|
26
|
+
(0, node_fs_1.appendFileSync)(QUEUE_FILE, JSON.stringify(entry) + "\n", "utf-8");
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Read all queue entries.
|
|
30
|
+
*/
|
|
31
|
+
function readQueue() {
|
|
32
|
+
if (!(0, node_fs_1.existsSync)(QUEUE_FILE))
|
|
33
|
+
return [];
|
|
34
|
+
const entries = [];
|
|
35
|
+
const content = (0, node_fs_1.readFileSync)(QUEUE_FILE, "utf-8");
|
|
36
|
+
for (const line of content.split("\n")) {
|
|
37
|
+
if (!line.trim())
|
|
38
|
+
continue;
|
|
39
|
+
try {
|
|
40
|
+
entries.push(JSON.parse(line));
|
|
41
|
+
}
|
|
42
|
+
catch {
|
|
43
|
+
// skip malformed
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
return entries;
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Atomically replace queue with remaining entries.
|
|
50
|
+
* Re-reads queue to merge any entries appended during processing (race-safe).
|
|
51
|
+
*/
|
|
52
|
+
function writeQueue(processedIds) {
|
|
53
|
+
ensureStoreDir();
|
|
54
|
+
// Re-read to catch entries appended since we started processing
|
|
55
|
+
const current = readQueue();
|
|
56
|
+
const remaining = current.filter((e) => !processedIds.has(e.sessionId));
|
|
57
|
+
const tmpFile = (0, node_path_1.join)(STORE_DIR, ".queue.jsonl.tmp");
|
|
58
|
+
const content = remaining.map((e) => JSON.stringify(e)).join("\n") + (remaining.length > 0 ? "\n" : "");
|
|
59
|
+
(0, node_fs_1.writeFileSync)(tmpFile, content, "utf-8");
|
|
60
|
+
(0, node_fs_1.renameSync)(tmpFile, QUEUE_FILE);
|
|
61
|
+
}
|
|
62
|
+
/**
|
|
63
|
+
* Acquire queue lock. Returns true if acquired, false if held by another process.
|
|
64
|
+
*/
|
|
65
|
+
function acquireLock() {
|
|
66
|
+
ensureStoreDir();
|
|
67
|
+
if ((0, node_fs_1.existsSync)(QUEUE_LOCK)) {
|
|
68
|
+
// Check if stale
|
|
69
|
+
try {
|
|
70
|
+
const lockContent = (0, node_fs_1.readFileSync)(QUEUE_LOCK, "utf-8");
|
|
71
|
+
const lockTime = parseInt(lockContent, 10);
|
|
72
|
+
if (Date.now() - lockTime < LOCK_STALE_MS) {
|
|
73
|
+
return false; // lock is fresh, another process is running
|
|
74
|
+
}
|
|
75
|
+
// Stale lock — break it
|
|
76
|
+
(0, node_fs_1.unlinkSync)(QUEUE_LOCK);
|
|
77
|
+
}
|
|
78
|
+
catch {
|
|
79
|
+
// Can't read lock — try to acquire anyway
|
|
80
|
+
try {
|
|
81
|
+
(0, node_fs_1.unlinkSync)(QUEUE_LOCK);
|
|
82
|
+
}
|
|
83
|
+
catch { /* ignore */ }
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
try {
|
|
87
|
+
(0, node_fs_1.writeFileSync)(QUEUE_LOCK, String(Date.now()), { flag: "wx" }); // O_EXCL
|
|
88
|
+
return true;
|
|
89
|
+
}
|
|
90
|
+
catch {
|
|
91
|
+
return false; // another process beat us
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* Release queue lock.
|
|
96
|
+
*/
|
|
97
|
+
function releaseLock() {
|
|
98
|
+
try {
|
|
99
|
+
(0, node_fs_1.unlinkSync)(QUEUE_LOCK);
|
|
100
|
+
}
|
|
101
|
+
catch {
|
|
102
|
+
// already released
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
//# sourceMappingURL=queue.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"queue.js","sourceRoot":"","sources":["../../src/store/queue.ts"],"names":[],"mappings":"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"}
|