@nocoo/otter 1.0.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 (81) hide show
  1. package/dist/bin.d.ts +3 -0
  2. package/dist/bin.d.ts.map +1 -0
  3. package/dist/bin.js +5 -0
  4. package/dist/bin.js.map +1 -0
  5. package/dist/cli.d.ts +2 -0
  6. package/dist/cli.d.ts.map +1 -0
  7. package/dist/cli.js +365 -0
  8. package/dist/cli.js.map +1 -0
  9. package/dist/collectors/applications.d.ts +19 -0
  10. package/dist/collectors/applications.d.ts.map +1 -0
  11. package/dist/collectors/applications.js +51 -0
  12. package/dist/collectors/applications.js.map +1 -0
  13. package/dist/collectors/base.d.ts +52 -0
  14. package/dist/collectors/base.d.ts.map +1 -0
  15. package/dist/collectors/base.js +186 -0
  16. package/dist/collectors/base.js.map +1 -0
  17. package/dist/collectors/claude-config.d.ts +39 -0
  18. package/dist/collectors/claude-config.d.ts.map +1 -0
  19. package/dist/collectors/claude-config.js +124 -0
  20. package/dist/collectors/claude-config.js.map +1 -0
  21. package/dist/collectors/homebrew.d.ts +16 -0
  22. package/dist/collectors/homebrew.d.ts.map +1 -0
  23. package/dist/collectors/homebrew.js +43 -0
  24. package/dist/collectors/homebrew.js.map +1 -0
  25. package/dist/collectors/index.d.ts +21 -0
  26. package/dist/collectors/index.d.ts.map +1 -0
  27. package/dist/collectors/index.js +28 -0
  28. package/dist/collectors/index.js.map +1 -0
  29. package/dist/collectors/opencode-config.d.ts +21 -0
  30. package/dist/collectors/opencode-config.d.ts.map +1 -0
  31. package/dist/collectors/opencode-config.js +88 -0
  32. package/dist/collectors/opencode-config.js.map +1 -0
  33. package/dist/collectors/shell-config.d.ts +24 -0
  34. package/dist/collectors/shell-config.d.ts.map +1 -0
  35. package/dist/collectors/shell-config.js +133 -0
  36. package/dist/collectors/shell-config.js.map +1 -0
  37. package/dist/commands/config.d.ts +17 -0
  38. package/dist/commands/config.d.ts.map +1 -0
  39. package/dist/commands/config.js +21 -0
  40. package/dist/commands/config.js.map +1 -0
  41. package/dist/commands/scan.d.ts +11 -0
  42. package/dist/commands/scan.d.ts.map +1 -0
  43. package/dist/commands/scan.js +36 -0
  44. package/dist/commands/scan.js.map +1 -0
  45. package/dist/commands/snapshot.d.ts +52 -0
  46. package/dist/commands/snapshot.d.ts.map +1 -0
  47. package/dist/commands/snapshot.js +203 -0
  48. package/dist/commands/snapshot.js.map +1 -0
  49. package/dist/config/manager.d.ts +13 -0
  50. package/dist/config/manager.d.ts.map +1 -0
  51. package/dist/config/manager.js +28 -0
  52. package/dist/config/manager.js.map +1 -0
  53. package/dist/index.d.ts +8 -0
  54. package/dist/index.d.ts.map +1 -0
  55. package/dist/index.js +8 -0
  56. package/dist/index.js.map +1 -0
  57. package/dist/snapshot/builder.d.ts +7 -0
  58. package/dist/snapshot/builder.d.ts.map +1 -0
  59. package/dist/snapshot/builder.js +68 -0
  60. package/dist/snapshot/builder.js.map +1 -0
  61. package/dist/storage/local.d.ts +44 -0
  62. package/dist/storage/local.d.ts.map +1 -0
  63. package/dist/storage/local.js +107 -0
  64. package/dist/storage/local.js.map +1 -0
  65. package/dist/uploader/icons.d.ts +41 -0
  66. package/dist/uploader/icons.d.ts.map +1 -0
  67. package/dist/uploader/icons.js +80 -0
  68. package/dist/uploader/icons.js.map +1 -0
  69. package/dist/uploader/webhook.d.ts +7 -0
  70. package/dist/uploader/webhook.d.ts.map +1 -0
  71. package/dist/uploader/webhook.js +54 -0
  72. package/dist/uploader/webhook.js.map +1 -0
  73. package/dist/utils/icons.d.ts +34 -0
  74. package/dist/utils/icons.d.ts.map +1 -0
  75. package/dist/utils/icons.js +113 -0
  76. package/dist/utils/icons.js.map +1 -0
  77. package/dist/utils/redact.d.ts +41 -0
  78. package/dist/utils/redact.d.ts.map +1 -0
  79. package/dist/utils/redact.js +317 -0
  80. package/dist/utils/redact.js.map +1 -0
  81. package/package.json +45 -0
@@ -0,0 +1,317 @@
1
+ /**
2
+ * Credential redaction utilities.
3
+ *
4
+ * Strips sensitive values from file content before including
5
+ * them in snapshots. Works on both structured (JSON) and
6
+ * line-oriented (ini-like) config formats.
7
+ */
8
+ const REDACTED = "[REDACTED]";
9
+ // ---------------------------------------------------------------------------
10
+ // JSON env-block redaction (for settings.json, etc.)
11
+ // ---------------------------------------------------------------------------
12
+ /** Keys whose values should always be redacted in JSON objects */
13
+ const SENSITIVE_KEY_PATTERNS = [
14
+ /token/i,
15
+ /secret/i,
16
+ /api.?key/i,
17
+ /password/i,
18
+ /credential/i,
19
+ /auth/i,
20
+ ];
21
+ function isSensitiveKey(key) {
22
+ return SENSITIVE_KEY_PATTERNS.some((p) => p.test(key));
23
+ }
24
+ /**
25
+ * Deep-walk a parsed JSON value and redact any string values
26
+ * whose keys match sensitive patterns.
27
+ *
28
+ * Returns [redactedValue, didRedact] tuple.
29
+ */
30
+ function redactObject(obj) {
31
+ if (obj === null || obj === undefined)
32
+ return [obj, false];
33
+ if (typeof obj !== "object")
34
+ return [obj, false];
35
+ if (Array.isArray(obj)) {
36
+ let anyRedacted = false;
37
+ const mapped = obj.map((item) => {
38
+ const [val, redacted] = redactObject(item);
39
+ if (redacted)
40
+ anyRedacted = true;
41
+ return val;
42
+ });
43
+ return [mapped, anyRedacted];
44
+ }
45
+ let anyRedacted = false;
46
+ const result = {};
47
+ for (const [key, value] of Object.entries(obj)) {
48
+ if (typeof value === "string" && isSensitiveKey(key)) {
49
+ result[key] = REDACTED;
50
+ anyRedacted = true;
51
+ }
52
+ else if (typeof value === "object" && value !== null) {
53
+ const [val, redacted] = redactObject(value);
54
+ result[key] = val;
55
+ if (redacted)
56
+ anyRedacted = true;
57
+ }
58
+ else {
59
+ result[key] = value;
60
+ }
61
+ }
62
+ return [result, anyRedacted];
63
+ }
64
+ /**
65
+ * Redact sensitive values in a JSON string.
66
+ * Returns the original string if no redaction was needed or parsing fails.
67
+ */
68
+ export function redactJsonSecrets(jsonContent) {
69
+ try {
70
+ const parsed = JSON.parse(jsonContent);
71
+ const [redacted, didRedact] = redactObject(parsed);
72
+ if (!didRedact)
73
+ return jsonContent;
74
+ // Re-serialize with 2-space indent
75
+ return JSON.stringify(redacted, null, 2);
76
+ }
77
+ catch {
78
+ // If not valid JSON, return as-is
79
+ return jsonContent;
80
+ }
81
+ }
82
+ // ---------------------------------------------------------------------------
83
+ // Line-oriented redaction (for .npmrc, .gitconfig, etc.)
84
+ // ---------------------------------------------------------------------------
85
+ /** Patterns that match credential lines in ini-style config files */
86
+ const LINE_REDACTION_PATTERNS = [
87
+ // .npmrc: //registry.npmjs.org/:_authToken=xxx
88
+ /^(\s*\/\/[^:]+\/:_authToken\s*=\s*).+$/,
89
+ // .npmrc: _auth=xxx
90
+ /^(\s*_auth\s*=\s*).+$/,
91
+ // .gitconfig: helper = store / credential block values
92
+ /^(\s*helper\s*=\s*store).*$/,
93
+ // Generic key=value where key contains token/secret/password/key
94
+ /^(\s*(?:.*(?:token|secret|password|api.?key|credential|auth)\w*)\s*=\s*).+$/i,
95
+ ];
96
+ // ---------------------------------------------------------------------------
97
+ // Shell script redaction (for .zshrc, .bashrc, .profile, etc.)
98
+ // ---------------------------------------------------------------------------
99
+ /**
100
+ * Patterns that match sensitive variable assignments in shell scripts.
101
+ * Captures the prefix (everything before the secret value) so we can
102
+ * replace just the value portion with [REDACTED].
103
+ */
104
+ const SHELL_REDACTION_PATTERNS = [
105
+ // export KEY="value" or export KEY='value' or export KEY=value
106
+ // where KEY contains: TOKEN, SECRET, KEY, PASSWORD, CREDENTIAL, AUTH
107
+ /^(\s*export\s+\w*(?:TOKEN|SECRET|KEY|PASSWORD|CREDENTIAL|AUTH)\w*=).*$/i,
108
+ // Plain assignment (no export): KEY="value"
109
+ /^(\s*\w*(?:TOKEN|SECRET|KEY|PASSWORD|CREDENTIAL|AUTH)\w*=).*$/i,
110
+ ];
111
+ /** Shell config filenames that should receive shell-script redaction */
112
+ const SHELL_CONFIG_NAMES = new Set([
113
+ ".zshrc",
114
+ ".zprofile",
115
+ ".zshenv",
116
+ ".zlogin",
117
+ ".bashrc",
118
+ ".bash_profile",
119
+ ".profile",
120
+ ".tmux.conf",
121
+ ".wgetrc",
122
+ ".curlrc",
123
+ ]);
124
+ /**
125
+ * Redact sensitive lines in ini-style / line-oriented config files.
126
+ * Each matching line has its value portion replaced with [REDACTED].
127
+ */
128
+ export function redactLineSecrets(content) {
129
+ return content
130
+ .split("\n")
131
+ .map((line) => {
132
+ for (const pattern of LINE_REDACTION_PATTERNS) {
133
+ const match = line.match(pattern);
134
+ if (match) {
135
+ return `${match[1]}${REDACTED}`;
136
+ }
137
+ }
138
+ return line;
139
+ })
140
+ .join("\n");
141
+ }
142
+ /**
143
+ * Redact sensitive variable assignments in shell scripts.
144
+ * Catches patterns like:
145
+ * export MY_API_KEY="sk-..."
146
+ * GITHUB_TOKEN=ghp_xxx
147
+ * export Z_AI_API_KEY="..."
148
+ */
149
+ export function redactShellSecrets(content) {
150
+ return content
151
+ .split("\n")
152
+ .map((line) => {
153
+ // Skip comments
154
+ const trimmed = line.trimStart();
155
+ if (trimmed.startsWith("#"))
156
+ return line;
157
+ for (const pattern of SHELL_REDACTION_PATTERNS) {
158
+ const match = line.match(pattern);
159
+ if (match) {
160
+ return `${match[1]}${REDACTED}`;
161
+ }
162
+ }
163
+ return line;
164
+ })
165
+ .join("\n");
166
+ }
167
+ // ---------------------------------------------------------------------------
168
+ // Value-pattern redaction (for history.jsonl and other freeform content)
169
+ // ---------------------------------------------------------------------------
170
+ /**
171
+ * Patterns that match credential-like values embedded in freeform text.
172
+ * These catch secrets that users may have pasted into CLI prompts.
173
+ * Each pattern replaces the matched portion with [REDACTED].
174
+ */
175
+ const VALUE_CREDENTIAL_PATTERNS = [
176
+ // JWT tokens (three base64 segments separated by dots)
177
+ /eyJ[A-Za-z0-9_-]{10,}\.eyJ[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}/g,
178
+ // Bearer / token auth headers
179
+ /(?:Bearer|Token)\s+[A-Za-z0-9_\-.~+/]{20,}/gi,
180
+ // AWS access keys (AKIA...)
181
+ /AKIA[0-9A-Z]{16}/g,
182
+ // GitHub tokens (ghp_, gho_, ghu_, ghs_, ghr_)
183
+ /gh[pousr]_[A-Za-z0-9_]{36,}/g,
184
+ // Anthropic API keys
185
+ /sk-ant-[A-Za-z0-9_-]{20,}/g,
186
+ // OpenAI API keys
187
+ /sk-(?:proj-)?[A-Za-z0-9]{20,}/g,
188
+ // Slack tokens (xoxb-, xoxp-, xoxs-, xoxa-)
189
+ /xox[bpsa]-[A-Za-z0-9-]{20,}/g,
190
+ // Generic long hex secrets (e.g. 40+ hex chars, common for API keys/tokens)
191
+ /(?:(?:token|key|secret|password|auth|credential|cookie)\s*[=:]\s*)['"]*([A-Za-z0-9_\-+/.]{32,})['"]*$/gim,
192
+ // Cookie session values (session=xxx, sid=xxx, _session_id=xxx)
193
+ /(?:session|sid|_session_id|connect\.sid)\s*=\s*[A-Za-z0-9%_\-+/.]{16,}/gi,
194
+ // npm tokens
195
+ /npm_[A-Za-z0-9]{36,}/g,
196
+ // Private key content (if someone pasted it)
197
+ /-----BEGIN\s+(?:RSA\s+)?PRIVATE\s+KEY-----[\s\S]*?-----END\s+(?:RSA\s+)?PRIVATE\s+KEY-----/g,
198
+ ];
199
+ /**
200
+ * Scan a string value and replace any credential-like patterns with [REDACTED].
201
+ * Returns [redactedString, didRedact].
202
+ */
203
+ function redactValuePatterns(value) {
204
+ let result = value;
205
+ let didRedact = false;
206
+ for (const pattern of VALUE_CREDENTIAL_PATTERNS) {
207
+ // Reset lastIndex for global regexes
208
+ pattern.lastIndex = 0;
209
+ if (pattern.test(result)) {
210
+ didRedact = true;
211
+ pattern.lastIndex = 0;
212
+ result = result.replace(pattern, REDACTED);
213
+ }
214
+ }
215
+ return [result, didRedact];
216
+ }
217
+ /**
218
+ * Deep-walk a parsed value and apply value-pattern redaction to all strings.
219
+ * Unlike redactObject (key-based), this inspects the VALUE content itself.
220
+ */
221
+ function redactDeepValues(obj) {
222
+ if (obj === null || obj === undefined)
223
+ return [obj, false];
224
+ if (typeof obj === "string") {
225
+ return redactValuePatterns(obj);
226
+ }
227
+ if (Array.isArray(obj)) {
228
+ let anyRedacted = false;
229
+ const mapped = obj.map((item) => {
230
+ const [val, redacted] = redactDeepValues(item);
231
+ if (redacted)
232
+ anyRedacted = true;
233
+ return val;
234
+ });
235
+ return [mapped, anyRedacted];
236
+ }
237
+ if (typeof obj === "object") {
238
+ let anyRedacted = false;
239
+ const result = {};
240
+ for (const [key, value] of Object.entries(obj)) {
241
+ const [val, redacted] = redactDeepValues(value);
242
+ result[key] = val;
243
+ if (redacted)
244
+ anyRedacted = true;
245
+ }
246
+ return [result, anyRedacted];
247
+ }
248
+ return [obj, false];
249
+ }
250
+ /**
251
+ * Redact credential-like values in JSONL content (one JSON object per line).
252
+ * Applies both key-based (sensitive key names) and value-based (credential
253
+ * patterns like JWTs, API keys, bearer tokens) redaction.
254
+ */
255
+ export function redactJsonlSecrets(content) {
256
+ return content
257
+ .split("\n")
258
+ .map((line) => {
259
+ const trimmed = line.trim();
260
+ if (!trimmed)
261
+ return line;
262
+ try {
263
+ const parsed = JSON.parse(trimmed);
264
+ // Apply key-based redaction first
265
+ const [keyRedacted] = redactObject(parsed);
266
+ // Then apply value-pattern redaction
267
+ const [valueRedacted, didRedact] = redactDeepValues(keyRedacted);
268
+ // Also check if key-based redaction changed anything
269
+ const keyChanged = JSON.stringify(keyRedacted) !== JSON.stringify(parsed);
270
+ if (!didRedact && !keyChanged)
271
+ return line;
272
+ return JSON.stringify(valueRedacted);
273
+ }
274
+ catch {
275
+ // Not valid JSON line — apply value-pattern redaction as plain text
276
+ const [result, didRedact] = redactValuePatterns(trimmed);
277
+ return didRedact ? result : line;
278
+ }
279
+ })
280
+ .join("\n");
281
+ }
282
+ // ---------------------------------------------------------------------------
283
+ // Public API: auto-detect format and redact
284
+ // ---------------------------------------------------------------------------
285
+ /**
286
+ * Redact credentials from file content.
287
+ * Auto-detects format based on file path extension or filename.
288
+ *
289
+ * @param content Raw file content
290
+ * @param filePath File path (used to determine format)
291
+ * @returns Content with sensitive values replaced by [REDACTED]
292
+ */
293
+ export function redactSecrets(content, filePath) {
294
+ const lower = filePath.toLowerCase();
295
+ if (lower.endsWith(".json")) {
296
+ return redactJsonSecrets(content);
297
+ }
298
+ // JSONL files (e.g. history.jsonl): value-pattern + key-based redaction
299
+ if (lower.endsWith(".jsonl")) {
300
+ return redactJsonlSecrets(content);
301
+ }
302
+ // Line-oriented configs: .npmrc, .gitconfig, .env, etc.
303
+ if (lower.endsWith(".npmrc") ||
304
+ lower.endsWith(".gitconfig") ||
305
+ lower.endsWith(".env") ||
306
+ lower.endsWith(".env.local") ||
307
+ lower.endsWith(".netrc")) {
308
+ return redactLineSecrets(content);
309
+ }
310
+ // Shell config files: .zshrc, .bashrc, .profile, etc.
311
+ const fileName = lower.split("/").pop() ?? "";
312
+ if (SHELL_CONFIG_NAMES.has(fileName)) {
313
+ return redactShellSecrets(content);
314
+ }
315
+ return content;
316
+ }
317
+ //# sourceMappingURL=redact.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"redact.js","sourceRoot":"","sources":["../../src/utils/redact.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,MAAM,QAAQ,GAAG,YAAY,CAAC;AAE9B,8EAA8E;AAC9E,qDAAqD;AACrD,8EAA8E;AAE9E,kEAAkE;AAClE,MAAM,sBAAsB,GAAG;IAC7B,QAAQ;IACR,SAAS;IACT,WAAW;IACX,WAAW;IACX,aAAa;IACb,OAAO;CACR,CAAC;AAEF,SAAS,cAAc,CAAC,GAAW;IACjC,OAAO,sBAAsB,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;AACzD,CAAC;AAED;;;;;GAKG;AACH,SAAS,YAAY,CAAC,GAAY;IAChC,IAAI,GAAG,KAAK,IAAI,IAAI,GAAG,KAAK,SAAS;QAAE,OAAO,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;IAC3D,IAAI,OAAO,GAAG,KAAK,QAAQ;QAAE,OAAO,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;IAEjD,IAAI,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC;QACvB,IAAI,WAAW,GAAG,KAAK,CAAC;QACxB,MAAM,MAAM,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;YAC9B,MAAM,CAAC,GAAG,EAAE,QAAQ,CAAC,GAAG,YAAY,CAAC,IAAI,CAAC,CAAC;YAC3C,IAAI,QAAQ;gBAAE,WAAW,GAAG,IAAI,CAAC;YACjC,OAAO,GAAG,CAAC;QACb,CAAC,CAAC,CAAC;QACH,OAAO,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;IAC/B,CAAC;IAED,IAAI,WAAW,GAAG,KAAK,CAAC;IACxB,MAAM,MAAM,GAA4B,EAAE,CAAC;IAC3C,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,GAA8B,CAAC,EAAE,CAAC;QAC1E,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,cAAc,CAAC,GAAG,CAAC,EAAE,CAAC;YACrD,MAAM,CAAC,GAAG,CAAC,GAAG,QAAQ,CAAC;YACvB,WAAW,GAAG,IAAI,CAAC;QACrB,CAAC;aAAM,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;YACvD,MAAM,CAAC,GAAG,EAAE,QAAQ,CAAC,GAAG,YAAY,CAAC,KAAK,CAAC,CAAC;YAC5C,MAAM,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC;YAClB,IAAI,QAAQ;gBAAE,WAAW,GAAG,IAAI,CAAC;QACnC,CAAC;aAAM,CAAC;YACN,MAAM,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC;QACtB,CAAC;IACH,CAAC;IACD,OAAO,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;AAC/B,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,iBAAiB,CAAC,WAAmB;IACnD,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACvC,MAAM,CAAC,QAAQ,EAAE,SAAS,CAAC,GAAG,YAAY,CAAC,MAAM,CAAC,CAAC;QACnD,IAAI,CAAC,SAAS;YAAE,OAAO,WAAW,CAAC;QACnC,mCAAmC;QACnC,OAAO,IAAI,CAAC,SAAS,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;IAC3C,CAAC;IAAC,MAAM,CAAC;QACP,kCAAkC;QAClC,OAAO,WAAW,CAAC;IACrB,CAAC;AACH,CAAC;AAED,8EAA8E;AAC9E,yDAAyD;AACzD,8EAA8E;AAE9E,qEAAqE;AACrE,MAAM,uBAAuB,GAAG;IAC9B,+CAA+C;IAC/C,wCAAwC;IACxC,oBAAoB;IACpB,uBAAuB;IACvB,uDAAuD;IACvD,6BAA6B;IAC7B,iEAAiE;IACjE,8EAA8E;CAC/E,CAAC;AAEF,8EAA8E;AAC9E,+DAA+D;AAC/D,8EAA8E;AAE9E;;;;GAIG;AACH,MAAM,wBAAwB,GAAG;IAC/B,+DAA+D;IAC/D,qEAAqE;IACrE,yEAAyE;IACzE,4CAA4C;IAC5C,gEAAgE;CACjE,CAAC;AAEF,wEAAwE;AACxE,MAAM,kBAAkB,GAAG,IAAI,GAAG,CAAC;IACjC,QAAQ;IACR,WAAW;IACX,SAAS;IACT,SAAS;IACT,SAAS;IACT,eAAe;IACf,UAAU;IACV,YAAY;IACZ,SAAS;IACT,SAAS;CACV,CAAC,CAAC;AAEH;;;GAGG;AACH,MAAM,UAAU,iBAAiB,CAAC,OAAe;IAC/C,OAAO,OAAO;SACX,KAAK,CAAC,IAAI,CAAC;SACX,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACZ,KAAK,MAAM,OAAO,IAAI,uBAAuB,EAAE,CAAC;YAC9C,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;YAClC,IAAI,KAAK,EAAE,CAAC;gBACV,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,GAAG,QAAQ,EAAE,CAAC;YAClC,CAAC;QACH,CAAC;QACD,OAAO,IAAI,CAAC;IACd,CAAC,CAAC;SACD,IAAI,CAAC,IAAI,CAAC,CAAC;AAChB,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,kBAAkB,CAAC,OAAe;IAChD,OAAO,OAAO;SACX,KAAK,CAAC,IAAI,CAAC;SACX,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACZ,gBAAgB;QAChB,MAAM,OAAO,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QACjC,IAAI,OAAO,CAAC,UAAU,CAAC,GAAG,CAAC;YAAE,OAAO,IAAI,CAAC;QAEzC,KAAK,MAAM,OAAO,IAAI,wBAAwB,EAAE,CAAC;YAC/C,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;YAClC,IAAI,KAAK,EAAE,CAAC;gBACV,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,GAAG,QAAQ,EAAE,CAAC;YAClC,CAAC;QACH,CAAC;QACD,OAAO,IAAI,CAAC;IACd,CAAC,CAAC;SACD,IAAI,CAAC,IAAI,CAAC,CAAC;AAChB,CAAC;AAED,8EAA8E;AAC9E,yEAAyE;AACzE,8EAA8E;AAE9E;;;;GAIG;AACH,MAAM,yBAAyB,GAAa;IAC1C,uDAAuD;IACvD,mEAAmE;IACnE,8BAA8B;IAC9B,8CAA8C;IAC9C,4BAA4B;IAC5B,mBAAmB;IACnB,+CAA+C;IAC/C,8BAA8B;IAC9B,qBAAqB;IACrB,4BAA4B;IAC5B,kBAAkB;IAClB,gCAAgC;IAChC,4CAA4C;IAC5C,8BAA8B;IAC9B,4EAA4E;IAC5E,0GAA0G;IAC1G,gEAAgE;IAChE,0EAA0E;IAC1E,aAAa;IACb,uBAAuB;IACvB,6CAA6C;IAC7C,6FAA6F;CAC9F,CAAC;AAEF;;;GAGG;AACH,SAAS,mBAAmB,CAAC,KAAa;IACxC,IAAI,MAAM,GAAG,KAAK,CAAC;IACnB,IAAI,SAAS,GAAG,KAAK,CAAC;IAEtB,KAAK,MAAM,OAAO,IAAI,yBAAyB,EAAE,CAAC;QAChD,qCAAqC;QACrC,OAAO,CAAC,SAAS,GAAG,CAAC,CAAC;QACtB,IAAI,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC;YACzB,SAAS,GAAG,IAAI,CAAC;YACjB,OAAO,CAAC,SAAS,GAAG,CAAC,CAAC;YACtB,MAAM,GAAG,MAAM,CAAC,OAAO,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;QAC7C,CAAC;IACH,CAAC;IAED,OAAO,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC;AAC7B,CAAC;AAED;;;GAGG;AACH,SAAS,gBAAgB,CAAC,GAAY;IACpC,IAAI,GAAG,KAAK,IAAI,IAAI,GAAG,KAAK,SAAS;QAAE,OAAO,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;IAE3D,IAAI,OAAO,GAAG,KAAK,QAAQ,EAAE,CAAC;QAC5B,OAAO,mBAAmB,CAAC,GAAG,CAAC,CAAC;IAClC,CAAC;IAED,IAAI,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC;QACvB,IAAI,WAAW,GAAG,KAAK,CAAC;QACxB,MAAM,MAAM,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;YAC9B,MAAM,CAAC,GAAG,EAAE,QAAQ,CAAC,GAAG,gBAAgB,CAAC,IAAI,CAAC,CAAC;YAC/C,IAAI,QAAQ;gBAAE,WAAW,GAAG,IAAI,CAAC;YACjC,OAAO,GAAG,CAAC;QACb,CAAC,CAAC,CAAC;QACH,OAAO,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;IAC/B,CAAC;IAED,IAAI,OAAO,GAAG,KAAK,QAAQ,EAAE,CAAC;QAC5B,IAAI,WAAW,GAAG,KAAK,CAAC;QACxB,MAAM,MAAM,GAA4B,EAAE,CAAC;QAC3C,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CACvC,GAA8B,CAC/B,EAAE,CAAC;YACF,MAAM,CAAC,GAAG,EAAE,QAAQ,CAAC,GAAG,gBAAgB,CAAC,KAAK,CAAC,CAAC;YAChD,MAAM,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC;YAClB,IAAI,QAAQ;gBAAE,WAAW,GAAG,IAAI,CAAC;QACnC,CAAC;QACD,OAAO,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;IAC/B,CAAC;IAED,OAAO,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;AACtB,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,kBAAkB,CAAC,OAAe;IAChD,OAAO,OAAO;SACX,KAAK,CAAC,IAAI,CAAC;SACX,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACZ,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAC;QAC5B,IAAI,CAAC,OAAO;YAAE,OAAO,IAAI,CAAC;QAE1B,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;YAEnC,kCAAkC;YAClC,MAAM,CAAC,WAAW,CAAC,GAAG,YAAY,CAAC,MAAM,CAAC,CAAC;YAC3C,qCAAqC;YACrC,MAAM,CAAC,aAAa,EAAE,SAAS,CAAC,GAAG,gBAAgB,CAAC,WAAW,CAAC,CAAC;YAEjE,qDAAqD;YACrD,MAAM,UAAU,GAAG,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,KAAK,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC;YAE1E,IAAI,CAAC,SAAS,IAAI,CAAC,UAAU;gBAAE,OAAO,IAAI,CAAC;YAC3C,OAAO,IAAI,CAAC,SAAS,CAAC,aAAa,CAAC,CAAC;QACvC,CAAC;QAAC,MAAM,CAAC;YACP,oEAAoE;YACpE,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,mBAAmB,CAAC,OAAO,CAAC,CAAC;YACzD,OAAO,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC;QACnC,CAAC;IACH,CAAC,CAAC;SACD,IAAI,CAAC,IAAI,CAAC,CAAC;AAChB,CAAC;AAED,8EAA8E;AAC9E,4CAA4C;AAC5C,8EAA8E;AAE9E;;;;;;;GAOG;AACH,MAAM,UAAU,aAAa,CAAC,OAAe,EAAE,QAAgB;IAC7D,MAAM,KAAK,GAAG,QAAQ,CAAC,WAAW,EAAE,CAAC;IAErC,IAAI,KAAK,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC;QAC5B,OAAO,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACpC,CAAC;IAED,wEAAwE;IACxE,IAAI,KAAK,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC;QAC7B,OAAO,kBAAkB,CAAC,OAAO,CAAC,CAAC;IACrC,CAAC;IAED,wDAAwD;IACxD,IACE,KAAK,CAAC,QAAQ,CAAC,QAAQ,CAAC;QACxB,KAAK,CAAC,QAAQ,CAAC,YAAY,CAAC;QAC5B,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC;QACtB,KAAK,CAAC,QAAQ,CAAC,YAAY,CAAC;QAC5B,KAAK,CAAC,QAAQ,CAAC,QAAQ,CAAC,EACxB,CAAC;QACD,OAAO,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACpC,CAAC;IAED,sDAAsD;IACtD,MAAM,QAAQ,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,IAAI,EAAE,CAAC;IAC9C,IAAI,kBAAkB,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC;QACrC,OAAO,kBAAkB,CAAC,OAAO,CAAC,CAAC;IACrC,CAAC;IAED,OAAO,OAAO,CAAC;AACjB,CAAC"}
package/package.json ADDED
@@ -0,0 +1,45 @@
1
+ {
2
+ "name": "@nocoo/otter",
3
+ "version": "1.0.0",
4
+ "description": "Backup and restore your Mac development environment configuration",
5
+ "type": "module",
6
+ "bin": {
7
+ "otter": "dist/bin.js"
8
+ },
9
+ "main": "./dist/index.js",
10
+ "types": "./dist/index.d.ts",
11
+ "scripts": {
12
+ "build": "tsc",
13
+ "test": "vitest run",
14
+ "test:watch": "vitest"
15
+ },
16
+ "files": [
17
+ "dist"
18
+ ],
19
+ "publishConfig": {
20
+ "access": "public"
21
+ },
22
+ "repository": {
23
+ "type": "git",
24
+ "url": "git+https://github.com/nocoo/otter.git",
25
+ "directory": "packages/cli"
26
+ },
27
+ "keywords": [
28
+ "macos",
29
+ "backup",
30
+ "dotfiles",
31
+ "developer-tools",
32
+ "cli"
33
+ ],
34
+ "license": "MIT",
35
+ "dependencies": {
36
+ "@aws-sdk/client-s3": "^3.1004.0",
37
+ "citty": "^0.1.0",
38
+ "consola": "^3.4.0",
39
+ "picocolors": "^1.1.0"
40
+ },
41
+ "devDependencies": {
42
+ "@otter/core": "workspace:*",
43
+ "@types/node": "^25.3.4"
44
+ }
45
+ }