@kevinbermudezc/context-guard 1.0.1 → 1.1.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.
Files changed (36) hide show
  1. package/README.md +70 -32
  2. package/dist/bin/claude-hook.js +27 -3
  3. package/dist/bin/claude-hook.js.map +1 -1
  4. package/dist/src/file-classifier.d.ts +15 -0
  5. package/dist/src/file-classifier.d.ts.map +1 -0
  6. package/dist/src/file-classifier.js +101 -0
  7. package/dist/src/file-classifier.js.map +1 -0
  8. package/dist/src/import-collapser.d.ts +13 -0
  9. package/dist/src/import-collapser.d.ts.map +1 -0
  10. package/dist/src/import-collapser.js +112 -0
  11. package/dist/src/import-collapser.js.map +1 -0
  12. package/dist/src/index.d.ts +2 -0
  13. package/dist/src/index.d.ts.map +1 -1
  14. package/dist/src/index.js +26 -0
  15. package/dist/src/index.js.map +1 -1
  16. package/dist/src/skeletonizer.d.ts +2 -0
  17. package/dist/src/skeletonizer.d.ts.map +1 -1
  18. package/dist/src/skeletonizer.js +86 -7
  19. package/dist/src/skeletonizer.js.map +1 -1
  20. package/dist/src/types.d.ts +1 -1
  21. package/dist/src/types.d.ts.map +1 -1
  22. package/dist/tests/claude-hook.test.js +39 -9
  23. package/dist/tests/claude-hook.test.js.map +1 -1
  24. package/dist/tests/file-classifier.test.d.ts +2 -0
  25. package/dist/tests/file-classifier.test.d.ts.map +1 -0
  26. package/dist/tests/file-classifier.test.js +46 -0
  27. package/dist/tests/file-classifier.test.js.map +1 -0
  28. package/dist/tests/framework-sfc.test.d.ts +2 -0
  29. package/dist/tests/framework-sfc.test.d.ts.map +1 -0
  30. package/dist/tests/framework-sfc.test.js +151 -0
  31. package/dist/tests/framework-sfc.test.js.map +1 -0
  32. package/dist/tests/import-collapser.test.d.ts +2 -0
  33. package/dist/tests/import-collapser.test.d.ts.map +1 -0
  34. package/dist/tests/import-collapser.test.js +35 -0
  35. package/dist/tests/import-collapser.test.js.map +1 -0
  36. package/package.json +1 -1
package/README.md CHANGED
@@ -31,40 +31,78 @@ Frontier models are incredible at reasoning, but reading massive files (1,000+ l
31
31
 
32
32
  ## 🏗️ How ContextGuard Works
33
33
 
34
- ContextGuard acts as an **admission turnstile** using Claude Code's native `PreToolUse` hook lifecycle:
34
+ ContextGuard acts as an **intelligent admission turnstile** using Claude Code's native `PreToolUse` hook lifecycle:
35
+
36
+ ```mermaid
37
+ flowchart TD
38
+ A["🤖 <b>Claude Code / Agent Invocation</b><br><code>Read</code> or <code>cat file</code>"] --> B{"Is it an Image, PDF,<br>or Notebook (.ipynb)?"}
39
+
40
+ B -- "YES" --> E["✅ <b>ALLOW (Exit 0)</b><br>Claude Code native multimodal vision & viewer"]
41
+
42
+ B -- "NO" --> C{"Is it a Binary (wasm/zip/so),<br>Lockfile or Minified file?"}
43
+
44
+ C -- "YES" --> D["🛑 <b>TURNSTILE HARD BLOCK (Exit 2)</b><br>• Binary: Blocks wasm, zip, sqlite, binaries<br>• Lockfile: Suggests <code>pnpm why</code> / CLI<br>• Minified: Recommends <code>src/</code> source"]
45
+
46
+ C -- "NO" --> F{"File &gt; 300 lines &<br>Un-scoped full read?"}
47
+
48
+ F -- "NO (Small or scoped range)" --> E
49
+
50
+ F -- "YES (Large un-scoped read)" --> G["🛡️ <b>CONTEXTGUARD SHUNT TRIGGER</b>"]
51
+
52
+ G --> H["<b>Tier 0: Local AST Skeletonizer</b><br>TS, JS, Python, Go, Rust, Java, C#<br>+ Svelte 5, Vue 3, Angular, Astro SFCs<br>• Collapses import walls (&gt;5 imports)<br>• Cost: <b>$0.00</b> | Latency: <b>&lt; 5ms</b>"]
53
+ G --> I["<b>Tier 1: Worker Model</b><br>Logs, JSON, Markdown, Docs<br>• Gemini 2.5 Flash / Local Ollama<br>• Cost: <b>~95% cheaper</b> than Frontier"]
54
+
55
+ H --> J["🛑 <b>HARD BLOCK (Exit Code 2)</b><br>Emits line-tagged skeleton <code>[L89]</code> to stderr"]
56
+ I --> J
57
+
58
+ J --> K["🎯 <b>Targeted Second Read</b><br>Claude reads feedback & fetches exact slice:<br><code>Read(file, offset=89, limit=35)</code><br><b>Tokens saved: 95% - 99%</b>"]
59
+
60
+ classDef block fill:#ef4444,stroke:#991b1b,stroke-width:2px,color:#fff;
61
+ classDef allow fill:#22c55e,stroke:#15803d,stroke-width:2px,color:#fff;
62
+ classDef trigger fill:#3b82f6,stroke:#1d4ed8,stroke-width:2px,color:#fff;
63
+ classDef tier fill:#6366f1,stroke:#4338ca,stroke-width:2px,color:#fff;
64
+ classDef action fill:#10b981,stroke:#047857,stroke-width:2px,color:#fff;
65
+
66
+ class D,J block;
67
+ class E allow;
68
+ class G trigger;
69
+ class H,I tier;
70
+ class K action;
71
+ ```
72
+
73
+ ---
35
74
 
75
+ ## 💡 Real-World Use Case: Before vs. After
76
+
77
+ Imagine Claude Code needs to inspect how refund errors are handled in `src/payment-gateway.ts`, a 1,500-line service file with 28 imports and several auxiliary database queries.
78
+
79
+ ### ❌ Without ContextGuard (Standard Behavior)
80
+ ```text
81
+ 1. Claude Code executes: Read("src/payment-gateway.ts")
82
+ └── ❌ Dumps all 1,500 lines into the frontier reasoning context
83
+ ├── Tokens burned: ~8,500 tokens (~$0.13 in Claude Opus for a single read)
84
+ ├── Context window saturated with 28 repetitive imports & unrelated schema logic
85
+ └── High risk of "Lost in the Middle" attention degradation and hallucinations
36
86
  ```
37
- CLAUDE CODE TOOL INVOCATION
38
- │
39
- ▼
40
- Does the file exceed the limit (e.g. 300 lines)
41
- AND is it an un-scoped full read?
42
- │
43
- ┌────────────┴────────────┐
44
- YES NO
45
- │ │
46
- ▼ ▼
47
- ┌───────────────────────────┐ [ALLOW: Exit 0]
48
- │ CONTEXTGUARD TRIGGER │ File is small or
49
- └─────────────┬─────────────┘ targeted slice requested
50
- │
51
- ┌────────────┴────────────┐
52
- ▼ ▼
53
- [Tier 0: Local AST] [Tier 1: Worker Model]
54
- TypeScript, Python, Go, Logs, JSON, Markdown or
55
- Rust, Java, C# semantic question queries
56
- • Cost: $0.00 • Gemini Flash / Ollama
57
- • Latency: < 5ms • Cost: ~95% cheaper
58
- │ │
59
- └────────────┬────────────┘
60
- │
61
- ▼
62
- [HARD BLOCK: Exit 2]
63
- Emits signature skeleton with [L120] line tags to stderr
64
- │
65
- ▼
66
- Claude receives system feedback & requests
67
- the exact slice needed (e.g. offset=130, limit=40)
87
+
88
+ ### ✅ With ContextGuard (Context Shield Active)
89
+ ```text
90
+ 1. Claude Code executes: Read("src/payment-gateway.ts")
91
+ └── 🛡️ ContextGuard intercepts in <15ms and aborts with Exit Code 2:
92
+ 🛑 [CONTEXTGUARD: READ BLOCKED (1,500 LINES)]
93
+ [L1-L32] 📦 28 imports collapsed (12 packages: @stripe/stripe-node, express...; 16 local).
94
+ [L45] export class PaymentGatewayService
95
+ [L52] constructor(private stripe: Stripe, private db: Database)
96
+ [L89] async processRefund(chargeId: string, amount: number): Promise<RefundResult>
97
+ [L145] async verifyWebhookSignature(payload: Buffer, sig: string): boolean
98
+ 👉 Please request a targeted range using offset and limit.
99
+
100
+ 2. Claude Code parses the structural skeleton and executes:
101
+ Read("src/payment-gateway.ts", offset=89, limit=35)
102
+ └── ✅ Allowed immediately!
103
+ ├── Tokens consumed: ~160 tokens (instead of 8,500)
104
+ ├── Savings: 98% token reduction and cost down to < $0.002
105
+ └── Razor-sharp attention, pinpoint accuracy, and zero hallucinations
68
106
  ```
69
107
 
70
108
  ---
@@ -10,6 +10,7 @@ import fs from 'node:fs';
10
10
  import path from 'node:path';
11
11
  import { CONFIG } from '../src/config.js';
12
12
  import { extractCodeSkeleton } from '../src/skeletonizer.js';
13
+ import { classifyFile } from '../src/file-classifier.js';
13
14
  async function runHook() {
14
15
  const inputChunks = [];
15
16
  for await (const chunk of process.stdin) {
@@ -34,11 +35,12 @@ async function runHook() {
34
35
  if (isReadTool) {
35
36
  const rawPath = toolInput.file_path || toolInput.path || toolInput.filePath || toolInput.AbsolutePath;
36
37
  targetFilePath = typeof rawPath === 'string' ? rawPath : null;
37
- // Check if Claude specified line bounds
38
+ // Check if Claude specified line bounds or page ranges (e.g. for PDFs)
38
39
  if (toolInput.offset !== undefined ||
39
40
  toolInput.limit !== undefined ||
40
41
  toolInput.StartLine !== undefined ||
41
- toolInput.EndLine !== undefined) {
42
+ toolInput.EndLine !== undefined ||
43
+ toolInput.pages !== undefined) {
42
44
  isScoped = true;
43
45
  }
44
46
  }
@@ -62,11 +64,33 @@ async function runHook() {
62
64
  if (!fs.existsSync(resolvedPath) || fs.statSync(resolvedPath).isDirectory()) {
63
65
  process.exit(0);
64
66
  }
67
+ const ext = path.extname(resolvedPath).toLowerCase();
68
+ // 3. Allow Claude Code native multimodal formats & notebooks (.png, .jpg, .pdf, .ipynb)
69
+ // Claude Code's Read tool natively renders images for multimodal vision, parses PDFs, and formats notebooks.
70
+ const CLAUDE_NATIVE_MEDIA_EXTENSIONS = new Set([
71
+ '.png', '.jpg', '.jpeg', '.gif', '.webp', '.svg', '.ico', '.bmp', '.avif',
72
+ '.pdf',
73
+ '.ipynb'
74
+ ]);
75
+ if (CLAUDE_NATIVE_MEDIA_EXTENSIONS.has(ext)) {
76
+ process.exit(0); // Exit 0 = ALLOW Claude native vision & viewer
77
+ }
78
+ // 4. Check for Non-Multimodal Binaries, Lockfiles, and Minified files
79
+ const classification = classifyFile(resolvedPath);
80
+ if (classification.category !== 'source_code') {
81
+ const feedback = [
82
+ `🛑 [CONTEXTGUARD: ACCESO DENEGADO - ${classification.category.toUpperCase()}]`,
83
+ classification.reason,
84
+ ``,
85
+ `👉 ${classification.recommendedAction}`
86
+ ].join('\n');
87
+ process.stderr.write(feedback + '\n');
88
+ process.exit(2);
89
+ }
65
90
  const stat = fs.statSync(resolvedPath);
66
91
  const rawContent = fs.readFileSync(resolvedPath, 'utf-8');
67
92
  const lines = rawContent.split('\n');
68
93
  const totalLines = lines.length;
69
- const ext = path.extname(resolvedPath);
70
94
  // If within safety thresholds, allow direct read
71
95
  if (totalLines <= CONFIG.maxLines && stat.size <= CONFIG.maxBytes) {
72
96
  process.exit(0); // Exit 0 = ALLOW
@@ -1 +1 @@
1
- {"version":3,"file":"claude-hook.js","sourceRoot":"","sources":["../../bin/claude-hook.ts"],"names":[],"mappings":";AAEA;;;;;;GAMG;AAEH,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EAAE,MAAM,EAAE,MAAM,kBAAkB,CAAC;AAC1C,OAAO,EAAE,mBAAmB,EAAE,MAAM,wBAAwB,CAAC;AAG7D,KAAK,UAAU,OAAO;IACpB,MAAM,WAAW,GAAa,EAAE,CAAC;IACjC,IAAI,KAAK,EAAE,MAAM,KAAK,IAAI,OAAO,CAAC,KAAK,EAAE,CAAC;QACxC,WAAW,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAC1B,CAAC;IAED,IAAI,WAAW,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QAC7B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,IAAI,OAA0B,CAAC;IAC/B,IAAI,CAAC;QACH,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,CAAC;IACrE,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,oCAAoC;IACvD,CAAC;IAED,MAAM,QAAQ,GAAG,OAAO,CAAC,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;IACnD,MAAM,SAAS,GAAG,OAAO,CAAC,UAAU,IAAI,OAAO,CAAC,KAAK,IAAI,EAAE,CAAC;IAE5D,IAAI,cAAc,GAAkB,IAAI,CAAC;IACzC,IAAI,QAAQ,GAAG,KAAK,CAAC;IAErB,yEAAyE;IACzE,MAAM,UAAU,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,WAAW,EAAE,UAAU,EAAE,WAAW,CAAC,CAAC,QAAQ,CAAC,QAAQ,IAAI,EAAE,CAAC,CAAC;IACnG,IAAI,UAAU,EAAE,CAAC;QACf,MAAM,OAAO,GAAG,SAAS,CAAC,SAAS,IAAI,SAAS,CAAC,IAAI,IAAI,SAAS,CAAC,QAAQ,IAAI,SAAS,CAAC,YAAY,CAAC;QACtG,cAAc,GAAG,OAAO,OAAO,KAAK,QAAQ,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC;QAC9D,wCAAwC;QACxC,IACE,SAAS,CAAC,MAAM,KAAK,SAAS;YAC9B,SAAS,CAAC,KAAK,KAAK,SAAS;YAC7B,SAAS,CAAC,SAAS,KAAK,SAAS;YACjC,SAAS,CAAC,OAAO,KAAK,SAAS,EAC/B,CAAC;YACD,QAAQ,GAAG,IAAI,CAAC;QAClB,CAAC;IACH,CAAC;IAED,sEAAsE;IACtE,IAAI,QAAQ,KAAK,MAAM,IAAI,QAAQ,KAAK,MAAM,EAAE,CAAC;QAC/C,MAAM,GAAG,GAAG,CAAC,SAAS,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;QAC7C,0EAA0E;QAC1E,IAAI,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,GAAG,CAAC,UAAU,CAAC,SAAS,CAAC,IAAI,GAAG,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;YACrG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QACD,MAAM,QAAQ,GAAG,GAAG,CAAC,KAAK,CAAC,2CAA2C,CAAC,CAAC;QACxE,IAAI,QAAQ,EAAE,CAAC;YACb,cAAc,GAAG,QAAQ,CAAC,CAAC,CAAC,CAAC;QAC/B,CAAC;IACH,CAAC;IAED,uEAAuE;IACvE,IAAI,CAAC,cAAc,IAAI,QAAQ,EAAE,CAAC;QAChC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,iBAAiB;IACpC,CAAC;IAED,MAAM,YAAY,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,cAAc,CAAC,CAAC;IACjE,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,YAAY,CAAC,IAAI,EAAE,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAC,WAAW,EAAE,EAAE,CAAC;QAC5E,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,IAAI,GAAG,EAAE,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAC;IACvC,MAAM,UAAU,GAAG,EAAE,CAAC,YAAY,CAAC,YAAY,EAAE,OAAO,CAAC,CAAC;IAC1D,MAAM,KAAK,GAAG,UAAU,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;IACrC,MAAM,UAAU,GAAG,KAAK,CAAC,MAAM,CAAC;IAChC,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,CAAC,YAAY,CAAC,CAAC;IAEvC,iDAAiD;IACjD,IAAI,UAAU,IAAI,MAAM,CAAC,QAAQ,IAAI,IAAI,CAAC,IAAI,IAAI,MAAM,CAAC,QAAQ,EAAE,CAAC;QAClE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,iBAAiB;IACpC,CAAC;IAED,2EAA2E;IAC3E,qDAAqD;IACrD,2EAA2E;IAC3E,MAAM,QAAQ,GAAG,mBAAmB,CAAC,UAAU,EAAE,GAAG,CAAC,CAAC;IACtD,MAAM,OAAO,GAAG,QAAQ,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,UAAU,UAAU,GAAG,EAAE,mCAAmC,CAAC;IAEzH,MAAM,eAAe,GAAG;QACtB,2EAA2E;QAC3E,eAAe,IAAI,CAAC,QAAQ,CAAC,YAAY,CAAC,cAAc,UAAU,aAAa,CAAC,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,OAAO;QACnH,kIAAkI;QAClI,EAAE;QACF,2DAA2D;QAC3D,kFAAkF;QAClF,OAAO;QACP,kFAAkF;QAClF,EAAE;QACF,wBAAwB;QACxB,4KAA4K;KAC7K,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAEb,wGAAwG;IACxG,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC;IAC7C,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,OAAO,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC"}
1
+ {"version":3,"file":"claude-hook.js","sourceRoot":"","sources":["../../bin/claude-hook.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,15 @@
1
+ export type FileCategory = 'binary' | 'lockfile' | 'minified' | 'source_code';
2
+ export interface FileClassification {
3
+ category: FileCategory;
4
+ reason?: string;
5
+ recommendedAction?: string;
6
+ }
7
+ /**
8
+ * Inspects magic bytes (first 512 bytes) to detect binary contents
9
+ */
10
+ export declare function isBinaryBuffer(buffer: Buffer): boolean;
11
+ /**
12
+ * Classifies a file to determine if it should be shunted, blocked, or parsed
13
+ */
14
+ export declare function classifyFile(filePath: string): FileClassification;
15
+ //# sourceMappingURL=file-classifier.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file-classifier.d.ts","sourceRoot":"","sources":["../../src/file-classifier.ts"],"names":[],"mappings":"AAGA,MAAM,MAAM,YAAY,GAAG,QAAQ,GAAG,UAAU,GAAG,UAAU,GAAG,aAAa,CAAC;AAE9E,MAAM,WAAW,kBAAkB;IACjC,QAAQ,EAAE,YAAY,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,iBAAiB,CAAC,EAAE,MAAM,CAAC;CAC5B;AA0BD;;GAEG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAmBtD;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,QAAQ,EAAE,MAAM,GAAG,kBAAkB,CAuDjE"}
@@ -0,0 +1,101 @@
1
+ import path from 'node:path';
2
+ import fs from 'node:fs';
3
+ const BINARY_EXTENSIONS = new Set([
4
+ // Images
5
+ '.png', '.jpg', '.jpeg', '.gif', '.webp', '.ico', '.bmp', '.tiff', '.avif',
6
+ // Documents & Media
7
+ '.pdf', '.doc', '.docx', '.xls', '.xlsx', '.ppt', '.pptx', '.mp3', '.mp4', '.mov', '.avi',
8
+ // Fonts & Binaries
9
+ '.woff', '.woff2', '.ttf', '.otf', '.eot',
10
+ '.wasm', '.dylib', '.so', '.dll', '.exe', '.bin', '.obj', '.o',
11
+ // Archives & Databases
12
+ '.zip', '.tar', '.gz', '.7z', '.rar', '.bz2', '.sqlite', '.sqlite3', '.db'
13
+ ]);
14
+ const LOCKFILES = new Set([
15
+ 'pnpm-lock.yaml',
16
+ 'package-lock.json',
17
+ 'yarn.lock',
18
+ 'cargo.lock',
19
+ 'composer.lock',
20
+ 'gemfile.lock',
21
+ 'poetry.lock',
22
+ 'bun.lockb',
23
+ 'bun.lock'
24
+ ]);
25
+ /**
26
+ * Inspects magic bytes (first 512 bytes) to detect binary contents
27
+ */
28
+ export function isBinaryBuffer(buffer) {
29
+ const checkLen = Math.min(buffer.length, 512);
30
+ if (checkLen === 0)
31
+ return false;
32
+ let nonPrintableCount = 0;
33
+ for (let i = 0; i < checkLen; i++) {
34
+ const byte = buffer[i];
35
+ // Check for null bytes (typical of binary data)
36
+ if (byte === 0) {
37
+ return true;
38
+ }
39
+ // Byte values below 32 (except common whitespace: \t, \n, \r) or above 126
40
+ if ((byte < 7 || (byte > 13 && byte < 32)) && byte !== 27) {
41
+ nonPrintableCount++;
42
+ }
43
+ }
44
+ // If > 25% of bytes are non-printable control characters, consider it binary
45
+ return nonPrintableCount / checkLen > 0.25;
46
+ }
47
+ /**
48
+ * Classifies a file to determine if it should be shunted, blocked, or parsed
49
+ */
50
+ export function classifyFile(filePath) {
51
+ const fileName = path.basename(filePath).toLowerCase();
52
+ const ext = path.extname(filePath).toLowerCase();
53
+ // 1. Check for Lockfiles
54
+ if (LOCKFILES.has(fileName)) {
55
+ return {
56
+ category: 'lockfile',
57
+ reason: `El archivo "${path.basename(filePath)}" es un lockfile de dependencias.`,
58
+ recommendedAction: `No leas el lockfile crudo. Usa comandos de introspección como "pnpm why <paquete>" o "npm ls <paquete>".`
59
+ };
60
+ }
61
+ // 2. Check for Minified / Sourcemaps
62
+ if (fileName.endsWith('.min.js') || fileName.endsWith('.min.css') || fileName.endsWith('.bundle.js') || fileName.endsWith('.map')) {
63
+ return {
64
+ category: 'minified',
65
+ reason: `El archivo "${path.basename(filePath)}" está minificado o es un sourcemap.`,
66
+ recommendedAction: `Inspecciona los archivos originales de código fuente en "src/" en lugar del bundle empaquetado.`
67
+ };
68
+ }
69
+ // 3. Check for Binary Extensions
70
+ if (BINARY_EXTENSIONS.has(ext)) {
71
+ const isDoc = ext === '.pdf' || ext.startsWith('.doc') || ext.startsWith('.xls');
72
+ return {
73
+ category: 'binary',
74
+ reason: `El archivo "${path.basename(filePath)}" es un recurso binario (${ext}).`,
75
+ recommendedAction: isDoc
76
+ ? `Usa herramientas como "pdftotext" o lectores de documentos para extraer texto plano.`
77
+ : `Los archivos multimedia y binarios no deben volcarse como texto. Usa herramientas de visión multimodal o comandos de sistema.`
78
+ };
79
+ }
80
+ // 4. Inspect buffer if file exists
81
+ try {
82
+ const fd = fs.openSync(filePath, 'r');
83
+ const buffer = Buffer.alloc(512);
84
+ const bytesRead = fs.readSync(fd, buffer, 0, 512, 0);
85
+ fs.closeSync(fd);
86
+ if (isBinaryBuffer(buffer.subarray(0, bytesRead))) {
87
+ return {
88
+ category: 'binary',
89
+ reason: `El archivo "${path.basename(filePath)}" contiene bytes binarios o caracteres nulos.`,
90
+ recommendedAction: `No intentes leer archivos binarios como texto plano.`
91
+ };
92
+ }
93
+ }
94
+ catch {
95
+ // If unable to open or read header, proceed with fallback
96
+ }
97
+ return {
98
+ category: 'source_code'
99
+ };
100
+ }
101
+ //# sourceMappingURL=file-classifier.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file-classifier.js","sourceRoot":"","sources":["../../src/file-classifier.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,13 @@
1
+ export interface CollapsedImportResult {
2
+ hasCollapsed: boolean;
3
+ lines: string[];
4
+ }
5
+ /**
6
+ * Checks if a line is an import statement
7
+ */
8
+ export declare function isImportLine(line: string, ext: string): boolean;
9
+ /**
10
+ * Processes a collection of lines, collapsing import walls exceeding threshold
11
+ */
12
+ export declare function collapseImportWall(rawLines: string[], ext: string, maxThreshold?: number): CollapsedImportResult;
13
+ //# sourceMappingURL=import-collapser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"import-collapser.d.ts","sourceRoot":"","sources":["../../src/import-collapser.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,qBAAqB;IACpC,YAAY,EAAE,OAAO,CAAC;IACtB,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AA0CD;;GAEG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAiB/D;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,EAAE,EAAE,GAAG,EAAE,MAAM,EAAE,YAAY,GAAE,MAAU,GAAG,qBAAqB,CAkEnH"}
@@ -0,0 +1,112 @@
1
+ /**
2
+ * Parses import source from JS/TS and Python statements
3
+ */
4
+ function extractImportSource(line) {
5
+ const trimmed = line.trim();
6
+ // TypeScript / JavaScript: import ... from 'source' or import 'source'
7
+ const tsMatch = trimmed.match(/from\s+['"]([^'"]+)['"]/);
8
+ if (tsMatch) {
9
+ const src = tsMatch[1];
10
+ return { source: src, isExternal: !src.startsWith('.') };
11
+ }
12
+ const tsBareMatch = trimmed.match(/^import\s+['"]([^'"]+)['"]/);
13
+ if (tsBareMatch) {
14
+ const src = tsBareMatch[1];
15
+ return { source: src, isExternal: !src.startsWith('.') };
16
+ }
17
+ // Python: from module import ... or import module
18
+ const pyFromMatch = trimmed.match(/^from\s+([A-Za-z0-9_.]+)\s+import/);
19
+ if (pyFromMatch) {
20
+ const src = pyFromMatch[1];
21
+ return { source: src, isExternal: !src.startsWith('.') };
22
+ }
23
+ const pyImportMatch = trimmed.match(/^import\s+([A-Za-z0-9_.]+)/);
24
+ if (pyImportMatch) {
25
+ const src = pyImportMatch[1];
26
+ return { source: src, isExternal: !src.startsWith('.') };
27
+ }
28
+ return null;
29
+ }
30
+ /**
31
+ * Checks if a line is an import statement
32
+ */
33
+ export function isImportLine(line, ext) {
34
+ const trimmed = line.trim();
35
+ const normalized = ext.toLowerCase().replace(/^\./, '');
36
+ if (['ts', 'tsx', 'js', 'jsx', 'mjs', 'cjs', 'svelte', 'vue', 'astro'].includes(normalized)) {
37
+ return trimmed.startsWith('import ') || trimmed.startsWith('import{') || /^const\s+.*\s*=\s*require\(/.test(trimmed);
38
+ }
39
+ if (normalized === 'py') {
40
+ return trimmed.startsWith('import ') || trimmed.startsWith('from ');
41
+ }
42
+ if (normalized === 'go') {
43
+ return trimmed.startsWith('import ') || trimmed.startsWith('import (');
44
+ }
45
+ return false;
46
+ }
47
+ /**
48
+ * Processes a collection of lines, collapsing import walls exceeding threshold
49
+ */
50
+ export function collapseImportWall(rawLines, ext, maxThreshold = 5) {
51
+ const imports = [];
52
+ const otherLines = [];
53
+ rawLines.forEach((line, index) => {
54
+ const lineNum = index + 1;
55
+ if (isImportLine(line, ext)) {
56
+ const parsed = extractImportSource(line) || { source: '', isExternal: true };
57
+ imports.push({
58
+ lineNum,
59
+ rawText: line.trim(),
60
+ source: parsed.source,
61
+ isExternal: parsed.isExternal
62
+ });
63
+ }
64
+ else {
65
+ otherLines.push({ lineNum, text: line });
66
+ }
67
+ });
68
+ // If imports are below or equal to threshold, keep them intact
69
+ if (imports.length <= maxThreshold) {
70
+ return {
71
+ hasCollapsed: false,
72
+ lines: rawLines
73
+ };
74
+ }
75
+ // Extract unique external and local package names
76
+ const externalPkgs = new Set();
77
+ const localModules = new Set();
78
+ imports.forEach((imp) => {
79
+ if (!imp.source)
80
+ return;
81
+ if (imp.isExternal) {
82
+ // For scoped packages like @angular/core, grab full package name
83
+ const parts = imp.source.split('/');
84
+ const pkg = imp.source.startsWith('@') ? `${parts[0]}/${parts[1] || ''}` : parts[0];
85
+ externalPkgs.add(pkg);
86
+ }
87
+ else {
88
+ const parts = imp.source.split('/');
89
+ const mod = parts.slice(0, 2).join('/');
90
+ localModules.add(mod);
91
+ }
92
+ });
93
+ const startLine = imports[0].lineNum;
94
+ const endLine = imports[imports.length - 1].lineNum;
95
+ const extList = Array.from(externalPkgs).slice(0, 4).join(', ');
96
+ const locList = Array.from(localModules).slice(0, 3).join(', ');
97
+ const summaryParts = [];
98
+ if (extList)
99
+ summaryParts.push(`Dependencias: ${extList}${externalPkgs.size > 4 ? '...' : ''}`);
100
+ if (locList)
101
+ summaryParts.push(`Locales: ${locList}${localModules.size > 3 ? '...' : ''}`);
102
+ const details = summaryParts.length > 0 ? ` (${summaryParts.join(' | ')})` : '';
103
+ const collapsedBanner = [
104
+ `[L${startLine}-L${endLine}] 📦 ${imports.length} imports colapsados${details}`,
105
+ `👉 Tip: Si necesitas ver todas las dependencias, corre Read(offset=${startLine}, limit=${endLine - startLine + 1})`
106
+ ].join('\n');
107
+ return {
108
+ hasCollapsed: true,
109
+ lines: [collapsedBanner]
110
+ };
111
+ }
112
+ //# sourceMappingURL=import-collapser.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"import-collapser.js","sourceRoot":"","sources":["../../src/import-collapser.ts"],"names":[],"mappings":"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"}
@@ -3,6 +3,8 @@ export * from './types.js';
3
3
  export * from './config.js';
4
4
  export * from './skeletonizer.js';
5
5
  export * from './worker-model.js';
6
+ export * from './file-classifier.js';
7
+ export * from './import-collapser.js';
6
8
  /**
7
9
  * Main engine of ContextGuard
8
10
  * Evaluates file size and either passes it through or shunts it to an AST/Worker summary.
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AAExE,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,mBAAmB,CAAC;AAClC,cAAc,mBAAmB,CAAC;AAElC;;;GAGG;AACH,wBAAsB,uBAAuB,CAAC,OAAO,EAAE,kBAAkB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAoGrG"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AAExE,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,mBAAmB,CAAC;AAClC,cAAc,mBAAmB,CAAC;AAClC,cAAc,sBAAsB,CAAC;AACrC,cAAc,uBAAuB,CAAC;AAEtC;;;GAGG;AACH,wBAAsB,uBAAuB,CAAC,OAAO,EAAE,kBAAkB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CA4HrG"}
package/dist/src/index.js CHANGED
@@ -3,10 +3,13 @@ import path from 'node:path';
3
3
  import { CONFIG } from './config.js';
4
4
  import { extractCodeSkeleton } from './skeletonizer.js';
5
5
  import { callWorkerModel } from './worker-model.js';
6
+ import { classifyFile } from './file-classifier.js';
6
7
  export * from './types.js';
7
8
  export * from './config.js';
8
9
  export * from './skeletonizer.js';
9
10
  export * from './worker-model.js';
11
+ export * from './file-classifier.js';
12
+ export * from './import-collapser.js';
10
13
  /**
11
14
  * Main engine of ContextGuard
12
15
  * Evaluates file size and either passes it through or shunts it to an AST/Worker summary.
@@ -21,6 +24,29 @@ export async function processWithContextGuard(options) {
21
24
  content: ''
22
25
  };
23
26
  }
27
+ // 1. Check for Binaries, Lockfiles, and Minified files
28
+ const classification = classifyFile(resolved);
29
+ if (classification.category === 'binary') {
30
+ return {
31
+ status: 'BLOCKED_BINARY',
32
+ reason: classification.reason,
33
+ content: `<!-- CONTEXTGUARD: ${classification.reason} -->\n<!-- ${classification.recommendedAction} -->`
34
+ };
35
+ }
36
+ if (classification.category === 'lockfile') {
37
+ return {
38
+ status: 'BLOCKED_LOCKFILE',
39
+ reason: classification.reason,
40
+ content: `<!-- CONTEXTGUARD: ${classification.reason} -->\n<!-- ${classification.recommendedAction} -->`
41
+ };
42
+ }
43
+ if (classification.category === 'minified') {
44
+ return {
45
+ status: 'BLOCKED_MINIFIED',
46
+ reason: classification.reason,
47
+ content: `<!-- CONTEXTGUARD: ${classification.reason} -->\n<!-- ${classification.recommendedAction} -->`
48
+ };
49
+ }
24
50
  const stat = fs.statSync(resolved);
25
51
  const rawContent = fs.readFileSync(resolved, 'utf-8');
26
52
  const lines = rawContent.split('\n');
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
@@ -1,6 +1,8 @@
1
1
  /**
2
2
  * Tier 0 Structural Skeletonizer
3
3
  * Extracts structural declarations, signatures, imports, and types with line numbers.
4
+ * Supports TypeScript, JavaScript, Python, Go, Rust, Java, C#, and
5
+ * Frontend Single File Components (Svelte, Vue, Angular, Astro).
4
6
  * Cost: $0.00 | Execution: < 5ms
5
7
  */
6
8
  export declare function isSupportedExtension(ext: string): string | null;
@@ -1 +1 @@
1
- {"version":3,"file":"skeletonizer.d.ts","sourceRoot":"","sources":["../../src/skeletonizer.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAiCH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAU/D;AAED,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAiC/E"}
1
+ {"version":3,"file":"skeletonizer.d.ts","sourceRoot":"","sources":["../../src/skeletonizer.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AA8DH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAa/D;AAED,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAoF/E"}
@@ -1,15 +1,45 @@
1
1
  /**
2
2
  * Tier 0 Structural Skeletonizer
3
3
  * Extracts structural declarations, signatures, imports, and types with line numbers.
4
+ * Supports TypeScript, JavaScript, Python, Go, Rust, Java, C#, and
5
+ * Frontend Single File Components (Svelte, Vue, Angular, Astro).
4
6
  * Cost: $0.00 | Execution: < 5ms
5
7
  */
8
+ import { isImportLine, collapseImportWall } from './import-collapser.js';
6
9
  const LANGUAGE_PATTERNS = {
7
- // TypeScript & JavaScript
10
+ // TypeScript, JavaScript & Angular
8
11
  ts: [
9
12
  /^(export\s+)?(default\s+)?(class|interface|type|enum)\s+([A-Za-z0-9_]+)/,
10
13
  /^(export\s+)?(async\s+)?function\s+([A-Za-z0-9_]+)\s*\(/,
11
14
  /^(export\s+)?const\s+([A-Za-z0-9_]+)\s*=\s*(async\s*)?\(/,
12
- /^(export\s+)?((public|private|protected|static|async|\*)\s+)*([A-Za-z0-9_]+)\s*\([^)]*\)\s*[:{]/
15
+ /^(export\s+)?((public|private|protected|static|async|readonly|\*)\s+)*([A-Za-z0-9_]+)\s*\([^)]*\)\s*[:{]/,
16
+ // Angular Decorators & Signals
17
+ /^@(Component|Injectable|Directive|Pipe|NgModule)\s*\(/,
18
+ /^@(Input|Output)\s*\(\s*\)\s+([A-Za-z0-9_]+)/,
19
+ /^(public|private|protected|readonly|\s+)*(readonly\s+)?([A-Za-z0-9_]+)\s*=\s*(input|output|model|computed|signal)(\.[A-Za-z0-9_]+)?\s*[\(<]/,
20
+ /^(ngOnInit|ngOnChanges|ngOnDestroy|ngAfterViewInit)\s*\(/
21
+ ],
22
+ // Svelte Component Logic
23
+ svelte: [
24
+ /^(export\s+)?let\s+([A-Za-z0-9_]+)/,
25
+ /^(let|const)\s+([A-Za-z0-9_{}\s,]+)\s*=\s*\$(props|state|derived|effect)\s*\(/,
26
+ /^\$:\s+/,
27
+ /^(export\s+)?(async\s+)?function\s+([A-Za-z0-9_]+)\s*\(/,
28
+ /^(export\s+)?const\s+([A-Za-z0-9_]+)\s*=\s*(async\s*)?\(/
29
+ ],
30
+ // Vue Component Logic
31
+ vue: [
32
+ /^(const|let)\s+([A-Za-z0-9_{}\s,]+)\s*=\s*(defineProps|defineEmits|defineModel)\s*[\(<]/,
33
+ /^(const|let)\s+([A-Za-z0-9_]+)\s*=\s*(ref|computed|reactive)\s*[\(<]/,
34
+ /^(export\s+)?(async\s+)?function\s+([A-Za-z0-9_]+)\s*\(/,
35
+ /^(export\s+)?const\s+([A-Za-z0-9_]+)\s*=\s*(async\s*)?\(/
36
+ ],
37
+ // Astro Component Frontmatter
38
+ astro: [
39
+ /^(export\s+)?interface\s+Props/,
40
+ /^(const|let)\s+([A-Za-z0-9_{}\s,]+)\s*=\s*Astro\.props/,
41
+ /^(export\s+)?(async\s+)?function\s+([A-Za-z0-9_]+)\s*\(/,
42
+ /^(export\s+)?const\s+([A-Za-z0-9_]+)\s*=\s*(async\s*)?\(/
13
43
  ],
14
44
  // Python
15
45
  py: [
@@ -37,6 +67,9 @@ export function isSupportedExtension(ext) {
37
67
  const normalized = ext.toLowerCase().replace(/^\./, '');
38
68
  const mapping = {
39
69
  ts: 'ts', tsx: 'ts', js: 'ts', jsx: 'ts', mjs: 'ts', cjs: 'ts',
70
+ svelte: 'svelte',
71
+ vue: 'vue',
72
+ astro: 'astro',
40
73
  py: 'py',
41
74
  go: 'go',
42
75
  rs: 'rs',
@@ -51,26 +84,72 @@ export function extractCodeSkeleton(content, ext) {
51
84
  const patterns = LANGUAGE_PATTERNS[langKey] || [];
52
85
  const lines = content.split('\n');
53
86
  const skeleton = [];
87
+ // Separate import lines and scan for style blocks
88
+ const importLines = [];
89
+ const bodyItems = [];
90
+ let insideStyleBlock = false;
91
+ let styleStartLine = 0;
92
+ let styleLineCount = 0;
54
93
  lines.forEach((line, index) => {
55
94
  const lineNum = index + 1;
56
95
  const trimmed = line.trim();
96
+ // 1. Detect and collapse <style> blocks (Svelte / Vue)
97
+ if (trimmed.startsWith('<style') && !insideStyleBlock) {
98
+ insideStyleBlock = true;
99
+ styleStartLine = lineNum;
100
+ styleLineCount = 1;
101
+ return;
102
+ }
103
+ if (insideStyleBlock) {
104
+ styleLineCount++;
105
+ if (trimmed.includes('</style>')) {
106
+ insideStyleBlock = false;
107
+ const styleEndLine = lineNum;
108
+ if (styleLineCount > 5) {
109
+ bodyItems.push({
110
+ lineNum: styleStartLine,
111
+ text: `[L${styleStartLine}-L${styleEndLine}] 🎨 ${styleLineCount} líneas de CSS colapsadas. Corre Read(offset=${styleStartLine}, limit=${styleLineCount}) si necesitas estilos.`
112
+ });
113
+ }
114
+ }
115
+ return;
116
+ }
57
117
  if (!trimmed || trimmed.startsWith('//') || trimmed.startsWith('#') || trimmed.startsWith('/*')) {
58
118
  return;
59
119
  }
60
- // Keep top-level import/from statements
61
- if (trimmed.startsWith('import ') || trimmed.startsWith('from ') || (langKey === 'go' && trimmed.startsWith('import ('))) {
62
- skeleton.push(`[L${lineNum}] ${trimmed}`);
120
+ // 2. Check for imports
121
+ if (isImportLine(line, ext)) {
122
+ importLines.push(line);
63
123
  return;
64
124
  }
125
+ // 3. Match Structural Patterns
65
126
  for (const pattern of patterns) {
66
127
  if (pattern.test(trimmed)) {
67
- // Strip trailing curly braces or semicolons for brevity
68
128
  const clean = trimmed.replace(/\{\s*$/, '').trim();
69
- skeleton.push(`[L${lineNum}] ${clean}`);
129
+ bodyItems.push({ lineNum, text: `[L${lineNum}] ${clean}` });
70
130
  break;
71
131
  }
72
132
  }
73
133
  });
134
+ // 4. Process and collapse import statements
135
+ if (importLines.length > 0) {
136
+ const collapsed = collapseImportWall(importLines, ext, 5);
137
+ if (collapsed.hasCollapsed) {
138
+ skeleton.push(collapsed.lines[0]);
139
+ }
140
+ else {
141
+ // If <= 5 imports, keep them as individual lines
142
+ importLines.forEach((impLine) => {
143
+ const originalIndex = lines.findIndex((l) => l.trim() === impLine.trim());
144
+ const lNum = originalIndex !== -1 ? originalIndex + 1 : 1;
145
+ skeleton.push(`[L${lNum}] ${impLine.trim()}`);
146
+ });
147
+ }
148
+ }
149
+ // 5. Append body structural declarations
150
+ bodyItems.forEach((item) => {
151
+ skeleton.push(item.text);
152
+ });
74
153
  return skeleton.length > 0 ? skeleton.join('\n') : null;
75
154
  }
76
155
  //# sourceMappingURL=skeletonizer.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"skeletonizer.js","sourceRoot":"","sources":["../../src/skeletonizer.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"skeletonizer.js","sourceRoot":"","sources":["../../src/skeletonizer.ts"],"names":[],"mappings":"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"}
@@ -18,7 +18,7 @@ export interface ProcessFileOptions {
18
18
  endLine?: number;
19
19
  forceWorker?: boolean;
20
20
  }
21
- export type ProcessFileStatus = 'PASSTHROUGH_FULL' | 'PASSTHROUGH_SLICE' | 'SHUNTED_LOCAL_AST' | 'SHUNTED_WORKER_MODEL' | 'SHUNT_FALLBACK' | 'ERROR';
21
+ export type ProcessFileStatus = 'PASSTHROUGH_FULL' | 'PASSTHROUGH_SLICE' | 'SHUNTED_LOCAL_AST' | 'SHUNTED_WORKER_MODEL' | 'SHUNT_FALLBACK' | 'BLOCKED_BINARY' | 'BLOCKED_LOCKFILE' | 'BLOCKED_MINIFIED' | 'ERROR';
22
22
  export interface ProcessFileResult {
23
23
  status: ProcessFileStatus;
24
24
  content: string;
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,cAAc,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,GAAG,UAAU,CAAC;AAEzE,MAAM,WAAW,kBAAkB;IACjC,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,cAAc,CAAC;IACzB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,kBAAkB;IACjC,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED,MAAM,MAAM,iBAAiB,GACzB,kBAAkB,GAClB,mBAAmB,GACnB,mBAAmB,GACnB,sBAAsB,GACtB,gBAAgB,GAChB,OAAO,CAAC;AAEZ,MAAM,WAAW,iBAAiB;IAChC,MAAM,EAAE,iBAAiB,CAAC;IAC1B,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAe;IAC9B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,iBAAiB;IAChC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,UAAU,CAAC,EAAE,eAAe,CAAC;IAC7B,KAAK,CAAC,EAAE,eAAe,CAAC;CACzB"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,cAAc,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,GAAG,UAAU,CAAC;AAEzE,MAAM,WAAW,kBAAkB;IACjC,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,cAAc,CAAC;IACzB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,kBAAkB;IACjC,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED,MAAM,MAAM,iBAAiB,GACzB,kBAAkB,GAClB,mBAAmB,GACnB,mBAAmB,GACnB,sBAAsB,GACtB,gBAAgB,GAChB,gBAAgB,GAChB,kBAAkB,GAClB,kBAAkB,GAClB,OAAO,CAAC;AAEZ,MAAM,WAAW,iBAAiB;IAChC,MAAM,EAAE,iBAAiB,CAAC;IAC1B,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAe;IAC9B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,iBAAiB;IAChC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,UAAU,CAAC,EAAE,eAAe,CAAC;IAC7B,KAAK,CAAC,EAAE,eAAe,CAAC;CACzB"}
@@ -94,18 +94,48 @@ describe('Claude Code Hook PreToolUse End-to-End', () => {
94
94
  assert.strictEqual(res.stderr, '');
95
95
  fs.rmSync(tempDir, { recursive: true });
96
96
  });
97
- it('should block open cat commands on large files with Exit Code 2', async () => {
97
+ it('should allow reading native multimodal and notebook files (images, PDFs, ipynb) with Exit Code 0', async () => {
98
98
  const tempDir = fs.mkdtempSync(path.join(os.tmpdir(), 'cg-hook-'));
99
- const tempFile = path.join(tempDir, 'huge.ts');
100
- fs.writeFileSync(tempFile, Array.from({ length: 200 }, () => 'code').join('\n'));
99
+ const imgFile = path.join(tempDir, 'screenshot.png');
100
+ fs.writeFileSync(imgFile, Buffer.from([0x89, 0x50, 0x4e, 0x47, 0x00]));
101
+ const resImg = await runHookWithStdin({
102
+ tool_name: 'Read',
103
+ tool_input: { file_path: imgFile }
104
+ });
105
+ assert.strictEqual(resImg.exitCode, 0, 'Must allow image file for multimodal vision');
106
+ assert.strictEqual(resImg.stderr, '');
107
+ const pdfFile = path.join(tempDir, 'document.pdf');
108
+ fs.writeFileSync(pdfFile, '%PDF-1.4 ...');
109
+ const resPdf = await runHookWithStdin({
110
+ tool_name: 'Read',
111
+ tool_input: { file_path: pdfFile, pages: '1-3' }
112
+ });
113
+ assert.strictEqual(resPdf.exitCode, 0, 'Must allow scoped PDF read');
114
+ assert.strictEqual(resPdf.stderr, '');
115
+ fs.rmSync(tempDir, { recursive: true });
116
+ });
117
+ it('should block non-multimodal binary files like wasm, archives, or compiled binaries with Exit Code 2', async () => {
118
+ const tempDir = fs.mkdtempSync(path.join(os.tmpdir(), 'cg-hook-'));
119
+ const wasmFile = path.join(tempDir, 'module.wasm');
120
+ fs.writeFileSync(wasmFile, Buffer.from([0x00, 0x61, 0x73, 0x6d, 0x01]));
101
121
  const res = await runHookWithStdin({
102
- tool_name: 'Bash',
103
- tool_input: {
104
- command: `cat ${tempFile}`
105
- }
122
+ tool_name: 'Read',
123
+ tool_input: { file_path: wasmFile }
124
+ });
125
+ assert.strictEqual(res.exitCode, 2, 'Must block non-multimodal binary file with exit code 2');
126
+ assert.ok(res.stderr.includes('ACCESO DENEGADO - BINARY'), 'Must emit binary warning');
127
+ fs.rmSync(tempDir, { recursive: true });
128
+ });
129
+ it('should block reading lockfiles with Exit Code 2 and suggest CLI introspection', async () => {
130
+ const tempDir = fs.mkdtempSync(path.join(os.tmpdir(), 'cg-hook-'));
131
+ const lockFile = path.join(tempDir, 'pnpm-lock.yaml');
132
+ fs.writeFileSync(lockFile, 'lockfileVersion: 5.4\npackages:\n foo: 1.0.0');
133
+ const res = await runHookWithStdin({
134
+ tool_name: 'Read',
135
+ tool_input: { file_path: lockFile }
106
136
  });
107
- assert.strictEqual(res.exitCode, 2, 'Must block raw cat with exit 2');
108
- assert.ok(res.stderr.includes('CONTEXTGUARD'));
137
+ assert.strictEqual(res.exitCode, 2, 'Must block lockfile with exit code 2');
138
+ assert.ok(res.stderr.includes('lockfile de dependencias'), 'Must advise using pnpm why');
109
139
  fs.rmSync(tempDir, { recursive: true });
110
140
  });
111
141
  });
@@ -1 +1 @@
1
- {"version":3,"file":"claude-hook.test.js","sourceRoot":"","sources":["../../tests/claude-hook.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,MAAM,MAAM,aAAa,CAAC;AACjC,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAC;AAC3C,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,EAAE,MAAM,SAAS,CAAC;AAEzB,MAAM,SAAS,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,yBAAyB,CAAC,CAAC;AAEzE,SAAS,gBAAgB,CAAC,OAAgB;IACxC,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE;QAC7B,MAAM,IAAI,GAAG,KAAK,CAAC,MAAM,EAAE,CAAC,SAAS,CAAC,EAAE;YACtC,GAAG,EAAE,EAAE,GAAG,OAAO,CAAC,GAAG,EAAE,uBAAuB,EAAE,KAAK,EAAE;SACxD,CAAC,CAAC;QAEH,IAAI,MAAM,GAAG,EAAE,CAAC;QAChB,IAAI,MAAM,GAAG,EAAE,CAAC;QAEhB,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,MAAM,EAAE,CAAC,KAAa,EAAE,EAAE,GAAG,MAAM,IAAI,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAC3E,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,MAAM,EAAE,CAAC,KAAa,EAAE,EAAE,GAAG,MAAM,IAAI,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAE3E,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,CAAC,IAAmB,EAAE,EAAE;YACvC,OAAO,CAAC,EAAE,QAAQ,EAAE,IAAI,IAAI,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC;QACnD,CAAC,CAAC,CAAC;QAEH,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAC;QAC1C,IAAI,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC;IACnB,CAAC,CAAC,CAAC;AACL,CAAC;AAED,QAAQ,CAAC,wCAAwC,EAAE,GAAG,EAAE;IACtD,EAAE,CAAC,uEAAuE,EAAE,KAAK,IAAI,EAAE;QACrF,MAAM,OAAO,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,UAAU,CAAC,CAAC,CAAC;QACnE,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;QAE/C,2BAA2B;QAC3B,MAAM,KAAK,GAAG,CAAC,6BAA6B,CAAC,CAAC;QAC9C,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,GAAG,EAAE,CAAC,EAAE,EAAE,CAAC;YAC7B,KAAK,CAAC,IAAI,CAAC,mBAAmB,CAAC,EAAE,CAAC,CAAC;QACrC,CAAC;QACD,KAAK,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC;QAC9C,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QAChB,EAAE,CAAC,aAAa,CAAC,QAAQ,EAAE,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;QAE7C,MAAM,GAAG,GAAG,MAAM,gBAAgB,CAAC;YACjC,SAAS,EAAE,MAAM;YACjB,UAAU,EAAE,EAAE,SAAS,EAAE,QAAQ,EAAE;SACpC,CAAC,CAAC;QAEH,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,EAAE,oDAAoD,CAAC,CAAC;QAC1F,MAAM,CAAC,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,gCAAgC,CAAC,EAAE,6BAA6B,CAAC,CAAC;QAChG,MAAM,CAAC,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,cAAc,CAAC,EAAE,iCAAiC,CAAC,CAAC;QAElF,EAAE,CAAC,MAAM,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,sDAAsD,EAAE,KAAK,IAAI,EAAE;QACpE,MAAM,OAAO,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,UAAU,CAAC,CAAC,CAAC;QACnE,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;QAC/C,EAAE,CAAC,aAAa,CAAC,QAAQ,EAAE,KAAK,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,EAAE,GAAG,EAAE,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;QAEjF,MAAM,GAAG,GAAG,MAAM,gBAAgB,CAAC;YACjC,SAAS,EAAE,MAAM;YACjB,UAAU,EAAE;gBACV,SAAS,EAAE,QAAQ;gBACnB,MAAM,EAAE,EAAE;gBACV,KAAK,EAAE,EAAE;aACV;SACF,CAAC,CAAC;QAEH,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,EAAE,iDAAiD,CAAC,CAAC;QACvF,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;QAEnC,EAAE,CAAC,MAAM,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,uEAAuE,EAAE,KAAK,IAAI,EAAE;QACrF,MAAM,OAAO,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,UAAU,CAAC,CAAC,CAAC;QACnE,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;QAE/C,2BAA2B;QAC3B,MAAM,KAAK,GAAG,CAAC,6BAA6B,CAAC,CAAC;QAC9C,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,GAAG,EAAE,CAAC,EAAE,EAAE,CAAC;YAC7B,KAAK,CAAC,IAAI,CAAC,mBAAmB,CAAC,EAAE,CAAC,CAAC;QACrC,CAAC;QACD,KAAK,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC;QAC9C,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QAChB,EAAE,CAAC,aAAa,CAAC,QAAQ,EAAE,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;QAE7C,MAAM,GAAG,GAAG,MAAM,gBAAgB,CAAC;YACjC,SAAS,EAAE,MAAM;YACjB,UAAU,EAAE,EAAE,SAAS,EAAE,QAAQ,EAAE;SACpC,CAAC,CAAC;QAEH,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,EAAE,oDAAoD,CAAC,CAAC;QAC1F,MAAM,CAAC,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,gCAAgC,CAAC,EAAE,6BAA6B,CAAC,CAAC;QAChG,MAAM,CAAC,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,cAAc,CAAC,EAAE,iCAAiC,CAAC,CAAC;QAElF,EAAE,CAAC,MAAM,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,sDAAsD,EAAE,KAAK,IAAI,EAAE;QACpE,MAAM,OAAO,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,UAAU,CAAC,CAAC,CAAC;QACnE,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;QAC/C,EAAE,CAAC,aAAa,CAAC,QAAQ,EAAE,KAAK,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,EAAE,GAAG,EAAE,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;QAEjF,MAAM,GAAG,GAAG,MAAM,gBAAgB,CAAC;YACjC,SAAS,EAAE,MAAM;YACjB,UAAU,EAAE;gBACV,SAAS,EAAE,QAAQ;gBACnB,MAAM,EAAE,EAAE;gBACV,KAAK,EAAE,EAAE;aACV;SACF,CAAC,CAAC;QAEH,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,EAAE,iDAAiD,CAAC,CAAC;QACvF,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;QAEnC,EAAE,CAAC,MAAM,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gEAAgE,EAAE,KAAK,IAAI,EAAE;QAC9E,MAAM,OAAO,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,UAAU,CAAC,CAAC,CAAC;QACnE,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;QAC/C,EAAE,CAAC,aAAa,CAAC,QAAQ,EAAE,KAAK,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,EAAE,GAAG,EAAE,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;QAEjF,MAAM,GAAG,GAAG,MAAM,gBAAgB,CAAC;YACjC,SAAS,EAAE,MAAM;YACjB,UAAU,EAAE;gBACV,OAAO,EAAE,OAAO,QAAQ,EAAE;aAC3B;SACF,CAAC,CAAC;QAEH,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,EAAE,gCAAgC,CAAC,CAAC;QACtE,MAAM,CAAC,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,cAAc,CAAC,CAAC,CAAC;QAE/C,EAAE,CAAC,MAAM,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
1
+ {"version":3,"file":"claude-hook.test.js","sourceRoot":"","sources":["../../tests/claude-hook.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=file-classifier.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file-classifier.test.d.ts","sourceRoot":"","sources":["../../tests/file-classifier.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,46 @@
1
+ import { describe, it } from 'node:test';
2
+ import assert from 'node:assert';
3
+ import path from 'node:path';
4
+ import fs from 'node:fs';
5
+ import os from 'node:os';
6
+ import { classifyFile } from '../src/file-classifier.js';
7
+ describe('File Classifier (SPEC-002)', () => {
8
+ it('should detect binary image files by extension', () => {
9
+ const res = classifyFile('assets/logo.png');
10
+ assert.strictEqual(res.category, 'binary');
11
+ assert.ok(res.reason?.includes('.png'));
12
+ });
13
+ it('should detect PDF documents by extension and advise pdftotext', () => {
14
+ const res = classifyFile('docs/manual.pdf');
15
+ assert.strictEqual(res.category, 'binary');
16
+ assert.ok(res.recommendedAction?.includes('pdftotext'));
17
+ });
18
+ it('should detect lockfiles and suggest CLI commands', () => {
19
+ const pnpmRes = classifyFile('pnpm-lock.yaml');
20
+ assert.strictEqual(pnpmRes.category, 'lockfile');
21
+ assert.ok(pnpmRes.recommendedAction?.includes('pnpm why'));
22
+ const npmRes = classifyFile('package-lock.json');
23
+ assert.strictEqual(npmRes.category, 'lockfile');
24
+ assert.ok(npmRes.recommendedAction?.includes('npm ls'));
25
+ });
26
+ it('should detect minified files and recommend source inspection', () => {
27
+ const res = classifyFile('dist/bundle.min.js');
28
+ assert.strictEqual(res.category, 'minified');
29
+ assert.ok(res.recommendedAction?.includes('src/'));
30
+ });
31
+ it('should detect binary contents with null bytes via buffer scanner', () => {
32
+ const tempDir = fs.mkdtempSync(path.join(os.tmpdir(), 'cg-bin-'));
33
+ const tempFile = path.join(tempDir, 'unknown_data');
34
+ // Write buffer with null bytes
35
+ const buf = Buffer.from([0x00, 0x01, 0x02, 0x00, 0x7f, 0x80]);
36
+ fs.writeFileSync(tempFile, buf);
37
+ const res = classifyFile(tempFile);
38
+ assert.strictEqual(res.category, 'binary');
39
+ fs.rmSync(tempDir, { recursive: true });
40
+ });
41
+ it('should classify normal code files as source_code', () => {
42
+ const res = classifyFile('src/index.ts');
43
+ assert.strictEqual(res.category, 'source_code');
44
+ });
45
+ });
46
+ //# sourceMappingURL=file-classifier.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file-classifier.test.js","sourceRoot":"","sources":["../../tests/file-classifier.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=framework-sfc.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"framework-sfc.test.d.ts","sourceRoot":"","sources":["../../tests/framework-sfc.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,151 @@
1
+ import { describe, it } from 'node:test';
2
+ import assert from 'node:assert';
3
+ import { extractCodeSkeleton } from '../src/skeletonizer.js';
4
+ describe('Frontend Frameworks & SFC Distillation (SPEC-002)', () => {
5
+ it('should distill Svelte components, extracting runes and collapsing styles', () => {
6
+ const svelteCode = `
7
+ <script lang="ts">
8
+ import { onMount } from 'svelte';
9
+
10
+ let { name, age } = $props();
11
+ let count = $state(0);
12
+ let double = $derived(count * 2);
13
+
14
+ function increment() {
15
+ count += 1;
16
+ }
17
+ </script>
18
+
19
+ <main>
20
+ <h1>Hello {name}!</h1>
21
+ <button on:click={increment}>Count: {count}</button>
22
+ </main>
23
+
24
+ <style>
25
+ main {
26
+ text-align: center;
27
+ padding: 1em;
28
+ max-width: 240px;
29
+ margin: 0 auto;
30
+ color: red;
31
+ }
32
+ h1 {
33
+ color: #ff3e00;
34
+ text-transform: uppercase;
35
+ font-size: 4em;
36
+ font-weight: 100;
37
+ }
38
+ </style>
39
+ `.trim();
40
+ const skeleton = extractCodeSkeleton(svelteCode, '.svelte');
41
+ assert.ok(skeleton !== null);
42
+ if (!skeleton)
43
+ throw new Error('Skeleton is null');
44
+ assert.ok(skeleton.includes('$props()'));
45
+ assert.ok(skeleton.includes('$state(0)'));
46
+ assert.ok(skeleton.includes('$derived(count * 2)'));
47
+ assert.ok(skeleton.includes('function increment()'));
48
+ // Style block should be collapsed
49
+ assert.ok(skeleton.includes('🎨') && skeleton.includes('líneas de CSS colapsadas'));
50
+ });
51
+ it('should distill Vue components with script setup macros and collapse scoped styles', () => {
52
+ const vueCode = `
53
+ <script setup lang="ts">
54
+ import { ref, computed } from 'vue';
55
+
56
+ const props = defineProps<{ title: string }>();
57
+ const emit = defineEmits<['submit']>();
58
+ const active = ref(false);
59
+ const formattedTitle = computed(() => props.title.toUpperCase());
60
+ </script>
61
+
62
+ <template>
63
+ <div class="card">
64
+ <h2>{{ formattedTitle }}</h2>
65
+ </div>
66
+ </template>
67
+
68
+ <style scoped>
69
+ .card {
70
+ background: #fff;
71
+ border-radius: 8px;
72
+ padding: 16px;
73
+ box-shadow: 0 2px 4px rgba(0,0,0,0.1);
74
+ }
75
+ h2 {
76
+ margin: 0;
77
+ font-size: 18px;
78
+ }
79
+ </style>
80
+ `.trim();
81
+ const skeleton = extractCodeSkeleton(vueCode, '.vue');
82
+ assert.ok(skeleton !== null);
83
+ if (!skeleton)
84
+ throw new Error('Skeleton is null');
85
+ assert.ok(skeleton.includes('defineProps'));
86
+ assert.ok(skeleton.includes('defineEmits'));
87
+ assert.ok(skeleton.includes('ref'));
88
+ assert.ok(skeleton.includes('computed'));
89
+ assert.ok(skeleton.includes('🎨') && skeleton.includes('CSS colapsadas'));
90
+ });
91
+ it('should distill Angular components with decorators and modern Signals', () => {
92
+ const angularCode = `
93
+ import { Component, input, output, signal } from '@angular/core';
94
+
95
+ @Component({
96
+ selector: 'app-user-badge',
97
+ templateUrl: './user-badge.component.html'
98
+ })
99
+ export class UserBadgeComponent {
100
+ readonly userId = input.required<string>();
101
+ readonly statusChanged = output<boolean>();
102
+ readonly isOnline = signal(false);
103
+
104
+ ngOnInit() {
105
+ console.log('init');
106
+ }
107
+
108
+ public toggleStatus() {
109
+ this.isOnline.set(!this.isOnline());
110
+ }
111
+ }
112
+ `.trim();
113
+ const skeleton = extractCodeSkeleton(angularCode, '.ts');
114
+ assert.ok(skeleton !== null);
115
+ if (!skeleton)
116
+ throw new Error('Skeleton is null');
117
+ assert.ok(skeleton.includes('@Component'));
118
+ assert.ok(skeleton.includes('export class UserBadgeComponent'));
119
+ assert.ok(skeleton.includes('userId = input.required<string>()'));
120
+ assert.ok(skeleton.includes('statusChanged = output<boolean>()'));
121
+ assert.ok(skeleton.includes('isOnline = signal(false)'));
122
+ assert.ok(skeleton.includes('ngOnInit()'));
123
+ assert.ok(skeleton.includes('public toggleStatus()'));
124
+ });
125
+ it('should distill Astro components extracting frontmatter and props', () => {
126
+ const astroCode = `
127
+ ---
128
+ import Header from '../components/Header.astro';
129
+
130
+ interface Props {
131
+ title: string;
132
+ }
133
+
134
+ const { title } = Astro.props;
135
+ ---
136
+ <html lang="en">
137
+ <body>
138
+ <Header />
139
+ <h1>{title}</h1>
140
+ </body>
141
+ </html>
142
+ `.trim();
143
+ const skeleton = extractCodeSkeleton(astroCode, '.astro');
144
+ assert.ok(skeleton !== null);
145
+ if (!skeleton)
146
+ throw new Error('Skeleton is null');
147
+ assert.ok(skeleton.includes('interface Props'));
148
+ assert.ok(skeleton.includes('const { title } = Astro.props'));
149
+ });
150
+ });
151
+ //# sourceMappingURL=framework-sfc.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"framework-sfc.test.js","sourceRoot":"","sources":["../../tests/framework-sfc.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=import-collapser.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"import-collapser.test.d.ts","sourceRoot":"","sources":["../../tests/import-collapser.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,35 @@
1
+ import { describe, it } from 'node:test';
2
+ import assert from 'node:assert';
3
+ import { collapseImportWall } from '../src/import-collapser.js';
4
+ describe('Import Collapser (SPEC-002)', () => {
5
+ it('should keep imports intact when total imports <= 5', () => {
6
+ const lines = [
7
+ "import { useState } from 'react';",
8
+ "import { useEffect } from 'react';",
9
+ "import { Button } from './Button.js';"
10
+ ];
11
+ const result = collapseImportWall(lines, '.tsx', 5);
12
+ assert.strictEqual(result.hasCollapsed, false);
13
+ assert.strictEqual(result.lines.length, 3);
14
+ });
15
+ it('should collapse import wall when total imports > 5', () => {
16
+ const lines = [
17
+ "import { Component } from '@angular/core';",
18
+ "import { CommonModule } from '@angular/common';",
19
+ "import { Observable } from 'rxjs';",
20
+ "import { map, filter } from 'rxjs/operators';",
21
+ "import { UserService } from './user.service.js';",
22
+ "import { UserDto } from './user.dto.js';",
23
+ "import { Config } from '../config.js';"
24
+ ];
25
+ const result = collapseImportWall(lines, '.ts', 5);
26
+ assert.strictEqual(result.hasCollapsed, true);
27
+ assert.strictEqual(result.lines.length, 1);
28
+ const banner = result.lines[0];
29
+ assert.ok(banner.includes('[L1-L7] 📦 7 imports colapsados'));
30
+ assert.ok(banner.includes('@angular/core') || banner.includes('rxjs'));
31
+ assert.ok(banner.includes('./user.service.js') || banner.includes('./user.dto.js'));
32
+ assert.ok(banner.includes('Read(offset=1, limit=7)'));
33
+ });
34
+ });
35
+ //# sourceMappingURL=import-collapser.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"import-collapser.test.js","sourceRoot":"","sources":["../../tests/import-collapser.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,MAAM,MAAM,aAAa,CAAC;AACjC,OAAO,EAAE,kBAAkB,EAAE,MAAM,4BAA4B,CAAC;AAEhE,QAAQ,CAAC,6BAA6B,EAAE,GAAG,EAAE;IAC3C,EAAE,CAAC,oDAAoD,EAAE,GAAG,EAAE;QAC5D,MAAM,KAAK,GAAG;YACZ,mCAAmC;YACnC,oCAAoC;YACpC,uCAAuC;SACxC,CAAC;QAEF,MAAM,MAAM,GAAG,kBAAkB,CAAC,KAAK,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC;QACpD,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC,YAAY,EAAE,KAAK,CAAC,CAAC;QAC/C,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC;IAC7C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,oDAAoD,EAAE,GAAG,EAAE;QAC5D,MAAM,KAAK,GAAG;YACZ,4CAA4C;YAC5C,iDAAiD;YACjD,oCAAoC;YACpC,+CAA+C;YAC/C,kDAAkD;YAClD,0CAA0C;YAC1C,wCAAwC;SACzC,CAAC;QAEF,MAAM,MAAM,GAAG,kBAAkB,CAAC,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC;QACnD,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC,YAAY,EAAE,IAAI,CAAC,CAAC;QAC9C,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC;QAE3C,MAAM,MAAM,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;QAC/B,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,QAAQ,CAAC,iCAAiC,CAAC,CAAC,CAAC;QAC9D,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,QAAQ,CAAC,eAAe,CAAC,IAAI,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC;QACvE,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,QAAQ,CAAC,mBAAmB,CAAC,IAAI,MAAM,CAAC,QAAQ,CAAC,eAAe,CAAC,CAAC,CAAC;QACpF,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,QAAQ,CAAC,yBAAyB,CAAC,CAAC,CAAC;IACxD,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kevinbermudezc/context-guard",
3
- "version": "1.0.1",
3
+ "version": "1.1.1",
4
4
  "description": "Intelligent context admission control and token optimization for Claude Code, Cursor, and Agentic workflows.",
5
5
  "publishConfig": {
6
6
  "access": "public"