新しい SSL/TLS 証明書を使用して MySQL DB インスタンスに接続するようにアプリケーションを更新 - Amazon Relational Database Service

新しい SSL/TLS 証明書を使用して MySQL DB インスタンスに接続するようにアプリケーションを更新

2019 年 9 月 19 日に Amazon RDS は、Secure Socket Layer または Transport Layer Security (SSL/TLS) を使用して RDS DB インスタンスに接続するための新しい認証局 (CA) 証明書を公開しました。ここでは、新しい証明書を使用するためのアプリケーションの更新について説明します。

このトピックでは、クライアントアプリケーションが SSL/TLS を使用して DB インスタンスに接続されているかどうかを判断できます。該当する場合はさらに、それらのアプリケーションの接続に証明書の検証が必要かどうかを確認できます。

注記

一部のアプリケーションは、サーバー上の証明書を正常に検証できる場合にのみ、MySQL DB インスタンスに接続されるように設定されています。そのようなアプリケーションの場合は、新しい CA 証明書を含むように、クライアントアプリケーションの信頼ストアを更新する必要があります。

disabledpreferred、および required の SSL モードを指定できます。preferred SSL モードを使用していて、CA 証明書が存在しないか、最新でない場合は、次の動作が適用されます。

  • より新しい MySQL のマイナーバージョンでは、接続は SSL を使用しない状態に戻り、正常に接続されます。

    これらの新しいバージョンでは OpenSSL プロトコルが使用されるため、サーバー証明書の有効期限が切れても、 required SSL モードが指定されていない限り、接続の成功は妨げられません。

    次の MySQL のマイナーバージョンでは、OpenSSL プロトコルが使用されます。

    • すべての MySQL 8.0 バージョン

    • MySQL 5.7.21 以降の MySQL 5.7 バージョン

    • MySQL 5.6.39 以降の MySQL 5.6 バージョン

    • MySQL 5.5.59 以降の MySQL 5.5 バージョン

  • 古い MySQL のマイナーバージョンでは、エラーが返されます。

    これらの古いバージョンでは yaSSL プロトコルを使用しているため、証明書の検証は厳密に行われ、接続は失敗します。

    次の MySQL のマイナーバージョンでは、yaSSL プロトコルが使用されます。

    • MySQL 5.7.19 以前の MySQL 5.7 バージョン

    • MySQL 5.6.37 以前の MySQL 5.6 バージョン

    • MySQL 5.5.57 以前の MySQL 5.5 バージョン

クライアントアプリケーションの信頼ストアで CA 証明書を更新した後、DB インスタンスで証明書をローテーションできます。これらの手順を開発環境またはステージング環境でテストしてから、本番環境で実装することを強くお勧めします。

証明書のローテーションの詳細については、「SSL/TLS 証明書の更新」を参照してください。証明書のダウンロードの詳細については、SSL/TLS を使用した DB インスタンスへの接続の暗号化 を参照してください。MySQL DB インスタンスで SSL/TLS を使用する方法については、「MySQL DB インスタンスで SSL を使用する」を参照してください。

アプリケーションが SSL を使用して MySQL DB インスタンスに接続しているかどうかの確認

Amazon RDS for MySQL バージョン 5.7 または 8.0 を使用しており、パフォーマンススキーマが有効になっている場合は、次のクエリを実行すると、接続で SSL/TLS が使用されているかどうかを確認できます。パフォーマンススキーマを有効にする方法については、MySQL のドキュメントの「Performance Schema Quick Start」を参照してください。

mysql> SELECT id, user, host, connection_type FROM performance_schema.threads pst INNER JOIN information_schema.processlist isp ON pst.processlist_id = isp.id;

この出力例では、admin で SSL が使用されているため、独自のセッション (webapp1) と、ログインしているアプリケーションの両方を確認できます。

+----+-----------------+------------------+-----------------+ | id | user | host | connection_type | +----+-----------------+------------------+-----------------+ | 8 | admin | 10.0.4.249:42590 | SSL/TLS | | 4 | event_scheduler | localhost | NULL | | 10 | webapp1 | 159.28.1.1:42189 | SSL/TLS | +----+-----------------+------------------+-----------------+ 3 rows in set (0.00 sec)

Amazon RDS for MySQL バージョンs 5.5 または 5.6を使用している場合は、アプリケーションが SSL を使用して接続されているかどうかをサーバー側から判別することはできません。これらのバージョンで SSL が使用されているかどうかを判別するには、アプリケーションの接続方法を調べます。次のセクションでは、クライアント接続設定の調査方法について詳しく説明します。

クライアントを接続するために証明書の検証が必要かどうかの確認

JDBC クライアントおよび MySQL クライアントを接続するために証明書の検証が必要かどうかを確認できます。

JDBC

MySQL Connector/J 8.0 を使用した次の例では、アプリケーションの JDBC 接続プロパティをチェックして、正常な接続に有効な証明書が必要かどうかを確認する 1 つの方法を示します。MySQL のすべての JDBC 接続オプションの詳細については、MySQL のドキュメントの「設定プロパティ」を参照してください。

MySQL Connector/J 8.0 を使用するとき、次の例のように、接続プロパティで sslModeVERIFY_CA または VERIFY_IDENTITY に設定されている場合、SSL 接続にはサーバー CA 証明書に対する検証が必要です。

Properties properties = new Properties(); properties.setProperty("sslMode", "VERIFY_IDENTITY"); properties.put("user", DB_USER); properties.put("password", DB_PASSWORD);
注記

MySQL Java Connector v5.1.38 以降または MySQL Java Connector v8.0.9 以降を使用してデータベースに接続する場合、データベースへの接続時に SSL/TLS を使用するようにアプリケーションを明示的に設定しなくても、これらのクライアントドライバーはデフォルトで SSL/TLS を使用します。また、SSL/TLS の使用時に証明書検証が部分的に実行され、データベースサーバー証明書の有効期限が切れていると、接続に失敗します。

MySQL

MySQL クライアントの以下の例では、スクリプトの MySQL 接続をチェックして、正常な接続に有効な証明書が必要かどうかを確認する 2 つの方法を示します。MySQL クライアントで使用するすべての接続オプションの詳細については、MySQL のドキュメントの「 Client-Side Configuration for Encrypted Connections」を参照してください。

MySQL 5.7 または MySQL 8.0 クライアントを使用するとき、次の例のように、--ssl-mode オプションに VERIFY_CA または VERIFY_IDENTITY を指定する場合、SSL 接続にはサーバー CA 証明書に対する検証が必要です。

mysql -h mysql-database.rds.amazonaws.com -uadmin -ppassword --ssl-ca=/tmp/ssl-cert.pem --ssl-mode=VERIFY_CA

MySQL 5.6 クライアントを使用するとき、次の例のように、--ssl-verify-server-cert オプションを指定する場合、SSL 接続にはサーバー CA 証明書に対する検証が必要です。

mysql -h mysql-database.rds.amazonaws.com -uadmin -ppassword --ssl-ca=/tmp/ssl-cert.pem --ssl-verify-server-cert

アプリケーション信頼ストアの更新

MySQL アプリケーションの信頼ストアの更新については、MySQL ドキュメントの「Installing SSL Certificates」を参照してください。

注記

信頼ストアを更新するとき、新しい証明書を追加できるだけでなく、古い証明書を保持できます。

JDBC のアプリケーション信頼ストアの更新

SSL/TLS 接続に JDBC を使用するアプリケーションの信頼ストアを更新できます。

JDBC アプリケーションの信頼ストアを更新するには

  1. すべての AWS リージョンで動作する 2019 ルート証明書をダウンロードし、そのファイルを信頼ストアのディレクトリに置きます。

    ルート証明書のダウンロードについては、SSL/TLS を使用した DB インスタンスへの接続の暗号化 を参照してください。

  2. 次のコマンドを使用して、証明書を .der 形式に変換します。

    openssl x509 -outform der -in rds-ca-2019-root.pem -out rds-ca-2019-root.der

    ファイル名を、ダウンロードしたファイル名に置き換えます。

  3. 次のコマンドを使用して、証明書をキーストアにインポートします。

    keytool -import -alias rds-root -keystore clientkeystore -file rds-ca-2019-root.der
  4. キーストアが正常に更新されたことを確認します。

    keytool -list -v -keystore clientkeystore.jks

    キーストアのパスワードを求められたら、パスワードを入力します。

    出力には次の内容が含まれている必要があります。

    rds-root,date, trustedCertEntry, Certificate fingerprint (SHA1): D4:0D:DB:29:E3:75:0D:FF:A6:71:C3:14:0B:BF:5F:47:8D:1C:80:96 # This fingerprint should match the output from the below command openssl x509 -fingerprint -in rds-ca-2019-root.pem -noout

アプリケーションで mysql JDBC ドライバーを使用している場合は、アプリケーションで以下のプロパティを設定します。

System.setProperty("javax.net.ssl.trustStore", certs); System.setProperty("javax.net.ssl.trustStorePassword", "password");

アプリケーションを起動するとき、以下のプロパティを設定します。

java -Djavax.net.ssl.trustStore=/path_to_truststore/MyTruststore.jks -Djavax.net.ssl.trustStorePassword=my_truststore_password com.companyName.MyApplication

SSL 接続を確立するための Java コードの例

次のコード例では、JDBC を使用してサーバー証明書を検証する SSL 接続のセットアップ方法を示します。

public class MySQLSSLTest { private static final String DB_USER = "username"; private static final String DB_PASSWORD = "password"; // This key store has only the prod root ca. private static final String KEY_STORE_FILE_PATH = "file-path-to-keystore"; private static final String KEY_STORE_PASS = "keystore-password"; public static void test(String[] args) throws Exception { Class.forName("com.mysql.jdbc.Driver"); System.setProperty("javax.net.ssl.trustStore", KEY_STORE_FILE_PATH); System.setProperty("javax.net.ssl.trustStorePassword", KEY_STORE_PASS); Properties properties = new Properties(); properties.setProperty("sslMode", "VERIFY_IDENTITY"); properties.put("user", DB_USER); properties.put("password", DB_PASSWORD); Connection connection = null; Statement stmt = null; ResultSet rs = null; try { connection = DriverManager.getConnection("jdbc:mysql://mydatabase.123456789012.us-east-1.rds.amazonaws.com:3306",properties); stmt = connection.createStatement(); rs=stmt.executeQuery("SELECT 1 from dual"); } finally { if (rs != null) { try { rs.close(); } catch (SQLException e) { } } if (stmt != null) { try { stmt.close(); } catch (SQLException e) { } } if (connection != null) { try { connection.close(); } catch (SQLException e) { e.printStackTrace(); } } } return; } }
重要

データベース接続で SSL/TLS を使用することを決定し、アプリケーションの信頼ストアを更新したら、rds-ca-2019 証明書を使用するようにデータベースを更新できます。手順については、「DB インスタンスの変更による CA 証明書の更新」のステップ 3 を参照してください。