### 6.2.22 连接到 MySQL 的疑难解答

[](<>)[](<>)[](<>)

如果您在尝试连接到 MySQL 服务器时遇到问题，以下项目描述了您可以采取的一些措施来纠正问题。

-   确保服务器正在运行。如果不是，客户端将无法连接到它。例如，如果尝试连接到服务器失败并显示如下消息之一，则一个原因可能是服务器未运行：

    ```
    $> mysql
    ERROR 2003: Can't connect to MySQL server on 'host_name' (111)
    $> mysql
    ERROR 2002: Can't connect to local MySQL server through socket
    '/tmp/mysql.sock' (111)
    ```

-   可能是服务器正在运行，但您尝试使用与服务器正在侦听的不同的 TCP/IP 端口、命名管道或 Unix 套接字文件进行连接。要在调用客户端程序时更正此问题，请指定[`- 港口`](connection-options.html#option_general_port)指示正确端口号的选项，或[`- 插座`](connection-options.html#option_general_socket)选项来指示正确的命名管道或 Unix 套接字文件。要找出套接字文件的位置，可以使用以下命令：

    ```
    $> netstat -ln | grep mysql
    ```

-   确保服务器未配置为忽略网络连接，或者（如果您尝试远程连接）未配置为仅在其网络接口上本地侦听。如果服务器以[`跳过网络`](server-system-variables.html#sysvar_skip_networking)启用系统变量，不接受 TCP/IP 连接。如果服务器以[`绑定地址`](server-system-variables.html#sysvar_bind_address)系统变量设置为`127.0.0.1`，它仅在环回接口上本地侦听 TCP/IP 连接，不接受远程连接。

-   检查以确保没有防火墙阻止对 MySQL 的访问。您的防火墙可以根据正在执行的应用程序或 MySQL 用于通信的端口号（默认为 3306）进行配置。在 Linux 或 Unix 下，检查您的 IP 表（或类似的）配置以确保端口未被阻塞。在 Windows 下，ZoneAlarm 或 Windows 防火墙等应用程序可能需要配置为不阻塞 MySQL 端口。

-   必须正确设置授权表，以便服务器可以使用它们进行访问控制。对于某些分发类型（例如 Windows 上的二进制分发，或 Linux 上的 RPM 和 DEB 分发），安装过程会初始化 MySQL 数据目录，包括`mysql`包含授权表的系统数据库。对于不这样做的发行版，您必须手动初始化数据目录。有关详细信息，请参阅[第 2.10 节，“安装后设置和测试”](postinstallation.html).

    要确定是否需要初始化授权表，请查找`mysql`数据目录下的目录。（数据目录通常命名为`数据`要么`变量`并且位于您的 MySQL 安装目录下。）确保您有一个名为`用户.MYD`在里面`mysql`数据库目录。如果不是，则初始化数据目录。这样做并启动服务器后，您应该能够连接到服务器。

-   全新安装后，如果您尝试以`根`如果不使用密码，您可能会收到以下错误消息。

    ```
    $> mysql -u root
    ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: NO)
    ```

    这意味着在安装过程中已经分配了 root 密码，并且必须提供它。看[第 2.10.4 节，“保护初始 MySQL 帐户”](default-privileges.html)关于可能分配密码的不同方式，以及在某些情况下如何找到它。如果您需要重置 root 密码，请参阅中的说明[第 B.3.3.2 节，“如何重置 Root 密码”](resetting-permissions.html).找到或重置密码后，再次登录`根`使用[`- 密码`](connection-options.html#option_general_password)（要么[`-p`](connection-options.html#option_general_password)） 选项：

    ```
    $> mysql -u root -p
    Enter password:
    ```

    但是，服务器将让您连接为`根`如果您已使用初始化 MySQL，则无需使用密码[**mysqld --initialize-insecure**](mysqld.html)（看[第 2.10.1 节，“初始化数据目录”](data-directory-initialization.html)详情）。这是一个安全风险，所以你应该为`根`帐户;看[第 2.10.4 节，“保护初始 MySQL 帐户”](default-privileges.html)获取说明。

-   如果您已将现有 MySQL 安装更新到较新版本，您是否执行了 MySQL 升级过程？如果没有，请这样做。添加新功能时，授权表的结构偶尔会发生变化，因此在升级后，您应该始终确保您的表具有当前结构。有关说明，请参阅[第 2.11 节，“升级 MySQL”](upgrading.html).

-   如果客户端程序在尝试连接时收到以下错误消息，这意味着服务器需要比客户端能够生成的格式更新的密码：

    ```
    $> mysql
    Client does not support authentication protocol requested
    by server; consider upgrading MySQL client
    ```

-   [](<>) [](<>) [](<>) [](<>) [](<>)请记住，客户端程序使用选项文件或环境变量中指定的连接参数。如果客户端程序似乎发送了错误的默认连接参数，而您没有在命令行中指定它们，请检查任何适用的选项文件和您的环境。例如，如果你得到`拒绝访问`当您在没有任何选项的情况下运行客户端时，请确保您没有在任何选项文件中指定旧密码！

    您可以通过使用[`--no-defaults`](option-file-options.html#option_general_no-defaults)选项。例如：

    ```
    $> mysqladmin --no-defaults -u root version
    ```

    客户端使用的选项文件列在[第 4.2.2.2 节，“使用选项文件”](option-files.html).环境变量列在[第 4.9 节，“环境变量”](environment-variables.html).

-   如果您收到以下错误，则表示您使用了不正确的`根`密码：

    ```
    $> mysqladmin -u root -pxxxx ver
    Access denied for user 'root'@'localhost' (using password: YES)
    ```

    如果即使您没有指定密码也出现上述错误，则表示您的某个选项文件中列出的密码不正确。试试[`--no-defaults`](option-file-options.html#option_general_no-defaults)选项如上一项中所述。

    有关更改密码的信息，请参阅[第 6.2.14 节，“分配帐户密码”](assigning-passwords.html).

    如果您丢失或忘记了`根`密码，见[第 B.3.3.2 节，“如何重置 Root 密码”](resetting-permissions.html).

-   `本地主机`是本地主机名的同义词，如果您明确指定没有主机，它也是客户端尝试连接的默认主机。

    你可以使用一个[`--主机=127.0.0.1`](connection-options.html#option_general_host)显式命名服务器主机的选项。这会导致与本地的 TCP/IP 连接[**mysqld**](mysqld.html)服务器。您还可以通过指定一个[`- 主持人`](connection-options.html#option_general_host)使用本地主机的实际主机名的选项。在这种情况下，主机名必须在`用户`服务器主机上的表行，即使您在与服务器相同的主机上运行客户端程序。

-   这`拒绝访问`错误消息告诉您您尝试登录的身份、您尝试连接的客户端主机以及您是否使用了密码。通常，您应该在`用户`与错误消息中给出的主机名和用户名完全匹配的表。例如，如果您收到一条错误消息，其中包含`使用密码：否`，这意味着您尝试在没有密码的情况下登录。

-   如果你得到一个`拒绝访问`尝试连接到数据库时出错`mysql -u *`用户名`*`，你可能有问题`用户`桌子。通过执行检查这一点`mysql -u root mysql`并发出这条 SQL 语句：

    ```
    SELECT * FROM user;
    ```

    结果应包括一行`主办`和`使用者`匹配客户端主机名和MySQL用户名的列。

-   如果在尝试从运行MySQL服务器的主机以外的主机进行连接时出现以下错误，则表示数据库中没有行`使用者`有一张桌子`主办`与客户端主机匹配的值：

    ```
    Host ... is not allowed to connect to this MySQL server
    ```

    您可以通过为尝试连接时使用的客户端主机名和用户名的组合设置一个帐户来解决此问题。

    如果你不知道你连接的机器的IP地址或主机名，你应该用`'%'`作为`主办`中的列值`使用者`桌子尝试从客户端计算机连接后，请使用`选择用户（）`查询以查看您是如何连接的。然后换一个`'%'`在`使用者`表行中显示的实际主机名。否则，您的系统将不安全，因为它允许从任何主机连接给定用户名。

    在Linux上，发生此错误的另一个原因是您使用的是二进制MySQL版本，该版本是使用不同版本的`格利伯`而不是你正在使用的图书馆。在这种情况下，您应该升级操作系统或`格利伯`，或者下载MySQL版本的源代码发行版并自己编译。源RPM通常很难编译和安装，所以这不是什么大问题。

-   如果在尝试连接时指定了主机名，但在主机名未显示或是IP地址的情况下收到错误消息，则表示MySQL服务器在尝试将客户端主机的IP地址解析为名称时出错：

    ```
    $> mysqladmin -u root -pxxxx -h some_hostname ver
    Access denied for user 'root'@'' (using password: YES)
    ```

    如果你试着以`根`并得到以下错误，这意味着在`使用者`有一张桌子`使用者`列值`“根”`而且[**mysqld**](mysqld.html)无法解析客户端的主机名：

    ```
    Access denied for user ''@'unknown'
    ```

    这些错误表明存在DNS问题。要修复它，执行[**mysqladmin刷新主机**](mysqladmin.html)重置内部DNS主机缓存。看见[第5.1.12.3节，“DNS查找和主机缓存”](host-cache.html).

    一些永久性的解决办法是：

    -   确定DNS服务器的问题并修复。

    -   在MySQL授权表中指定IP地址而不是主机名。

    -   在中输入客户机名称`/etc/主持人`在Unix或`\windows\hosts`在窗户上。

    -   开始[**mysqld**](mysqld.html)和[`跳过\u名称\u解析`](server-system-variables.html#sysvar_skip_name_resolve)系统变量已启用。

    -   开始[**mysqld**](mysqld.html)和[`--跳过主机缓存`](server-options.html#option_mysqld_skip-host-cache)选项

    -   在Unix上，如果在同一台计算机上运行服务器和客户端，请连接到`本地服务器`.连接到`本地服务器`，MySQL程序尝试使用Unix套接字文件连接到本地服务器，除非指定了连接参数以确保客户端进行TCP/IP连接。有关更多信息，请参阅[第4.2.4节，“使用命令选项连接到MySQL服务器”](connecting.html).

    -   在Windows上，如果在同一台计算机上运行服务器和客户端，并且服务器支持命名管道连接，请连接到主机名`.`（句号）。连接到`.`使用命名管道，而不是TCP/IP。

-   如果`mysql-u根`有效但是`mysql-h*`你的主机名`*-u根`结果`拒绝访问`（在哪里*`你的主机名`*是本地主机的实际主机名），您的主机名可能不正确`使用者`桌子这里的一个常见问题是`主办`价值观`使用者`表行指定了一个非限定的主机名，但系统的名称解析例程返回一个完全限定的域名（反之亦然）。例如，如果您有一行带有host`“冥王星”`在`使用者`表，但您的DNS告诉MySQL您的主机名为`“布鲁托。实例com'`，行不工作。尝试将一行添加到`使用者`表，其中包含主机的IP地址作为`主办`列值。（或者，您可以向`使用者`有一张桌子`主办`包含通配符的值（例如，`“冥王星”`).然而，使用`主办`以`%`是*缺乏信心的*而且是*不*推荐！）

-   如果`mysql-u*`用户名`*`有效但是`mysql-u*`用户名`* *`一些`*`否则，您尚未授予给定用户对名为的数据库的访问权限*`一些`*.

-   如果`mysql-u*`用户名`*`在服务器主机上执行时工作，但`mysql-h*`主机名`*-u*`用户名`*`在远程客户端主机上执行时不工作，因为您尚未启用从远程主机访问给定用户名的服务器。

-   如果你不明白为什么会`拒绝访问`，从`使用者`表中列出所有具有`主办`包含通配符的值（包含`'%'`或`'_'`角色）。一个非常常见的错误是插入带有`主办`=`'%'`和`使用者`=`'*`某个用户`*'`，认为这使您能够指定`本地服务器`从同一台机器连接。这不起作用的原因是默认权限包括一行`主办`=`“本地主机”`和`使用者`=`''`.因为那一排有`主办`价值`“本地主机”`这比`'%'`，当从连接时，它优先于新行使用`本地服务器`! 正确的步骤是插入第二行`主办`=`“本地主机”`和`使用者`=`'*`某个用户`*'`，或使用`主办`=`“本地主机”`和`使用者`=`''`.删除行后，请记住发出[`同花顺特权`](flush.html#flush-privileges)语句重新加载grant表。另见[第6.2.6节，“访问控制，第1阶段：连接验证”](connection-access.html).

-   如果你能够连接到MySQL服务器，但是`拒绝访问`无论何时发布消息[`选择到外边去`](select-into.html)或[`加载数据`](load-data.html)声明，你在`使用者`表中没有[`文件`](privileges-provided.html#priv_file)特权已启用。

-   如果直接更改拨款表（例如，使用[`插入`](insert.html), [`使现代化`](update.html)或[`删去`](delete.html)语句）并且您的更改似乎被忽略，请记住，您必须执行[`同花顺特权`](flush.html#flush-privileges)声明或声明[**mysqladmin刷新权限**](mysqladmin.html)命令使服务器重新加载特权表。否则，在下次重新启动服务器之前，您的更改不会生效。记住，在你改变了`根`带有[`使现代化`](update.html)语句中，在刷新权限之前，您不需要指定新密码，因为服务器在此之前不知道您已更改了密码。

-   如果您的特权在会话中间似乎已经改变，可能是MySQL管理员已经更改了它们。重新加载授权表会影响新的客户端连接，但也会影响现有连接，如中所示[第6.2.13节“特权变更生效时”](privilege-changes.html).

-   如果Perl、PHP、Python或ODBC程序存在访问问题，请尝试使用`mysql-u*`用户名`* *`db\_名称`*`或`mysql-u*`用户名`*-p*`暗语`* *`db\_名称`*`。如果您能够使用[**mysql**](mysql.html)客户端，问题在于你的程序，而不是访问权限。（两者之间没有空隙`-p`密码；你也可以使用[`--密码=*`暗语`*`](connection-options.html#option_general_password)指定密码的语法。如果你使用`-p`或[`--密码`](connection-options.html#option_general_password)选项没有密码值，MySQL会提示您输入密码。）

-   出于测试目的，启动[**mysqld**](mysqld.html)服务器与[`--跳过拨款表`](server-options.html#option_mysqld_skip-grant-tables)选项然后可以更改MySQL grant表并使用[`表演补助金`](show-grants.html)声明，以检查您的修改是否达到预期效果。当您对更改感到满意时，执行[**mysqladmin刷新权限**](mysqladmin.html)告诉[**mysqld**](mysqld.html)服务器重新加载权限。这使您可以开始使用新的授权表内容，而无需停止和重新启动服务器。

-   如果其他一切都失败了，那么启动[**mysqld**](mysqld.html)带有调试选项的服务器（例如，[`--debug=d，常规，查询`](server-options.html#option_mysqld_debug))。这将打印有关尝试连接的主机和用户信息，以及有关发出的每个命令的信息。看见[第5.9.4节，“DBUG包”](dbug-package.html).

-   如果您对MySQL grant表有任何其他问题，请在[MySQL社区松弛](https://mysqlcommunity.slack.com/)，始终提供MySQL grant表的转储。你可以把桌子和[**mysqldump-mysql**](mysqldump.html)命令要提交错误报告，请参阅[第1.6节，“如何报告错误或问题”](bug-reports.html).在某些情况下，您可能需要重新启动[**mysqld**](mysqld.html)具有[`--跳过拨款表`](server-options.html#option_mysqld_skip-grant-tables)跑[**mysqldump**](mysqldump.html).
