agentshield 0.0.1 → 0.0.2-beta.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.
Files changed (3) hide show
  1. package/README.md +4 -16
  2. package/dist/index.js +15 -11
  3. package/package.json +18 -2
package/README.md CHANGED
@@ -1,10 +1,10 @@
1
1
  # đŸ›Ąī¸ AgentShield
2
2
 
3
- English | [įŽ€äŊ“中文](./README_CN.md)
3
+ English | [中文](./README_CN.md)
4
4
 
5
- The missing safety layer for AI Agents - Give your AI Agent a "regret pill".
5
+ **The missing safety layer for Claude Code, Cowork, OpenCode and all AI Agents - Your "regret pill" for AI-assisted development.**
6
6
 
7
- **A hardlink-based zero-copy backup system that protects your workspace from unintended AI modifications.**
7
+ A workspace history version management tool that protects your workspace from unintended AI Agent modifications.
8
8
 
9
9
  ## ✨ Features
10
10
 
@@ -85,21 +85,9 @@ shield clean
85
85
  shield clean --days=3
86
86
  ```
87
87
 
88
- ## 🔍 Default Exclusions
89
-
90
- These patterns are automatically excluded from backup:
91
-
92
- - `.git`, `.git/**`
93
- - `node_modules`, `node_modules/**`
94
- - `*.log`, `*.tmp`, `*.swp`
95
- - `dist/`, `build/`, `.next/`, `.nuxt/`
96
- - `coverage/`, `.cache/`
97
- - `__pycache__/`, `*.pyc`
98
- - `.DS_Store`, `Thumbs.db`
99
-
100
88
  ## 🤝 Contributing
101
89
 
102
- Issues and Pull Requests are welcome!
90
+ Issues and Pull Requests are very welcome!
103
91
 
104
92
  ## 📄 License
105
93
 
package/dist/index.js CHANGED
@@ -63,10 +63,10 @@ import {
63
63
  mkdirSync,
64
64
  linkSync,
65
65
  copyFileSync,
66
- statSync as statSync2,
66
+ statSync,
67
67
  readFileSync,
68
68
  writeFileSync,
69
- unlinkSync as unlinkSync2
69
+ unlinkSync
70
70
  } from "fs";
71
71
  import { join as join3, dirname } from "path";
72
72
 
@@ -111,8 +111,8 @@ function matchesPattern(filePath, patterns) {
111
111
  return false;
112
112
  }
113
113
  function patternToRegex(pattern) {
114
- let regex = pattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*\*/g, "{{GLOBSTAR}}").replace(/\*/g, "[^/]*").replace(/{{GLOBSTAR}}/g, ".*");
115
- return new RegExp(`(^|/)${regex}($|/)`);
114
+ const regex = pattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*\*\//g, "{{GLOBSTAR_SLASH}}").replace(/\*\*/g, "{{GLOBSTAR}}").replace(/\*/g, "[^/]*").replace(/{{GLOBSTAR_SLASH}}/g, "(.*/)?").replace(/{{GLOBSTAR}}/g, ".*");
115
+ return new RegExp(`(^|/)${regex}($|/|$)`);
116
116
  }
117
117
  function getAllFiles(dir, baseDir = dir) {
118
118
  const files = [];
@@ -197,7 +197,7 @@ class BackupManager {
197
197
  return null;
198
198
  }
199
199
  try {
200
- const stats = statSync2(fullPath);
200
+ const stats = statSync(fullPath);
201
201
  if (!stats.isFile()) {
202
202
  return null;
203
203
  }
@@ -206,13 +206,11 @@ class BackupManager {
206
206
  const backupFilename = `${timestamp}_${safeFilename}`;
207
207
  const backupPath = join3(this.snapshotsDir, backupFilename);
208
208
  mkdirSync(dirname(backupPath), { recursive: true });
209
- let usedHardlink = false;
210
209
  if (forceFullCopy) {
211
210
  copyFileSync(fullPath, backupPath);
212
211
  } else {
213
212
  try {
214
213
  linkSync(fullPath, backupPath);
215
- usedHardlink = true;
216
214
  } catch (err) {
217
215
  copyFileSync(fullPath, backupPath);
218
216
  }
@@ -327,8 +325,8 @@ class BackupManager {
327
325
  const backupPath = join3(this.snapshotsDir, entry.backupPath);
328
326
  try {
329
327
  if (existsSync(backupPath)) {
330
- const stats = statSync2(backupPath);
331
- unlinkSync2(backupPath);
328
+ const stats = statSync(backupPath);
329
+ unlinkSync(backupPath);
332
330
  freedBytes += stats.size;
333
331
  removed++;
334
332
  }
@@ -359,7 +357,7 @@ class ShieldWatcher {
359
357
  backupManager;
360
358
  watcher = null;
361
359
  debounceMap = new Map;
362
- debounceMs = 50;
360
+ debounceMs = 1000;
363
361
  constructor(config, backupManager) {
364
362
  this.config = config;
365
363
  this.backupManager = backupManager;
@@ -570,7 +568,13 @@ async function cmdSnapshot(options) {
570
568
  console.log(`✓ Complete: ${result.backed} files backed up, ${result.skipped} skipped`);
571
569
  }
572
570
  async function cmdRestore(options) {
573
- const config = await getConfig(options);
571
+ const pathArg = options.flags["path"] || ".";
572
+ const workspace = resolve(pathArg);
573
+ if (!existsSync2(workspace)) {
574
+ console.error(`Error: Directory not found: ${workspace}`);
575
+ process.exit(1);
576
+ }
577
+ const config = getDefaultConfig(workspace);
574
578
  const backupManager = new BackupManager(config);
575
579
  const fileArg = options.args[0];
576
580
  if (!fileArg) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "agentshield",
3
- "version": "0.0.1",
3
+ "version": "0.0.2-beta.0",
4
4
  "description": "Instant file protection for AI agent operations - hardlink-based zero-copy backup system",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -20,7 +20,9 @@
20
20
  "build:bin:windows": "bun build --compile --target=bun-windows-x64 ./src/index.ts --outfile shield.exe",
21
21
  "build:bin:linux": "bun build --compile --target=bun-linux-x64 ./src/index.ts --outfile shield-linux",
22
22
  "build:bin:all": "bun run build:bin && bun run build:bin:windows && bun run build:bin:linux",
23
- "prepublishOnly": "bun run build:npm"
23
+ "prepublishOnly": "bun run build:npm",
24
+ "lint": "eslint src --ext .ts",
25
+ "lint:fix": "eslint src --ext .ts --fix"
24
26
  },
25
27
  "keywords": [
26
28
  "agent",
@@ -48,6 +50,20 @@
48
50
  },
49
51
  "devDependencies": {
50
52
  "@types/bun": "latest",
53
+ "@typescript-eslint/eslint-plugin": "^6.0.0",
54
+ "@typescript-eslint/parser": "^6.0.0",
55
+ "eslint": "^8.45.0",
51
56
  "typescript": "^5.0.0"
57
+ },
58
+ "eslintConfig": {
59
+ "root": true,
60
+ "parser": "@typescript-eslint/parser",
61
+ "plugins": [
62
+ "@typescript-eslint"
63
+ ],
64
+ "extends": [
65
+ "eslint:recommended",
66
+ "plugin:@typescript-eslint/recommended"
67
+ ]
52
68
  }
53
69
  }