@dcrays/mobook-security-plugin 2.0.11 → 2.0.12
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/index.js +25 -16
- package/openclaw.plugin.json +1 -1
- package/package.json +1 -1
package/index.js
CHANGED
|
@@ -135,57 +135,64 @@ function verifyLuhn(cardNumber) {
|
|
|
135
135
|
const ID_CARD_REGEX = /\b[1-9]\d{5}(?:19|20)\d{2}(?:0[1-9]|1[0-2])(?:0[1-9]|[12]\d|3[01])\d{3}[\dXx]\b/g;
|
|
136
136
|
const BANK_CARD_REGEX = /\b[3-6]\d{15,18}\b/g;
|
|
137
137
|
|
|
138
|
+
// ---- 脱敏辅助:部分保留 + 星号遮盖 ----
|
|
139
|
+
function maskKeep(str, keepHead, keepTail = 0, minStars = 4) {
|
|
140
|
+
if (str.length <= keepHead + keepTail) return "*".repeat(str.length);
|
|
141
|
+
const stars = Math.max(minStars, str.length - keepHead - keepTail);
|
|
142
|
+
return str.slice(0, keepHead) + "*".repeat(stars) + (keepTail > 0 ? str.slice(-keepTail) : "");
|
|
143
|
+
}
|
|
144
|
+
|
|
138
145
|
const SENSITIVE_PATTERNS = [
|
|
139
146
|
{
|
|
140
147
|
pattern: ID_CARD_REGEX,
|
|
141
148
|
validator: verifyIdCard,
|
|
142
|
-
|
|
149
|
+
replacer: (m) => maskKeep(m, 3, 4), // 310***********1234
|
|
143
150
|
name: "身份证号"
|
|
144
151
|
},
|
|
145
152
|
{
|
|
146
153
|
pattern: /\b1[3-9]\d{9}\b/g,
|
|
147
|
-
|
|
154
|
+
replacer: (m) => maskKeep(m, 3, 4), // 138****5678
|
|
148
155
|
name: "手机号"
|
|
149
156
|
},
|
|
150
157
|
{
|
|
151
158
|
pattern: BANK_CARD_REGEX,
|
|
152
159
|
validator: verifyLuhn,
|
|
153
|
-
|
|
160
|
+
replacer: (m) => maskKeep(m, 4, 4), // 6222***********1234
|
|
154
161
|
name: "银行卡号"
|
|
155
162
|
},
|
|
156
163
|
{
|
|
157
|
-
pattern: /\b[a-zA-Z0-9._%+-]
|
|
158
|
-
|
|
164
|
+
pattern: /\b([a-zA-Z0-9._%+-]+)@((?:qq|163|126|sina|sohu|gmail|outlook|hotmail|yahoo)\.[a-z]{2,})\b/gi,
|
|
165
|
+
replacer: (_m, local, domain) => maskKeep(local, 1, 0) + "@" + domain, // j*****@gmail.com
|
|
159
166
|
name: "个人邮箱"
|
|
160
167
|
},
|
|
161
168
|
{
|
|
162
169
|
pattern: /\b(sk-[a-zA-Z0-9-]{20,})\b/g,
|
|
163
|
-
|
|
170
|
+
replacer: (m) => maskKeep(m, 5, 0), // sk-pr**************
|
|
164
171
|
name: "API Key (sk-)"
|
|
165
172
|
},
|
|
166
173
|
{
|
|
167
174
|
pattern: /\b(AKIA[0-9A-Z]{16})\b/g,
|
|
168
|
-
|
|
175
|
+
replacer: (m) => maskKeep(m, 4, 0), // AKIA************
|
|
169
176
|
name: "AWS Access Key"
|
|
170
177
|
},
|
|
171
178
|
{
|
|
172
179
|
pattern: /\b(ghp_[a-zA-Z0-9]{36,})\b/g,
|
|
173
|
-
|
|
180
|
+
replacer: (m) => maskKeep(m, 4, 0), // ghp_****...
|
|
174
181
|
name: "GitHub Token"
|
|
175
182
|
},
|
|
176
183
|
{
|
|
177
184
|
pattern: /(password|passwd|pwd|secret_key|secret|token|api_key|apikey|access_key|private_key)\s*[=:]\s*["']?[^\s"',]{6,}/gi,
|
|
178
|
-
|
|
185
|
+
replacer: (_m, key) => key + "=***", // password=***
|
|
179
186
|
name: "密码/密钥字段"
|
|
180
187
|
},
|
|
181
188
|
{
|
|
182
189
|
pattern: /\b(10\.\d{1,3}\.\d{1,3}\.\d{1,3}|172\.(1[6-9]|2\d|3[01])\.\d{1,3}\.\d{1,3}|192\.168\.\d{1,3}\.\d{1,3})\b/g,
|
|
183
|
-
|
|
190
|
+
replacer: (m) => m.split(".")[0] + ".*.*.*", // 10.*.*.*
|
|
184
191
|
name: "内网IP"
|
|
185
192
|
},
|
|
186
193
|
{
|
|
187
194
|
pattern: /[^\s"']*\/extensions\/mobook-security-plugin[^\s"']*/g,
|
|
188
|
-
|
|
195
|
+
replacer: () => "***插件路径已脱敏***",
|
|
189
196
|
name: "安全插件路径"
|
|
190
197
|
},
|
|
191
198
|
];
|
|
@@ -198,19 +205,21 @@ function sanitizeContent(content) {
|
|
|
198
205
|
rule.pattern.lastIndex = 0;
|
|
199
206
|
|
|
200
207
|
if (rule.validator) {
|
|
208
|
+
// 有校验器的规则(身份证、银行卡等)
|
|
201
209
|
let hasMatch = false;
|
|
202
|
-
sanitized = sanitized.replace(rule.pattern, (
|
|
210
|
+
sanitized = sanitized.replace(rule.pattern, (...args) => {
|
|
211
|
+
const match = args[0];
|
|
203
212
|
if (rule.validator(match)) {
|
|
204
213
|
hasMatch = true;
|
|
205
|
-
return rule.
|
|
214
|
+
return rule.replacer(...args);
|
|
206
215
|
}
|
|
207
216
|
return match;
|
|
208
217
|
});
|
|
209
218
|
if (hasMatch) matches.push(rule.name);
|
|
210
|
-
} else if (rule.
|
|
219
|
+
} else if (rule.replacer) {
|
|
220
|
+
// 使用 replacer 函数
|
|
211
221
|
rule.pattern.lastIndex = 0;
|
|
212
|
-
const
|
|
213
|
-
const replaced = sanitized.replace(rule.pattern, () => repl);
|
|
222
|
+
const replaced = sanitized.replace(rule.pattern, (...args) => rule.replacer(...args));
|
|
214
223
|
if (replaced !== sanitized) {
|
|
215
224
|
matches.push(rule.name);
|
|
216
225
|
sanitized = replaced;
|
package/openclaw.plugin.json
CHANGED