Amazon RDS Oracle ウォレットの CA 証明書バンドルを使用して SSL/TLS エンドポイントに接続するにはどうすればよいですか?
Oracle ウォレットを使用して Oracle DB インスタンスの Amazon Relational Database Service (Amazon RDS) から外部の SSL/TLS エンドポイントと安全に通信したいと考えています。
解決策
**注:**AWS コマンドラインインターフェイス (AWS CLI) コマンドの実行中にエラーが発生した場合は、「AWS CLI エラーのトラブルシューティング」を参照してください。また、AWS CLI の最新バージョンを使用しているようにしてください。
ターゲット SSL/TLS エンドポイントのルート証明書と中間証明書をダウンロードする
-
ウェブブラウザで、アクセスしたい URL (Web サービスの SSL/TLS エンドポイント) を開きます。
-
ブラウザのアドレスバーに証明書の詳細を表示するには、南京錠マークを選択します。または、ローカルワークステーションのコマンドラインで次のようなコマンドを実行します。
注: status.aws.amazon.com は、アクセスする URL に置き換えてください。
$ openssl s_client -connect status.aws.amazon.com:443 CONNECTED(00000003) depth=2 C = US, O = Amazon, CN = Amazon Root CA 1 verify return:1 depth=1 C = US, O = Amazon, CN = Amazon RSA 2048 M01 verify return:1 depth=0 CN = status.aws.amazon.com verify return:1 --- Certificate chain 0 s:CN = status.aws.amazon.com i:C = US, O = Amazon, CN = Amazon RSA 2048 M01 1 s:C = US, O = Amazon, CN = Amazon RSA 2048 M01 i:C = US, O = Amazon, CN = Amazon Root CA 1 2 s:C = US, O = Amazon, CN = Amazon Root CA 1 i:C = US, ST = Arizona, L = Scottsdale, O = "Starfield Technologies, Inc.", CN = Starfield Services Root Certificate Authority - G2 3 s:C = US, ST = Arizona, L = Scottsdale, O = "Starfield Technologies, Inc.", CN = Starfield Services Root Certificate Authority - G2 i:C = US, O = "Starfield Technologies, Inc.", OU = Starfield Class 2 Certification Authority
-
証明書プロバイダーから、一覧表示された関連するルート証明書と中間証明書をダウンロードします。この例では、スタックトレースで、Amazon Root CA 1 と Amazon RSA 2048 M01 の証明書が必要であることが示されています。Amazon Trust Services リポジトリから証明書をダウンロードします。
-
証明書を pem 形式でダウンロードできない場合は、DER/CRT 形式で証明書をダウンロードします。ダウンロードした証明書を PEM 形式に変換するには、ローカルワークステーションのコマンドラインで次のようなコマンドを実行します。
$ openssl x509 -inform der -in "Amazon Root CA 1.der" -outform pem -out "Amazon Root CA 1.pem" $ openssl x509 -inform der -in "Amazon RSA 2048 M01.der" -outform pem -out "Amazon RSA 2048 M01.pem"
Oracle ウォレットを作成してから、SSL/TLS エンドポイントのルート証明書と中間証明書をロードする
-
orapki ユーティリティを使用して Oracle ウォレットを作成します。orapki ユーティリティは、Oracle クライアントソフトウェアをインストールするときに使用できます。Oracle JDeveloper Studio エディションには orapki ユーティリティも含まれています。ソースデータベース環境でウォレットを作成する必要があります。
-
ウォレットの作成時に、いくつか選択できるパラメーターがあります。例えば、auto_login_only を使用すると、開くためにパスワードを必要としない自動ログインウォレット (cwallet.sso) を作成できます。
-
ウォレットを作成するディレクトリに移動します。その後、ローカルワークステーションのコマンドラインで次のコマンドを実行します。
cd /app/client/wallet> orapki wallet create -wallet . -auto_login_only
-
次の 2 つの証明書をウォレットに追加します。
orapki wallet add -wallet . -trusted_cert -cert "Amazon Root CA 1.pem" -auto_login_only orapki wallet add -wallet . -trusted_cert -cert "Amazon RSA 2048 M01.pem" -auto_login_only
-
ウォレットの内容を確認し、証明書を追加したことを確認します。
>ls -ltrh cwallet.sso -rw------- 1 oracle oinstall 2.3K Aug 13 11:39 cwallet.sso >orapki wallet display -wallet .Oracle PKI Tool Release 19.0.0.0.0 - Production Version 19.3.0.0.0 Copyright (c) 2004, 2019, Oracle and/or its affiliates. All rights reserved. Requested Certificates: User Certificates: Trusted Certificates: Subject: CN=Amazon RSA 2048 M01,O=Amazon,C=US Subject: CN=Amazon Root CA 1,O=Amazon,C=US
S3 バケットにウォレットをアップロードする
新しい Amazon Simple Storage Service (Amazon S3) バケットを作成するか、既存のバケットを使用してウォレットをアップロードします。AWS CLI を使用する場合は、Oracle ウォレットを作成したクライアントマシンで次のコマンドを実行します。または、Amazon S3 コンソールからウォレットをアップロードします。
aws s3 cp cwallet.sso s3://wallet4321/
注: wallet4321 は、該当する S3 バケットの名前に置き換えてください。
データベースユーザーと権限の設定
-
SQL\ *Plus をプライマリユーザーとして使用して RDS for Oracle DB インスタンスに接続します。
-
UTL_HTTP パッケージを使用できるようにするデータベースユーザーに対して、必要な権限を付与します。
SQL> define user=' '; SQL> BEGIN rdsadmin.rdsadmin_util.grant_sys_object('DBA_DIRECTORIES', UPPER('&user')); END; 2 / old 1: BEGIN rdsadmin.rdsadmin_util.grant_sys_object('DBA_DIRECTORIES', UPPER('&user')); END; new 1: BEGIN rdsadmin.rdsadmin_util.grant_sys_object('DBA_DIRECTORIES', UPPER('app_user')); END; PL/SQL procedure successfully completed. SQL> BEGIN rdsadmin.rdsadmin_util.grant_sys_object('UTL_HTTP', UPPER('&user')); END; 2 / old 1: BEGIN rdsadmin.rdsadmin_util.grant_sys_object('UTL_HTTP', UPPER('&user')); END; new 1: BEGIN rdsadmin.rdsadmin_util.grant_sys_object('UTL_HTTP', UPPER('app_user')); END; PL/SQL procedure successfully completed. SQL> BEGIN rdsadmin.rdsadmin_util.grant_sys_object('UTL_FILE', UPPER('&user')); END; 2 / old 1: BEGIN rdsadmin.rdsadmin_util.grant_sys_object('UTL_FILE', UPPER('&user')); END; new 1: BEGIN rdsadmin.rdsadmin_util.grant_sys_object('UTL_FILE', UPPER('app_user')); END; PL/SQL procedure successfully completed.
注: app_user は、UTL_HTTP コマンドを実行できるようにする RDS データベースユーザーの名前に置き換えてください。
-
ウォレット用のディレクトリを作成します。
注: 各ウォレットを独自のディレクトリに保存するのがベストプラクティスです。
SQL> exec rdsadmin.rdsadmin_util.create_directory('WALLET');
S3 バケットから RDS DB インスタンスにウォレットをダウンロードする
注: このステップは、Amazon S3 統合の有無にかかわらず完了できます。
**Amazon S3 統合を使用する **
-
Amazon S3 統合を使用して、S3 バケットから DB インスタンスにウォレットをダウンロードします。
-
S3 バケットからウォレットファイルをダウンロードするには、DB インスタンスに接続されている SQL*Plus セッションで次のコマンドを実行します。
SQL> SELECT rdsadmin.rdsadmin_s3_tasks.download_from_s3( p_bucket_name => 'wallet4321', p_s3_prefix => 'cwallet.sso', p_directory_name => 'WALLET') AS TASK_ID FROM DUAL; OUTPUT 1691935899410-1902
-
結果を表示するには、前のステップの task-id を使用してタスクの出力ファイルを表示します。
SQL> SELECT text FROM table(rdsadmin.rds_file_util.read_text_file('BDUMP','dbtask-1691935899410-1902.log')); OUTPUT 2023-08-13 14:11:39.497 UTC [INFO ] This task is about to list the Amazon S3 objects for AWS Region us-east-1, bucket name wallet4321, and prefix cwallet.sso. 2023-08-13 14:11:39.552 UTC [INFO ] The task successfully listed the Amazon S3 objects for AWS Region us-east-1, bucket name wallet4321, and prefix cwallet.sso. 2023-08-13 14:11:39.568 UTC [INFO ] This task is about to download the Amazon S3 object or objects in /rdsdbdata/userdirs/01 from bucket name wallet4321 and key cwallet.sso. 2023-08-13 14:11:39.719 UTC [INFO ] The task successfully downloaded the Amazon S3 object or objects from bucket name wallet4321 with key cwallet.sso to the location /rdsdbdata/userdirs/01. 2023-08-13 14:11:39.720 UTC [INFO ] The task finished successfully.
-
ウォレットが DB インスタンスにダウンロードされたことを確認します。
SQL> select * from table (rdsadmin.rds_file_util.listdir(p_directory => 'WALLET')); FILENAME TYPE FILESIZE MTIME ------------------- ---------- ---------- -------------------- 01/ directory 4096 13-AUG-2023 14:11:39 cwallet.sso file 2349 13-AUG-2023 14:11:39
-
UTL_HTTP トランザクションのウォレットパスを設定します。
SQL> DECLAREl_wallet_path all_directories.directory_path%type; BEGIN select directory_path into l_wallet_path from all_directories where upper(directory_name)='WALLET'; utl_http.set_wallet('file:/' || l_wallet_path); END; / PL/SQL procedure successfully completed.
-
Web サービスホストの DNS 名前解決を確認します。
SQL> SELECT UTL\_INADDR.GET\_HOST\_ADDRESS(host => 'status.aws.amazon.com') FROM DUAL
Oracle ウォレットを使用してリモート Web サービス URL を参照します。
SQL> SELECT utl_http.request('https://status.aws.amazon.com/robots.txt') AS ROBOTS_TXT FROM DUAL; ROBOTS_TXT -------------------------------------------------------------------------------- {"message":"Not Found"}
**S3 統合なし **
-
Oracle の ACL でアウトバウンドトラフィックを許可するには、DB インスタンスに接続されている SQL*Plus セッションで次のコマンドを実行します。
SQL> define user='app_user'; SQL> BEGIN DBMS_NETWORK_ACL_ADMIN.CREATE_ACL ( acl => 's3.xml', description => 'AWS S3 ACL', principal => UPPER('&user'), is_grant => TRUE, privilege => 'connect'); COMMIT; END; / old 3: ( acl => 's3.xml', description => 'AWS S3 ACL', principal => UPPER('&user'), is_grant => TRUE, privilege => 'connect'); new 3: ( acl => 's3.xml', description => 'AWS S3 ACL', principal => UPPER('app_user'), is_grant => TRUE, privilege => 'connect'); PL/SQL procedure successfully completed. SQL> BEGIN DBMS_NETWORK_ACL_ADMIN.ASSIGN_ACL ( acl => 's3.xml', host => '*.amazonaws.com'); COMMIT; END; / PL/SQL procedure successfully completed.
-
DB インスタンスに接続されている SQL*Plus セッションで次のプロシージャを作成します。
SQL> CREATE OR REPLACE PROCEDURE s3_download_presigned_url ( p_s3_url IN VARCHAR2, p_local_filename IN VARCHAR2, p_local_directory IN VARCHAR2, p_wallet_directory IN VARCHAR2 DEFAULT NULL ) AS -- Local variables l_req utl_http.req; l_wallet_path VARCHAR2(4000); l_fh utl_file.file_type; l_resp utl_http.resp; l_data raw(32767); l_file_size NUMBER; l_file_exists BOOLEAN; l_block_size BINARY_INTEGER; l_http_status NUMBER; -- User-defined exceptions e_https_requires_wallet EXCEPTION; e_wallet_dir_invalid EXCEPTION; e_http_exception EXCEPTION; BEGIN -- Validate input IF (regexp_like(p_s3_url, '^https:', 'i') AND p_wallet_directory IS NULL) THEN raise e_https_requires_wallet; END IF; -- Use wallet, if specified IF (p_wallet_directory IS NOT NULL) THEN BEGIN SELECT directory_path INTO l_wallet_path FROM dba_directories WHERE upper(directory_name)= upper(p_wallet_directory); utl_http.set_wallet('file:' || l_wallet_path); EXCEPTION WHEN NO_DATA_FOUND THEN raise e_wallet_dir_invalid; END; END IF; -- Do HTTP request BEGIN l_req := utl_http.begin_request(p_s3_url, 'GET', 'HTTP/1.1'); l_fh := utl_file.fopen(p_local_directory, p_local_filename, 'wb', 32767); l_resp := utl_http.get_response(l_req); -- If we get HTTP error code, write that instead l_http_status := l_resp.status_code; IF (l_http_status != 200) THEN dbms_output.put_line('WARNING: HTTP response ' || l_http_status || ' - ' || l_resp.reason_phrase || '. Details in ' || p_local_filename ); END IF; -- Loop over response and write to file BEGIN LOOP utl_http.read_raw(l_resp, l_data, 32766); utl_file.put_raw(l_fh, l_data, true); END LOOP; EXCEPTION WHEN utl_http.end_of_body THEN utl_http.end_response(l_resp); END; -- Get file attributes to see what we did utl_file.fgetattr( location => p_local_directory, filename => p_local_filename, fexists => l_file_exists, file_length => l_file_size, block_size => l_block_size ); utl_file.fclose(l_fh); dbms_output.put_line('wrote ' || l_file_size || ' bytes'); EXCEPTION WHEN OTHERS THEN utl_http.end_response(l_resp); utl_file.fclose(l_fh); dbms_output.put_line(dbms_utility.format_error_stack()); dbms_output.put_line(dbms_utility.format_error_backtrace()); raise; END; EXCEPTION WHEN e_https_requires_wallet THEN dbms_output.put_line('ERROR: HTTPS requires a valid wallet location'); WHEN e_wallet_dir_invalid THEN dbms_output.put_line('ERROR: wallet directory not found'); WHEN others THEN raise; END s3_download_presigned_url;
-
署名付き URL を生成するには、AWS CLI を使用して次のコマンドを実行します。署名付き URL は、デフォルトで 1 時間有効です。
>aws s3 presign s3://wallet4321/cwallet.sso https://wallet4321.s3.amazonaws.com/cwallet.sso?AWSAccessKeyId=AKIAJWTPIJJA4FAQURFA&Signature=u8ysKQyp4O6ws3Qy5qZak8PfmLE%3D&Expires=1588199836
-
S3 バケットからウォレットをダウンロードするには、DB インスタンスに接続されている SQL*Plus セッションで s3_download_presigned_url プロシージャを実行します。s3_download_presigned_url プロシージャを実行する前に、次の入力パラメータを更新します。
p_s3 url - 生成した署名付き URL を入力します
p_local_filename - ウォレットファイルの名前を入力します
p_local_directory - ウォレットを保存するために DB インスタンスに作成したディレクトリの名前を入力します
p_wallet_directory - S3_SSL_WALLET と入力します。DB インスタンスは、このディレクトリを使用して Amazon S3 ウェブサービス証明書を含んでいるウォレットを保存します。
次のコマンドの例では、HTTP を使用して S3 ウェブサービスにアクセスします。コマンドを実行する前に、署名付き URL の https を http に置き換えてください。
SQL> SET SERVEROUTPUT ON; SQL> set define #; SQL> BEGIN s3_download_presigned_url( p_s3_url=> 'http://wallet4321.s3.amazonaws.com/cwallet.sso?AWSAccessKeyId=AKIAJWTPIJJA4FAQURFA&Signature=u8ysKQyp4O6ws3Qy5qZak8PfmLE%3D&Expires=1588199836', p_local_filename => 'cwallet.sso', p_local_directory => 'WALLET' ); END; /
次のコマンドの例では、HTTP を使用して Amazon S3 ウェブサービスにアクセスします。
注: HTTPS を使用するには、Amazon S3 ウェブサービスウォレットを DB インスタンスディレクトリ S3_SSL_WALLET に保存する必要があります。
SQL> exec rdsadmin.rdsadmin_util.create_directory('S3_SSL_WALLET'); SQL> SET SERVEROUTPUT ON; SQL> set define #; SQL> BEGIN s3_download_presigned_url( p_s3_url=> 'https://wallet4321.s3.amazonaws.com/cwallet.sso?AWSAccessKeyId=AKIAJWTPIJJA4FAQURFA&Signature=u8ysKQyp4O6ws3Qy5qZak8PfmLE%3D&Expires=1588199836', p_local_filename => 'cwallet.sso', p_local_directory => 'WALLET', p_wallet_directory => 'S3_SSL_WALLET' ); END; /
-
ウォレットが RDS for Oracle DB インスタンスにダウンロードされたことを確認します。
SQL> select * from table (rdsadmin.rds_file_util.listdir(p_directory => 'WALLET')); FILENAME TYPE FILESIZE MTIME ------------------- ---------- ---------- -------------------- 01/ directory 4096 13-AUG-2023 15:15:39 cwallet.sso file 2349 13-AUG-2023 15:15:39
-
url_http トランザクションのウォレットパスを設定します。
SQL> DECLARE l_wallet_path all_directories.directory_path%type; BEGIN select directory_path into l_wallet_path from all_directories where upper(directory_name)='WALLET'; utl_http.set_wallet('file:/' || l_wallet_path); END; / PL/SQL procedure successfully completed.
-
Web サービスホストの DNS 名前解決を確認します。
SQL> SELECT UTL_INADDR.GET_HOST_ADDRESS(host => 'status.aws.amazon.com') FROM DUAL
Oracle ウォレットを使用してリモート Web サービス URL を参照します。
SQL> SELECT utl_http.request('https://status.aws.amazon.com/robots.txt') AS ROBOTS_TXT FROM DUAL;ROBOTS_TXT -------------------------------------------------------------------------------- User-agent: * Allow: /
よくあるエラー
ORA-28759: failure to open file
このエラーが表示されるのは、参照しているウォレットが指定した場所にない場合です。ディレクトリをリストして、ウォレットファイルの場所を確認してください。
SQL> select directory_name, directory_path from dba_directories where directory_name = 'WALLET'; DIRECTORY_NAME DIRECTORY_PATH -------------------------------------------------------------------------------- WALLET /rdsdbdata/userdirs/01
ORA-28768: bad magic number
このエラーが表示されるのは、S3 バケットとそのコンテンツが AWS Key Management Service (AWS KMS) で暗号化されている場合です。バケットオブジェクトの暗号化を解除してください。
ORA-12535: TNS: operation timed out
このエラーが表示される原因としては、インスタンスがプライベートサブネットにあることや、ルートテーブルにインターネットへのルートがないことが考えられます。
関連するコンテンツ
- 質問済み 5年前lg...
- 質問済み 3ヶ月前lg...
- AWS公式更新しました 1年前
- AWS公式更新しました 5ヶ月前
- AWS公式更新しました 5ヶ月前