JDK8与MySQL环境下SonarQube 7.4安装配置实战指南
有不少朋友私信问我为什么在2024年还在折腾 SonarQube 7.4 这种老版本是不是团队技术栈太落后。其实很多时候不是不想用新版而是环境不允许生产机锁定了 JDK 8数据库早就跑着 MySQL内网又没法随便起 Docker 容器。我在帮某套内部系统做代码质量验收时就切切实实被这套组合绑住过。这篇文章把 Windows 环境下安装 SonarQube 7.4 sonar-scanner-cli 的全过程、配置细节和踩坑经验完整写出来给同样被困在老旧技术栈里的同学一份可以直接抄作业的参考。SonarQube 7.4 对 JDK8 和 MySQL 的支持非常成熟7.9 之后的版本开始转向 JDK11同时也逐步放弃 MySQL 支持如果你项目里跑的还是大量 JDK8 时代的老工程用 7.4 反而是最省心的选择。1. 为什么还要选 SonarQube 7.4版本兼容性的现实逻辑1.1 版本升级带来的三个硬门槛很多人装新版 SonarQube 会忽略一个关键点升级不只是换个压缩包解压而是会连带动好几个依赖。SonarQube 自身的 Web 服务和内置 Elasticsearch 都是 Java 进程对 JDK 版本有严格要求。从 7.9 开始官方要求 JDK11从 8.x 的某些版本开始JDK 版本要求更高同时数据库支持列表里逐渐把 MySQL 移除。反过来说SonarQube 7.4 当时同时支持 JDK8 和 MySQL而且运行非常稳定。既然你的服务器只肯装 JDK8数据库也定死是 MySQL 5.7那 7.4 就是那个时代最合理的选择。还有个现实因素很多旧项目的构建脚本、持续集成流水线都是按 JDK8 环境写的你硬换新 SonarQube 就得把整个链路全部升级问题从装一个工具变成升级一套体系。1.2 这套组合适合什么场景如果你接触的是下面这类环境SonarQube 7.4 值得用生产环境强制使用 JDK8且短期内没有任何升级计划数据库已经有 MySQL 5.7 在跑不想额外引入 PostgreSQL 等新组件内网隔离无法使用 Docker 镜像只能离线下载安装包项目以传统 Java Web 工程为主只要求静态代码扫描和基础质量门禁我实战中发现7.4 在 4G 内存的 Windows 服务器上也能跑配置得当不会频繁 OOM。新版 SonarQube 对内存的要求明显更高低配环境跑起来会有点吃力。所以老版本不等于差只是适合特定约束条件。1.3 和 sonar-scanner-cli 的版本搭配思路sonar-scanner-cli 是独立于 SonarQube Server 的扫描器负责在项目机器上分析代码并把结果上传到服务器。版本搭配有一个朴素原则扫描器不要比服务器新太多。我用 7.4 服务器时习惯选择同时期的 sonar-scanner-cli 3.x这样 Web API 的接口字段、token 校验方式都很匹配。后来的 4.x 扫描器也能连 7.4但偶尔会出现某些字段不再被识别的情况。如果你已经在用 7.4 服务器保守一点挑 3.x 版本的扫描器最省心。2. JDK 与 MySQL 的准备细节回填最容易绕路的地方2.1 安装 JDK8 时的三个关键注意点SonarQube 7.4 虽然要求 JDK8但不是说随便装个 JRE 就行。我在多个环境里试过最稳的组合是完整安装 JDK 8 而不是精简版 JRE。因为后续 sonar-scanner-cli 本身也要跑 Java 进程有些启动脚本会去调用 JAVA_HOME 下的工具环境里只有一个 JRE 容易出问题。配置 JAVA_HOME 时建议指向 JDK 的根目录比如JAVA_HOMEC:\Program Files\Java\jdk1.8.0_202 PATH%JAVA_HOME%\bin;%PATH%有一个特别容易忽略的隐患JDK 安装路径不能包含中文和特殊符号如果安装目录是C:\Java\jdk1.8.0_202这种简洁路径会少很多麻烦。Windows 的默认安装路径里带有Program Files空格大部分情况下问题不大但一旦 SonarQube 的 wrapper 脚本解析路径出错你要第一时间怀疑这里。我当时就是在conf/wrapper.conf里直接写死了 java.exe 的绝对路径才绕开空格问题。2.2 MySQL 数据库初始化字符集和授权一步到位SonarQube 需要自己管理数据库里面的表结构初始化和数据迁移都靠启动时自动完成。所以 MySQL 侧只需要提前创建库和账号不需要手动建表。在 MySQL 5.7 环境里执行下面这几条命令CREATE DATABASE sonar DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; CREATE USER sonarlocalhost IDENTIFIED BY sonar_password; GRANT ALL PRIVILEGES ON sonar.* TO sonarlocalhost; FLUSH PRIVILEGES;字符集必须指定 utf8如果遗漏后续 SonarQube 在初始化时可能出现索引长度超限或者中文乱码。排序规则方面utf8_general_ci 在大多数场景下已经够用没必要追求更复杂的排序规则。授权这里直接给了sonar.*的 ALL 权限这是为了初始化表格时不被权限卡住。线下测试环境可以这样生产环境如果安全要求高可以再收窄到建表、增删改查等具体权限但初始化阶段可能会有坑。MySQL 8 在写这篇的时候已经被大量使用但那不是 SonarQube 7.4 的友好伙伴。7.4 自带的 MySQL JDBC 驱动比较旧连接 MySQL 8 时经常报认证插件错误如果你只有 MySQL 8 可用一个勉强可行的办法是在连接串上追加allowPublicKeyRetrievaltrue但我不推荐在 7.4 上硬撑 MySQL 8直接把数据库降回 5.7 或者换用 Docker 版 MySQL 5.7 会稳定得多。2.3 防火墙和端口规划Windows 自带防火墙可能会导致局域网内其他机器访问不了 SonarQube 平台。SonarQube 默认端口是 9000Elasticsearch 节点间通信用 9001。如果你只是本机扫描不用关心这些但团队协作扫描其他同事的机器也要访问你的平台就要在防火墙里放行 9000 端口。我建议在一开始就规划好端口。常见的冲突是 9000 端口被其他 Java Web 项目占用如果那样可以改sonar.web.port19000等任意端口同时在扫描器配置里同步修改 sonar.host.url。改端口这件事本身不复杂但很容易忘了改扫描器导致已经装好的平台用不了。3. 解压部署与 sonar.properties 配置一次讲完数据库、端口和内存3.1 下载解压与目录结构的理解SonarQube 7.4 的发行包是一个 zip 压缩包名字类似sonarqube-7.4.zip。解压之后你会看到几个核心目录binWindows 和 Linux 的启动脚本confSonarQube 主配置目录lib各类 Jar 包和 JDBC 驱动logs运行日志目录web内置 Web 服务器资源elasticsearch内置的 Elasticsearch解压路径尽量避免带空格和中文比如D:\sonarqube\sonarqube-7.4就很合适。千万不要图省事直接解压在桌面路径里的空格和中文会导致 Elasticsearch 启动失败而且报错信息很隐晦。3.2 sonar.properties 里真正需要改的四项配置打开conf\sonar.properties你不需要把所有配置都看懂但以下四项必须按环境改第一是数据库连接。找到被注释掉的sonar.jdbc.url和sonar.jdbc.username、sonar.jdbc.password改成下面这样sonar.jdbc.usernamesonar sonar.jdbc.passwordsonar_password sonar.jdbc.urljdbc:mysql://localhost:3306/sonar?useUnicodetruecharacterEncodingutf8useSSLfalseautoReconnecttrue这里characterEncodingutf8明确指定编码避免中文项目名和注释出现乱码。useSSLfalse是本地环境省去证书验证如果你网络环境强制要求 SSL这行要调整。第二是 Web 端口sonar.web.port9000如果 9000 被占用这里改成别的端口。要注意改端口时必须同步扫描器配置这是我前面强调过的点。第三是 Web 登录账号在外部认证相关配置7.4 版本默认用内置账号即可先把/etc/sonar.properties里的基础配置改好登录方式后面再说。第四是访问上下文路径。如果你不打算把 SonarQube 放在 Nginx 子路径下保持默认即可不要随便设置sonar.web.context。一旦设置了这个值整个访问路径都会变化扫描器上传地址也要跟着变初学者很容易在这里绕晕。3.3 内存配置别让 Elasticsearch 吃光服务器内存SonarQube 7.4 会同时启动两个 Java 进程一个是 Web 服务器一个是内置 Elasticsearch。如果你机器内存只有 4G默认配置下很容易出现内存不足表现就是 Web 界面打不开或者启动日志里写 OOM。Web 侧的内存配置在conf\wrapper.conf里找wrapper.java.maxmemory建议在 4G 总内存环境下设置为 1024 或 1536。Elasticsearch 侧的内存配置在elasticsearch\config\jvm.options里把-Xms和-Xmx都设为 1g 或 1.5g。两个进程加起来控制在 2.5G 以内Windows 系统本身和 MySQL 才有余量。我之前有台测试服务器一共 4G 内存一开始没管默认配置结果 SonarQube 启动后系统直接卡到几十秒才响应一次。调完内存之后就好了这个环节千万别跳过。3.4 安装为 Windows 服务的方式命令行启动适合调试但要长期运行最好注册为 Windows 服务。进入bin\windows-x86-64目录用管理员身份打开命令行执行InstallNTService.bat安装成功后在 Windows 服务列表里能看到对应服务。启动 SonarQube 时直接启动这个服务关机重启后也会自动运行。卸载服务时执行UninstallNTService.bat。这里有一个经验先直接启动一次确认配置没问题再装成服务否则服务启动失败时排查窗口一闪而过反而更难定位。4. 第一次启动与 Web 界面验证从日志倒逼问题定位4.1 启动脚本的正确打开方式在bin\windows-x86-64目录下双击StartSonar.bat首次启动时你可能会看到大量日志刷屏这是正常的。SonarQube 第一次启动要做数据库初始化、创建表结构、加载内置插件耗时可能比后续启动更久。如果窗口一闪而过说明启动脚本在加载阶段就失败了。这时不要重复双击直接去logs目录下看日志。7.4 版本会生成sonar.log、web.log、ce.log、es.log等文件。其中es.log记录 Elasticsearch 启动情况web.log记录 Web 服务初始化情况sonar.log是整体运行的主日志。4.2 首次访问与默认账号处理启动完成后浏览器访问http://localhost:9000。如果页面能打开说明 Web 服务本身没问题。默认账号是admin/admin登录后系统会提示你修改默认密码。这一步一定要做。SonarQube 默认口令在安全扫描工具里属于高危项如果放到公网内网不进行加固分分钟被内部安全测试扫出来。改密码之后后续生成扫描 token 也更安全。4.3 Web 界面能打开但登录后数据为空这种情况经常出现在sonar.jdbc.url配置错误但 Web 服务还能启动的场景。SonarQube 连接数据库失败不会导致 Web 进程崩溃而是让你看到一个没有项目、没有历史记录的空白界面。排查方法是看logs\sonar.log里有没有数据库连接异常同时用命令行简单测试一下 MySQL 连接。我第一次搭的时候就是因为 MySQL 授权写成了sonar%但 JDBC 连接串用的是 localhost实际匹配不上登录进去一片空白。把授权改成sonarlocalhost之后立即好了。5. sonar-scanner-cli 的下载、配置与一次完整项目扫描5.1 扫描器安装与环境变量sonar-scanner-cli 是独立的命令行扫描器下载解压后同样建议放到无空格路径。以 3.x 版本为例解压后目录包含bin、conf等目录。把bin目录加入 PATH命令行里就能直接执行sonar-scanner。Windows 下确认执行sonar-scanner -h如果提示找不到命令检查JAVA_HOME和 PATH 是否配置正确。扫描器也是 Java 程序没有正确的 Java 环境就跑不起来。5.2 扫描器与服务器的连接配置扫描器连接服务器的地址配置在conf\sonar-scanner.propertiessonar.host.urlhttp://127.0.0.1:9000 sonar.sourceEncodingUTF-8127.0.0.1写死成 localhost 也行。如果 SonarQube 服务器不是本机把 IP 换成服务器地址。sonar.sourceEncodingUTF-8很重要项目里有中文注释和中文文件名时不指定编码扫描结果会出现大量乱码问题。5.3 创建 token 代替密码登录在 SonarQube Web 界面右上角点击用户头像进入我的账号可以生成一个 token。扫描器执行上传时用 token 比用账号密码更安全而且 token 失效也能单独吊销。使用 token 有两种方式一种是在sonar-scanner.properties里配置sonar.login你的token另一种是在命令行里通过-Dsonar.login你的token传入。我建议在本地调试用命令行传入避免 token 泄露到公共配置仓库。5.4 扫描一个最简单的 Java 项目假设你项目目录是D:\demo\order-service结构大概是这样D:\demo\order-service ├── pom.xml ├── sonar-project.properties └── src └── main └── java └── com └── demo └── OrderService.java在项目根目录新建sonar-project.propertiessonar.projectKeyorder-service sonar.projectName订单服务 sonar.projectVersion1.0 sonar.sourcessrc sonar.java.binariestarget/classes sonar.sourceEncodingUTF-8这里sonar.projectKey是整个 SonarQube 平台里的唯一标识sonar.java.binaries指向编译后的 class 文件目录。因为 sonar-scanner 不是 Maven 插件它无法自己完成 Java 编译所以扫描前要先构建项目。我习惯先执行mvn clean compile然后再执行sonar-scanner扫描完成后命令行会返回结果Web 界面里刷新就能看到订单服务这个项目包含代码异味、bug、重复代码、安全漏洞等指标。如果分析报告里看不到问题先检查sonar.sourcessrc是否写对。很多人默认写成sonar.sources.结果把 target 目录也扫进去反而出现大量没意义的报告内容。扫描路径精确到源码目录报告才会干净。6. 安装过程中的真实坑位清单从日志反推故障6.1 端口冲突导致的 Elasticsearch 启动失败SonarQube 的 Elasticsearch 除了自身占用 9001 端口还会占用一些额外端口。最常见的报错是BindException或Address already in use在es.log里能看到。解决方法很简单查一下是哪个进程占用了端口然后要么杀掉冲突进程要么改掉 SonarQube 的 Web 端口。如果你只想临时启动一次检查配置也可以先把其他 web 服务停掉。6.2 MySQL 连接失败时的典型日志特征假设sonar.jdbc.url写错或者账号密码不对sonar.log会出现类似Cannot connect to database的提示。遇到这种情况先不要急着改数据库账号把下面几项逐项检查MySQL 是否真的启动成功账号密码里是否有特殊字符需要转义数据库字符集是否为 utf8连接串里的库名是否和CREATE DATABASE sonar完全一致有一次我排查了一个多小时最后发现是密码里包含符号在 properties 文件里没有做转义连接串被解析错了。所以这种老版本工具密码还是用纯字母数字组合最省心。6.3 扫描器上传失败与 token 权限问题扫描器执行到最后弹出Not authorized之类的错误通常不是扫描器问题而是 token 没有访问权限。7.4 版本里如果你用全局管理员账号生成的 token扫描完会自动创建项目。如果你用的是普通用户 token可能需要先在 Web 界面里手动创建项目。最简单的调试方式是先用管理员账号生成一个 token放到sonar.login里跑一遍通了之后再按实际权限收敛。6.4 系统内存不足导致的启动卡死如果启动日志里出现native memory allocation failed或者进程非常卡顿基本就是内存分配不合理。前面提到过把 Web JVM 和 Elasticsearch 的堆内存都调到一个保守值不要贪心。有同学觉得服务器有 16G 内存就大胆给 Elasticsearch 分配 8G结果 Windows 预留内存和其他进程叠加一样不稳定。6.5 中文乱码和编码不一致代码里的中文注释、中文项目名只要 SonarQube 服务器端数据库字符集是 utf8扫描器端也默认 UTF-8一般不会乱码。如果出现乱码修改sonar-scanner.properties里的sonar.sourceEncodingUTF-8然后重新扫描。以前老项目如果是 GBK 编码就相应改成GBK关键是要和源码实际编码一致。6.6 日志文件就是你最好的排错手册遇到问题先别到处问我总结了一个快速定位思路先看logs\sonar.log有没有明显的错误堆栈再看logs\es.log确认 Elasticsearch 是否启动成功接着看logs\web.log确认 Web 容器是否完成初始化。很多时候问题都集中在数据库连接或者内存分配日志里都会明确写出来。把完整堆栈贴到搜索引擎搜索比你重新装一遍快得多。7. 装机之后的日常维护与几条真心建议SonarQube 7.4 跑起来之后不是放着不管就行。它的数据全部存在 MySQL 里所以数据库备份是第一优先级。我通常会写一个简单的计划任务定期执行 MySQL 的mysqldump备份备份到独立磁盘。不要只盯着 SonarQube 本身的目录备份那些配置文件和一个重装包没有太大区别真正有价值的质量报告历史数据全在数据库里。内存观察也重要。SonarQube 长时间运行后Web 进程的内存使用会缓慢上升这属于正常现象。但如果有一天发现页面响应极慢优先看服务器可用内存和logs目录是否被日志文件撑爆。日志文件不清理磁盘满了之后扫描任务会莫名其妙失败。关于版本升级如果以后环境允许从 7.4 跳到新版时要先检查 JDK 和数据库兼容性不要直接在原目录上覆盖解压。旧版本的配置目录结构和新版差异很大直接覆盖等于把脏配置带到了新环境。我建议先用一台测试机从零部署新版把插件、扫描器都验证通过再考虑替换生产环境。最后分享一个个人习惯每次安装完 SonarQube 平台我都会把下载的 zip 包、JDK 版本、MySQL 版本、扫描器版本完整记录在一个备忘文档里。这类老版本工具对环境非常敏感隔几个月再回头看光靠记忆很难还原当时的组合。把版本钉死后续无论排查问题还是复现环境都会快很多。如果你现在正在为了 JDK8 和 MySQL 的环境折腾 SonarQube 7.4别急着放弃。这套组合跑熟之后非常稳定而且项目质量数据沉淀下来之后对团队带来的价值远比工具本身大。按上面这些步骤走一遍基本都能顺利跑起来。