排查数据库插入慢的问题

项目背景

我负责的模块是这个应用的一部分(在服务器A),但数据库(在服务器B,这个应用整体功能也在服务器B上),同库。主要是不影响这个应用的其他业务,而且分库分表维护起来,比较麻烦。

简单说就是我负责的模块,需要对远程服务器上的数据库特定的几张表,进行增删改查操作。

问题

上周还正常,这周一来了,插入删除数据的效率贼慢,能插入,就是时间太长了。

排查思路

  1. 排查服务器之间的网络问题;
  2. 排查数据库是否锁表;
  3. 检查数据库性能;

排查网络问题

检查两台服务器之间的网络是否通畅

检查两台服务器之间的网络是否通畅,可以通过以下步骤进行:

  1. 检查物理连接:
    • 确保两台服务器的网线正确连接到交换机或路由器的可用端口。
    • 检查连接的物理状态,包括插头是否牢固、灯光指示是否正常等。
  1. 验证IP配置:
    • 在两台服务器上分别运行网络配置查看命令(如Linux中的ifconfig或ip addr,Windows中的ipconfig),确保它们的网络接口配置正确。
    • 检查IP地址、子网掩码和网关设置,确保它们在同一子网内,且没有IP地址冲突。
  1. 检查防火墙设置:
    • 检查两台服务器上的防火墙设置,确保它们允许ICMP协议(用于ping命令)和其他必要的网络协议通过。
    • 如果启用了防火墙,可以尝试暂时禁用防火墙进行测试,以排除防火墙导致的网络问题。
  1. 使用ping命令测试连通性:
    • 在一台服务器上使用ping命令(如ping <另一台服务器的IP地址>)来测试与另一台服务器的连通性。
    • 如果能够收到回复,说明两台服务器之间的网络连接是通畅的。
  1. 使用traceroute或tracert命令检查路由:
    • 在一台服务器上使用traceroute(Linux)或tracert(Windows)命令来查看数据包从源服务器到目标服务器的路由路径。
    • 这可以帮助你发现可能存在的网络故障点或延迟较高的节点。
  1. 测试特定端口的连通性:
    • 如果需要测试特定应用层服务的连通性(如数据库、Web服务等),可以使用telnet或nc(netcat)命令来测试目标端口的可达性。
    • 在一台服务器上执行类似telnet <另一台服务器的IP地址> <端口号>的命令,如果连接成功,则说明该端口在两台服务器之间是通畅的。
  1. 检查网络设备和线路:
    • 检查交换机、路由器等网络设备的状态和配置,确保它们正常运行且配置正确。
    • 使用网络线缆测试仪检查网络线路是否损坏或存在其他问题。

通过以上步骤,你应该能够较为全面地检查两台服务器之间的网络连通性。如果仍然存在问题,可能需要进一步深入排查网络配置、硬件故障或外部网络问题。

检查两台服务器之间的网速

  1. 使用ping命令(测试延迟) :
    • 虽然ping命令主要用于测试网络连通性,但通过观察ping命令的响应时间(即延迟),也可以间接了解网络速度。较低的延迟通常意味着较好的网络性能。
  1. 使用traceroute命令(测试传输路径) :
    • traceroute命令可以显示数据包从源服务器到目标服务器所经过的路由路径。通过分析这些路径中的节点和延迟,可以了解网络连接的效率。
  1. 使用iperf3工具(测试带宽) :

iperf3 使用需要关闭防火墙。

iperf3 下载地址

CentOS 下载地址

ruby 复制代码
rpm -ih ftp://ftp.pbone.net/mirror/archive.fedoraproject.org/fedora/linux/updates/24/x86_64/i/iperf3-3.1.3-1.fc24.x86_64.rpm

Windows10 64位下载地址

网盘提取地址

下载到电脑到,并解压后,会得到两个文件:cygwin1.dll 和 iperf3.exe,将这两个文件拷贝到 c:\windows 目录下。

最后打开 cmd,执行 iperf3 --version ,若安装成功,会打印出版本信息。

iperf3 使用方法

在客户端和服务端分别安转 iperf3软件,先启动服务端,再启动客户端。

  • 服务端:收包,使用 -s 参数指定, iperf3 -s

  • 客户端:发包,使用 -c xx.xx.xx.xx 来指定要往哪个服务端发包, iperf3 -c 172.20.20.200

css 复制代码
iperf3 -c 172.20.20.200 -i 2 -u -b 100M -f m -t 4 --get-server-output
  • 第一列 Interval:测试的时长
  • 第二列 Transfer:在 Interval 时长里,传输的数据量
  • 第三列 BandWidth:带宽
  • 第四列 Jitter:网络抖动,连续发送数据包时延差值的平均值,越小说明网络质量越好
  • 第五列 Lost/Total Datagrams:丢失的数据包与发送的总数据包

我们可以看到 传输的数据量,1s 是10M,带宽 是100M/s,网速还是可以的。

排查数据库锁表

在 MySQL 中,你可以使用多种方法来查看表是否被锁定。以下是一些常用的方法:

  1. 使用 ****SHOW OPEN TABLES ****命令 :
    这个命令会显示所有打开的表,其中 In_use 列指示了哪些表正在被使用。
sql 复制代码
SHOW OPEN TABLES WHERE In_use > 0;

如果某个表的 In_use 值大于 0,那么它可能正在被锁定。但是,这并不能确切地告诉你表被哪种锁锁定(例如,读锁或写锁)。

  1. 使用 ****SHOW ENGINE INNODB STATUS ****命令 :

对于使用 InnoDB 存储引擎的表,你可以使用这个命令来获取详细的锁定信息。这个命令的输出包含了很多信息,其中 TRANSACTIONS 部分会显示当前活动的事务和它们持有的锁。

sql 复制代码
SHOW ENGINE INNODB STATUS\G

在输出中,查找 TRANSACTIONS 部分,并查看 LOCK WAIT 或 holding lock 等相关的行。

  1. 使用 ****information_schema ****数据库 :

information_schema 数据库包含了关于 MySQL 服务器元数据的表。你可以查询这些表来获取关于锁的信息。

例如,对于 InnoDB 表,你可以查询 INNODB_LOCKS 和 INNODB_LOCK_WAITS 表来获取锁的信息。

sql 复制代码
SELECT * FROM information_schema.INNODB_LOCKS;  
SELECT * FROM information_schema.INNODB_LOCK_WAITS;
  1. 使用性能模式 :
    如果你的 MySQL 服务器启用了性能模式(Performance Schema),你可以查询 performance_schema 数据库中的表来获取关于锁的信息。

例如,events_statements_history 和 events_waits_history_long 等表可能包含与锁定相关的信息。

  1. 第三方工具 :

除了上述的 SQL 命令外,还有一些第三方工具和图形界面(如 Percona Toolkit、MySQL Workbench 等)可以帮助你更直观地查看和管理 MySQL 的锁。

  1. 检查错误日志 :

如果表被锁定并导致超时或其他错误,这些信息可能会记录在 MySQL 的错误日志中。检查这些日志可能会提供有关锁定问题的线索。

请注意,不同的锁定类型(例如,共享锁、排他锁、元数据锁等)和存储引擎(如 InnoDB、MyISAM 等)可能会影响你如何查看和管理锁定。因此,在解决锁定问题时,了解你的数据库架构和使用的存储引擎是非常重要的。

检查数据库性能

不是网络,不是锁表的问题,那大概率就是数据库性能的问题。

我检查业务逻辑,对几张核心表进行排查了一下,有一张历史表的数据量在20w 左右,随着更长时间的运行,数据量也是越来越大的,而且对关键的id 有索引。

这就是我疑问的所在,就算拿1万条数据,与20万条数据比对,在有索引的情况,性能应该是不错的。

可事实就是贼慢。

分析了下业务逻辑,与业务老师商量,插入历史表这段逻辑,可以屏蔽。性能一下子提升了不少。

MySQL表中插入和删除操作性能低下可能由多种原因引起。对于拥有20万条记录的表来说,性能问题可能并不是特别显著,但如果你感觉性能明显慢于预期,以下是一些可能的原因和相应的解决策略:

  1. 硬件性能:
    • 磁盘I/O:如果磁盘性能不佳(如使用传统的机械硬盘而非SSD),那么插入和删除操作可能会受到磁盘读写速度的限制。
    • CPU和内存:低性能的CPU或不足的内存也可能导致性能问题。
  1. 索引问题:
    • 过多索引:每次插入或删除记录时,相关的索引都需要更新,过多的索引会拖慢这些操作。
    • 缺失索引:对于经常用于搜索、排序或连接的字段,如果没有适当的索引,那么查询性能会受到影响,间接导致插入和删除操作看起来更慢(因为它们可能需要更多的锁定和等待)。
  1. 表类型和设计:
    • MyISAM vs InnoDB:MyISAM通常具有更快的插入和读取性能,但不支持事务和外键;而InnoDB则提供了事务支持、行级锁定等,但在某些情况下可能不如MyISAM快。
    • 表结构:过多的字段或字段类型选择不当也可能影响性能。
  1. 锁定机制:
    • 表锁 vs 行锁:MyISAM使用表锁,而InnoDB使用行锁。在高并发环境下,表锁可能导致性能瓶颈。
    • 死锁:多个事务相互等待对方释放资源,导致死锁,这会严重影响性能。
  1. 数据库配置:
    • 缓冲区大小:如InnoDB的缓冲池大小配置不当,可能导致性能问题。
    • 日志设置:二进制日志、慢查询日志等配置不当也可能影响性能。
  1. 查询优化:
    • 复杂的触发器或外键约束:每次插入或删除记录时,相关的触发器或外键约束都需要执行,如果它们很复杂,会拖慢操作。
    • 大量数据的单次操作:一次性插入或删除大量数据会比分批操作更慢。
  1. 网络延迟:如果你是在远程连接数据库,网络延迟也可能是一个因素。

解决策略:

  • 优化硬件:考虑升级磁盘、CPU或内存。
  • 审查和优化索引:删除不必要的索引,为经常查询的字段添加合适的索引。
  • 选择合适的表类型:基于你的需求选择合适的存储引擎。
  • 优化查询和事务:减少复杂查询和触发器,使用合适的事务隔离级别,避免长时间持有锁。
  • 调整数据库配置:根据硬件和工作负载调整缓冲区大小、日志设置等。
  • 分批处理:对于大量数据的插入或删除操作,考虑分批处理。
  • 监控和分析:使用MySQL的性能监控工具(如SHOW PROFILE, EXPLAIN, Performance Schema等)来分析和定位性能瓶颈。

最后,建议在进行任何优化操作之前备份数据库,并在测试环境中验证优化效果。

好了,以上就是全部内容了,如果对你有帮助,麻烦多多点赞,转发,收藏,就是对我最大的鼓励!

相关推荐
2301_32241428049 小时前
基于SpringBoot+Vue的休闲零食超市管理系统的设计与实现59004-计算机毕设 原创(免费领源码+部署教程+开发环境)
java·vue.js·spring boot·redis·mysql·决策树·推荐算法
金銀銅鐵11 小时前
[Java] 用 GUI 展示 EnumSet 增减元素时的内部变化(上)
java·后端·ai编程
念何架构之路12 小时前
go-grpc设计思想
开发语言·后端·golang
库库的数据库笔记12 小时前
国产信创数据库的MySQL兼容性深度对比解析
大数据·数据库·mysql·oceanbase·政务
system_error_x12 小时前
SpringBoot 集成 Thymeleaf 简洁入门
java·spring boot·后端
步行cgn14 小时前
Spring MVC 视图机制的核心接口与类
java·开发语言·后端·spring·mvc
码事漫谈14 小时前
AI 读你的提示词,其实很没耐心
后端
用户83562907805115 小时前
如何使用 Python 格式化 Excel 单元格中的长文本
后端·python
我命由我1234515 小时前
Python 开发 - Python 的 pathlib
java·开发语言·后端·python·学习·java-ee·学习方法
IT_陈寒15 小时前
Java性能优化完全指南
前端·人工智能·后端