目录
一、前置知识点:MySQL 逻辑架构解析
(一)客户端和连接服务层(最上层)
(二)核心服务层(第二层)
(三)存储引擎层
(四)数据存储层
二、案例实验环境
(一)环境搭建
(二)所需资源
三、案例需求
(一)MySQL 常见故障解决
(二)MySQL 性能优化
四、案例实现思路
(一)单库常见故障分析
(二)主从常见故障分析
(三)MySQL 优化
五、案例实施
(一)MySQL 单实例故障排查
1. 故障现象 1:无法连接到数据库,提示 “Can't connect to local MySQL server through socket '/data/mysql/mysql.sock'”
2. 故障现象 2:ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: NO)
3. 故障现象 3:远程连接数据库偶尔很慢
4. 故障现象 4:Can't open file: 'xxx_forums.MYI'.(errno: 145)
5. 故障现象 5:ERROR 1129 (HY000): Host 'xxx.xx.xxx.xxx' is blocked because of many connection errors; unblock with 'mysqladmin flush-hosts'
6. 故障现象 6:客户端报 Too many connections
7. 故障现象 7:Warning: World-writable config file '/etc/my.cnf' is ignored ERROR! MySQL is running but PID file could not be found
8. 故障现象 8:InnoDB: Error: page 14178 log sequence number 29455369832 InnoDB: is in the future! Current system log sequence number 29455369832
(二)MySQL 主从故障排查
1. 故障现象 1:从库的 Slave_IO_Running 为 NO,提示主库和从库的 server-id 值一样
2. 故障现象 2:从库的 Slave_IO_Running 为 NO,状态码报错如 1007、1032、1062、1452 等
3. 故障现象 3:Error initializing relay log position: I/O error reading the header from the binary log
(三)MySQL 优化
1. 硬件方面
2. 配置参数优化
3. SQL 方面
六、示例配置片段(my.cnf)
七、MySQL 性能优化总结
(一)三层优化体系协同
(二)动态平衡原则
八、故障排查实战建议
(一)单实例故障快速定位流程
(二)主从复制故障排查步骤
(三)优化效果验证方法
九、生产环境最佳实践
(一)日常运维规范
(二)高可用架构设计
MySQL 的逻辑架构可划分为多个层次,各层次协同工作以实现数据库的功能。
掌握单库和主从架构下的常见故障现象、分析方法和解决措施,能够快速定位和解决数据库故障,确保数据库的正常运行。
从硬件、配置参数、SQL 语句等方面对 MySQL 进行优化,提升数据库的性能,满足高性能网站架构的需求。
对单实例数据库中可能出现的故障进行分析,包括数据库启动问题、连接问题、表损坏问题、权限问题等,总结故障现象、原因和解决方法。
分析主从架构下的常见故障,如主从同步失败、数据不一致、从库连接问题等,了解故障产生的原因,掌握相应的排查和解决方法。
从硬件选择、配置参数调整、SQL 语句优化等多个方面入手,对 MySQL 进行全面优化,提高数据库的性能和稳定性。
1. 故障现象 1:无法连接到数据库,提示 “Can't connect to local MySQL server through socket '/data/mysql/mysql.sock'”
2. 故障现象 2:ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: NO)
skip-grant-tables=on
,重启数据库,跳过权限验证。mysql> update mysql.user set authentication_string=password('新密码') where user='root' and Host='localhost';
mysql> flush privileges;
mysql> UPDATE mysql.user SET authentication_string='' WHERE user='root' AND Host='localhost';
mysql> FLUSH PRIVILEGES;
mysql> ALTER USER 'root'@'localhost' IDENTIFIED BY '新密码';
skip-grant-tables
参数,重启数据库,使用新密码登录。mysql> grant all on *.* to 'root'@'mysql-server' identified by '新密码';
mysql> CREATE USER 'root'@'mysql-server' IDENTIFIED BY '新密码';
mysql> GRANT all ON *.* TO 'root'@'mysql-server';
3. 故障现象 3:远程连接数据库偶尔很慢
skip-name-resolve
,禁止 DNS 解析,重启数据库。注意以后授权不能使用主机名授权,需使用 IP 地址授权。4. 故障现象 4:Can't open file: 'xxx_forums.MYI'.(errno: 145)
myisamchk -r 数据文件目录/数据表名.MYI
chown
和chmod
命令修改文件属组和权限。5. 故障现象 5:ERROR 1129 (HY000): Host 'xxx.xx.xxx.xxx' is blocked because of many connection errors; unblock with 'mysqladmin flush-hosts'
mysqladmin -uroot -p -h 服务器IP flush-hosts
max_connect_errors=100
,然后重启 MySQL。6. 故障现象 6:客户端报 Too many connections
max_connections=10000
,重启 MySQL 服务。set GLOBAL max_connections=10000;
7. 故障现象 7:Warning: World-writable config file '/etc/my.cnf' is ignored ERROR! MySQL is running but PID file could not be found
chmod 644 /etc/my.cnf
。8. 故障现象 8:InnoDB: Error: page 14178 log sequence number 29455369832 InnoDB: is in the future! Current system log sequence number 29455369832
innodb_force_recovery=4
,启动数据库后备份数据文件。1. 故障现象 1:从库的 Slave_IO_Running 为 NO,提示主库和从库的 server-id 值一样
2. 故障现象 2:从库的 Slave_IO_Running 为 NO,状态码报错如 1007、1032、1062、1452 等
mysql> stop slave;
mysql> set GLOBAL SQL_SLAVE_SKIP_COUNTER=1;
mysql> start slave;
set global read_only=true;
3. 故障现象 3:Error initializing relay log position: I/O error reading the header from the binary log
mysql> CHANGE MASTER TO MASTER_LOG_FILE='mysql-bin.xxx', MASTER_LOG_POS=xxx;
1. 硬件方面
2. 配置参数优化
3. SQL 方面
CREATE DATABASE test;
USE test;
CREATE TABLE users(
id INT PRIMARY KEY AUTO_INCREMENT,
name VARCHAR(50) NOT NULL,
email VARCHAR(100) NOT NULL,
age INT NOT NULL,
created_at DATETIME DEFAULT CURRENT_TIMESTAMP
);
DELIMITER $$
CREATE PROCEDURE insert_users()
BEGIN
DECLARE i INT DEFAULT 0;
WHILE i<100000 DO
INSERT INTO users (name, email, age)
VALUES (CONCAT('user', i), CONCAT('user', i, '@example.com'), FLOOR(RAND()*100));
SET i=i+1;
END WHILE;
END$$
DELIMITER ;
CALL insert_users();
mysql> EXPLAIN SELECT * FROM users WHERE name='user123';
mysql> ALTER TABLE users ADD INDEX idx_name (name);
mysql> EXPLAIN SELECT * FROM users WHERE name='user123';
以下是一个针对 32 核 CPU、64G 内存、500G SSD 的生产环境示例配置,包含硬件适配、缓冲池优化、日志管理及 InnoDB 高级参数:
[mysqld]
# 核心配置 - 硬件适配
innodb_buffer_pool_size = 40G # 占用60%内存,缓存数据与索引
innodb_log_file_size = 2G # 日志文件大小,提升事务提交性能
innodb_flush_log_at_trx_commit = 2 # 高并发场景折中策略,每秒刷盘
max_connections = 1000 # 最大连接数,配合thread_cache_size=100
thread_cache_size = 100 # 缓存100个空闲线程,减少线程创建开销
# 查询优化 - 内存管理
tmp_table_size = 128M # 内存临时表上限,与max_heap_table_size一致
max_heap_table_size = 128M # 内存哈希表上限,避免磁盘临时表
sort_buffer_size = 4M # 单线程排序缓冲区(适用于中等数据集)
join_buffer_size = 8M # 无索引JOIN的缓冲区(根据表大小调整)
# 日志与监控 - 故障排查
slow_query_log = ON # 启用慢查询日志,记录执行超过阈值的SQL
long_query_time = 1 # 慢查询阈值设为1秒,敏感业务可降至0.5
log_error = /var/log/mysql/error.log # 错误日志路径,建议独立磁盘分区
binlog_format = ROW # 主从复制推荐ROW格式,数据一致性更高
expire_logs_days = 7 # 自动清理7天前的二进制日志,节省磁盘空间
# InnoDB高级优化 - SSD场景
innodb_io_capacity = 2000 # SSD磁盘IOPS预估,适配硬件性能
innodb_flush_method = O_DIRECT # 直接读写磁盘,绕过操作系统缓存
innodb_thread_concurrency = 0 # 自适应并发线程数,充分利用32核CPU
innodb_autoinc_lock_mode = 2 # 高并发插入模式,提升自增主键性能
硬件层(基础支撑)
innodb_buffer_pool_size
)以缓存更多数据,建议占物理内存 60%-80%,减少磁盘 I/O。innodb_io_capacity=2000
等参数提升 IOPS;分离数据文件与日志文件到独立磁盘,降低 I/O 竞争。配置层(资源调度)
max_connections
限制并发连接数,配合thread_cache_size
缓存线程,避免频繁创建线程消耗资源。innodb_log_file_size
平衡事务提交速度与恢复时间;根据业务特性选择innodb_flush_log_at_trx_commit
(如金融场景用 1,日志非敏感场景用 2)。tmp_table_size
过小导致磁盘临时表,或过大导致内存溢出;为排序、JOIN 等操作分配合理缓冲区(sort_buffer_size
、join_buffer_size
)。SQL 层(效率核心)
idx_name
),避免全表扫描(type=ALL
);使用复合索引(如(user_id, created_at)
)优化多条件查询。SELECT *
,仅查询必要字段;避免在WHERE
子句中对字段做函数运算(如DATE(created_at)
),防止索引失效。EXPLAIN
确认索引命中情况(key
字段),优化rows
预估行数至最小,消除Using temporary
/Using filesort
等额外开销。innodb_buffer_pool_size
并增大swap
空间临时过渡,但长期需升级硬件。innodb_read_io_threads
提升读性能;秒杀场景需调优innodb_lock_wait_timeout
避免锁竞争。连接类故障(优先排查)
systemctl status mysql # Linux系统
net start mysql # Windows系统
telnet 127.0.0.1 3306 # 本地连接测试
nmap -p 3306 服务器IP # 远程端口扫描
log_error
路径): tail -f /var/log/mysql/error.log
权限与安全故障
skip-grant-tables
后重启),避免未授权访问。%
(如'root'@'192.168.1.%'
),减少安全风险;生产环境禁止使用GRANT ALL
,按需分配权限(如SELECT, INSERT ON db.table
)。表损坏与数据恢复
# 备份后修复
myisamchk -r /var/lib/mysql/数据库名/表名.MYI
innodb_force_recovery=4
启动数据库并导出数据,恢复后需重建表结构。mysqldump
或物理备份(如 Percona XtraBackup)预防数据丢失。基础连通性检查
SHOW MASTER STATUS; # 确认二进制日志已启用,记录File和Position
CHANGE MASTER TO
MASTER_HOST='主库IP',
MASTER_USER='复制用户',
MASTER_PASSWORD='密码',
MASTER_LOG_FILE='mysql-bin.000001',
MASTER_LOG_POS=100;
START SLAVE;
SHOW SLAVE STATUS\G # 重点查看Slave_IO_Running和Slave_SQL_Running是否为Yes
常见同步问题处理
my.cnf
中的server-id=2
(主库默认 1),重启后重新同步。# 停止从库,删除损坏的中继日志
STOP SLAVE;
RESET SLAVE; # 谨慎操作,会清空所有中继日志
# 重新指定主库日志位置
CHANGE MASTER TO MASTER_LOG_FILE='新的binlog文件', MASTER_LOG_POS=新位置;
START SLAVE;
FLUSH TABLES WITH READ LOCK; # 锁定主库表
mysqldump -h 主库IP -u root -p 数据库名 > full_backup.sql
UNLOCK TABLES; # 解锁
STOP SLAVE;
RESET SLAVE ALL;
# 导入备份后重新配置主从
CHANGE MASTER TO ...;
START SLAVE;
性能指标监控
SHOW GLOBAL STATUS LIKE 'Threads_connected'; # 当前连接数
SHOW GLOBAL STATUS LIKE 'Slow_queries'; # 慢查询总数
SHOW GLOBAL STATUS LIKE 'Innodb_buffer_pool_hit_rate'; # 缓冲池命中率(理想值>95%)
iostat -x 5 # 磁盘I/O监控(重点关注%util是否接近100%)
vmstat 5 # 内存与CPU负载监控
慢查询分析
mysqldumpslow -s t -t 10 /var/log/mysql/slow.log # 按执行时间排序,取前10条
pt-query-digest /var/log/mysql/slow.log > slow_analysis.txt
Rows_examined
(扫描行数)、Query_time
(执行时间)、未使用索引的查询(rows_examined > rows_sent
)。压力测试验证
# 安装sysbench
apt-get install sysbench # Ubuntu/Debian
# 测试100张表,每张表100万条数据
sysbench oltp_read_write --tables=100 --table-size=1e6 prepare
# 启动100个线程压测300秒
sysbench oltp_read_write --threads=100 --time=300 run
定期备份策略
mysqldump --single-transaction
(InnoDB)或物理备份工具(如 Percona XtraBackup)。binlog
)实现,备份命令: bash
mysqlbinlog --start-datetime="2025-05-19 00:00:00" --stop-datetime="2025-05-20 00:00:00" /var/log/mysql/mysql-bin.* > incremental_backup.sql
监控报警体系
max_connections*80%
时报警。df -h
)。版本与补丁管理
主从 + 读写分离
INSERT INTO mysql_servers (hostgroup_id, hostname, port, weight)
VALUES (1, '主库IP', 3306, 100); # 写节点(hostgroup_id=1)
INSERT INTO mysql_servers (hostgroup_id, hostname, port, weight)
VALUES (2, '从库IP1', 3306, 50), (2, '从库IP2', 3306, 50); # 读节点(hostgroup_id=2)
故障切换机制
# 主库配置
vi /etc/mha/master.cnf
[server default]
master_host=主库IP
master_user=mha_user
master_password=密码
# 从库配置
vi /etc/mha/slave1.cnf
[server]
hostname=从库IP1
# 启动MHA管理节点
masterha_manager --conf=/etc/mha/master.cnf
分布式架构扩展
// Sharding-JDBC配置
sharding-sphere.sharding.tables.users.actual-data-nodes=ds$->{0..1}.users$->{0..1}
sharding-sphere.sharding.tables.users.table-strategy.inline.sharding-column=user_id
sharding-sphere.sharding.tables.users.table-strategy.inline.algorithm-expression=users$->{user_id % 2}