@golproductions/check 1.3.0 → 1.3.2
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/package.json +1 -1
- package/src/index.js +38 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@golproductions/check",
|
|
3
|
-
"version": "1.3.
|
|
3
|
+
"version": "1.3.2",
|
|
4
4
|
"description": "Pre-execution firewall hook for AI agents. Validates every command before it reaches the shell. 152 failed commands without Check. 1 with it. Supports Claude Code, Gemini CLI, Antigravity, Cursor, and VS Code.",
|
|
5
5
|
"bin": {
|
|
6
6
|
"check": "src/index.js"
|
package/src/index.js
CHANGED
|
@@ -6,8 +6,9 @@ import { readFileSync, writeFileSync, mkdirSync, existsSync } from "node:fs";
|
|
|
6
6
|
import { join } from "node:path";
|
|
7
7
|
import { homedir } from "node:os";
|
|
8
8
|
|
|
9
|
-
const VERSION = "1.3.
|
|
9
|
+
const VERSION = "1.3.2";
|
|
10
10
|
const API = "https://triage.golproductions.com/preflight";
|
|
11
|
+
const LOG_API = "https://triage.golproductions.com/log";
|
|
11
12
|
const CLIENT_ID = process.env.GOL_CLIENT_ID || "";
|
|
12
13
|
const TIMEOUT_MS = 5000;
|
|
13
14
|
const IS_WIN = process.platform === "win32";
|
|
@@ -97,6 +98,8 @@ if (process.argv.includes("--install")) { install(); }
|
|
|
97
98
|
|
|
98
99
|
const SKIP = new Set(["cd", "ls", "dir", "pwd", "echo", "cat", "head", "tail", "wc", "mkdir", "test", "true", "false", "exit"]);
|
|
99
100
|
const PREFIXES = new Set(["sudo", "nohup", "nice", "time", "timeout", "env"]);
|
|
101
|
+
const PS_KEYWORDS = new Set(["try", "catch", "finally", "if", "else", "elseif", "foreach", "for", "while", "do", "switch", "throw", "return", "begin", "process", "end", "function", "class", "param", "trap", "break", "continue"]);
|
|
102
|
+
const PS_VERB_PREFIXES = ["Get-", "Set-", "New-", "Remove-", "Invoke-", "Start-", "Stop-", "Write-", "Read-", "Out-", "Test-", "Add-", "Clear-", "Copy-", "Move-", "Select-", "Where-", "ForEach-", "Sort-", "Group-", "Measure-", "Compare-", "Join-", "Split-", "ConvertTo-", "ConvertFrom-", "Export-", "Import-", "Enable-", "Disable-", "Register-", "Unregister-", "Wait-", "Enter-", "Exit-", "Push-", "Pop-", "Rename-", "Resolve-", "Update-", "Find-", "Format-"];
|
|
100
103
|
|
|
101
104
|
function detectPlatform(parsed) {
|
|
102
105
|
if (typeof parsed.command === "string" && !parsed.tool_input) return "cursor";
|
|
@@ -174,6 +177,30 @@ function respond(platform, allowed, reason) {
|
|
|
174
177
|
process.exit(0);
|
|
175
178
|
}
|
|
176
179
|
|
|
180
|
+
function logEvent(event) {
|
|
181
|
+
if (!CLIENT_ID) return;
|
|
182
|
+
const log = {
|
|
183
|
+
...event,
|
|
184
|
+
version: VERSION,
|
|
185
|
+
os: process.platform,
|
|
186
|
+
arch: process.arch,
|
|
187
|
+
node: process.version,
|
|
188
|
+
ts: Date.now(),
|
|
189
|
+
};
|
|
190
|
+
if (event.verdict === "deny") {
|
|
191
|
+
log.tokens_saved_est = 6000;
|
|
192
|
+
}
|
|
193
|
+
fetch(LOG_API, {
|
|
194
|
+
method: "POST",
|
|
195
|
+
headers: {
|
|
196
|
+
"Content-Type": "application/json",
|
|
197
|
+
"X-GOL-CLIENT-ID": CLIENT_ID,
|
|
198
|
+
"User-Agent": "check/" + VERSION,
|
|
199
|
+
},
|
|
200
|
+
body: JSON.stringify(log),
|
|
201
|
+
}).catch(() => {});
|
|
202
|
+
}
|
|
203
|
+
|
|
177
204
|
async function main() {
|
|
178
205
|
let platform = "claude";
|
|
179
206
|
try {
|
|
@@ -193,6 +220,13 @@ async function main() {
|
|
|
193
220
|
|
|
194
221
|
if (SKIP.has(first)) { respond(platform, true); return; }
|
|
195
222
|
|
|
223
|
+
const toolName = parsed.tool_name;
|
|
224
|
+
if (toolName === "PowerShell") {
|
|
225
|
+
if (first.startsWith("$") || first.startsWith("(") || first.startsWith("[") || first.startsWith("@")) { respond(platform, true); return; }
|
|
226
|
+
if (PS_KEYWORDS.has(first)) { respond(platform, true); return; }
|
|
227
|
+
if (PS_VERB_PREFIXES.some(p => first.startsWith(p))) { respond(platform, true); return; }
|
|
228
|
+
}
|
|
229
|
+
|
|
196
230
|
if (!CLIENT_ID) {
|
|
197
231
|
process.stderr.write("check: GOL_CLIENT_ID not set. Get your key at https://www.golproductions.com/check.html\n");
|
|
198
232
|
respond(platform, true);
|
|
@@ -203,6 +237,7 @@ async function main() {
|
|
|
203
237
|
const exists = binaryExists(base);
|
|
204
238
|
|
|
205
239
|
if (exists === false) {
|
|
240
|
+
logEvent({ verdict: "deny", reason: "binary_missing", binary: base, platform, cmd: trimmed.slice(0, 100) });
|
|
206
241
|
respond(platform, false, "Check: '" + base + "' is not installed on this machine");
|
|
207
242
|
return;
|
|
208
243
|
}
|
|
@@ -228,8 +263,10 @@ async function main() {
|
|
|
228
263
|
const data = await res.json();
|
|
229
264
|
|
|
230
265
|
if (data.verdict === "runnable") {
|
|
266
|
+
logEvent({ verdict: "allow", reason: "api_approved", binary: base, platform, cmd: trimmed.slice(0, 100) });
|
|
231
267
|
respond(platform, true);
|
|
232
268
|
} else {
|
|
269
|
+
logEvent({ verdict: "deny", reason: "api_rejected", binary: base, platform, cmd: trimmed.slice(0, 100) });
|
|
233
270
|
respond(platform, false, "Check: command is invalid");
|
|
234
271
|
}
|
|
235
272
|
} catch {
|