本文介绍配置了SSL链路加密后,如何通过MySQL命令行终端以及JDBC连接数据库。
前提条件
操作步骤
使用云端证书连接MySQL
开启SSL加密后,客户端和RDS MySQL之间的连接是否加密与客户端的类型和设置有关。例如,客户端可能默认采用加密连接。您可以修改客户端的设置或代码,要求建立加密连接以及验证RDS MySQL的身份。
命令行
对于MySQL 5.7.11及以后版本的客户端,在连接命令中添加--ssl-mode选项可以设置SSL加密。
对于MariaDB客户端以及MySQL 5.7.11之前的客户端,请使用--ssl和--ssl-verify-server-cert等选项。具体请参见MariaDB和MySQL官方文档。
--ssl-mode=DISABLED表示连接不加密。
--ssl-mode=PREFERRED或者不添加--ssl-mode选项,表示尝试加密连接,如果无法加密则采用非加密连接。
--ssl-mode=REQUIRED,表示必须加密连接,如果无法加密则连接失败。
--ssl-mode=VERIFY_CA,表示必须加密连接,并用本地的CA证书验证服务器证书是否有效。
--ssl-mode=VERIFY_IDENTITY,表示必须加密连接,并用本地的CA证书验证服务器证书是否有效,并验证服务器证书的主机名或IP地址是否与实际连接的主机名或IP地址匹配。
示例一:尝试加密连接,如果无法加密则采用非加密连接。
mysql -h {RDS连接地址} -u {RDS账号} -p --ssl-mode=PREFERRED
示例二:要求加密连接,并验证服务器证书的有效性。
mysql -h {RDS连接地址} -u {RDS账号} -p --ssl-mode=VERIFY_CA --ssl-ca={CA证书路径}/ApsaraDB-CA-Chain.pem
上述示例里的{RDS连接地址}、{RDS账号}和{CA证书路径}需替换为实际的值。
更多关于--ssl-mode选项的说明,请参见MySQL官方文档。
MySQL Workbench
打开MySQL Workbench,选择
。填写RDS连接地址和账号密码。
在SSL页签下,设置Use SSL参数,指定SSL CA File为下载的PEM格式CA证书,然后单击Test Connection或者OK。
说明关于Use SSL参数的选项,可以参考命令行连接方式的--ssl-mode说明。
DMS
在DMS中录入RDS MySQL实例时,可设置开启SSL参数。具体操作,请参见云数据库录入。
也可以在已录入的实例上右键,选择编辑实例,然后在高级信息中设置。
应用程序代码
Java
Connector/J(mysql-connector-java)是MySQL官方提供的JDBC驱动程序。本示例使用mysql-connector-java 8.0.19版本作为依赖。
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.19</version>
</dependency>
以下示例代码使用sslMode属性指定SSL模式。mysql-connector-java从8.0.13版本开始支持该属性,如果您使用更早的版本,则需要改为使用useSSL、requireSSL和verifyServerCertificate属性,具体请参见MySQL文档。
示例代码:
package com.aliyun.sample;
import com.mysql.cj.jdbc.MysqlDataSource;
import java.sql.Connection;
import java.sql.SQLException;
public class Sample {
public static void main(String[] args) {
Connection conn = null;
MysqlDataSource mysqlDS=null;
try{
mysqlDS = new MysqlDataSource();
//可按需设置SslMode。关于该属性的选项,请参见命令行连接方式的说明。
mysqlDS.setSslMode("VERIFY_IDENTITY");
//truststore用于存储CA证书,这里设置truststore类型为JKS。
mysqlDS.setTrustCertificateKeyStoreType("JKS");
// 请将file:/后面的路径改为您的ApsaraDB-CA-Chain.jks文件的路径。
mysqlDS.setTrustCertificateKeyStoreUrl("file:/D:\\ApsaraDB-CA-Chain\\ApsaraDB-CA-Chain.jks");
// 下载的JKS文件的密码为apsaradb,不能修改。
mysqlDS.setTrustCertificateKeyStorePassword("apsaradb");
// 您的数据库连接串
mysqlDS.setServerName("rm-xxxxxx.mysql.rds.aliyuncs.com");
// 您的数据库端口
mysqlDS.setPort(3306);
// 您的数据库账号
mysqlDS.setUser("xxxxxx");
// 您的数据库密码
mysqlDS.setPassword("xxxxxx");
// 您的数据库名
mysqlDS.setDatabaseName("xxxxxx");
conn = mysqlDS.getConnection();
}catch(Exception e){
e.printStackTrace();
} finally {
try {
if (conn != null)
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
Python
# 安装pymysql pip install pymysql
import pymysql
try:
ssl_config = {"ca":"/path/to/path/ca.crt", "mode":"VERIFY_CA"} # ca为证书的路径,mode为ssl-mode
conn = pymysql.connect(host='******.mysql.rds.aliyuncs.com', user='*****', passwd='******', db='*****', ssl=ssl_config)
cursor = conn.cursor()
cursor.execute('select version()')
data = cursor.fetchone()
print('Database version:', data[0])
cursor.close()
except pymysql.Error as e:
print(e)
使用自定义证书连接MySQL
命令行
对于MySQL 5.7.11及以后版本的客户端,在连接命令中添加--ssl-mode选项可以设置SSL加密。
对于MariaDB客户端以及MySQL 5.7.11之前的客户端,请使用--ssl和--ssl-verify-server-cert等选项。具体请参见MariaDB和MySQL官方文档。
--ssl-mode=DISABLED表示连接不加密。
--ssl-mode=PREFERRED或者不添加--ssl-mode选项,表示尝试加密连接,如果无法加密则采用非加密连接。
--ssl-mode=REQUIRED,表示必须加密连接,如果无法加密则连接失败。
--ssl-mode=VERIFY_CA,表示必须加密连接,并用本地的CA证书验证服务器证书是否有效。
--ssl-mode=VERIFY_IDENTITY,表示必须加密连接,并用本地的CA证书验证服务器证书是否有效,并验证服务器证书的主机名或IP地址是否与实际连接的主机名或IP地址匹配。
示例:
尝试加密连接,如果无法加密则采用非加密连接。
mysql -h {RDS连接地址} -u {RDS账号} -p --ssl-mode=PREFERRED
要求加密连接,并验证服务器证书的有效性。
mysql -h {RDS连接地址} -u {RDS账号} -p --ssl-mode=VERIFY_CA --ssl-ca={自定义CA证书路径}
上述示例里的
{RDS连接地址}
、{RDS账号}
、{CA证书路径}
、{自定义CA证书路径}
需替换为实际的值。更多关于--ssl-mode选项的说明,请参见MySQL官方文档。
MySQL Workbench
打开MySQL Workbench,选择Database > Manage Connections。
填写RDS连接地址和账号密码。
在SSL页签下,设置Use SSL参数,如果为云端证书则指定SSL CA File为下载的PEM格式CA证书,如果配置的为自定义证书则指定SSL CA File为自定义的CA证书,然后单击Test Connection或者OK。
关于Use SSL参数的选项,可以参考命令行连接方式的--ssl-mode说明。
DMS
在DMS中录入RDS MySQL实例时,可设置开启SSL参数。具体操作,请参见云数据库录入。
也可以在已录入的实例上右键,选择编辑实例,然后在高级信息中设置。
应用程序代码
Java
Connector/J(mysql-connector-java)是MySQL官方提供的JDBC驱动程序。本示例使用mysql-connector-java 8.0.19版本作为依赖。
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.19</version>
</dependency>
配置为自定义证书,需要手动生成JKS文件,具体步骤如下:
将你的客户端证书和私钥转换成PKCS#12格式,因为keytool不直接支持从PEM格式导入私钥和证书。使用OpenSSL做这个转换:
openssl pkcs12 -export -in {自定义CA证书} -inkey {自定义CA证书私钥} -out keystore.p12 -name ganyang -CAfile {自定义CA证书} # 需要输入密码,连接时需要使用 Enter Encryption Password: Verifying - Enter Encryption Password:
使用keytool导入刚才创建的PKCS#12文件到新的JKS文件):
keytool -importkeystore -deststorepass JKS-password -destkeypass key-password -destkeystore keystore.jks -deststoretype pkcs12 -srckeystore keystore.p12 -srcstoretype pkcs12 -srcstorepass P12-password -alias your-alias
关键词解释:
-deststorepass 为JKS文件设置的密码。 -destkeypass 为JKS文件里的密钥设置的密码。 -destkeystore 想要创建或已有的JKS文件。 -deststoretype 想要创建文件的类型是PKCS#12。 -srckeystore 之前生成的PKCS#12文件。 -srcstoretype 表明源文件的类型是PKCS#12。 -srcstorepass 保护PKCS#12文件的密码。 -alias 用户给的客户端证书和私钥设置的别名。
获取创建的JKS文:在keytool成功导入后可在执行目录下找到keystore.jks。
以下示例代码使用sslMode属性指定SSL模式。mysql-connector-java从8.0.13版本开始支持该属性,如果您使用更早的版本,则需要改为使用useSSL、requireSSL和verifyServerCertificate属性,具体请参见MySQL文档。
package com.aliyun.sample;
import com.mysql.cj.jdbc.MysqlDataSource;
import java.sql.Connection;
import java.sql.SQLException;
public class Sample {
public static void main(String[] args) {
Connection conn = null;
MysqlDataSource mysqlDS=null;
try{
mysqlDS = new MysqlDataSource();
//可按需设置SslMode。关于该属性的选项,请参见命令行连接方式的说明。
mysqlDS.setSslMode("VERIFY_IDENTITY");
//以下为云端证书的JKS实现方式,如果MySQL配置为自定义证书,替换为通过自定义证书生成的JKS文件路径和对应密码即可
//truststore用于存储CA证书,这里设置truststore类型为JKS。
mysqlDS.setTrustCertificateKeyStoreType("JKS");
// 请将file:/后面的路径改为您的ApsaraDB-CA-Chain.jks文件的路径
mysqlDS.setTrustCertificateKeyStoreUrl("file:/D:\\ApsaraDB-CA-Chain\\ApsaraDB-CA-Chain.jks");
// 下载的JKS文件的密码为apsaradb,不能修改。
mysqlDS.setTrustCertificateKeyStorePassword("apsaradb");
// 您的数据库连接串
mysqlDS.setServerName("rm-xxxxxx.mysql.rds.aliyuncs.com");
// 您的数据库端口
mysqlDS.setPort(3306);
// 您的数据库账号
mysqlDS.setUser("xxxxxx");
// 您的数据库密码
mysqlDS.setPassword("xxxxxx");
// 您的数据库名
mysqlDS.setDatabaseName("xxxxxx");
conn = mysqlDS.getConnection();
}catch(Exception e){
e.printStackTrace();
} finally {
try {
if (conn != null)
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
Python
# 安装pymysql pip install pymysql
import pymysql
try:
ssl_config = {"ca":"/path/to/path/ca.crt", "mode":"VERIFY_CA"} # ca为证书的路径,mode为ssl-mode
conn = pymysql.connect(host='******.mysql.rds.aliyuncs.com', user='*****', passwd='******', db='*****', ssl=ssl_config)
cursor = conn.cursor()
cursor.execute('select version()')
data = cursor.fetchone()
print('Database version:', data[0])
cursor.close()
except pymysql.Error as e:
print(e)