12种mysql常见错误总结 +分析示例

2021-06-24 10:20:13 浏览数 (1)

前言

小伙伴们好,我是阿沐!最近呢,正筹备上云工作,需要考虑到很多场景;比如mongo、mysql、redis、splinx等等迁移工作,这就涉及到版本兼容问题;在迁移之前,阿沐迁移了mysql到其他容器中,发现迁移机器mysql版本号比较高5.7以上,就出现了sql语句兼容问题。所以趁机会整理了很久以前遇到的各种mysql常见问题跟掘金小伙伴们分享下。小伙伴们可以收藏起来哦,遇到常规错误可以快速查询解决~~~

1、localhost上的mysql无法连接
报错代码:
代码语言:javascript复制
ERROR 2003 (HY000):Can’t connect to MySQL server on 'localhost' (10061)
报错原因:
代码语言:javascript复制
① 很明显,localhost本机是存在的;但是它却没有提供mysql的服务供给使用

② 检查磁盘空间是否还有剩余可用空间,尽量保持有足够的磁盘空间可用

③ 查看mysql的负载能力,可能存在mysql的负载过高我们连接不上;一般是看processlist来看下具体线程和连接数运行情况:
       
       1、show processlist只能列出当前100条,我们可以看到所有用户的连接情况
       
       mysql> show processlist;
         ---- ----------------- ----------- ------ --------- ------- ------------------------ ------------------ 
        | Id | User            | Host      | db   | Command | Time  | State                  | Info             |
         ---- ----------------- ----------- ------ --------- ------- ------------------------ ------------------ 
        |  4 | event_scheduler | localhost | NULL | Daemon  | 30404 | Waiting on empty queue | NULL             |
        | 14 | root            | localhost | NULL | Query   |     0 | starting               | show processlist |
         ---- ----------------- ----------- ------ --------- ------- ------------------------ ------------------ 
        2 rows in set (0.00 sec)
       
       2、查看全部的链接情况
       
       mysql> show full processlist;
         ---- ----------------- ----------- ------ --------- ------- ------------------------ ----------------------- 
        | Id | User            | Host      | db   | Command | Time  | State                  | Info                  |
         ---- ----------------- ----------- ------ --------- ------- ------------------------ ----------------------- 
        |  4 | event_scheduler | localhost | NULL | Daemon  | 30527 | Waiting on empty queue | NULL                  |
        | 14 | root            | localhost | NULL | Query   |     0 | starting               | show full processlist |
         ---- ----------------- ----------- ------ --------- ------- ------------------------ ----------------------- 
        2 rows in set (0.00 sec)
        
# 注意,针对以上查看结果进行详细字段说明:

① Id 当用户登录mysql时,系统会为用户分配一个"connection_id",可以使用函数connection_id()来查看:
    mysql> select connection_id();
     ----------------- 
    | connection_id() |
     ----------------- 
    |              14 |  -- 系统分配的id为14
     ----------------- 
    1 row in set (0.01 sec)

② User 展示当前链接用户

③ Host 连接mysql的ip地址;可查到来源端口,同时可以跟踪出现问题语句的用户

④ db   连接数据库的名称

⑤ Command 当前链接执行的命令;query(查询)、sleep(休眠)、connect(连接)、daemon(守护进程)

⑥ Time  当前连接持续时长,单位时间是秒

⑦ State 展示当前连接的sql语句状态

⑧ Info 展示sql语句,对用来判断sql语句是否有问题很重要
问题解决方案:
代码语言:javascript复制
① mysql未启动,则启动即可:

    mac端:brew services start mysql   mysql.server start 
    centos端: systemctl start mysqld.service    service mysql start
    其他:找到执行文件根目录执行 启动也ok
2、localhost/IP地址连接不上
报错代码:
代码语言:javascript复制
➜  ~ mysql -uroot -p
Enter password:
ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: YES)
报错原因:
代码语言:javascript复制
① 概述:用户root访问localhost/IP被拒绝访问

② 一般是数据库的用户名或者密码跟服务器上mysql设置的不一致,导致匹配失败
问题解决方案:
代码语言:javascript复制
# 注意解决步骤:

① 查看mysql配置文件

② 查看 mysql 配置文件加载顺序

③ 修改配置文件跳过权限验证(skip-grant-tables)

④ 登录mysql客户端修改密码
注意mac版本方案:
① 查看mysql运行情况,看看在哪里
代码语言:javascript复制
➜  ~ ps aux | grep mysql   -- 查看mysql的运行进程 可以看到启动地址
amu       15262   0.0  4.9  4899000 407680   ??  S     1:14下午   0:01.18 /usr/local/opt/mysql/bin/mysqld 
--basedir=/usr/local/opt/mysql 
--datadir=/usr/local/var/mysql 
--plugin-dir=/usr/local/opt/mysql/lib/plugin 
--log-error=liyangyang.local.err 
--pid-file=liyangyang.local.pid 
--socket=/tmp/mysql.sock
② 查看mysql配置文件加载情况:
代码语言:javascript复制
➜  ~ /usr/local/opt/mysql/bin/mysqld --verbose --help | grep -A 1 'Default options'
Default options are read from the following files in the given order:
/etc/my.cnf /etc/mysql/my.cnf /usr/local/etc/my.cnf ~/.my.cnf

# 概述:
① 服务器首先读取的是 /etc/my.cnf文件

② 如果前一个文件不存在则继续读/etc/mysql/my.cnf文件,依此类推往下寻找,一直到最后一个~/.my.cnf文件

③ 如果以上所有文件都不存在;则说明安装mysql之后未进行配置文件;可以自己编辑一份名为my.cnf;修改文件拥有者和所属组且赋予可执行权限即可
       
       ① mkdir /usr/local/mysql/etc  

       ② vim /usr/local/mysql/etc/my.cnf  -- 内容可以复制一份本地的配置文件即可

       ③ chown -R root:root /usr/local/mysql/etc/

       ④ chmod 755 /usr/local/mysql/etc/my.cnf
③ 查看mysql读取配置文件方法:
代码语言:javascript复制
## 查看是否使用了指定目录的my.cnf
➜  ~ ps aux | grep mysql | grep 'my.cnf'

## 查看mysql默认读取my.cnf的目录
➜  ~ mysql --help | grep 'my.cnf'
                      order of preference, my.cnf, $MYSQL_TCP_PORT,
/etc/my.cnf /etc/mysql/my.cnf /usr/local/etc/my.cnf ~/.my.cnf

这些就是mysql默认会搜寻my.cnf的目录,顺序排前的优先;等同于上面搜索语句
④ 免密码登录并修改密码
代码语言:javascript复制
### mysql 5.8版本之前的修改方法:

① 在mysql配置文件中,[mysqld]下添加一行,使其登录时跳过权限检查
[mysqld]
skip_grant_tables

② 重启mysql服务;登录mysql -uroot -p

### mysql5.8版本之后修改方法:

    ① 执行目录下执行,例如我本地运行地址:
    /usr/local/opt/mysql/bin/mysqld  -console --skip-grant-tables --shared-memory
    
    ② 新开启一个窗口:mysqld -uroot -p 直接回车(大家可以升级版本测试下)

### 以上操作完毕后 进度mysql终端,修改密码:

set password for root@localhost = '新密码';
或者
update user set authentication_string='新密码' where user='root'; 
或者
alter user 'root'@'localhost' identified with mysql_native_password by '新密码';

### 注意:刷新mysql相关权限
flush privileges;

### 最终流程:
mysql> update user set authentication_string='root' where user='root';
Query OK, 1 row affected (0.01 sec)
Rows matched: 1  Changed: 1  Warnings: 0

mysql> set password for root@localhost = 'root';
Query OK, 0 rows affected (0.02 sec)

mysql> alter user 'root'@'localhost' identified with mysql_native_password by 'root';
Query OK, 0 rows affected (0.01 sec)

mysql> flush privileges;
Query OK, 0 rows affected (0.01 sec)

mysql> exit
Bye

此时再登录时我们的密码已经更新为root
3、无法连接mysql服务器
报错代码:
代码语言:javascript复制
➜  ~ mysql -uroot -p
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)
报错原因:
代码语言:javascript复制
① mysql服务器没有开启

② mysql服务器开启了,但不能找到 socket 文件
概述mysql的连接方式:
代码语言:javascript复制
mysql的登陆方式有两种,分别是socket和tcp/ip方式登陆

### socket(套接字)连接方式:

只能在mysql客户端和数据库实例在同一台服务器上的情况下使用(本地连接);

通常连接localhost是通过一个Unix域套接字文件进行,一般是/tmp/mysql.sock;

若套接字文件被删除了,本地客户就不能再连接了

### 登录实例后查询
mysql> show variables like 'socket';
 --------------- ----------------- 
| Variable_name | Value           |
 --------------- ----------------- 
| socket        | /tmp/mysql.sock |
 --------------- ----------------- 
1 row in set (0.04 sec)

### 当然我们也可以通过socket文件登录数据库
➜  ~ mysql -uroot -proot -S /tmp/mysql.sock -- 用户名   密码   Socket文件路径地址(可不带默认)
mysql: [Warning] Using a password on the command line interface can be insecure.
Welcome to the MySQL monitor.  Commands end with ; or g.
............. 省略部分
#### 注意事项:
mysql.sock必须是mysql中配置的文件且必须在/tmp下存在;若不存在则启动不了mysql

### TCP/IP连接方式:
➜  ~ mysql -uroot -proot -h 127.0.0.1 -- 用户名   密码   ip:port
mysql: [Warning] Using a password on the command line interface can be insecure.
Welcome to the MySQL monitor.  Commands end with ; or g.
............. 省略部分

#### 说明概述
若通过tcp/ip地址连接mysql;它将先检查权限视图表,检测请求方的ip是否允许被连接
mysql> use mysql;
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A
Database changed
mysql> select host, user from user;
 ----------- ------------------ 
| host      | user             |
 ----------- ------------------ 
| localhost | mysql.infoschema |
| localhost | mysql.session    |
| localhost | mysql.sys        |
| localhost | root             |
 ----------- ------------------ 
4 rows in set (0.00 sec)
    ① host 表示该用户只能通过localhost的ip访问此数据库
    ② host:% 表示任何ip都可以连接mysql实例
问题解决方案:
代码语言:javascript复制
① 修改配置文件增加socket路径
       ➜  ~ vim /usr/local/etc/my.cnf
       [mysqld] 
       socket=/tmp/mysql.sock
② 使用软连接将已经存在的mysql.sock软链到/tmp/mysql.sock
       ln -s /usr/local/xxx/mysql.sock  /tmp/mysql.sock

③ 最最最暴力解决方案;卸载mysql,mysql相关的全部删除;为了实践演示我本机mac删除卸载重装


	

0 人点赞