MYSQLi 和 ssl 连接到数据库服务器

MYSQLi and ssl connection to db server

提问人:LukeJ 提问时间:11/19/2016 最后编辑:jwwLukeJ 更新时间:6/10/2023 访问量:5903

问:

我在使用 php 建立 ssl 连接时遇到了一些奇怪的问题。 我有网络和数据库服务器。在两者上,我都通过openssl生成了证书。它们是完全一样的。

所以我尝试使用mysql命令从web服务器连接:

mysql -h 10.1.1.1 -uroot -p
Password
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 71
Server version: 5.5.5-10.1.19-MariaDB MariaDB Server

Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql>

所以现在我想看看它是否真的是ssl:

mysql> status;
--------------
mysql  Ver 14.14 Distrib 5.6.33, for Linux (x86_64) using  EditLine wrapper

Connection id:          71
Current database:
Current user:           [email protected]
SSL:                    Cipher in use is DHE-RSA-AES256-SHA
Current pager:          stdout
Using outfile:          ''
Using delimiter:        ;
Server version:         5.5.5-10.1.19-MariaDB MariaDB Server
Protocol version:       10
Connection:             10.1.1.1 via TCP/IP
Server characterset:    latin1
Db     characterset:    latin1
Client characterset:    utf8
Conn.  characterset:    utf8
TCP port:               3306
Uptime:                 1 hour 6 min 51 sec

Threads: 1  Questions: 153  Slow queries: 0  Opens: 21  Flush tables: 1  Open tables: 15  Queries per second avg: 0.038
--------------

mysql>

所以我看到连接已经建立。我写了一些php脚本来连接到我的数据库:

<?php
ini_set ('error_reporting', E_ALL);
ini_set ('display_errors', '1');
error_reporting (E_ALL|E_STRICT);

$db = mysqli_init();
mysqli_options ($db, MYSQLI_OPT_SSL_VERIFY_SERVER_CERT, true);

$db->ssl_set('/etc/mysql/newcerts/client-key-rsa.pem', '/etc/mysql/newcerts/client-cert.pem', '/etc/mysql/newcerts/ca-cert.pem', NULL, NULL);
$link = mysqli_real_connect ($db, '10.1.1.1', 'root', 'xxxxxx', 'mysql', 3306, NULL, MYSQLI_CLIENT_SSL);
if (!$link)
{
    die ('Connect error (' . mysqli_connect_errno() . '): ' . mysqli_connect_error() . "\n");
} else {
    $res = $db->query('SHOW TABLES;');
    print_r ($res);
    $db->close();
}
?>

但是现在当我在我的网络服务器上运行这个脚本时,我收到这个错误:

[root@web-01 config]# php test.php

Warning: mysqli_real_connect(): Unable to locate peer certificate CN in /home/extranet/app/config/test.php on line 10

Warning: mysqli_real_connect(): Cannot connect to MySQL by using SSL in /home/extranet/app/config/test.php on line 10

Warning: mysqli_real_connect(): [2002]  (trying to connect via tcp://10.1.1.1:3306) in /home/extranet/app/config/test.php on line 10

Warning: mysqli_real_connect(): (HY000/2002):  in /home/extranet/app/config/test.php on line 10
Connect error (2002):

这太奇怪了。我试过 mysql_connet() 并且有效...

有什么想法吗?

我正在使用 PHP 5.6.25

编辑: 当然,我也在我的 Web 服务器 .my.cnf 文件中添加了行:

[client]
port=3306
ssl-ca=/etc/mysql/newcerts/ca-cert.pem
ssl-cert=/etc/mysql/newcerts/client-cert.pem
ssl-key=/etc/mysql/newcerts/client-key-rsa.pem

这在 Web 服务器命令行中也能正常工作:

mysql -h 10.1.1.1 -u root --password \
    --ssl \
    --ssl-ca /etc/mysql/newcerts/ca-cert.pem \
    --ssl-cert /etc/mysql/newcerts/client-cert.pem \
    --ssl-key /etc/mysql/newcerts/client-key-rsa.pem \

证书用户/组/权限

[root@web-01 newcerts]# ls -alZ
drwxr-xr-x root root ?                                .
drwxr-xr-x root root ?                                ..
-rw-r--r-- root root ?                                ca-cert.pem
-rw-r--r-- root root ?                                ca-key.pem
-rw-r--r-- root root ?                                client-cert.pem
-rw-r--r-- root root ?                                client-key.pem
-rw-r--r-- root root ?                                client-key-rsa.pem
-rw-r--r-- root root ?                                client-req.pem
-rw-r--r-- root root ?                                server-cert.pem
-rw-r--r-- root root ?                                server-key.pem
-rw-r--r-- root root ?                                server-req.pem

SELinux 已禁用:

# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
#     enforcing - SELinux security policy is enforced.
#     permissive - SELinux prints warnings instead of enforcing.
#     disabled - No SELinux policy is loaded.
SELINUX=disabled
# SELINUXTYPE= can take one of these two values:
#     targeted - Targeted processes are protected,
#     minimum - Modification of targeted policy. Only selected processes are protected.
#     mls - Multi Level Security protection.
SELINUXTYPE=targeted
php mysql mysqli ssl-证书 php-openssl

评论

0赞 Matt Clark 11/19/2016
正如错误所指出的,你能在证书上检查通用名称吗?Unable to locate peer certificate CNopenssl x509 -in *cert.pem -text -noout

答:

0赞 Mitesh Sharma 3/31/2017 #1

我也面临着同样的错误,我在推文下面做了,并为我工作。

$link = mysqli_real_connect ($db, '10.1.1.1', 'root', 'xxxxxx', 'mysql', 3306, NULL, MYSQLI_CLIENT_SSL_DONT_VERIFY_SERVER_CERT);

评论

0赞 Jason Carter 11/4/2021
切勿在生产服务器上执行此操作。它使您的客户端暴露在中间人攻击之下。
0赞 Robert Karsai 9/21/2017 #2

使用 PHP 7.1(服务器 CN 名称不同的 IP 地址。我连接IP地址...),这段代码似乎有效:

<?php
ini_set ('error_reporting', E_ALL);
ini_set ('display_errors', '1');
error_reporting (E_ALL|E_STRICT);
$db = mysqli_init();
mysqli_options ($db, MYSQLI_OPT_SSL_VERIFY_SERVER_CERT, true);
$db->ssl_set('client-key.pem', 'client-cert.pem', 'ca-cert.pem', NULL, NULL);
if (!mysqli_real_connect($db, 'serverip', 'user', 'userpass', 'databbasename', serverportonlynumbernoapostro, NULL, MYSQLI_CLIENT_SSL_DONT_VERIFY_SERVER_CERT))
{
die("Connect Error: " . mysqli_connect_error());
}
?>

在我的示例中:certs 文件夹 = PHP 文件