MySQL服务
一、MySQL简介
1、问题:为什么需要数据库?
比如:一个学生管理系统,众多学生的信息存储在文件中:
- 读写速度太慢
 - 文件内容明文存储
 - 不能多人同时操作
 - 数据量大时索引效率低下
 - 多文件存储时数据关联差
 
数据库特点
- 支持加密技术、提供安全性保证
 - 支持多用户环境,允许用户并行访问和操作数据
 - 支持为不同用户设置不同权限
 - 数据共享
 
2、相关术语
- 
DBMS:数据库管理系统
 - 
RDBMS :指的是关系型数据库管理系统
 - 
DBA:数据库管理员
 - 
- 负责数据库的建立、调整、重构
 - 负责数据的完整性、安全机制、查询和优化等服务
 
 
3、数据库分类
- 
按数据的存储格式
 - 
- 
关系型数据库(RDBMS)
 - 
- RDBMS是所有现代数据库系统的基础
 - 代表:MySQL、SQLServer、Oracle等
 - 数据存储在被称为表(table)的数据库对象中
 - 表是由相关的数据项的集合,由行和列组成
 
 
 - 
 - 
RDBMS – database – table - row | column
 
关系数据结构
- 指数据以什么方式来存储 -- 二维表形式
 

#MySQL历史
- MySQL是关系型数据库
 - 最早可追溯到1979年,作为很底层的面向报表的存储工具而诞生
 - 1996年1.0版本发布、2003年5.0版本发布
 - 2009年Oracle收购sun公司,发布5.5版本、添加较多新特性
 - 2016年Oracle跳过5.x命令系列、抛弃6和7分支,直接进入MySQL8版本
 - 2018年8.0发布
 
#MySQL版本
- 社区版:开源、免费版,不提供官方技术支持
 - 企业版:开源、收费版,可以适用30天
 - 集群版:开源、免费版
 - 高级集群版:收费版
 
#rpm包和源码包
| rpm****包 | 源码包 | |
|---|---|---|
| 软件包 | mariadb、mariadb-server | mysql、ncurses | 
| 端口 | TCP 3306 | |
| 配置文件 | /etc/my.cnf | |
| 数据位置 | /var/lib/mysql | 安装目录下/data | 
| 启停管理 | systemctl | 安装目录下/bin | 
- 
非关系型数据库(NoSQL)
 - 
- 
NoSQL:not only sql,不仅仅是sql
 - 
优势:
 - 
- 支持存储更多的格式:key-value形式、文档形式、列存储等,更灵活
 - 善于处理海量数据的维护和处理
 - 速度快、效率高,可用硬盘或随机存储器作为载体
 - 扩展简单、高并发、稳定、成本低
 
 
 - 
 - 
非关系型数据库种类
 - 
- 
键值存储:Redis
 - 
- 每个单独的项都存储为键值对
 
 - 
面向文档:MongoDB
 - 
- 每个键与称之为文档的复杂数据结构配对
 
 - 
宽列存储:HBase
 - 
- 将数据列存储、取代行
 
 
 - 
 
二、MySQL语法
1、数据文件

注:每个数据库中.frm是表结构文件、.MYD是当前数据库数据文件、.MYI是当前数据表索引文件
2、储存引擎
- MyISAM是mysql最开始时的默认存储引擎
 - InnoDB是5.5版本之后的默认存储引擎
 - Memory是内存式数据库
 

3、SQL语句
- 
SQL:Structure Query Language,结构化查询语言
 - 
SQL使我们有能力访问数据
 - 
SQL是指结构化查询语言
 - 
用SQL语句来操作数据、是一种标准
 - 
SQL语言
 - 
- 开始是美国国家标准局(ANSI)制定
 - 现在是国际化标准组织(ISO)制定
 - +:各个厂商的方言
 
 
4**、SQL分类**
- 
DDL:Data Definition Language,数据定义语言
 - 
- 用来操作库、表、列,如:create、alter、drop
 
 - 
DML:Data Manipulation Language,数据操作语言
 - 
- 用来操作表记录,如:insert、update、delete
 
 - 
DQL:Data Query Language,数据查询语言
 - 
- 用来查询数据,如:select
 
 - 
DCL:Data Control Language,数据控制语言
 
用于设置用户的访问授权和安全级别,如:grant
5、SQL语法
- 对语句关键字忽略大小写
 - 对数据库名和表名严格区分大小写
 - 对列名、列名别名忽略大小写
 - 对变量名严格区分大小写
 - 每句语句后面需有;结尾
 
6**、DQL语言**
#查询指定列
- 
查询语法: select 指定列名 from 表名;
 - 
指定列名:
 - 
- 单列:列名
 - 多列:列名1,列名2,…
 - 所有:*
 
 
查询表中所有数据:
- select * from 表名;
 
查询表中单列数据:
- select 列名 from 表名;
 
查询表中若干列:
- select 列名1,列名2… from 表名;
 
#查询后指定别名
查询表中单列数据:
- select 列名 as 别名 from 表名;
 
查询表中若干列:
- select 列名1 as 别名1,列名2 as 别名2,… from 表名;
 
#查询指定行的数据
查询表中前n行:
- select * from 表名 limit n;
 
查询表中从第n行开始的m行:
- select * from 表名 limit n,m;
 
#条件查询
- 
where 列名=值;
 - 
where 子句操作符; (=、<>、!=、<、<=、>、>=、between、is null)
 - 
where 与and、or组合
 - 
in操作符:列名 in (值1,值2)
 - 
not操作符:列名 not in (值1,值2)
 - 
like操作符:
 - 
- 列名 like ‘字符串%’ #%表示任何字符出现任意次数
 - 列名 like ‘字符串_’ #_表示单个字符
 
 
#排序查询
默认排序:
- select * from 表名;
 
按指定列排序:
- select * from 表名 order by 列名;
 
按指定列倒序排序:
- select * from 表名 order by 列名 desc;
 
#查询结果去重
mysql> select distinct * from table
#查询数据的记录数
mysql> select count(*) from xinxi;
7**、DML语言**
#查看表结构
- desc 表名;
 

#MySQL数据类型
- 数值类型
 
| 子类型 | 大小 | 用途 | 
|---|---|---|
| tinyint | 1 byte | 非常小的整数 | 
| smallint | 2 bytes | 小整数 | 
| int | 4 bytes | 标准整数 | 
| bigint | 8 bytes | 大整数 | 
| float | 4 bytes | 单精度浮点数 | 
| double | 8 bytes | 双精度浮点数 | 
| decimal | 可指定 | 定点数,或货币类型 | 
- 字符串类型
 
| 子类型 | 大小 | 用途 | 
|---|---|---|
| char | 0-255 bytes | 定长字符串 | 
| varchar | 0-65535 bytes | 变长字符串 | 
| text | 0-65535 bytes | 长文本数据 | 
| blob | 0-65535 bytes | 二进制形式的长文本 | 
- 日期和时间类型
 
| 子类型 | 大小 | 取值范围 | 零值 | 格式 | 用途 | 
|---|---|---|---|---|---|
| date | 3 bytes | 1901~2155 | 0000-00-00 | YYYY-MM-DD | 日期值 | 
| time | 3 bytes | 1000-01-01~9999-12-3 | 00:00:00 | HH:MM:SS | 时间值 | 
| year | 1 byte | -838:59:59~838:59:59 | 0000 | YYYY | 年份值 | 
| datetime | 8 bytes | 1000-01-01 00:00:00 ~ 9999-12-31 23:59:59 | 0000-00-00 00:00:00 | YYYY-MM-DD HH:MM:SS | 日期和时间值 | 
| timestamp | 4 bytes | 1970-01-01 00:00:01 ~ 2038-01-19 03:14:07 | 0000-00-00 00:00:00 | YYYY-MM-DD HH:MM:SS | 时间戳,默认当前时间 | 
注:指定长度,字符串类型直接截取,数值类型不会截取,数值是显示长度
扩展——
- 枚举:enum(M、F、r)
 
枚举对应选项可以按数字填写。

#添加数据记录
添加所有列:
- insert into 表名 values(值1,值2…);
 
添加必须列:
- insert into 表名(列名1,列名2…) values(值1,值2…);
 

#修改数据记录
修改所有记录:
- update 表名 set 列名=数值;
 
修改指定记录:
- update 表名 set 列名=数值 where 列名1 = 值1;
 
update xinxi set sex=1 where name='zhao';

update xinxi set address='dongbei' where address is null;
#删除数据记录
删除所有数据:
- delete from 表名;
 
删除指定数据:
- delete from 表名 where 列名 = 值;
 
8**、DDL语言**
#数据库的增删改查
- 
创建数据库:create database 数据库名;
 - 
切换数据库:use 数据名
 - 
删除数据库:drop database 数据库名;
 - 
查看所有表:show tables;
 
#创建数据表
创建表:
create table 表名(
字段1 数据类型 非空约束 默认值约束,
字段2 数据类型 非空约束 默认值约束,
…
 字段n 数据类型 非空约束 默认值约束
);
create table jop1(id smallint(10) not null auto_increment, name varchar(20) not null,primary key(id,name),birth date default '2000-1-1');

#删除数据表
删除表:
- drop table 表名;(多表时,隔开)
 
#修改数据表
- 
修改表名:alter table 原表名 rename 新表名;
 - 
增加列:alter table 表名 add 列名 数据类型 [first | after 列名];
 

- 
删除列:alter table 表名 drop 列名;
 - 
修改列名:alter table 表名 change 原列名 新列名 数据类型 [约束 默认值];
 

- 修改列的类型:alter table 表名 modify 列名 数据类型;
 
主键约束:
- 添加:alter table 表名 add primary key(列名);
 - 删除:alter table 表名 drop primary key;
 
唯一键约束:
- 添加:alter table 表名 add unique key(列名);
 - 删除:用约束名
 
补充——
主键约束特点:
①一张表只能有一个主键,加在列上
②约束的列不能有重复数据、不能为null
③主键可加多列上,称为联合主键
约束:
- 约束是用于限制加入表的数据;可以在创建表的时候规则约束、也可以在建完表后进行调整。
 - 常见约束:
 
①域约束:非空(not null)、默认值(default)
②实体约束:主键、唯一键
③表间约束:外键
#数据完整性
- 域完整性:指表中列的完整性,需要满足特定的数据类型或约束
 - 实体完整性:指表中行的完整性,主要保证操作记录的非空、唯一且不重复
 - 表间完整性:指表间的完整性,主要用于保证两表数据的一致性
 
9、MySQL原理图

#存储引擎
- 
作用:
 - 
- 存储数据
 - 建立索引(类似书的目录、加快查询)
 - 展示数据(读取数据文件转换成用户识别的数据库表)
 - 更新数据等
 
 
#InnoDB
- 
支持事务:
 - 
- C:一致性,事务运行时不改变数据库中的数据
 - A:原子性,事务里的语句要么全部执行、要么全部不执行
 - I:隔离性,指两个以上事务间独立运行、互不干扰
 - D:持久性,事务运行完对文件影响是持久的、不会随意回滚
 
 - 
展示数据(读取数据文件转换成用户识别的数据库表)
 - 
支持行级锁
 - 
支持外键
 
#索引
- 
常用分类
 - 
- 单列索引:在表中的某个字段上创建索引
 
 
| 索引类型/约束 | 允许插入重复值 | 允许插入空值 | 
|---|---|---|
| 普通索引 | 允许 | 允许 | 
| 唯一索引 | 不允许 | 允许 | 
| 主键索引 | 不允许 | 不允许 | 
- 
组合索引:在表中的多个字段组合上创建索引
 - 
在InnoDB中
 - 
- 主键索引也被称为聚簇索引
 - 非主键索引也被称为非聚簇索引、辅助索引
 
 - 
存储的key-value:
 - 
- 主键索引的key是主键的值、value是该行的记录
 - 辅助索引的key是索引列的值、value是该行的主键的值
 
 - 
索引使用
 - 
- 用主键查任何字段:主键索引文件 -> 数据
 - 用辅助索引值查主键值或索引列的值:辅助索引文件 -> 数据
 
 - 
创建索引场景
 - 
- 创建了主键默认会生成主键索引
 - 创建了唯一键默认会生成唯一索引
 - 常用来作为查询条件的字段可以设置为索引
 - 创建普通索引不会对表数据添加约束
 
 
#创建索引
单列索引
create (unique) index 索引名 on 表名(列名);
组合索引
create index 索引名 on 表名(列名1,列名2 );
#删除索引
drop index 索引名 on 表名;
#查看索引
show index from 表名;
9**、DCL语言**
#MySQL连接
连接命令:mysql 选项 选项参数
选项:
-u 用户名
-p 密码
-h 登录地址
-P 端口
-S 套接字文件(套接字是一个文件、指定了登录地址和端口)
#MySQL连接 – 本机
- 刚装完无密码连接:mysql
 - 刚装完只有在mysql数据库里只有root用户
 - 给root设置密码:mysqladmin -uroot password 密码值
 - 设置密码后连接:mysql -uroot -p,回车输入密码
 - 本机客户端连接服务器、可以省略-h、-P选项
 - 本机完整访问:mysql -hlocalhost -P3306 –uroot -p,回车输入密码
 
#MySQL连接 – 远程
- 
mysql用户登录认证:用户名 + 登录地址 == 唯一标识
 - 
创建用户:
 - 
- create user '****用户名'@'登录地址’ identified by '密码’
 
 

- 
登录地址就会存储在mysql数据库中user表的Host字段
 - 
登录地址可设置:
 - 
- 本地登录:localhost、127.0.0.1
 - 远程登录:%,代表除本地访问外的所有IP地址
 - 固定IP:指定可以访问的IP地址
 
 - 
删除用户:drop user ‘用户名’@‘登录地址’
 
#查看用户的授权
- 
查看某个存在用户的权限:
 - 
- show grants for ‘用户名’@‘登录地址’;
 
 - 
结果分析:
 - 
- 操作的用户: ‘用户名’@‘登录地址’
 - 拥有的权限:select、insert、update、delete、all等
 - 操作的对象:数据库名.数据表名、数据库.、.*
 
 
#给用户授权
- 
授权存在用户:
 - 
- grant 权限 on 数据库名.数据表名 to ‘用户名’@‘登录地址’;
 
 

- 
授权新用户:
 - 
- grant 权限 on 数据库名.数据表名 to ‘用户名’@‘登录地址’ identified by ‘密码’;
 
 

- 更新授权:flush privileges;
 
#取消授权
- 
取消权限:
 - 
- revoke 权限 on 数据库名.数据表名 from ‘用户名’@‘登录地址’;
 
 

10**、MySQL数据多表操作**
#多表关联作用
- 每张表里的数据都是有关联的
 - 不同关联的字段创建在不同的数据表里
 - 联表可以同时查询多张表里的数据、去除重复列
 
#表与表的连接
- 
表连接
 - 
- 内连接:inner join => 2
 - 左连接:left join => 1、2
 - 右连接:right join => 3、2
 
 

关联查看
select * from xinxi x inner join paihangbang p on x.name=p.name;

select * from xinxi x left join paihangbang p on x.name=p.name;

截取关联查看
select x.name,sex,score,rank from xinxi x inner join paihangbang p on x.name=p.name;

扩展——
- 在查询过程中执行顺序:from>where>group(包含聚合函数,如min、max、avg等)>having>order>select
 
#表与表的关系
- 
表关系
 - 
- 一对一
 - 一对多
 - 多对多
 
 - 
表示成E-R图
 

- 
外键特点:
 - 
- 外键约束,参照完整性,用来在两个表的数据之间建立连接;
 - 一张表可以设置多个外键,一个外键可以加载单列或多列上;
 - 外键是表中的一个字段、不一定是本表的主键,但需要对应另一个表的唯一键;
 - 外键定义后,不允许删除另一个表中有关联的行;
 - 关联的两张表的字段类型、字符集需要相同;
 
 
创建外键语法:ALTER TABLE <数据表名> ADD CONSTRAINT <索引名> FOREIGN KEY(<列名>) REFERENCES <主表名> (<列名>);
例:ALTER TABLE paihangbang ADD CONSTRAINT fk_name FOREIGN KEY(name) REFERENCES xinxi(name);
查看外键:show create table 表名;
删除外键
语法:ALTER TABLE <表名> DROP FOREIGN KEY <外键约束名>; #删约束
语法:drop index 约束名 on 表名; #删外键索引
#级联关系:
- 想删除主表的字段,需要把该字段上关联的外键先删除;
 - 想添加从表的字段,需要在主表的数据范围里面
 
**#**视图
- 定义:视图是虚拟的表,只包含使用时动态检索数据的查询
 - 创建:create view 视图名 as select语句
 

- 查看:select * from 视图名;
 

- 修改:alter view 视图名 as select 语句;
 - 删除:drop view 视图名;
 
#InnoDB
- 
支持事务:
 - 
- C:一致性,事务运行时不改变数据库中的数据
 - A:原子性,事务里的语句要么全部执行、要么全部不执行
 - I:隔离性,指两个以上事务间独立运行、互不干扰
 - D:持久性,事务运行完对文件影响是持久的、不会随意回滚
 - 展示数据(读取数据文件转换成用户识别的数据库表)
 
 - 
事务的隔离级别:
 - 
- READ_UNCOMMITTED(读未提交)(脏读)
 - READ_COMMITTED(读已提交)(不可重复读)
 - REPEATABLE_READ(可重复读,MySQL默认) (加锁)
 - SERIALIZABLE(串行读)
 
 
#存储过程
- 
定义:实现一组SQL语句作为一个整体来执行的数据库对象
 - 
特点:
 - 
- 包含非常多的SQL语句,可提升效率
 - 是可以自定义的函数
 - 被预编译一次、能反复执行
 
 - 
使用:
 - 
- 创建:create procedure 存储过程名()
 - 调用:call 存储过程名
 - 删除:drop procedure 存储过程名
 
 
三、MySQL运维
1、运维管理
- 用户管理:创建、删除、授权
 - 密码管理:设置、修改、忘记
 - 数据管理:备份与恢复
 
2、用户管理
- 
用户管理:创建(create)、删除(drop)、授权(grant)
 - 
- 管理员用户:'root'@'localhost’
 - 普通用户:管理员创建的用户
 
 
#密码管理
设置密码:
- 
初始管理员密码设置: mysqladmin -u用户名 password 密码
 - 
创建普通用户时设置密码:create user '用户名'@'登录地址' identified by '用户密码';
 - 
修改密码:
 - 
- 
更改自己的密码,所有用户都可以使用
 - 
- set password = password('新密码');
 
 
 - 
 - 
管理员用户修改普通用户的密码
 - 
- set password for '用户名'@'登录地址'= password("新密码");
 
 - 
set password方法的封装
 - 
- update user set password=password('新密码') where User='用户名' and Host='登录地址';
 - flush privileges; #或重启服务
 
 - 
忘记密码(管理员用户)
 
①vim /etc/my.cnf
#mysql默认启动区域
[mysqld]
#添加跳过权限表验证
skip-grant-table
②systemctl restart mariadb
③update user set password=password('新密码') where User='用户名' and Host='登录地址';
④去掉skip-grant-table
⑤systemctl restart mariadb
3、数据库备份与恢复(三种方式)
- 
数据文件备份:cp scp rsync
 - 
- cp -a /usr/local/mysql/data 备份目录 (源码包)
 - cp -a /var/lib/mysql 备份目录 (rpm包)
 
 - 
mysqldump备份: 调用当前时间命名 $(date +"%y-%m-%d")
 - 
- 备份:mysqldump 数据库名 > 备份文件名
 - 还原:mysql 数据库名 < 备份文件名
 
 - 
#还原数据时,根据还原的sql内容决定指定还原位置。
 
参数:
-A(--all-databases)、-B(--databases)、-d(--no-data)、-t(--no-create-info)
备份所有数据库
- mysqldump -u用户名 -p密码 --all-databases > 文件名.sql
 
备份多个数据库
- mysqldump -u用户名 -p密码 --databases 数据库名1 数据库名2 > 文件名.sql
 
备份一个数据库
- mysqldump -u用户名 -p密码 要备份的数据库名 > 文件名.sql
 
备份一个数据库表
- 
mysqldump -u用户名 -p密码 要备份的数据库名 表名 > 文件名.sql
 - 
二进制日志自动备份
 - 
- 修改配置文件,打开二进制日志log-bin
 
 
查看所有log变量:show variables like '%log%';
开启二进制日志配置、产生二进制日志
vim /etc/my.cnf
log-bin=mysql-bin
查看二进制日志文件(/var/lib/mysql/):
- mysqlbinlog mysql-bin.000001
 - mysql> show binlog events in '二进制文件名';
 

指定二进制事件的起止位置进行数据恢复(-u和-p参数根据连接进数据库参数而定)(需要切换到log文件位置)
mysqlbinlog --start-position 245 --stop-position 473 mysql-bin.000001 | mysql -uroot -p123



开启通用查询日志(gennral_log)
vim /etc/my.cnf
general_log=on
#指定通用日志文件名,默认在数据文件位置、名字为:主机名.log
general_log_file=/var/lib/mysql/general.log
systemctl restart mariadb
5、数据库日志
- 
show variables like '%log%’;
 - 
- 查询日志:general_log,记录所有查询语句
 - 慢查询日志:slow_query_log,显示时间较慢的查询
 - 二进制日志:log_bin,记录改变数据结构的语句
 - 中继日志:relay_log,主从结构中的同步的日志
 
 










