zoukankan      html  css  js  c++  java
  • MySQL之架构性能篇之存储引擎

    官方参考资料:

    https://docs.oracle.com/cd/E17952_01/mysql-8.0-en/storage-engines.html
    https://docs.oracle.com/cd/E17952_01/mysql-5.7-en/storage-engines.html
    

    存储引擎

    MyISAM 引擎特点:

    不支持事务
    表级锁定
    读写相互阻塞,写入不能读,读时不能写
    只缓存索引
    不支持外键约束
    不支持聚簇索引
    读取数据较快,占用资源较少
    不支持MVCC(多版本并发控制机制)高并发
    崩溃恢复性较差
    MySQL5.5.5 前默认的数据库引擎
    

    MyISAM 存储引擎适用场景

    只读(或者写较少)
    表较小(可以接受长时间进行修复操作)
    

    MyISAM 引擎文件

    tbl_name.frm 表格式定义
    tbl_name.MYD 数据文件
    tbl_name.MYI 索引文件
    

    InnoDB 引擎

    InnoDB引擎特点

    行级锁
    支持事务,适合处理大量短期事务
    读写阻塞与事务隔离级别相关
    可缓存数据和索引
    支持聚簇索引
    崩溃恢复性更好
    支持MVCC高并发
    从MySQL5.5后支持全文索引
    从MySQL5.5.5开始为默认的数据库引擎
    

    InnoDB数据库文件

    所有InnoDB表的数据和索引放置于同一个表空间中

    数据文件:ibdata1, ibdata2,存放在datadir定义的目录下
    表格式定义:tb_name.frm,存放在datadir定义的每个数据库对应的目录下
    

    每个表单独使用一个表空间存储表的数据和索引

    两类文件放在对应每个数据库独立目录中
    数据文件(存储数据和索引):tb_name.ibd
    表格式定义:tb_name.frm
    

    启用:innodb_file_per_table=ON (MariaDB 5.5以后版是默认值)
    参看:https://mariadb.com/kb/en/library/xtradbinnodb-server-system-variables/#innodb_file_per_table

    其它存储引擎

    管理存储引擎

    查看mysql支持的存储引擎

    show engines;
    

    查看当前默认的存储引擎

    show variables like '%storage_engine%';
    

    设置默认的存储引擎

    vim /etc/my.cnf
    [mysqld]
    default_storage_engine= InnoDB
    

    查看库中所有表使用的存储引擎

    show table status from db_name;
    

    查看库中指定表的存储引擎

    show table status like 'tb_name';
    show create table tb_name;
    

    设置表的存储引擎:

    CREATE TABLE tb_name(... ) ENGINE=InnoDB;
    ALTER TABLE tb_name ENGINE=InnoDB;
    

    MySQL 中的系统数据库

    mysql 数据库

    是mysql的核心数据库,类似于Sql Server中的master库,主要负责存储数据库的用户、权限设置、关
    键字等mysql自己需要使用的控制和管理信息
    

    information_schema 数据库

    MySQL 5.0之后产生的,一个虚拟数据库,物理上并不存在information_schema数据库类似与"数据字典",提供了访问数据库元数据的方式,即数据的数据。比如数据库名或表名,列类型,访问权限(更加细化的访问方式)
    

    performance_schema 数据库

    MySQL 5.5开始新增的数据库,主要用于收集数据库服务器性能参数,库里表的存储引擎均为PERFORMANCE_SCHEMA,用户不能创建存储引擎为PERFORMANCE_SCHEMA的表
    

    sys 数据库

    MySQL5.7之后新增加的数据库,库中所有数据源来自performance_schema。目标是把performance_schema的把复杂度降低,让DBA能更好的阅读这个库里的内容。让DBA更快的了解
    DataBase的运行情况
    

    服务器配置和状态

    可以通过mysqld选项,服务器系统变量和服务器状态变量进行MySQL的配置和查看状态

    官方帮助:

    https://dev.mysql.com/doc/refman/8.0/en/server-option-variable-reference.html
    https://dev.mysql.com/doc/refman/5.7/en/server-option-variable-reference.html
    https://mariadb.com/kb/en/library/full-list-of-mariadb-options-system-andstatus-variables/
    

    注意:

    其中有些参数支持运行时修改,会立即生效
    有些参数不支持动态修改,且只能通过修改配置文件,并重启服务器程序生效
    有些参数作用域是全局的,为所有会话设置
    有些可以为每个用户提供单独(会话)的设置
    

    服务器选项
    注意: 服务器选项用横线,不用下划线

    获取mysqld的可用选项列表:

    #查看mysqld可用选项列表和及当前值
    mysqld --verbose --help
    #获取mysqld当前启动选项
    mysqld --print-defaults
    

    范例:

    #查看可用选项列表和当前值
    [root@centos8 ~]# /usr/libexec/mysqld --verbose --help
    #查看mysqld的当前启动选项
    [root@centos8 ~]# /usr/libexec/mysqld --print-defaults
    /usr/libexec/mysqld would have been started with the following arguments:
    --plugin-load-add=auth_gssapi.so --datadir=/var/lib/mysql --
    socket=/var/lib/mysql/mysql.sock --log-error=/var/log/mariadb/mariadb.log --pidfile=/
    run/mariadb/mariadb.pid
    

    设置服务器选项方法:

    1. 在命令行中设置
    shell> /usr/bin/mysqld_safe --skip-name-resolve=1
    shell> /usr/libexec/mysqld --basedir=/usr
    

    2.在配置文件my.cnf中设置

    vim /etc/my.cnf
    [mysqld]
    skip_name_resolve=1
    skip-grant-tables
    

    范例: skip-grant-tables是服务器选项,但不是系统变量

    [root@centos8 ~]# mysqladmin variables | grep skip_grant_tables
    [root@centos8 ~]# mysql
    Welcome to the MariaDB monitor. Commands end with ; or g.
    Your MariaDB connection id is 12
    Server version: 10.3.17-MariaDB MariaDB Server
    Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.
    Type 'help;' or 'h' for help. Type 'c' to clear the current input statement.
    MariaDB [(none)]> show variables like 'skip_grant_tables';
    Empty set (0.001 sec)
    

    服务器系统变量

    服务器系统变量:可以分全局和会话两种

    注意: 系统变量用下划线,不用横线

    获取系统变量

    SHOW GLOBAL VARIABLES; #只查看global变量
    SHOW [SESSION] VARIABLES;#查看所有变量(包括global和session)
    #查看指定的系统变量
    SHOW VARIABLES LIKE 'VAR_NAME';
    SELECT @@VAR_NAME;
    #查看选项和部分变量
    [root@centos8 ~]# mysqladmin variables
    

    修改服务器变量的值:

    help SET
    

    修改全局变量:仅对修改后新创建的会话有效;对已经建立的会话无效

    SET GLOBAL system_var_name=value;
    SET @@global.system_var_name=value;
    

    修改会话变量:

    SET [SESSION] system_var_name=value;
    SET @@[session.]system_var_name=value;
    

    范例: character_set_results是系统变量并非服务器选项

    [root@centos8 ~]# mysql
    MariaDB [(none)]> show variables like 'character_set_results';
    +-----------------------+-------+
    | Variable_name | Value |
    +-----------------------+-------+
    | character_set_results | utf8 |
    +-----------------------+-------+
    1 row in set (0.001 sec)
    MariaDB [(none)]> set character_set_results="utf8mb4";
    Query OK, 0 rows affected (0.000 sec)
    
    MariaDB [(none)]> show variables like 'character_set_results';
    +-----------------------+---------+
    | Variable_name | Value |
    +-----------------------+---------+
    | character_set_results | utf8mb4 |
    +-----------------------+---------+
    1 row in set (0.001 sec)
    
    [root@centos8 ~]# vim /etc/my.cnf.d/mariadb-server.cnf
    [mysqld]
    character_set_results=utf8mb4
    
    #character_set_results不是服务器选项,写入配置文件将导致无法启动
    [root@centos8 ~]# systemctl restart mariadb
    

    范例:修改mysql的最大并发连接数

    注意: CentOS 8.2 已无此问题,CentOS7 仍有此问题

    #默认值为151
    [root@centos8 ~]# mysqladmin variables | grep 'max_connections'
    | max_connections | 151
    
    [root@centos8 ~]# mysql
    MariaDB [(none)]> show variables like 'max_connections';
    +-----------------+-------+
    | Variable_name | Value |
    +-----------------+-------+
    | max_connections | 151 |
    +-----------------+-------+
    1 row in set (0.001 sec)
    
    MariaDB [hellodb]> set global max_connections=2000;
    Query OK, 0 rows affected (0.000 sec)
    
    MariaDB [hellodb]> show variables like 'max_connections';
    +-----------------+-------+
    | Variable_name | Value |
    +-----------------+-------+
    | max_connections | 2000 |
    +-----------------+-------+
    1 row in set (0.001 sec)
    
    [root@centos8 ~]# vim /etc/my.cnf.d/mariadb-server.cnf
    [mysqld]
    max_connections = 8000
    [root@centos8 ~]# systemctl restart mariadb
    
    [root@centos8 ~]# mysql -uroot -p
    
    MariaDB [(none)]> select @@max_connections;
    +-------------------+
    | @@max_connections |
    +-------------------+
    | 594 |
    +-------------------+
    1 row in set (0.000 sec)
    
    #方法1
    [root@centos8 ~]# vim /usr/lib/systemd/system/mariadb.service
    [Service]
    #加下面一行
    LimitNOFILE=65535
    
    #方法2
    [root@centos8 ~]# mkdir /etc/systemd/system/mariadb.service.d/
    [root@node3 ~]# vim /etc/systemd/system/mariadb.service.d/limits.conf
    [Service]
    LimitNOFILE=65535
    [root@centos8 ~]# systemctl daemon-reload
    [root@centos8 ~]# systemctl restart mariadb
    [root@centos8 ~]# mysql -uroot -p -e "select @@max_connections"
    +-------------------+
    | @@max_connections |
    +-------------------+
    | 8000 |
    +-------------------+
    

    范例:修改页大小

    参看:https://mariadb.com/kb/en/innodb-system-variables/#innodb_page_size

    说明:初始化数据目录后,不能更改此系统变量的值。 在MariaDB实例启动时设置InnoDB的页面大
    小,此后保持不变。

    [root@centos8 ~]# mysqladmin variables | grep innodb_page_size
    | innodb_page_size | 16384
    
    [root@centos8 ~]# mysql
    
    MariaDB [(none)]> show variables like "innodb_page_size";
    +------------------+-------+
    | Variable_name | Value |
    +------------------+-------+
    | innodb_page_size | 16384 |
    +------------------+-------+
    1 row in set (0.001 sec)
    
    [root@centos8 ~]# vim /etc/my.cnf.d/mariadb-server.cnf
    [mysqld]
    innodb_page_size=64k
    [root@centos8 ~]# rm -rf /var/lib/mysql/*
    [root@centos8 ~]# systemctl restart mariadb
    [root@centos8 ~]# mysql
    
    MariaDB [(none)]> show variables like "innodb_page_size";
    +------------------+-------+
    | Variable_name | Value |
    +------------------+-------+
    | innodb_page_size | 65536 |
    +------------------+-------+
    1 row in set (0.001 sec)
    

    服务器状态变量

    服务器状态变量:分全局和会话两种

    状态变量(只读):用于保存mysqld运行中的统计数据的变量,不可更改

    SHOW GLOBAL STATUS;
    SHOW [SESSION] STATUS;
    

    范例:

    MariaDB [(none)]> show status like "innodb_page_size";
    +------------------+-------+
    | Variable_name | Value |
    +------------------+-------+
    | Innodb_page_size | 16384 |
    +------------------+-------+
    
    MariaDB [hellodb]> SHOW GLOBAL STATUS like 'com_select';
    +---------------+-------+
    | Variable_name | Value |
    +---------------+-------+
    | Com_select | 5 |
    +---------------+-------+
    1 row in set (0.001 sec)
    

    服务器变量 SQL_MODE

    SQL_MODE:对其设置可以完成一些约束检查的工作,可分别进行全局的设置或当前会话的设置

    参考:
    https://mariadb.com/kb/en/library/sql-mode/

    https://dev.mysql.com/doc/refman/5.7/en/server-options.html#option_mysqld_sql-mode

    常见MODE:

    NO_AUTO_CREATE_USER: 禁止GRANT创建密码为空的用户
    NO_ZERO_DATE:在严格模式,不允许使用'0000-00-00'的时间
    ONLY_FULL_GROUP_BY: 对于GROUP BY聚合操作,如果在SELECT中的列,没有在GROUP BY
    中出现,那么将认为这个SQL是不合法的
    NO_BACKSLASH_ESCAPES: 反斜杠""作为普通字符而非转义字符
    PIPES_AS_CONCAT: 将"||"视为连接操作符而非"或"运算符
    

    范例:CentOS 8 修改SQL_MODE变量实现分组语句控制

    MariaDB [hellodb]> show variables like 'sql_mode';
    
    MariaDB [hellodb]> select classid,count(*) from students group by classid;
    
    MariaDB [hellodb]> select stuid,classid,count(*) from students group by classid;
    
    #修改SQL_MODE
    MariaDB [hellodb]> set sql_mode="ONLY_FULL_GROUP_BY";
    Query OK, 0 rows affected (0.000 sec)
    
    MariaDB [hellodb]> show variables like 'sql_mode';
    +---------------+--------------------+
    | Variable_name | Value |
    +---------------+--------------------+
    | sql_mode | ONLY_FULL_GROUP_BY |
    +---------------+--------------------+
    1 row in set (0.001 sec)
    
    MariaDB [hellodb]> select classid,count(*) from students group by classid;
    +---------+----------+
    | classid | count(*) |
    +---------+----------+
    | NULL | 2 |
    | 1 | 4 |
    | 2 | 3 |
    | 3 | 4 |
    | 4 | 4 |
    | 5 | 1 |
    | 6 | 4 |
    | 7 | 3 |
    +---------+----------+
    8 rows in set (0.001 sec)
    

    范例:CentOS 7 修改SQL_MODE变量

    MariaDB [hellodb]> create table test (id int ,name varchar(3));
    Query OK, 0 rows affected (0.04 sec)
    
    MariaDB [hellodb]> insert test values(1,'abcde');
    Query OK, 1 row affected, 1 warning (0.00 sec)
    
    MariaDB [hellodb]> show warnings;
    +---------+------+-------------------------------------------+
    | Level | Code | Message |
    +---------+------+-------------------------------------------+
    | Warning | 1265 | Data truncated for column 'name' at row 1 |
    +---------+------+-------------------------------------------+
    1 row in set (0.00 sec)
    
    MariaDB [hellodb]> select * from test;
    +------+------+
    | id | name |
    +------+------+
    | 1 | abc |
    +------+------+
    1 row in set (0.00 sec)
    
    MariaDB [hellodb]> show variables like 'SQL_MODE';
    +---------------+-------+
    | Variable_name | Value |
    +---------------+-------+
    | sql_mode | |
    +---------------+-------+
    1 row in set (0.00 sec)
    
    MariaDB [hellodb]> SET SQL_MODE=TRADITIONAL;
    Query OK, 0 rows affected (0.00 sec)
    
    MariaDB [hellodb]> show variables like 'SQL_MODE';
    
  • 相关阅读:
    函数
    特殊集合
    集合
    数组复习
    数组
    IPython--转
    python 单例模式总结
    拼多多笔试题
    python 创建实例--待完善
    转--算法时间复杂度
  • 原文地址:https://www.cnblogs.com/xuanlv-0413/p/14778665.html
Copyright © 2011-2022 走看看