SpringBoot 在线依赖包漏洞扫描仪,一键发现潜在安全漏洞

在日常项目开发中,依赖第三方库几乎是不可避免的。从 spring-boot-starter 到 MyBatis、Log4j,再到各种工具类库,几乎每个应用都需要几十甚至上百个依赖。

然而,这些依赖并非完全安全。很多开发者可能在不知情的情况下,使用了存在 已知漏洞 的版本,轻则引发应用崩溃,重则导致远程代码执行或数据泄漏。

本文带你实现一个依赖库漏洞在线扫描仪,包含以下内容:

1、执行后自动扫描所有依赖 jar 包

2、匹配漏洞数据库,检测已知漏洞

3、将扫描结果 可视化展示,直观告诉你哪个依赖存在漏洞、漏洞危害描述、对应的 CVE 编号等信息

1. 需求痛点

1. 依赖数量庞大:一个典型的 Spring Boot 应用常常包含 100+ 依赖,人工排查几乎不可能。

2. 漏洞信息分散:CVE 公告、NVD、GitHub issue,开发者很难第一时间获取。

3. 缺乏修复指导:即使知道某个版本有漏洞,很多团队也不清楚应该升级到哪个安全版本。

因此,一个 一键扫描 + 漏洞说明 + 修复建议 的工具,能够极大提升团队安全响应效率。

2. 现状分析

目前常见方案:

OWASP Dependency-Check:功能强大,但集成较重,国内文档少。

Snyk / WhiteSource:商业化产品,部分功能需付费。

手工排查:低效且容易遗漏。

所以,我们希望在 SpringBoot 应用内部,做一个 轻量级依赖漏洞扫描仪,即插即用,足够简单。

3. 解决思路

1. 扫描依赖 :读取当前应用的所有 jar 包版本。 2. 匹配漏洞库 :根据 groupId/artifactId/version 判断是否命中漏洞。 3. 输出漏洞详情:包括 - CVE 编号 - 漏洞描述 - 危害等级(CVSS) - 修复方案(安全版本范围) - 官方参考链接

4. 前端可视化:表格展示结果,按严重性排序,高危一目了然。


4. 系统设计

依赖收集器:获取所有依赖及版本信息

漏洞在线扫描:调用相关漏洞查询库完成漏洞分析

漏洞匹配器:判断依赖版本是否落在漏洞范围

结果展示层:Spring Boot REST API + 前端表格

5. 关键实现

5.1 漏洞数据结构

定义一个漏洞实体,包含详细说明与修复方案:

typescript 复制代码
public class Vulnerability {
    private String cve;
    private String description;
    private String severity;
    private String vulnerableVersions;
    private String safeVersion;
    private String reference;

    public boolean isVersionVulnerable(String version) {
        // 可用 Maven ArtifactVersion 进行范围匹配
        return VersionRangeChecker.isVulnerable(version, vulnerableVersions);
    }
}

示例漏洞数据(JSON 文件):

css 复制代码
[  {    "groupId": "org.apache.logging.log4j",    "artifactId": "log4j-core",    "vulnerableVersions": "<=2.14.1",    "safeVersion": "2.15.0+",    "cve": "CVE-2021-44228",    "description": "Log4j 2 JNDI 远程代码执行漏洞,攻击者可通过恶意日志消息执行任意代码。",    "severity": "Critical",    "reference": "https://nvd.nist.gov/vuln/detail/CVE-2021-44228"  }]

5.2 扫描依赖并匹配漏洞

typescript 复制代码
@GetMapping("/dependencies/scan")
public ResponseEntity<Map<String, Object>> scanDependencies() {
    logger.info("开始执行依赖扫描...");
    
    long startTime = System.currentTimeMillis();
    
    try {
        // 1. 收集依赖
        List<DependencyInfo> dependencies = dependencyCollector.collect();
        logger.info("收集到 {} 个依赖", dependencies.size());
        
        // 2. 匹配漏洞
        List<DependencyRisk> risks = vulnerabilityMatcher.matchVulnerabilities(dependencies);
        
        // 3. 按风险等级排序
        risks = vulnerabilityMatcher.sortByRiskLevel(risks);
        
        // 4. 获取统计信息
        VulnerabilityMatcher.RiskStatistics statistics = vulnerabilityMatcher.getRiskStatistics(risks);
        
        long endTime = System.currentTimeMillis();
        long duration = endTime - startTime;
        
        logger.info("依赖扫描完成,耗时 {} ms,{}", duration, statistics.toString());
        
        // 构建响应
        Map<String, Object> response = new HashMap<>();
        response.put("success", true);
        response.put("message", "扫描完成");
        response.put("data", risks);
        
        // 修复统计信息:总依赖数应该是所有依赖,不是只有有漏洞的
        Map<String, Object> statisticsMap = new HashMap<>();
        statisticsMap.put("totalDependencies", dependencies.size());  // 所有依赖数量
        statisticsMap.put("vulnerableDependencies", risks.size());     // 有漏洞的依赖数量
        statisticsMap.put("criticalCount", statistics.criticalCount);
        statisticsMap.put("highCount", statistics.highCount);
        statisticsMap.put("mediumCount", statistics.mediumCount);
        statisticsMap.put("lowCount", statistics.lowCount);
        statisticsMap.put("scanDuration", duration);
        
        response.put("statistics", statisticsMap);
        
        return ResponseEntity.ok(response);
        
    } catch (Exception e) {
        logger.error("依赖扫描失败", e);
        
        Map<String, Object> errorResponse = new HashMap<>();
        errorResponse.put("success", false);
        errorResponse.put("message", "扫描失败: " + e.getMessage());
        errorResponse.put("data", List.of());
        
        return ResponseEntity.status(500).body(errorResponse);
    }
}

返回的 JSON 示例:

css 复制代码
[  {    "groupId": "org.apache.logging.log4j",    "artifactId": "log4j-core",    "version": "2.14.1",    "riskLevel": "Critical",    "cve": "CVE-2021-44228",    "description": "Log4j JNDI 注入可导致远程代码执行。",    "safeVersion": "2.15.0+",    "reference": "https://nvd.nist.gov/vuln/detail/CVE-2021-44228"  }]

6. 前端可视化

xml 复制代码
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>依赖包安全扫描仪</title>
    <script src="https://cdn.tailwindcss.com"></script>
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css">
</head>
<body class="bg-gray-50 min-h-screen">
    <!-- 导航栏 -->
    <nav class="bg-white shadow-lg">
        <div class="max-w-7xl mx-auto px-4">
            <div class="flex justify-between items-center py-4">
                <div class="flex items-center space-x-3">
                    <i class="fas fa-shield-alt text-blue-600 text-2xl"></i>
                    <h1 class="text-xl font-bold text-gray-800">依赖包安全扫描仪</h1>
                </div>
                <div class="flex items-center space-x-4">
                    <span class="text-sm text-gray-600">Spring Boot 2.7.18</span>
                    <div class="flex items-center space-x-2">
                        <div id="statusIndicator" class="w-2 h-2 bg-green-500 rounded-full"></div>
                        <div id="statusSpinner" class="loading-spinner" style="display: none;"></div>
                        <span id="statusText" class="text-sm">就绪</span>
                    </div>
                </div>
            </div>
        </div>
    </nav>

    <div class="max-w-7xl mx-auto px-4 py-8">
        <!-- 操作面板 -->
        <div class="bg-white rounded-lg shadow-md p-6 mb-8">
            <div class="flex flex-col space-y-4">
                <div class="flex flex-col sm:flex-row justify-between items-start sm:items-center space-y-4 sm:space-y-0">
                    <div>
                        <h2 class="text-lg font-semibold text-gray-800 mb-2">扫描控制</h2>
                        <p class="text-gray-600 text-sm">扫描当前应用的所有依赖包,检测已知安全漏洞</p>
                    </div>
                    <div class="flex space-x-3">
                        <button 
                            id="scanButton"
                            class="bg-blue-600 hover:bg-blue-700 disabled:bg-gray-400 text-white px-6 py-2 rounded-lg font-medium transition-colors duration-200 flex items-center space-x-2">
                            <i class="fas fa-search mr-2"></i>开始扫描
                        </button>
                        <button 
                            id="exportButton"
                            class="bg-green-600 hover:bg-green-700 disabled:bg-gray-400 text-white px-6 py-2 rounded-lg font-medium transition-colors duration-200 flex items-center space-x-2">
                            <i class="fas fa-download mr-2"></i>导出结果
                        </button>
                    </div>
                </div>
                
                <!-- 风险等级过滤器 -->
                <div id="riskFilters" class="flex flex-wrap items-center space-x-4 pt-4 border-t border-gray-200" style="display: none;">
                    <span class="text-sm font-medium text-gray-600">风险等级过滤:</span>
                    <label class="flex items-center space-x-2">
                        <input type="checkbox" id="filter-all" class="rounded border-gray-300 text-blue-600 focus:ring-blue-500" checked>
                        <span class="text-sm text-gray-700">全部</span>
                    </label>
                    <label class="flex items-center space-x-2">
                        <input type="checkbox" id="filter-critical" class="rounded border-gray-300 text-red-600 focus:ring-red-500" checked>
                        <span class="text-sm text-red-700">严重</span>
                    </label>
                    <label class="flex items-center space-x-2">
                        <input type="checkbox" id="filter-high" class="rounded border-gray-300 text-orange-600 focus:ring-orange-500" checked>
                        <span class="text-sm text-orange-700">高危</span>
                    </label>
                    <label class="flex items-center space-x-2">
                        <input type="checkbox" id="filter-medium" class="rounded border-gray-300 text-yellow-600 focus:ring-yellow-500" checked>
                        <span class="text-sm text-yellow-700">中危</span>
                    </label>
                    <label class="flex items-center space-x-2">
                        <input type="checkbox" id="filter-low" class="rounded border-gray-300 text-blue-600 focus:ring-blue-500" checked>
                        <span class="text-sm text-blue-700">低危</span>
                    </label>
                </div>
            </div>
        </div>

        <!-- 统计信息 -->
        <div id="statisticsContainer" class="statistics-grid mb-6" style="display: none;">
            <div class="statistics-card bg-white rounded-lg shadow-md p-6">
                <div class="flex items-center">
                    <div class="p-3 rounded-full bg-blue-100 text-blue-600">
                        <i class="fas fa-cube text-xl"></i>
                    </div>
                    <div class="ml-4">
                        <p class="text-sm font-medium text-gray-600">总依赖数</p>
                        <p id="totalDependencies" class="text-2xl font-bold text-gray-900">0</p>
                    </div>
                </div>
            </div>
            <div class="statistics-card bg-white rounded-lg shadow-md p-6">
                <div class="flex items-center">
                    <div class="p-3 rounded-full bg-red-100 text-red-600">
                        <i class="fas fa-exclamation-triangle text-xl"></i>
                    </div>
                    <div class="ml-4">
                        <p class="text-sm font-medium text-gray-600">存在漏洞</p>
                        <p id="vulnerableDependencies" class="text-2xl font-bold text-gray-900">0</p>
                    </div>
                </div>
            </div>
            <div class="statistics-card bg-white rounded-lg shadow-md p-6">
                <div class="flex items-center">
                    <div class="p-3 rounded-full bg-red-100 text-red-600">
                        <i class="fas fa-fire text-xl"></i>
                    </div>
                    <div class="ml-4">
                        <p class="text-sm font-medium text-gray-600">严重/高危</p>
                        <p id="criticalHighCount" class="text-2xl font-bold text-red-600">0</p>
                    </div>
                </div>
            </div>
            <div class="statistics-card bg-white rounded-lg shadow-md p-6">
                <div class="flex items-center">
                    <div class="p-3 rounded-full bg-yellow-100 text-yellow-600">
                        <i class="fas fa-exclamation-circle text-xl"></i>
                    </div>
                    <div class="ml-4">
                        <p class="text-sm font-medium text-gray-600">中危/低危</p>
                        <p id="mediumLowCount" class="text-2xl font-bold text-yellow-600">0</p>
                    </div>
                </div>
            </div>
            <div class="statistics-card bg-white rounded-lg shadow-md p-6">
                <div class="flex items-center">
                    <div class="p-3 rounded-full bg-purple-100 text-purple-600">
                        <i class="fas fa-clock text-xl"></i>
                    </div>
                    <div class="ml-4">
                        <p class="text-sm font-medium text-gray-600">扫描耗时</p>
                        <p id="scanDuration" class="text-2xl font-bold text-gray-900">0s</p>
                    </div>
                </div>
            </div>
        </div>

        <!-- 加载状态 -->
        <div id="loadingSpinner" class="text-center py-8" style="display: none;">
            <i class="fas fa-spinner fa-spin text-4xl text-blue-600 mb-4"></i>
            <p class="text-gray-600">正在扫描依赖包...</p>
        </div>
        
        <!-- 扫描结果 -->
        <div id="scanResultsContainer" class="bg-white rounded-lg shadow-md" style="display: none;">
            <div class="px-6 py-4 border-b border-gray-200">
                <h3 class="text-lg font-semibold text-gray-800">扫描结果</h3>
                <p class="text-sm text-gray-600 mt-1">发现 <span id="resultCount">0</span> 个存在安全漏洞的依赖包</p>
            </div>
            
            <div class="overflow-x-auto">
                <table class="min-w-full divide-y divide-gray-200 compact-table">
                    <thead class="bg-gray-50">
                        <tr>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider dependency-cell">依赖包</th>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider version-cell">版本</th>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider risk-cell">风险</th>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider cve-cell">CVE编号</th>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider safe-version-cell">安全版本</th>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider details-cell">详情</th>
                            <th class="text-left text-xs font-medium text-gray-500 uppercase tracking-wider action-cell">操作</th>
                        </tr>
                    </thead>
                    <tbody id="resultsTableBody" class="bg-white divide-y divide-gray-200">
                        <!-- 动态生成的扫描结果行 -->
                    </tbody>
                </table>
            </div>
        </div>

        <!-- 无结果提示 -->
        <div id="noResultsMessage" class="bg-white rounded-lg shadow-md p-8 text-center" style="display: none;">
            <i class="fas fa-check-circle text-green-500 text-4xl mb-4"></i>
            <h3 class="text-lg font-semibold text-gray-800 mb-2">恭喜!未发现安全漏洞</h3>
            <p class="text-gray-600">您的依赖包都是安全的,没有发现已知的安全漏洞。</p>
        </div>

        <!-- 错误提示 -->
        <div id="errorMessage" class="bg-red-50 border border-red-200 rounded-lg p-4 mb-6" style="display: none;">
            <div class="flex items-center">
                <i class="fas fa-exclamation-triangle text-red-500 mr-3"></i>
                <div>
                    <h4 class="text-red-800 font-medium">扫描失败</h4>
                    <p id="errorText" class="text-red-700 text-sm mt-1"></p>
                </div>
            </div>
        </div>
    </div>

    <!-- 详情模态框 -->
    <div id="detailModal" class="fixed inset-0 bg-gray-600 bg-opacity-50 overflow-y-auto h-full w-full z-50" style="display: none;" onclick="closeModal()">
        <div class="relative top-10 mx-auto p-6 border w-11/12 md:w-4/5 lg:w-3/4 xl:w-2/3 shadow-lg rounded-lg bg-white max-h-screen overflow-y-auto" onclick="event.stopPropagation()">
            <div class="flex justify-between items-center mb-6">
                <div class="flex items-center space-x-3">
                    <div id="modalSeverityIcon" class="p-2 rounded-full">
                        <i class="fas fa-shield-alt text-xl"></i>
                    </div>
                    <div>
                        <h3 class="text-xl font-bold text-gray-800">漏洞详情与解决方案</h3>
                        <p class="text-sm text-gray-600" id="modalSubtitle">详细的漏洞信息和修复建议</p>
                    </div>
                </div>
                <button onclick="closeModal()" class="text-gray-400 hover:text-gray-600 transition-colors">
                    <i class="fas fa-times text-xl"></i>
                </button>
            </div>
            
            <div id="modalContent">
                <!-- 基本信息卡片 -->
                <div class="bg-gray-50 rounded-lg p-4 mb-6">
                    <h4 class="text-lg font-semibold text-gray-800 mb-3 flex items-center">
                        <i class="fas fa-info-circle text-blue-600 mr-2"></i>基本信息
                    </h4>
                    <div class="grid grid-cols-1 md:grid-cols-2 gap-4">
                        <div>
                            <label class="block text-sm font-medium text-gray-700 mb-1">依赖包</label>
                            <p id="modalDependency" class="text-sm text-gray-900 font-mono bg-white p-2 rounded border"></p>
                        </div>
                        <div>
                            <label class="block text-sm font-medium text-gray-700 mb-1">当前版本</label>
                            <p id="modalVersion" class="text-sm text-gray-900 font-mono bg-white p-2 rounded border"></p>
                        </div>
                        <div>
                            <label class="block text-sm font-medium text-gray-700 mb-1">CVE编号</label>
                            <p id="modalCve" class="text-sm text-gray-900 font-mono bg-white p-2 rounded border"></p>
                        </div>
                        <div>
                            <label class="block text-sm font-medium text-gray-700 mb-1">风险等级</label>
                            <span id="modalSeverityBadge" class="inline-flex px-2 py-1 text-xs font-semibold rounded-full"></span>
                        </div>
                    </div>
                </div>

                <!-- 漏洞详情卡片 -->
                <div class="bg-red-50 border border-red-200 rounded-lg p-4 mb-6">
                    <h4 class="text-lg font-semibold text-red-800 mb-3 flex items-center">
                        <i class="fas fa-exclamation-triangle text-red-600 mr-2"></i>漏洞详情
                    </h4>
                    <div>
                        <label class="block text-sm font-medium text-red-700 mb-2">漏洞描述</label>
                        <div id="modalDescription" class="text-sm text-red-800 bg-white p-3 rounded border leading-relaxed"></div>
                    </div>
                    
                    <!-- 影响版本 -->
                    <div id="vulnerableVersionsContainer" class="mt-4" style="display: none;">
                        <label class="block text-sm font-medium text-red-700 mb-2">影响版本</label>
                        <p id="modalVulnerableVersions" class="text-sm text-red-800 bg-white p-2 rounded border font-mono"></p>
                    </div>
                </div>
                
                <!-- 解决方案卡片 -->
                <div class="bg-green-50 border border-green-200 rounded-lg p-4 mb-6">
                    <h4 class="text-lg font-semibold text-green-800 mb-3 flex items-center">
                        <i class="fas fa-tools text-green-600 mr-2"></i>解决方案
                    </h4>
                    
                    <!-- 推荐版本 -->
                    <div class="mb-4">
                        <label class="block text-sm font-medium text-green-800 mb-2 flex items-center">
                            <i class="fas fa-arrow-up text-green-600 mr-1"></i>推荐升级版本
                        </label>
                        <div class="flex items-center space-x-2 bg-white p-3 rounded border">
                            <p id="modalSafeVersion" class="text-sm text-green-700 font-medium flex-1"></p>
                            <button id="copyVersionBtn" onclick="copySafeVersion()" class="text-green-600 hover:text-green-800 p-1 rounded hover:bg-green-100 transition-colors" title="复制版本号">
                                <i class="fas fa-copy"></i>
                            </button>
                        </div>
                        <div id="upgradeHint" class="mt-2 text-xs text-green-600 flex items-center">
                            <i class="fas fa-lightbulb mr-1"></i>
                            升级到推荐版本可修复此安全漏洞
                        </div>
                    </div>

                    <!-- Maven 升级指令 -->
                    <div class="mb-4">
                        <label class="block text-sm font-medium text-green-800 mb-2 flex items-center">
                            <i class="fab fa-java text-green-600 mr-1"></i>Maven 升级指令
                        </label>
                        <div class="bg-gray-900 text-green-400 p-3 rounded font-mono text-sm relative">
                            <pre id="mavenCommand" class="whitespace-pre-wrap"></pre>
                            <button onclick="copyMavenCommand()" class="absolute top-2 right-2 text-green-400 hover:text-green-300 transition-colors" title="复制Maven指令">
                                <i class="fas fa-copy"></i>
                            </button>
                        </div>
                    </div>

                    <!-- Gradle 升级指令 -->
                    <div class="mb-4">
                        <label class="block text-sm font-medium text-green-800 mb-2 flex items-center">
                            <i class="fas fa-cube text-green-600 mr-1"></i>Gradle 升级指令
                        </label>
                        <div class="bg-gray-900 text-blue-400 p-3 rounded font-mono text-sm relative">
                            <pre id="gradleCommand" class="whitespace-pre-wrap"></pre>
                            <button onclick="copyGradleCommand()" class="absolute top-2 right-2 text-blue-400 hover:text-blue-300 transition-colors" title="复制Gradle指令">
                                <i class="fas fa-copy"></i>
                            </button>
                        </div>
                    </div>

                    <!-- 通用解决建议 -->
                    <div id="solutionTips" class="bg-white border-l-4 border-green-500 p-3 rounded">
                        <h5 class="font-medium text-green-800 mb-2 flex items-center">
                            <i class="fas fa-list-ul mr-2"></i>修复建议
                        </h5>
                        <ul id="solutionList" class="text-sm text-green-700 space-y-1 list-disc list-inside">
                            <!-- 动态生成解决方案列表 -->
                        </ul>
                    </div>
                </div>

                <!-- 相关信息 -->
                <div class="bg-blue-50 border border-blue-200 rounded-lg p-4">
                    <h4 class="text-lg font-semibold text-blue-800 mb-3 flex items-center">
                        <i class="fas fa-external-link-alt text-blue-600 mr-2"></i>相关信息
                    </h4>
                    
                    <div id="modalReferenceContainer" class="mb-3" style="display: none;">
                        <label class="block text-sm font-medium text-blue-700 mb-2">官方参考链接</label>
                        <a id="modalReference" target="_blank" class="text-sm text-blue-600 hover:text-blue-800 underline break-all"></a>
                    </div>

                    <!-- 相关资源链接 -->
                    <div class="grid grid-cols-1 md:grid-cols-2 gap-3">
                        <a id="cveDetailsLink" target="_blank" class="flex items-center p-2 text-sm text-blue-600 hover:text-blue-800 hover:bg-blue-100 rounded transition-colors">
                            <i class="fas fa-search mr-2"></i>CVE详情查询
                        </a>
                        <a id="mavenCentralLink" target="_blank" class="flex items-center p-2 text-sm text-blue-600 hover:text-blue-800 hover:bg-blue-100 rounded transition-colors">
                            <i class="fas fa-box mr-2"></i>Maven Central
                        </a>
                        <a id="osvDetailsLink" target="_blank" class="flex items-center p-2 text-sm text-blue-600 hover:text-blue-800 hover:bg-blue-100 rounded transition-colors">
                            <i class="fas fa-database mr-2"></i>OSV数据库
                        </a>
                        <a id="githubAdvisoryLink" target="_blank" class="flex items-center p-2 text-sm text-blue-600 hover:text-blue-800 hover:bg-blue-100 rounded transition-colors">
                            <i class="fab fa-github mr-2"></i>GitHub安全公告
                        </a>
                    </div>
                </div>
            </div>
        </div>
    </div>

    <script src="app.js"></script>
</body>
</html>

红色标记高危漏洞

  • 一行信息清楚展现漏洞 + 修复方案
  • 可点击链接查看官方公告

7. 实战应用场景

1. 本地开发自查

开发者在调试时即可运行扫描,第一时间发现依赖风险。

2. 应急响应

当新漏洞爆出(如 Log4Shell),立刻扫描项目,快速定位受影响模块,并知道该升到哪个版本。

3. CI/CD 集成

在构建流水线中调用 /dependencies API:

  • 若发现高危漏洞 → 直接 fail 构建
  • 提示需升级到安全版本后,才能继续部署

8. 总结

本文实现了一个轻量级的 SpringBoot 在线「依赖包漏洞扫描仪」:

自动收集依赖,无需人工干预

匹配漏洞库,输出 CVE 编号 + 漏洞描述

提供漏洞详情信息,避免知道有问题但不知如何解决

可视化展示,直观易懂

github.com/yuboon/java...

相关推荐
㳺三才人子5 小时前
初探 Flask
后端·python·flask·html
星栈独行5 小时前
我在 Rust 全栈项目里用 JWT 做无状态认证
开发语言·后端·rust·前端框架·开源·github·web
Java爱好狂.6 小时前
Java程序员体系化学习路线(2026最新版)
java·后端·java面试·java架构师·java程序员·java八股文·java学习路线
陈随易6 小时前
Redis 8.8发布,一定要更新
前端·后端·程序员
装不满的克莱因瓶7 小时前
SpringBoot 如何将 lib 目录中jar包打包进最终的jar包里面
spring boot·后端·maven·jar·mvn
ltl7 小时前
Transformer 原论文实验结果:为什么 28.4 BLEU 足以改写路线图
后端
excel8 小时前
为什么我推荐使用 Termius:现代 SSH 工具的完整体验
前端·后端
卷毛的技术笔记8 小时前
Java后端硬核实战:用Spring AI Alibaba+Redis给LLM装上“超强记忆中枢”
java·人工智能·redis·后端·spring·ai·系统架构
IT_陈寒9 小时前
Java的Optional差点让我掉坑里,这几个坑你别踩
前端·人工智能·后端
子兮曰10 小时前
Harness 驾驭工程深度教程:从 AGENTS.md 到全链路 AI 编码基础设施
前端·后端·ai编程