fix(security): harden JWT, CORS, and H2 Console for production

This commit is contained in:
matevip 2026-04-11 18:21:17 +08:00
parent c619ffee4e
commit fe83b72d67
3 changed files with 65 additions and 3 deletions

View File

@ -0,0 +1,57 @@
package vip.mate.config;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.ApplicationArguments;
import org.springframework.boot.ApplicationRunner;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;
/**
* Startup security validator warns about insecure default configurations.
*
* @author MateClaw Team
*/
@Slf4j
@Component
@Order(1)
public class SecurityStartupValidator implements ApplicationRunner {
private static final String DEFAULT_JWT_SECRET = "MateClaw-JWT-Secret-Key-2024-Please-Change-In-Production";
@Value("${mateclaw.jwt.secret}")
private String jwtSecret;
@Value("${spring.h2.console.enabled:false}")
private boolean h2ConsoleEnabled;
@Value("${mateclaw.cors.allowed-origins:*}")
private String corsOrigins;
@Override
public void run(ApplicationArguments args) {
boolean hasWarnings = false;
if (DEFAULT_JWT_SECRET.equals(jwtSecret)) {
log.warn("╔══════════════════════════════════════════════════════════════╗");
log.warn("║ SECURITY WARNING: Using default JWT secret! ║");
log.warn("║ Set JWT_SECRET environment variable for production. ║");
log.warn("╚══════════════════════════════════════════════════════════════╝");
hasWarnings = true;
}
if (h2ConsoleEnabled) {
log.warn("[Security] H2 Console is enabled at /h2-console. Set H2_CONSOLE_ENABLED=false in production.");
hasWarnings = true;
}
if ("*".equals(corsOrigins.trim())) {
log.warn("[Security] CORS allows all origins. Set MATECLAW_CORS_ALLOWED_ORIGINS in production.");
hasWarnings = true;
}
if (!hasWarnings) {
log.info("[Security] Startup security check passed.");
}
}
}

View File

@ -1,6 +1,7 @@
package vip.mate.config;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
@ -19,6 +20,10 @@ public class WebMvcConfig implements WebMvcConfigurer {
private final WorkspaceAccessInterceptor workspaceAccessInterceptor;
/** CORS allowed origins, comma-separated. Default "*" for dev, restrict in production. */
@Value("${mateclaw.cors.allowed-origins:*}")
private String allowedOrigins;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(workspaceAccessInterceptor)
@ -28,7 +33,7 @@ public class WebMvcConfig implements WebMvcConfigurer {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/api/**")
.allowedOriginPatterns("*")
.allowedOriginPatterns(allowedOrigins.split(","))
.allowedMethods("GET", "POST", "PUT", "DELETE", "OPTIONS")
.allowedHeaders("*")
.allowCredentials(true)

View File

@ -40,7 +40,7 @@ spring:
h2:
console:
enabled: true
enabled: ${H2_CONSOLE_ENABLED:false}
path: /h2-console
# Spring AI Alibaba (DashScope) - Spring AI Alibaba 1.1.x 配置路径
@ -92,7 +92,7 @@ springdoc:
# MateClaw 自定义配置
mateclaw:
jwt:
secret: MateClaw-JWT-Secret-Key-2024-Please-Change-In-Production
secret: ${JWT_SECRET:MateClaw-JWT-Secret-Key-2024-Please-Change-In-Production}
expiration: 86400000
# 搜索配置已迁移至数据库mate_system_setting 表),通过 UI 系统设置管理
# MCP server 配置已迁移至数据库mate_mcp_server 表),通过 UI 管理