API Gatewayのカスタムドメイン,HTTPS,相互TLS認証

#1.構成#

API Gateway > プライベートサブネットにあるALB > lambda
　を
API Gatewayを,カスタムドメイン,HTTPS,相互TLS認証
　でアクセスできるようにしたいと思います。

**API Gatewayで相互TLS認証を利用するには、カスタムドメインが必須となります。**


#2.前提#

- プライベートサブネットにあるALBから、Lambdaをターゲットとしたターゲットグループが作成済であることとします。
- この作成手順は、割愛します。


#3.ACM#

ここでは、API Gateway のカスタムドメインで利用するSSL証明書を、Certficate Manager から、パブリック証明書を取得します。

手順は次のページにある、【Certficate ManagerでSSLを取得する】の通り行います。

https://dev.classmethod.jp/articles/api-gateway-custom-domain-ssl/

**なお、API Gateway でカスタムドメインを利用する場合、次のように ACM でリクエストしたドメインを利用する必要があることに注意が必要です。**

（例）

- API Gatewayのカスタムドメイン：api.example.com
- ACMでリクエストしたドメイン名：*.example.com

（参考）
 
https://docs.aws.amazon.com/ja_jp/apigateway/latest/developerguide/how-to-custom-domains.html#edge-optimized-custom-domain-names

*API のホスト名としてカスタムドメイン名を設定する場合、API 所有者はカスタムドメイン名の SSL/TLS 証明書を提供する必要があります。*

https://docs.aws.amazon.com/ja_jp/apigateway/latest/developerguide/how-to-custom-domains.html#regional-custom-domain-names

*特定のリージョンの API のカスタムドメイン名を作成すると、API Gateway は API のリージョン別ドメイン名を作成します。カスタムドメイン名をリージョン別ドメイン名にマッピングするように、DNS レコードを設定する必要があります。カスタムドメイン名の証明書を提供する必要もあります。*


#4.S3#

カスタムドメインの相互TLS認証に必要な証明書を取得し、S３にアップロードします。

手順は次のページにある、【クライアント証明書の発行】の手順の通り openssl でクライアント証明書を発行し、ルートCA証明書をS3にアップしておきます。

https://dev.classmethod.jp/articles/api-gateway-support-mutual-tls-auth/


#5.API Gateway#

##5-1.VPCリンク##
「HTTP API の　VPC リンク」を選択し、ENIを配置するVPC、サブネット、セキュリティを指定し作成します。
![スクリーンショット 2021-07-16 18.39.37.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/2c6a6918-7eba-e283-9831-16849a9f8188.png)
![スクリーンショット 2021-07-16 18.39.47.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/d28e8990-422b-e0b6-7dba-f6d53f07d2b8.png)
![スクリーンショット 2021-07-16 18.40.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/3190585f-28d0-89c2-970b-be0d7c8bf30d.png)

##5-2.API##
HTTP API を作成していきます。

Step 1：API の作成
この段階では、統合にプライベートリソースを指定できないため、「API 名」だけ入力しておきます。（統合は後で作成します。）
![スクリーンショット 2021-07-16 18.19.09.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/9e7041dd-76a5-b001-40bb-c9afd2bfe8c1.png)

Step 2：ルートを設定
ここでは、「Step 1」で、統合がまだないので、何もせずに進みます。
![スクリーンショット 2021-07-11 16.33.51.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/fb1f3712-cbd6-d515-5076-45c73791ee0f.png)

Step 3：ステージを定義
デフォルトで何もせずに進みます。
![スクリーンショット 2021-07-11 16.34.03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/10030f51-341d-f9db-f67d-01f3c1cf2222.png)

なお、HTTP API は、"デフォルトステージ"と"自動デプロイ"に対応しています。

デフォルトステージは、
https://XXXXXXXXXX.execute-api.ap-northeast-1.amazonaws.com
のようにアクセスすることも可能になります。

自動デプロイは、その名の通り、APIを変更すると自動的にステージへデプロイしてくれる機能です。

(参考)

https://docs.aws.amazon.com/ja_jp/apigateway/latest/developerguide/http-api-vs-rest.html

Step 4：確認して作成
「作成」します。

**ルート**
左側の「ルート」をクリックし、「Create」をクリックします。

今回は「GET」のみにし作成します。
![スクリーンショット 2021-07-16 18.58.06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/48ab1e00-a978-cbf9-35c3-76c7288c7060.png)

**統合**
左側の「統合」をクリックし、「統合を管理」をクリック、「Create」します。

ひとつ前の手順で作成したルートを指定します。
![スクリーンショット 2021-07-16 19.02.11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/8faea092-9f4f-044c-18fb-78d13d2e4bce.png)
「プライベートリソース」を指定。
![スクリーンショット 2021-07-16 19.02.22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/e52910d6-b88f-a03a-c1a2-9a2e26bf28d6.png)
「手動で選択」、「ALB/NLB」を指定し、作成済のロードバランサーとリスナーを選択。
![スクリーンショット 2021-07-16 19.02.33.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/58ef824d-099c-6a5a-62a4-848440e56741.png)
作成済の「VPCリンク」を指定。
![スクリーンショット 2021-07-16 19.02.44.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/fab53ad9-1b36-6101-5a1d-fb4cd551ba88.png)

##5-3.カスタムドメイン名##

API Gateway > カスタムドメイン名 > 作成 を開き、設定していきます。

「ドメイン名」を入力し、「相互 TLS 認証」を ON。　トラストストア URI にルートCA証明書の S3 URI を入力します。
![スクリーンショット 2021-07-16 18.49.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/c583c60e-a548-fe79-af71-2942435a74f8.png)

「ACM 証明書」に、作成済のSSL証明書を指定します。
![スクリーンショット 2021-07-11 16.19.53.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/10cbf832-cfbe-eabc-fc2d-3847095b9242.png)

「APIマッピング」から、「APIマッピングを設定」を開きます。
![スクリーンショット 2021-07-16 19.09.44.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/7823ff50-a861-8ccc-b1dc-71f1558a8e98.png)

カスタムドメイン名に紐付けるAPIとステージを指定します。
![スクリーンショット 2021-07-16 19.10.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/65b27dd6-dcba-cdd9-852b-cba88218e044.png)


#6.テスト#

これで基本的な作成は終わりで、カスタムドメイン名を利用し、相互TLS認証でアクセスすることが可能ですが、このまままでは、デフォルトのAPIエンドポイントで相互TLS認証なしでアクセスできてしまいます。
そのため、デフォルトのAPIエンドポイントは無効にしておきましょう。
![スクリーンショット 2021-07-16 19.29.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/3352f705-a840-227d-cb11-c1d1990369d7.png)

テストは、クライアント証明書と秘密鍵を利用して、レスポンスがかえってくればOK。

```
curl -i --key my_client.key --cert my_client.pem  https://<設定したカスタムドメイン名>
```


#7.リンク#

[Amazon API Gateway](https://qiita.com/leomaro7/items/66ea3233097fa410fef9)