加油
努力

Tomcat搭配MySQL部署在2核2G的服务器上,推荐什么配置优化?

在 2 核 2G(双核 CPU,2GB 内存)的服务器上同时运行 Tomcat 和 MySQL,资源非常紧张。这种配置下,核心策略是“极致压缩内存占用”和“限制并发”,否则极易触发 Linux 的 OOM Killer(内存溢出杀手),导致服务频繁崩溃。

以下是针对该硬件配置的详细优化方案:

1. 操作系统层面优化(基础)

在调整应用之前,必须先确保系统本身不浪费资源。

  • 关闭 Swap(交换分区)
    • 原因:2G 内存非常宝贵,一旦开启 Swap,MySQL 或 Tomcat 发生轻微内存波动就会触发磁盘交换,导致服务器瞬间卡死(I/O 等待飙升)。
    • 操作:临时关闭 sudo swapoff -a;永久关闭需修改 /etc/fstab 注释掉 swap 行。
  • 清理后台服务
    • 禁用不必要的 systemd 服务(如 NetworkManager, Bluetooth, Avahi 等),只保留网络、SSH 和必要的日志轮转服务。
  • 文件系统挂载参数
    • 如果是 CentOS/Ubuntu,建议将 /tmp 挂载为 tmpfs(内存盘),减少磁盘 I/O。
    • 数据库目录挂载参数可考虑添加 noatime 以减少元数据写入开销。

2. MySQL 优化(重中之重)

MySQL 是内存大户,必须严格限制其最大内存使用量,预留至少 500MB 给 Tomcat 和系统内核。

A. 关键配置文件 (my.cnf) 调整

建议将 innodb_buffer_pool_size 设置为物理内存的 30%~40%(约 600MB-800MB),这是最核心的优化点。

[mysqld]
# 基础设置
port = 3306
basedir = /usr/local/mysql
datadir = /var/lib/mysql
socket = /tmp/mysql.sock
pid-file = /var/run/mysqld/mysqld.pid
user = mysql

# --- 内存核心配置 (关键) ---
# 限制 InnoDB 缓冲池大小,防止吃光内存
innodb_buffer_pool_size = 600M 
# 如果主要是小表查询,可适当调低;如果是大表,尽量接近 700M
innodb_log_file_size = 256M 

# --- 连接与线程 ---
# 限制最大连接数,2G 机器不建议超过 50
max_connections = 50 
thread_cache_size = 10
skip-name-resolve  # 禁用 DNS 解析,提升连接速度并减少网络请求

# --- 日志与性能 ---
# 关闭慢查询日志(生产环境建议开启但限制时间,测试环境可关闭以省 IO)
slow_query_log = 0
long_query_time = 10

# 安全设置
local_infile = 0
symbolic-links = 0

B. 启动参数检查

确保启动脚本中没有额外的 -Xmx-Xms 类似参数(那是 Java 的),MySQL 主要靠 my.cnf 控制。


3. Tomcat 优化

Tomcat 需要足够的堆内存来运行 JVM,同时不能影响 MySQL。建议预留 400MB~500MB 给 Tomcat。

A. JVM 内存参数 (setenv.shcatalina.sh)

不要直接使用默认值,强制指定最小和最大堆内存,避免动态扩容带来的抖动。

# 编辑 $CATALINA_BASE/bin/setenv.sh (如果没有则新建)
export CATALINA_OPTS="-Xms400m -Xmx500m"
# 可选:开启 G1 垃圾回收器,对低内存更友好
export CATALINA_OPTS="$CATALINA_OPTS -XX:+UseG1GC -XX:MaxGCPauseMillis=200"
# 可选:开启 JIT 编译优化
export CATALINA_OPTS="$CATALINA_OPTS -XX:+AggressiveOpts -XX:+UseStringDeduplication"

注意:-Xmx500m 表示最大堆 500MB,加上非堆内存(Metaspace, Thread Stack 等),总占用约为 600-700MB。

B. Tomcat 自身配置 (server.xml)

  • Connector 线程数:默认通常较大,需减小。
    <Connector port="8080" protocol="HTTP/1.1"
               connectionTimeout="20000"
               redirectPort="8443"
               maxThreads="100"      <!-- 降低并发上限 -->
               minSpareThreads="10"
               acceptCount="50"      <!-- 排队队列长度 -->
               />
  • APR/NIO:确保使用 NIO 模式(Tomcat 8+ 默认),避免使用 BIO。

4. 中间件与架构层面的妥协

由于硬件限制,软件架构上必须做减法:

  1. 关闭不必要的功能
    • 如果不需要,关闭 Tomcat 的 AJP 协议(只保留 HTTP)。
    • 关闭 MySQL 的 Query Cache(MySQL 5.7+ 已废弃,8.0 中移除,无需担心)。
  2. 应用层优化
    • JDBC 连接池:将 Druid 或 HikariCP 的最大连接数限制在 10-20 之间,不要设置过大。
    • 静态资源:如果可能,将图片、CSS、JS 等静态资源托管到对象存储(如阿里云 OSS)或 CDN,减轻服务器带宽和 CPU 压力。
  3. 监控与报警
    • 部署轻量级监控(如 Prometheus + Node Exporter,或者简单的 Shell 脚本),监控 free -hdmesg | grep -i kill
    • 一旦内存使用率超过 90%,立即收到告警。

5. 预期效果与风险提示

指标 优化前风险 优化后预期
内存使用 容易爆满,触发 OOM 稳定在 1.6GB 左右,留有余地
并发能力 高并发下直接假死 支持中小流量(QPS 100-300 级别)
稳定性 随机崩溃 长时间运行稳定,无频繁重启

重要提示
2 核 2G 属于入门级/测试级配置。

  • 如果是个人博客、内部管理系统、低频 API,上述配置可以跑通。
  • 如果是电商、高并发业务、复杂报表,此配置存在极大风险。即使优化到极致,遇到突发流量依然会挂。
  • 终极建议:如果预算允许,优先升级内存至 4G,成本增加不多,但稳定性和承载能力会有质的飞跃。如果无法升级,务必做好限流(Nginx 限流)和降级预案。
云服务器