本系列文章从此篇起开始逐渐移到MySQL优化这个主题上来。
因为本博主要走开源路线,况且MySQL等开源数据库都是在 *nix 上跑的比较好,一方面MySQL本身是开源系统,同出一脉,自然在 *nix 上运行会比较稳妥。另一方面,牵涉到底层的话,可以引申出很多话题来说明,为什么MySQL在基于*nix的系统上运行的如此出色,这一点有待以后更好的研究。
这里推荐一下某大神的技术博客, 何登成的技术博客, 里面好多底层分析。
MySQL通用调优
安装与日志
MySQL的安装,这里主要讨论编译安装,列出一些有助于管理的参数:
--prefix 安装路径
--datadir 数据库实体文件路径
--with-charset 设定默认字符集
--with-collation 默认校验规则
--with-extra-charsets 其他字符集,本博习惯complex,意思是不能动态加载的所有字符集
--with-unix-socket-path unix 的socket 路径,本博不用这个配置,不过很多人用,留着吧
--with-mysqld-user mysqld 守护进程的运行账户,一般单独配个系统账户
--with-partition MySQL分区支持
--without-debug 去除Debug模式,production 服务器还是关一下
--with-mysqld-ldflags mysqld的其他link参数, 设定为 -all-static , 跟下面那个参数一样,据说提高 5% - 10%
--with-client-ldflags 客户端的其他link参数
--with-innodb 支持innodb
--without-embedded-server 内建服务器, 关闭
--enable-thread-safe-client 线程安全客户端支持
--enable-assembler 允许使用汇编模式
--enable-profiling 打开profiling,查看性能的
--with-big-tables 支持大表,32位的系统也能支持4G的Rows
以上是本博经常用的参数,基本够用,有时候根据需求可以自己调节。
配置调优
MySQL配置调优中,列出本博的配置和参数
open_files_limit = 10240 打开文件限制,配合 lsof 可以计算出这个值
back_log = 600 要求MySQL 能有的连接数量
max_connections = 5000 最大连接用户数
max_connect_errors = 10 错误连接次数,安全配置参数
external-locking = FALSE 多服务器下开启,单服务器关闭
max_allowed_packet = 32M 数据包限制,稍微放大点
default-storage-engine = MyISAM
thread_stack = 192K 线程分配的最大内存
transaction_isolation = READ-COMMITTED 事务隔离级别
tmp_table_size = 246M 内存表大小
max_heap_table_size = 246M 内存表堆大小, 这2个参数可以通过官方提供的公式计算得出
MySQL的配置中,对于不同数据库引擎,也有不同的配置
MyISAM
myisam_sort_buffer_size = 128M
myisam_max_sort_file_size = 10G
myisam_repair_threads = 1
myisam_recover
myisam 的各类优化,看名字就略知一二,具体参考手册
InnoDB
innodb_additional_mem_pool_size = 16M
innodb_buffer_pool_size = 512M
innodb_data_file_path = ibdata1:256M:autoextend
innodb_file_io_threads = 4 文件读写IO数,linux 一直是4, win上起作用
innodb_thread_concurrency = 8 可以设置为CPU个数
innodb_flush_log_at_trx_commit = 2
innodb_log_buffer_size = 16M
innodb_log_file_size = 128M
innodb_log_files_in_group = 3
innodb_max_dirty_pages_pct = 90
innodb_lock_wait_timeout = 120
innodb_file_per_table = 0
Cache
query_cache_size = 512M
query_cache_limit = 2M
query_cache_min_res_unit = 2k
table_cache = 614
sort_buffer_size = 1M
join_buffer_size = 1M
thread_cache_size = 300
key_buffer_size = 256M
read_buffer_size = 1M
read_rnd_buffer_size = 16M
bulk_insert_buffer_size = 64M
以上是cache 的优化
日志配置
log-bin = /dir
binlog_cache_size = 4M
binlog_format = MIXED
max_binlog_cache_size = 8M
max_binlog_size = 1G
relay-log-index = /dir
relay-log-info-file = /dir
relay-log = /dir
expire_logs_days = 30
slow_query_log=1
slow_query_log_file = /dir
long_query_time = 3
日志部分 开启binlog, relay log 和slow log, 同时设定目录。
以上这些只是博主参照网络上说明,以及个人经验,在需求特定的情况下的一个配置,具体的定制化的配置需要根据需求来做,有几个方法,mysql 本身提供各类情况下的配置,可以做参考, 另外网络上的知识,特别是MySQL官方文档,可以提供更多帮助。
MySQL 并发调优
针对 InnoDB 来说, 可以使用 SHOW INNODB STATUS 来观察并发情况。
InnoDB的并发关键问题是,要计算出 innodb_thread_concurrency 的最优数量,也就是一次能进入内核的数量,因为在实际情况中无法准确设定mysql线程进入内核的数量,因此要利用一些方法,计算出来。
innodb_commit_concurrency 这个参数决定某一时刻能提交的线程数量。
innodb_thread_sleep_delay 线程睡眠微妙数,不能进入内核的线程,会进入睡眠,之后在这个值的睡眠时候后,再次提交,若再不能进入,则进入等待队列,交由服务器管理。
因此InnoDB的并发,需要根据实际情况来调优,本质上,就是进入线程内核的数量。
MySQL配置方面的其他优化
首先,需要理解,优化是由需求决定的,所有找出瓶颈才能更好的调优。
利用工具查看状态
phpmyadmin是php开发中经常被用到的客户端。Web形式,很方便。它可以查看数据库服务器的状态,并给出建议,是个不错的方法。
innodb的文件分割
据说innodb中有一种模式,是把库分成几个文件,提高读取效率。
延迟写入
延迟写入磁盘,虽然可以减少I/O操作,带来性能,同样的,也由副作用,因此在配置的时候还是必须看需求。
innodb的事务日志
InnoDB的 buffer pool 是个很有帮助的东西,直接读取内存,但是当数据改变时,缓存里面是不会修改更新,因此,MySQL会将这些更新,写进事务日志里面,然后通过事务日志来更新磁盘。原因很简单,日志顺序操作磁盘。
以上啰啰嗦嗦了很多,但是还没有很详尽的写出来各类优化配置,等本博写完这一系列后,挑选几个场景,具体说明如何发现瓶颈,如何优化。