AWS

S3にyumリポジトリを作成してプライベートサブネットから参照する

スポンサーリンク
S3にyumリポジトリを作成してプライベートサブネットから参照する AWS
スポンサーリンク
スポンサーリンク

プライベートサブネット内のAmazon Linux  2から、S3上の自作yumリポジトリにアクセスする

Amazon Linux  (2)の場合、プライベートサブネットからでも、S3バケット上に構築されているAmazon Linuxリポジトリを参照することで、yumを実行することができます。

Amazon Linux repositories are hosted in Amazon Simple Storage Service (Amazon S3) buckets. To update and install packages on your instance without an internet connection, create an S3 Amazon Virtual Private Cloud (Amazon VPC) gateway endpoint.

How can I update yum or install packages without internet access on my EC2 instances running Amazon Linux 1 or Amazon Linux 2?

ただしAmazon Linuxリポジトリから、全てのパッケージをインストールできるわけではありません。
例えばOracleやMicrosoft SQL ServerバージョンのRDSに接続するためには、専用のクライアントが必要になりますが、これらはNATゲートウェイ等を設置しなければ、EC2にインストールすることはできません。

そこで今回は、S3上に自作のyumリポジトリを構築します。
そのリポジトリに2種類のデータベースエンジン(Oracle、Microsoft SQL Server)のクライアントパッケージを格納し、プライベートサブネット内のインスタンスにインストールします。

構築する環境

AWS認定資格試験テキスト AWS認定ソリューションアーキテクト - アソシエイト 改訂第2版 | 佐々木 拓郎, 林 晋一郎, 金澤 圭 | 産業研究 | Kindleストア | Amazon
Amazonで佐々木 拓郎, 林 晋一郎, 金澤 圭のAWS認定資格試験テキスト AWS認定ソリューションアーキテクト - アソシエイト 改訂第2版。アマゾンならポイント還元本が多数。一度購入いただいた電子書籍は、KindleおよびFire端末、スマートフォンやタブレットなど、様々な端末でもお楽しみいただけます。
Diagram of create yum repository in S3 and access from private subnet.

2つのVPCを作成します。
一方のVPCはyumリポジトリ作成用です。最新のAmazon Linux 2インスタンスを配置し、クライアント用リポジトリを作成し、S3バケットにアップロードします。
もう一方のVPCに、自作リポジトリの検証インスタンスを配置します。こちらのVPCにはインターネットゲートウェイやNATゲートウェイを配置せず、S3用VPCエンドポイントを経由して、S3バケットにアクセスします。

CloudFormationテンプレートファイル

上記の構成をCloudFormationで構築します。
以下のURLにCloudFormationテンプレートを配置してます。

awstut-fa/031 at main · awstut-an-r/awstut-fa
Contribute to awstut-an-r/awstut-fa development by creating an account on GitHub.

テンプレートファイルのポイント解説

静的Webサイトホスティング機能を有効化して、S3バケットをyumリポジトリ化する

S3バケットを確認します。
ポイントは静的Webサイトホスティングに関する設定です。

Resources: Bucket: Type: AWS::S3::Bucket Properties: BucketName: !Ref Prefix AccessControl: Private WebsiteConfiguration: IndexDocument: index.html
Code language: YAML (yaml)

WebsiteConfigurationプロパティで静的Webサイトホスティング機能を設定します。本機能を有効化することで、yumクライアントからのHTTP通信を受け付けることができます。
注意点はIndexDocumentプロパティです。本プロパティに「index.html」を設定します。これは本プロパティを設定しなければ、ホスティング機能が有効化できないためです。そのため実際にインデックスファイルを設置するわけではありませんが、形式的に設定します。

バケットポリシーでアクセス制限する

作成したバケットへのアクセスを、バケットポリシーを使って制限します。
ポイントはアクセスを許可する条件です。今回は以下の方針でアクセス制限します。

  1. 送信元のIPアドレスが、NATゲートウェイに付与したElastic IPアドレスの場合は、アクセスを許可する ※ VPC1内のインスタンス用
  2. 送信元のVPCがVPC2の場合は、アクセスを許可する ※ VPC2内のインスタンス用
Resources: BucketPolicy: Type: AWS::S3::BucketPolicy Properties: Bucket: !Ref Bucket PolicyDocument: Version: 2012-10-17 Statement: - Action: - s3:* Effect: Allow Resource: - !Sub "arn:aws:s3:::${Bucket}/*" Condition: IpAddress: "aws:SourceIp": - !Ref EIP Principal: "*" - Action: - s3:* Effect: Allow Resource: - !Sub "arn:aws:s3:::${Bucket}/*" Condition: StringEquals: "aws:SourceVpc": - !Ref VPC Principal: "*"
Code language: YAML (yaml)

2つのポリシーを定義します。
1つ目のポリシーは、インスタンス1からのアクセスを許可するためのものです。Conditionプロパティがポイントです。IpAddressプロパティに「aws:SourceIp」およびNATゲートウェイに付与したElastic IPアドレスを設定することで、同アドレスからの通信を許可するポリシーとなります。インスタンス1がS3バケットにアクセスする際は、NATゲートウェイを経由し、送信元アドレスがElastic IPアドレスに付け替わるためです。
2つ目のポリシーは、インスタンス2からのアクセスを許可するためのものです。こちらもConditionプロパティで条件を設定します。StringEqualsプロパティに「aws:SourceVpc」およびVPC2のIDを設定することで、同VPC内からの通信を許可するポリシーとなります。

createrepoでリポジトリを作成して、S3バケットにアップロードする

yumリポジトリを作成するために、インスタンス1で実行する内容を確認します。

Resources: RunShellScriptAssociation1: Type: AWS::SSM::Association Properties: AssociationName: !Sub "${Prefix}-runshellscript-association1" Name: AWS-RunShellScript Parameters: commands: - "sudo yum update -y" - !Sub "mkdir ${Repository}" # download oracle client - !Sub "curl https://download.oracle.com/otn_software/linux/instantclient/1914000/{oracle-instantclient19.14-basic-19.14.0.0.0-1.x86_64.rpm} --output ./${Repository}/#1" - !Sub "curl https://download.oracle.com/otn_software/linux/instantclient/1914000/{oracle-instantclient19.14-sqlplus-19.14.0.0.0-1.x86_64.rpm} --output ./${Repository}/#1" # download mssql-tools - "curl -OL https://packages.microsoft.com/config/rhel/7/prod.repo" - "sudo mv ./prod.repo /etc/yum.repos.d/msprod.repo" - !Sub "sudo yum install -y --downloadonly --downloaddir=./${Repository} mssql-tools" # create repository - "sudo yum -y install createrepo" - !Sub "createrepo ./${Repository}" - !Sub "aws s3 cp ./${Repository} s3://${Bucket}/ --recursive" Targets: - Key: InstanceIds Values: - !Ref Instance1 WaitForSuccessTimeoutSeconds: !Ref WaitForSuccessTimeoutSeconds
Code language: YAML (yaml)

今回はインスタンス初期化処理の一環として、SSMドキュメントAWS-RunShellScriptを実行し、リポジトリ作成を行います。同ドキュメントを使用した初期化処理に関しては、以下のページをご確認ください。

commandsプロパティで、実際に実行するコマンドを定義します。コマンドの内容は以下の通りです。

  • 事前準備(パッケージ更新、パッケージ格納用のディレクトリ作成)
  • Oracle用クライアント(sqlplus)パッケージのダウンロード
  • Microsoft SQL Server用クライアント(sqlcmd)パッケージのダウンロード
  • createrepoコマンドをインストールおよび実行して、上記ディレクトリをyumリポジトリ化する
  • AWS CLIを使用して、S3バケットにリポジトリデータをアップロードする。

なお各クライアントのインストール手順は、以下の公式サイトを参照しました。

Database Clientインストレーション・ガイド
RPMをダウンロードし、yum installコマンドを使用してOracle Instant Clientをインストールする方法を学習します。
Linux に SQL Server コマンドライン ツールをインストールする - SQL Server
SQL Server コマンドライン ツール、Microsoft ODBC ドライバー、およびそれらの依存関係を Linux にインストールする方法について説明します。

S3用VPCエンドポイント

VPC2の方を確認します。
同VPCはインターネットとの接点を作成せず、VPCエンドポイントを通じて、S3バケットへアクセスします。

Resources: S3Endpoint: Type: AWS::EC2::VPCEndpoint Properties: RouteTableIds: - !Ref PrivateRouteTable ServiceName: !Sub "com.amazonaws.${AWS::Region}.s3" VpcId: !Ref VPC
Code language: YAML (yaml)

特別な設定は不要です。
ServiceNameプロパティにS3を設定します。
S3用のVPCエンドポイントはゲートウェイタイプですから、VPC2のIDおよび同VPC内のサブネットに関連づいたルートテーブルを設定します。

yumに自作リポジトリを登録する

インスタンス2で実行する内容を確認します。
ポイントは自作したyumリポジトリを参照する方法です。

Resources: RunShellScriptAssociation2: Type: AWS::SSM::Association Properties: AssociationName: !Sub "${Prefix}-runshellscript-association2" Name: AWS-RunShellScript Parameters: commands: - !Sub | sudo cat << EOF > /etc/yum.repos.d/${Repository}.repo [${Repository}] name=${Repository} baseurl=${BucketWebsiteURL}/ gpgcheck=0 enabled=1 EOF - "sudo yum clean all" Targets: - Key: InstanceIds Values: - !Ref Instance2 WaitForSuccessTimeoutSeconds: !Ref WaitForSuccessTimeoutSeconds
Code language: YAML (yaml)

こちらもSSMドキュメントAWS-RunShellScriptを実行して、自作リポジトリ参照に必要な処理を行います。
一般に、yum実行時に参照されるリポジトリは、/etc/yum.repos.dディレクトリ配下の設定ファイルで定義します。同ディレクトリに、自作リポジトリ用の設定ファイルを作成・設置します。
今回は「myrepo」という名前でリポジトリを登録します。

環境構築

CloudFormationを使用して、本環境を構築し、実際の挙動を確認します。

CloudFormationスタックを作成し、スタック内のリソースを確認する

CloudFormationスタックを作成します。
スタックの作成および各スタックの確認方法については、以下のページをご確認ください。

各スタックのリソースを確認した結果、今回作成された主要リソースの情報は以下の通りです。

  • S3バケット:fa-031
  • インスタンス1:i-04533bae0ba1dd468
  • インスタンス2:i-054ec8995ebc83925

AWS Management Consoleからも、リソースの作成状況を確認します。
まずインスタンスの作成状況です。

Two instances have created.

確かに2つのインスタンスが作成されています。

次にインスタンス1におけるSSMドキュメントの実行結果を確認します。

SSM document successfully executed.

Outputから実行結果を確認することができます。

S3バケットを確認します。

The yum repository file is uploaded.

両クライアント用のパッケージ等が、バケットにアップロードされていることがわかります。

S3 static website hosting feature is enabled.

静的Webサイトホスティング機能が有効化され、HTTPリクエストを受け付ける準備が整っていることも確認できます。

自作リポジトリの登録状況を確認

準備が整いましたので、インスタンス2にアクセスします。
インスタンスへのアクセスは、SSM Session Managerを使用します。
詳細は以下のページをご確認ください。

% aws ssm start-session \ --target i-054ec8995ebc83925 Starting session with SessionId: root-0ec77415ecf2fb260 sh-4.2$
Code language: JavaScript (javascript)

自作リポジトリの登録用ファイルを確認します。

sh-4.2$ ls -l /etc/yum.repos.d/ total 12 -rw-r--r-- 1 root root 1003 Oct 26 17:55 amzn2-core.repo -rw-r--r-- 1 root root 1105 Mar 16 01:52 amzn2-extras.repo -rw-r--r-- 1 root root 105 Mar 19 02:02 myrepo.repo
Code language: Bash (bash)

確かにファイル(myrepo.repo)が作成されています。
中身も確認します。

sh-4.2$ cat /etc/yum.repos.d/myrepo.repo [myrepo] name=myrepo baseurl=http://fa-031.s3-website-ap-northeast-1.amazonaws.com/ gpgcheck=0 enabled=1
Code language: Bash (bash)

baseurlの値に注目です。S3のWebサイトエンドポイントのURLが指定されています。これによって、myrepoを参照する際は、S3バケットにアクセスすることになります。

yumが認識しているリポジトリ一覧を確認します。

sh-4.2$ yum repolist Loaded plugins: extras_suggestions, langpacks, priorities, update-motd 2 packages excluded due to repository priority protections repo id repo name status amzn2-core/2/x86_64 Amazon Linux 2 core repository 27418 amzn2extra-docker/2/x86_64 Amazon Extras repo for docker 56 myrepo myrepo 4+2 repolist: 27478
Code language: Bash (bash)

デフォルトのAmazon Linuxリポジトリに加え、myrepoが認識されていることがわかります。

myrepoからインストールできるパッケージを確認します。

sh-4.2$ yum list all | grep myrepo msodbcsql17.x86_64 17.9.1.1-1 myrepo mssql-tools.x86_64 17.9.1.1-1 myrepo oracle-instantclient19.14-basic.x86_64 19.14.0.0.0-1 myrepo 19.14.0.0.0-1 myrepo sh-4.2$
Code language: Bash (bash)

myrepoが正常に認識され、両クライアントがインストールできる状態であることがわかります。

Oracle用クライアントのインストール

まずOracle用クライアントをインストールします。

sh-4.2$ sudo yum install -y oracle-instantclient19.14-basic.x86_64 ... Installed: oracle-instantclient19.14-basic.x86_64 0:19.14.0.0.0-1 Complete! sh-4.2$ sudo yum install -y oracle-instantclient19.14-sqlplus.x86_64 ... Installed: oracle-instantclient19.14-sqlplus.x86_64 0:19.14.0.0.0-1 Complete!
Code language: Bash (bash)

正常にインストールできました。

インストールされたパッケージを確認します。

sh-4.2$ yum list installed | grep oracle oracle-instantclient19.14-basic.x86_64 oracle-instantclient19.14-sqlplus.x86_64
Code language: Bash (bash)

確かにmyrepoからOracleクライアントがインストールされました。

バージョンも確認します。

sh-4.2$ sqlplus -V SQL*Plus: Release 19.0.0.0.0 - Production Version 19.14.0.0.0
Code language: Bash (bash)

正常にバージョンが表示されました。

Microsoft SQL Server用クライアントのインストール

まずSQL Server用クライアントをインストールします。

sh-4.2$ sudo yum install -y mssql-tools ... Installed: mssql-tools.x86_64 0:17.9.1.1-1 Dependency Installed: libtool-ltdl.x86_64 0:2.4.2-22.2.amzn2.0.2 msodbcsql17.x86_64 0:17.9.1.1-1 unixODBC.x86_64 0:2.3.1-14.amzn2 Complete!
Code language: Bash (bash)

正常にインストールできました。

インストールされたパッケージを確認します。

sh-4.2$ yum list installed | grep mssql-tools mssql-tools.x86_64 17.9.1.1-1 @myrepo
Code language: PHP (php)

確かにmyrepoからSQL Serverクライアントがインストールされました。

バージョンを確認します。

sh-4.2$ /opt/mssql-tools/bin/sqlcmd -? Microsoft (R) SQL Server Command Line Tool Version 17.9.0001.1 Linux Copyright (C) 2017 Microsoft Corporation. All rights reserved. ...
Code language: Bash (bash)

正常にバージョンが表示されました。

まとめ

S3上に、自作のyumリポジトリを構築する方法を確認しました。
自作リポジトリを参照することで、Amazon Linuxリポジトリに存在しないパッケージについても、プライベートサブネット内のインスタンスにインストールすることができました。

タイトルとURLをコピーしました