Add comprehensive security validation to prevent malicious code injection

Co-authored-by: whyour <22700758+whyour@users.noreply.github.com>
This commit is contained in:
copilot-swe-agent[bot]
2026-02-08 15:23:03 +00:00
co-authored by whyour
parent a030e19fc0
commit ac8090d937
4 changed files with 309 additions and 12 deletions
+66 -3
View File
@@ -4,6 +4,57 @@ import { ScheduleType } from '../interface/schedule';
import path from 'path';
import config from '../config';
/**
* Security validation function to detect potentially malicious shell code patterns
*/
const validateShellSecurity = (value: string, helpers: any, fieldName: string) => {
if (!value) return value;
// Define dangerous patterns that should be blocked
const dangerousPatterns = [
// Command substitution
/\$\([^)]*\)/,
/`[^`]*`/,
// File downloads
/\b(curl|wget|fetch)\s+/i,
// Suspicious domains or external URLs
/https?:\/\/[^\s]+/i,
// Hidden files starting with dot (common in malware)
/\s*\.\w+\s*$/,
// Background process spawning with suspicious names
/nohup\s+[^\s]*\.\w+/,
// Redirect to dev null (hiding output)
/>.*\/dev\/null.*&/,
// Base64 decode patterns (often used to obfuscate malicious code)
/\b(base64|decode|eval)\s+/i,
// File execution from temp or hidden directories
/\/(tmp|\.)\//,
];
for (const pattern of dangerousPatterns) {
if (pattern.test(value)) {
return helpers.error('string.unsafe', {
pattern: pattern.source,
field: fieldName
});
}
}
// Check for excessive length (potential buffer overflow or obfuscation)
if (value.length > 10000) {
return helpers.error('string.max', { limit: 10000 });
}
return value;
};
const validateSchedule = (value: string, helpers: any) => {
if (
value.startsWith(ScheduleType.ONCE) ||
@@ -32,13 +83,25 @@ export const scheduleSchema = Joi.string()
export const commonCronSchema = {
name: Joi.string().optional(),
command: Joi.string().required(),
command: Joi.string().required().custom((value, helpers) => {
return validateShellSecurity(value, helpers, 'command');
}).messages({
'string.unsafe': '命令包含潜在危险的模式,已被安全系统拦截',
}),
schedule: scheduleSchema,
labels: Joi.array().optional(),
sub_id: Joi.number().optional().allow(null),
extra_schedules: Joi.array().optional().allow(null),
task_before: Joi.string().optional().allow('').allow(null),
task_after: Joi.string().optional().allow('').allow(null),
task_before: Joi.string().optional().allow('').allow(null).custom((value, helpers) => {
return validateShellSecurity(value, helpers, 'task_before');
}).messages({
'string.unsafe': '前置命令包含潜在危险的模式,已被安全系统拦截',
}),
task_after: Joi.string().optional().allow('').allow(null).custom((value, helpers) => {
return validateShellSecurity(value, helpers, 'task_after');
}).messages({
'string.unsafe': '后置命令包含潜在危险的模式,已被安全系统拦截',
}),
log_name: Joi.string()
.optional()
.allow('')