@octocodeai/octocode-engine 16.5.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 (95) hide show
  1. package/README.md +558 -0
  2. package/dist/lsp/client.d.ts +28 -0
  3. package/dist/lsp/client.js +98 -0
  4. package/dist/lsp/config.d.ts +3 -0
  5. package/dist/lsp/config.js +7 -0
  6. package/dist/lsp/evidence.d.ts +4 -0
  7. package/dist/lsp/evidence.js +28 -0
  8. package/dist/lsp/index.d.ts +7 -0
  9. package/dist/lsp/index.js +6 -0
  10. package/dist/lsp/initConstants.d.ts +4 -0
  11. package/dist/lsp/initConstants.js +27 -0
  12. package/dist/lsp/lspClientPool.d.ts +27 -0
  13. package/dist/lsp/lspClientPool.js +87 -0
  14. package/dist/lsp/lspErrorCodes.d.ts +12 -0
  15. package/dist/lsp/lspErrorCodes.js +12 -0
  16. package/dist/lsp/manager.d.ts +23 -0
  17. package/dist/lsp/manager.js +94 -0
  18. package/dist/lsp/native.d.ts +35 -0
  19. package/dist/lsp/native.js +3 -0
  20. package/dist/lsp/resolver.d.ts +26 -0
  21. package/dist/lsp/resolver.js +73 -0
  22. package/dist/lsp/schemas.d.ts +9 -0
  23. package/dist/lsp/schemas.js +30 -0
  24. package/dist/lsp/types.d.ts +85 -0
  25. package/dist/lsp/types.js +1 -0
  26. package/dist/lsp/uri.d.ts +15 -0
  27. package/dist/lsp/uri.js +24 -0
  28. package/dist/lsp/validation.d.ts +6 -0
  29. package/dist/lsp/validation.js +23 -0
  30. package/dist/lsp/workspaceRoot.d.ts +2 -0
  31. package/dist/lsp/workspaceRoot.js +7 -0
  32. package/dist/security/commandUtils.d.ts +1 -0
  33. package/dist/security/commandUtils.js +7 -0
  34. package/dist/security/commandValidator.d.ts +7 -0
  35. package/dist/security/commandValidator.js +472 -0
  36. package/dist/security/contentSanitizer.d.ts +2 -0
  37. package/dist/security/contentSanitizer.js +181 -0
  38. package/dist/security/filePatterns.d.ts +1 -0
  39. package/dist/security/filePatterns.js +209 -0
  40. package/dist/security/ignoredPathFilter.d.ts +3 -0
  41. package/dist/security/ignoredPathFilter.js +72 -0
  42. package/dist/security/index.d.ts +16 -0
  43. package/dist/security/index.js +13 -0
  44. package/dist/security/mask.d.ts +1 -0
  45. package/dist/security/mask.js +49 -0
  46. package/dist/security/maskUtils.d.ts +1 -0
  47. package/dist/security/maskUtils.js +7 -0
  48. package/dist/security/native.d.ts +9 -0
  49. package/dist/security/native.js +161 -0
  50. package/dist/security/paramExtractors.d.ts +7 -0
  51. package/dist/security/paramExtractors.js +75 -0
  52. package/dist/security/pathPatterns.d.ts +1 -0
  53. package/dist/security/pathPatterns.js +26 -0
  54. package/dist/security/pathUtils.d.ts +1 -0
  55. package/dist/security/pathUtils.js +37 -0
  56. package/dist/security/pathValidator.d.ts +22 -0
  57. package/dist/security/pathValidator.js +229 -0
  58. package/dist/security/regexes/ai-providers.d.ts +2 -0
  59. package/dist/security/regexes/ai-providers.js +177 -0
  60. package/dist/security/regexes/analytics.d.ts +2 -0
  61. package/dist/security/regexes/analytics.js +50 -0
  62. package/dist/security/regexes/auth-crypto.d.ts +6 -0
  63. package/dist/security/regexes/auth-crypto.js +255 -0
  64. package/dist/security/regexes/aws.d.ts +2 -0
  65. package/dist/security/regexes/aws.js +68 -0
  66. package/dist/security/regexes/cloudProviders.d.ts +2 -0
  67. package/dist/security/regexes/cloudProviders.js +328 -0
  68. package/dist/security/regexes/communications.d.ts +4 -0
  69. package/dist/security/regexes/communications.js +260 -0
  70. package/dist/security/regexes/databases.d.ts +2 -0
  71. package/dist/security/regexes/databases.js +135 -0
  72. package/dist/security/regexes/devTools.d.ts +2 -0
  73. package/dist/security/regexes/devTools.js +236 -0
  74. package/dist/security/regexes/index.d.ts +3 -0
  75. package/dist/security/regexes/index.js +31 -0
  76. package/dist/security/regexes/monitoring.d.ts +2 -0
  77. package/dist/security/regexes/monitoring.js +92 -0
  78. package/dist/security/regexes/payments-commerce.d.ts +3 -0
  79. package/dist/security/regexes/payments-commerce.js +197 -0
  80. package/dist/security/regexes/types.d.ts +2 -0
  81. package/dist/security/regexes/types.js +1 -0
  82. package/dist/security/regexes/vcs.d.ts +2 -0
  83. package/dist/security/regexes/vcs.js +105 -0
  84. package/dist/security/registry.d.ts +48 -0
  85. package/dist/security/registry.js +156 -0
  86. package/dist/security/securityConstants.d.ts +3 -0
  87. package/dist/security/securityConstants.js +12 -0
  88. package/dist/security/types.d.ts +35 -0
  89. package/dist/security/types.js +1 -0
  90. package/dist/security/withSecurityValidation.d.ts +21 -0
  91. package/dist/security/withSecurityValidation.js +107 -0
  92. package/index.cjs +97 -0
  93. package/index.d.ts +934 -0
  94. package/index.js +652 -0
  95. package/package.json +311 -0
@@ -0,0 +1,181 @@
1
+ import { nativeSanitizeContent } from './native.js';
2
+ import { securityRegistry } from './registry.js';
3
+ const MAX_STRING_LENGTH = 10_000;
4
+ const MAX_STRING_LENGTH_DISPLAY = '10,000';
5
+ const MAX_ARRAY_LENGTH = 100;
6
+ const MAX_DEPTH = 20;
7
+ const DANGEROUS_KEYS = new Set(['__proto__', 'constructor', 'prototype']);
8
+ function shouldApplyExtraPattern(fileContext, filePath) {
9
+ if (!fileContext)
10
+ return true;
11
+ if (!filePath)
12
+ return false;
13
+ fileContext.lastIndex = 0;
14
+ const applies = fileContext.test(filePath);
15
+ fileContext.lastIndex = 0;
16
+ return applies;
17
+ }
18
+ function detectWithExtraPatterns(content, filePath, extraPatterns) {
19
+ let sanitized = content;
20
+ const secrets = [];
21
+ for (const pattern of extraPatterns) {
22
+ if (!shouldApplyExtraPattern(pattern.fileContext, filePath)) {
23
+ continue;
24
+ }
25
+ pattern.regex.lastIndex = 0;
26
+ if (pattern.regex.test(sanitized)) {
27
+ secrets.push(pattern.name);
28
+ pattern.regex.lastIndex = 0;
29
+ sanitized = sanitized.replace(pattern.regex, `[REDACTED-${pattern.name.toUpperCase()}]`);
30
+ }
31
+ pattern.regex.lastIndex = 0;
32
+ }
33
+ return { sanitized, secrets };
34
+ }
35
+ export const ContentSanitizer = {
36
+ sanitizeContent(content, filePath) {
37
+ if (content == null || typeof content !== 'string') {
38
+ return {
39
+ content: content == null ? '' : String(content),
40
+ hasSecrets: false,
41
+ secretsDetected: [],
42
+ warnings: [],
43
+ };
44
+ }
45
+ const rustResult = nativeSanitizeContent(content, filePath ?? null);
46
+ const extraPatterns = securityRegistry.extraSecretPatterns;
47
+ if (extraPatterns.length > 0) {
48
+ const { sanitized: finalContent, secrets: extraSecrets } = detectWithExtraPatterns(rustResult.content, filePath, extraPatterns);
49
+ const allSecrets = [...rustResult.secretsDetected, ...extraSecrets];
50
+ const hasSecrets = allSecrets.length > 0;
51
+ return {
52
+ content: finalContent,
53
+ hasSecrets,
54
+ secretsDetected: allSecrets,
55
+ warnings: hasSecrets ? [`${allSecrets.length} secret(s) redacted`] : [],
56
+ };
57
+ }
58
+ return {
59
+ content: rustResult.content,
60
+ hasSecrets: rustResult.hasSecrets,
61
+ secretsDetected: rustResult.secretsDetected,
62
+ warnings: rustResult.warnings,
63
+ };
64
+ },
65
+ validateInputParameters(params) {
66
+ return validateRecursive(params, 0, new WeakSet());
67
+ },
68
+ };
69
+ function validateRecursive(params, depth, ancestorStack) {
70
+ if (!params || typeof params !== 'object') {
71
+ return {
72
+ sanitizedParams: {},
73
+ isValid: false,
74
+ hasSecrets: false,
75
+ warnings: ['Invalid parameters: must be an object'],
76
+ };
77
+ }
78
+ if (depth > MAX_DEPTH) {
79
+ return {
80
+ sanitizedParams: {},
81
+ isValid: false,
82
+ hasSecrets: false,
83
+ warnings: ['Maximum nesting depth exceeded'],
84
+ };
85
+ }
86
+ if (ancestorStack.has(params)) {
87
+ return {
88
+ sanitizedParams: {},
89
+ isValid: false,
90
+ hasSecrets: false,
91
+ warnings: ['Circular reference detected'],
92
+ };
93
+ }
94
+ ancestorStack.add(params);
95
+ const sanitizedParams = {};
96
+ const warnings = new Set();
97
+ let hasSecrets = false;
98
+ let hasValidationErrors = false;
99
+ for (const [key, value] of Object.entries(params)) {
100
+ if (typeof key !== 'string' || key.trim() === '') {
101
+ warnings.add(`Invalid parameter key: ${key}`);
102
+ hasValidationErrors = true;
103
+ continue;
104
+ }
105
+ if (DANGEROUS_KEYS.has(key)) {
106
+ warnings.add(`Dangerous parameter key blocked: ${key}`);
107
+ hasValidationErrors = true;
108
+ continue;
109
+ }
110
+ if (typeof value === 'string') {
111
+ let v = value;
112
+ if (v.length > MAX_STRING_LENGTH) {
113
+ warnings.add(`Parameter ${key} exceeds maximum length (${MAX_STRING_LENGTH_DISPLAY} characters)`);
114
+ v = v.substring(0, MAX_STRING_LENGTH);
115
+ }
116
+ const r = ContentSanitizer.sanitizeContent(v, undefined);
117
+ if (r.hasSecrets) {
118
+ hasSecrets = true;
119
+ r.secretsDetected.forEach((s) => warnings.add(`Secrets detected in ${key}: ${s}`));
120
+ }
121
+ sanitizedParams[key] = r.content;
122
+ }
123
+ else if (Array.isArray(value)) {
124
+ const truncated = value.length > MAX_ARRAY_LENGTH
125
+ ? (() => {
126
+ warnings.add(`Parameter ${key} array exceeds maximum length (${MAX_ARRAY_LENGTH} items)`);
127
+ return value.slice(0, MAX_ARRAY_LENGTH);
128
+ })()
129
+ : value;
130
+ let arrHasSecrets = false;
131
+ let arrHasErrors = false;
132
+ const sanitizedArr = truncated.map(item => {
133
+ if (typeof item === 'string') {
134
+ const r = ContentSanitizer.sanitizeContent(item, undefined);
135
+ if (r.hasSecrets) {
136
+ arrHasSecrets = true;
137
+ }
138
+ return r.content;
139
+ }
140
+ if (item !== null && typeof item === 'object' && !Array.isArray(item)) {
141
+ const r = validateRecursive(item, depth + 1, ancestorStack);
142
+ if (r.hasSecrets)
143
+ arrHasSecrets = true;
144
+ if (!r.isValid) {
145
+ arrHasErrors = true;
146
+ r.warnings.forEach(w => warnings.add(`${key}[]: ${w}`));
147
+ }
148
+ return r.sanitizedParams;
149
+ }
150
+ return item;
151
+ });
152
+ if (arrHasSecrets)
153
+ hasSecrets = true;
154
+ if (arrHasErrors)
155
+ hasValidationErrors = true;
156
+ sanitizedParams[key] = sanitizedArr;
157
+ }
158
+ else if (value !== null && typeof value === 'object') {
159
+ const r = validateRecursive(value, depth + 1, ancestorStack);
160
+ if (r.hasSecrets)
161
+ hasSecrets = true;
162
+ if (!r.isValid) {
163
+ hasValidationErrors = true;
164
+ r.warnings.forEach(w => warnings.add(`Invalid nested object in parameter ${key}: ${w}`));
165
+ }
166
+ else {
167
+ sanitizedParams[key] = r.sanitizedParams;
168
+ }
169
+ }
170
+ else {
171
+ sanitizedParams[key] = value;
172
+ }
173
+ }
174
+ ancestorStack.delete(params);
175
+ return {
176
+ sanitizedParams,
177
+ isValid: !hasValidationErrors,
178
+ hasSecrets,
179
+ warnings: Array.from(warnings),
180
+ };
181
+ }
@@ -0,0 +1 @@
1
+ export declare const IGNORED_FILE_PATTERNS: RegExp[];
@@ -0,0 +1,209 @@
1
+ export const IGNORED_FILE_PATTERNS = [
2
+ /\.env$/,
3
+ /\.env\..+$/,
4
+ /^\.npmrc$/,
5
+ /^\.pypirc$/,
6
+ /^\.netrc$/,
7
+ /^\.dockercfg$/,
8
+ /^\.docker\/config\.json$/,
9
+ /^credentials$/,
10
+ /^\.credentials$/,
11
+ /^\.aws\/credentials$/,
12
+ /^\.aws\/config$/,
13
+ /^\.ssh\/.*$/,
14
+ /^id_rsa$/,
15
+ /^id_dsa$/,
16
+ /^id_ecdsa$/,
17
+ /^id_ed25519$/,
18
+ /^id_rsa\.pub$/,
19
+ /^id_dsa\.pub$/,
20
+ /^id_ecdsa\.pub$/,
21
+ /^id_ed25519\.pub$/,
22
+ /^known_hosts$/,
23
+ /^authorized_keys$/,
24
+ /.*_rsa$/,
25
+ /.*_dsa$/,
26
+ /.*_ecdsa$/,
27
+ /.*_ed25519$/,
28
+ /^private.*\.key$/,
29
+ /^private.*\.pem$/,
30
+ /^.*[-_]private[-_].*\.key$/,
31
+ /^.*[-_]private[-_].*\.pem$/,
32
+ /[-_]private\.key$/,
33
+ /[-_]private\.pem$/,
34
+ /^.*\.private\.key$/,
35
+ /^.*\.private\.pem$/,
36
+ /\.pem$/,
37
+ /\.key$/,
38
+ /\.crt$/,
39
+ /\.cer$/,
40
+ /\.keystore$/,
41
+ /\.p12$/,
42
+ /\.pfx$/,
43
+ /\.jks$/,
44
+ /\.ppk$/,
45
+ /^service[-_]account.*\.json$/,
46
+ /^.*-service[-_]account.*\.json$/,
47
+ /^application[-_]default[-_]credentials\.json$/,
48
+ /^gcloud[-_]credentials\.json$/,
49
+ /^kubeconfig$/,
50
+ /^\.kube\/config$/,
51
+ /^k8s[-_]config$/,
52
+ /^terraform\.tfstate$/,
53
+ /^terraform\.tfstate\.backup$/,
54
+ /^terraform\.tfvars$/,
55
+ /^\.terraform\.lock\.hcl$/,
56
+ /^\.pgpass$/,
57
+ /^\.my\.cnf$/,
58
+ /^\.psqlrc$/,
59
+ /^secrets\.yml$/,
60
+ /^master\.key$/,
61
+ /^config\/master\.key$/,
62
+ /^wp-config\.php$/,
63
+ /^google-services\.json$/,
64
+ /^GoogleService-Info\.plist$/,
65
+ /^keystore\.properties$/,
66
+ /\.mobileprovision$/,
67
+ /\.provisionprofile$/,
68
+ /^\.token$/,
69
+ /^token\.txt$/,
70
+ /^access_token$/,
71
+ /^refresh_token$/,
72
+ /^bearer_token$/,
73
+ /^auth_token$/,
74
+ /^client_secret.*\.json$/,
75
+ /^oauth2.*\.json$/,
76
+ /^\.password$/,
77
+ /^password\.txt$/,
78
+ /^passwords\.txt$/,
79
+ /^\.secret$/,
80
+ /^secret\.txt$/,
81
+ /^secrets\.txt$/,
82
+ /^apikey\.txt$/,
83
+ /^api_key\.txt$/,
84
+ /^api-key\.txt$/,
85
+ /^\.git-credentials$/,
86
+ /^git-credentials$/,
87
+ /^\.htpasswd$/,
88
+ /^auth\.json$/,
89
+ /^\.ftpconfig$/,
90
+ /^ftpconfig\.json$/,
91
+ /^_netrc$/,
92
+ /^\.bash_history$/,
93
+ /^\.zsh_history$/,
94
+ /^\.sh_history$/,
95
+ /^\.history$/,
96
+ /^\.mysql_history$/,
97
+ /^\.psql_history$/,
98
+ /^\.sqlite_history$/,
99
+ /^\.pip\/pip\.conf$/,
100
+ /^credentials\.xml$/,
101
+ /^secrets\/.*\.xml$/,
102
+ /^shadow$/,
103
+ /^shadow\.bak$/,
104
+ /^gshadow$/,
105
+ /^\.muttrc$/,
106
+ /^\.mailrc$/,
107
+ /^\.ircrc$/,
108
+ /^\.s3cfg$/,
109
+ /^s3cfg$/,
110
+ /^\.slack-token$/,
111
+ /^slack[-_]token$/,
112
+ /^\.github[-_]token$/,
113
+ /^github[-_]token$/,
114
+ /^\.netrc\.heroku$/,
115
+ /^\.circleci\/local[-_]config\.yml$/,
116
+ /^vault[-_]pass.*\.txt$/,
117
+ /^\.vault[-_]pass.*$/,
118
+ /^\.npm[-_]token$/,
119
+ /^settings\.xml$/,
120
+ /^\.m2\/settings\.xml$/,
121
+ /^gradle\.properties$/,
122
+ /^\.gradle\/gradle\.properties$/,
123
+ /^\.subversion\/auth\/.*$/,
124
+ /^Login Data$/,
125
+ /^Cookies$/,
126
+ /\/Login Data$/,
127
+ /\/Cookies$/,
128
+ /\/logins\.json$/,
129
+ /\/key[34]\.db$/,
130
+ /\.mozilla\/firefox\/.*\/logins\.json$/,
131
+ /\.mozilla\/firefox\/.*\/key[34]\.db$/,
132
+ /\.config\/chromium\/.*\/Login Data$/,
133
+ /\.config\/google-chrome\/.*\/Login Data$/,
134
+ /\.kdbx$/,
135
+ /\.kdb$/,
136
+ /^1Password\.sqlite$/,
137
+ /^1Password.*\.sqlite$/,
138
+ /\.agilekeychain\//,
139
+ /\.opvault\//,
140
+ /^password-store$/,
141
+ /^passwords\.kdbx$/,
142
+ /^keepass\.kdbx$/,
143
+ /^wallet\.dat$/,
144
+ /^default_wallet$/,
145
+ /^\.bitcoin\/wallet\.dat$/,
146
+ /^\.ethereum\/keystore\/.*$/,
147
+ /^\.electrum\/wallets\/.*$/,
148
+ /\/keystore\/UTC--.*$/,
149
+ /^dump\.rdb$/,
150
+ /^mongodb\.dump$/,
151
+ /\.bson$/,
152
+ /\.dump$/,
153
+ /^\.idea\/dataSources\.xml$/,
154
+ /^\.idea\/webServers\.xml$/,
155
+ /^\.idea\/deployment\.xml$/,
156
+ /^\.vagrant\/machines\/.*\/private_key$/,
157
+ /^\.vagrant\.d\/insecure_private_key$/,
158
+ /^cookies\.txt$/,
159
+ /^\.cookies$/,
160
+ /^session$/,
161
+ /^sessionid$/,
162
+ /^\.wget-hsts$/,
163
+ /^core\.\d+$/,
164
+ /\.core$/,
165
+ /\.dmp$/,
166
+ /\.mdmp$/,
167
+ /^Credentials$/,
168
+ /^NTUSER\.DAT$/,
169
+ /^SAM$/,
170
+ /\.keychain$/,
171
+ /\.keychain-db$/,
172
+ /\.csr$/,
173
+ /^oauth[-_]token.*$/,
174
+ /^bearer[-_]token.*$/,
175
+ /^jwt[-_]token.*$/,
176
+ /^\.token\..*$/,
177
+ /^api[-_]keys?\..*$/,
178
+ /^\.redis_history$/,
179
+ /^\.mongo_history$/,
180
+ /^\.dbshell$/,
181
+ /^docker-compose\.override\.yml$/,
182
+ /^docker-compose\..*\.yml$/,
183
+ /^\.gcp[-_]credentials\.json$/,
184
+ /^\.azure[-_]credentials$/,
185
+ /^\.do[-_]token$/,
186
+ /^\.linode[-_]token$/,
187
+ /^\.msmtprc$/,
188
+ /^\.fetchmailrc$/,
189
+ /^wireguard\.conf$/,
190
+ /^wg[0-9]+\.conf$/,
191
+ /\.ovpn$/,
192
+ /^PASSWORDS\.md$/,
193
+ /^SECRETS\.md$/,
194
+ /^CREDENTIALS\.md$/,
195
+ /^ACCESS\.md$/,
196
+ /\.asc$/,
197
+ /\.gpg$/,
198
+ /^\.ssh\/config$/,
199
+ /\.rdp$/,
200
+ /^credentials\.db$/,
201
+ /^credentials\.sqlite$/,
202
+ /\.postman_environment\.json$/,
203
+ /^\.ruby-env$/,
204
+ /^\.rbenv-vars$/,
205
+ /^\.python-env$/,
206
+ /^\.node-env$/,
207
+ /^\.rsync[-_]password$/,
208
+ /^rsync[-_]password$/,
209
+ ];
@@ -0,0 +1,3 @@
1
+ export declare function shouldIgnorePath(pathToCheck: string): boolean;
2
+ export declare function shouldIgnoreFile(fileName: string): boolean;
3
+ export declare function shouldIgnore(fullPath: string): boolean;
@@ -0,0 +1,72 @@
1
+ import { IGNORED_PATH_PATTERNS } from './pathPatterns.js';
2
+ import { IGNORED_FILE_PATTERNS } from './filePatterns.js';
3
+ import { securityRegistry } from './registry.js';
4
+ let _compiledPathRegex = null;
5
+ let _compiledFileRegex = null;
6
+ let _cachedVersion = -1;
7
+ function stripNamedGroups(source) {
8
+ return source.replace(/\(\?<[^>]+>/g, '(?:');
9
+ }
10
+ function invalidateIfNeeded() {
11
+ const ver = securityRegistry.version;
12
+ if (ver !== _cachedVersion) {
13
+ _compiledPathRegex = null;
14
+ _compiledFileRegex = null;
15
+ _cachedVersion = ver;
16
+ }
17
+ }
18
+ function getCompiledPathRegex() {
19
+ invalidateIfNeeded();
20
+ if (!_compiledPathRegex) {
21
+ const extra = securityRegistry.extraIgnoredPathPatterns;
22
+ const all = extra.length > 0
23
+ ? [...IGNORED_PATH_PATTERNS, ...extra]
24
+ : IGNORED_PATH_PATTERNS;
25
+ _compiledPathRegex = new RegExp(all.map(r => stripNamedGroups(r.source)).join('|'));
26
+ }
27
+ return _compiledPathRegex;
28
+ }
29
+ function getCompiledFileRegex() {
30
+ invalidateIfNeeded();
31
+ if (!_compiledFileRegex) {
32
+ const extra = securityRegistry.extraIgnoredFilePatterns;
33
+ const all = extra.length > 0
34
+ ? [...IGNORED_FILE_PATTERNS, ...extra]
35
+ : IGNORED_FILE_PATTERNS;
36
+ _compiledFileRegex = new RegExp(all.map(r => stripNamedGroups(r.source)).join('|'));
37
+ }
38
+ return _compiledFileRegex;
39
+ }
40
+ export function shouldIgnorePath(pathToCheck) {
41
+ if (!pathToCheck || pathToCheck.trim() === '') {
42
+ return true;
43
+ }
44
+ const normalizedPath = normalizePathForIgnoreMatching(pathToCheck.replace(/\\/g, '/'));
45
+ const regex = getCompiledPathRegex();
46
+ const pathParts = normalizedPath.split('/');
47
+ for (const part of pathParts) {
48
+ if (regex.test(part))
49
+ return true;
50
+ }
51
+ return regex.test(normalizedPath);
52
+ }
53
+ function normalizePathForIgnoreMatching(normalizedPath) {
54
+ if (normalizedPath === '/private/var')
55
+ return '/var';
56
+ if (normalizedPath.startsWith('/private/var/')) {
57
+ return normalizedPath.slice('/private'.length);
58
+ }
59
+ return normalizedPath;
60
+ }
61
+ export function shouldIgnoreFile(fileName) {
62
+ if (!fileName || fileName.trim() === '') {
63
+ return true;
64
+ }
65
+ const normalizedPath = fileName.replace(/\\/g, '/');
66
+ const fileNameOnly = normalizedPath.split('/').pop() || '';
67
+ const regex = getCompiledFileRegex();
68
+ return regex.test(fileNameOnly) || regex.test(normalizedPath);
69
+ }
70
+ export function shouldIgnore(fullPath) {
71
+ return shouldIgnorePath(fullPath) || shouldIgnoreFile(fullPath);
72
+ }
@@ -0,0 +1,16 @@
1
+ export type { SensitiveDataPattern, SanitizationResult, ValidationResult, PathValidationResult, ToolResult, ISanitizer, } from './types.js';
2
+ export { ContentSanitizer } from './contentSanitizer.js';
3
+ export { maskSensitiveData } from './mask.js';
4
+ export { PathValidator, pathValidator, resetPathValidator, } from './pathValidator.js';
5
+ export { validateCommand } from './commandValidator.js';
6
+ export { withSecurityValidation, withBasicSecurityValidation, configureSecurity, } from './withSecurityValidation.js';
7
+ export type { SecurityDepsConfig } from './withSecurityValidation.js';
8
+ export { extractResearchFields, extractRepoOwnerFromParams, } from './paramExtractors.js';
9
+ export { shouldIgnore, shouldIgnorePath, shouldIgnoreFile, } from './ignoredPathFilter.js';
10
+ export { redactPath } from './pathUtils.js';
11
+ export { ALLOWED_COMMANDS, DANGEROUS_PATTERNS, PATTERN_DANGEROUS_PATTERNS, } from './securityConstants.js';
12
+ export { IGNORED_PATH_PATTERNS } from './pathPatterns.js';
13
+ export { IGNORED_FILE_PATTERNS } from './filePatterns.js';
14
+ export { allRegexPatterns } from './regexes/index.js';
15
+ export { SecurityRegistry, securityRegistry } from './registry.js';
16
+ export type { ISecurityRegistry } from './registry.js';
@@ -0,0 +1,13 @@
1
+ export { ContentSanitizer } from './contentSanitizer.js';
2
+ export { maskSensitiveData } from './mask.js';
3
+ export { PathValidator, pathValidator, resetPathValidator, } from './pathValidator.js';
4
+ export { validateCommand } from './commandValidator.js';
5
+ export { withSecurityValidation, withBasicSecurityValidation, configureSecurity, } from './withSecurityValidation.js';
6
+ export { extractResearchFields, extractRepoOwnerFromParams, } from './paramExtractors.js';
7
+ export { shouldIgnore, shouldIgnorePath, shouldIgnoreFile, } from './ignoredPathFilter.js';
8
+ export { redactPath } from './pathUtils.js';
9
+ export { ALLOWED_COMMANDS, DANGEROUS_PATTERNS, PATTERN_DANGEROUS_PATTERNS, } from './securityConstants.js';
10
+ export { IGNORED_PATH_PATTERNS } from './pathPatterns.js';
11
+ export { IGNORED_FILE_PATTERNS } from './filePatterns.js';
12
+ export { allRegexPatterns } from './regexes/index.js';
13
+ export { SecurityRegistry, securityRegistry } from './registry.js';
@@ -0,0 +1 @@
1
+ export declare function maskSensitiveData(text: string): string;
@@ -0,0 +1,49 @@
1
+ import { nativeMaskSensitiveData } from './native.js';
2
+ import { securityRegistry } from './registry.js';
3
+ import { maskEveryOtherChar } from './maskUtils.js';
4
+ function applyJsMask(text, patterns) {
5
+ const applicable = patterns.filter(p => !p.fileContext);
6
+ if (applicable.length === 0)
7
+ return text;
8
+ const matches = [];
9
+ for (const p of applicable) {
10
+ p.regex.lastIndex = 0;
11
+ let m;
12
+ const re = new RegExp(p.regex.source, p.regex.flags.replace('g', '') + 'g');
13
+ while ((m = re.exec(text)) !== null) {
14
+ matches.push({ start: m.index, end: m.index + m[0].length });
15
+ if (m[0].length === 0)
16
+ re.lastIndex++;
17
+ }
18
+ }
19
+ if (matches.length === 0)
20
+ return text;
21
+ matches.sort((a, b) => a.start - b.start);
22
+ const deduped = [];
23
+ let lastEnd = 0;
24
+ for (const m of matches) {
25
+ if (m.start >= lastEnd) {
26
+ deduped.push(m);
27
+ lastEnd = m.end;
28
+ }
29
+ }
30
+ let result = text;
31
+ for (let i = deduped.length - 1; i >= 0; i--) {
32
+ const { start, end } = deduped[i];
33
+ result =
34
+ result.slice(0, start) +
35
+ maskEveryOtherChar(text.slice(start, end)) +
36
+ result.slice(end);
37
+ }
38
+ return result;
39
+ }
40
+ export function maskSensitiveData(text) {
41
+ if (!text)
42
+ return text;
43
+ let result = nativeMaskSensitiveData(text);
44
+ const extra = securityRegistry.extraSecretPatterns;
45
+ if (extra.length > 0) {
46
+ result = applyJsMask(result, extra);
47
+ }
48
+ return result;
49
+ }
@@ -0,0 +1 @@
1
+ export declare function maskEveryOtherChar(text: string): string;
@@ -0,0 +1,7 @@
1
+ export function maskEveryOtherChar(text) {
2
+ let result = '';
3
+ for (let i = 0; i < text.length; i++) {
4
+ result += i % 2 === 0 ? '*' : text[i];
5
+ }
6
+ return result;
7
+ }
@@ -0,0 +1,9 @@
1
+ export interface NativeSanitizationResult {
2
+ content: string;
3
+ hasSecrets: boolean;
4
+ secretsDetected: string[];
5
+ warnings: string[];
6
+ }
7
+ export declare const nativeSanitizeContent: (content: string, filePath: string | null) => NativeSanitizationResult;
8
+ export declare const nativeMaskSensitiveData: (text: string) => string;
9
+ export declare const nativePatternCount: () => number;