LoginSignup
0
0

【AWS×Webアプリ】CloudFront+Basic認証(Terraform)

Posted at

目的

・AWS上の静的Webサイトホスティングを有効にしたS3をCloudFrontで公開。
・Basic認証を実装。

前提条件

・Terraformを使用してAWS上にリソースを作成する。
・Amazon CloudFront KeyValueStore+CloudFront Functionsを使用して実装する。
・作成する内容は以下と同様

TFファイル

aws_cloudfront.tf(前回からの追加箇所のみ抜粋)
resource "aws_cloudfront_distribution" "WebBucketDistribution" {
  enabled = true
  default_root_object = "index.html"
  price_class = "PriceClass_200"

  origin {
    origin_id                = "WebBucketOrigin"
    domain_name              = aws_s3_bucket.WebBucket.bucket_regional_domain_name
    origin_access_control_id = aws_cloudfront_origin_access_control.WebBucketOriginAccessControl.id
  }

  viewer_certificate {
    cloudfront_default_certificate = true
  }

  default_cache_behavior {
    target_origin_id       = "WebBucketOrigin"
    viewer_protocol_policy = "redirect-to-https"
    compress = true
    cached_methods         = ["GET", "HEAD"]
    allowed_methods        = ["GET", "HEAD"]

    cache_policy_id = aws_cloudfront_cache_policy.WebBucketCachePolicy.id
    origin_request_policy_id = aws_cloudfront_origin_request_policy.WebBucketOriginRequestPolicy.id

    function_association {
      event_type   = "viewer-request"
      function_arn = aws_cloudfront_function.WebBucketBasicAuthFunction.arn
    }
  }

  restrictions {
    geo_restriction {
      restriction_type = "none"
    }
  }
}

resource "aws_cloudfront_function" "WebBucketBasicAuthFunction" {
  name    = "WebBucketBasicAuthFunction"
  runtime = "cloudfront-js-2.0"
  publish = true
  code    = file("${path.module}/cloudfront_function/WebBucketBasicAuthFunction.js")
  key_value_store_associations = [aws_cloudfront_key_value_store.WebBucketBasicAuthKVS.arn]
}
aws_cloudfront_kvs.tf

resource "aws_cloudfront_key_value_store" "WebBucketBasicAuthKVS" {
  name    = "WebBucketBasicAuthKVS"
}

resource "aws_cloudfrontkeyvaluestore_key" "Test_User1" {
  key_value_store_arn = aws_cloudfront_key_value_store.WebBucketBasicAuthKVS.arn
  key                 = "Test_User1"
  value               = "Password1"
}

resource "aws_cloudfrontkeyvaluestore_key" "Test_User2" {
  key_value_store_arn = aws_cloudfront_key_value_store.WebBucketBasicAuthKVS.arn
  key                 = "Test_User2"
  value               = "Password2"
}

◆aws_cloudfront.tf
・WebBucketDistribution(function_association):CloudFront Functionの呼び出しを追加
・WebBucketBasicAuthFunction:Basic認証を行うCloudFront Functionの設定

◆aws_cloudfront_kvs.tf
・WebBucketBasicAuthKVS:CloudFront KeyValueStore
・Test_User1:KeyValueStoreに登録する情報1
・Test_User2:KeyValueStoreに登録する情報2

動作確認

①コンソールよりKeyValueStoreのIDを関数に設定し、変更を保存および関数の発行を実施

WebBucketBasicAuthFunction
import cf from 'cloudfront';
const kvsId = 'KeyValueStoreのIDを設定';
const kvsHandle = cf.kvs(kvsId);
async function handler(event) {
    const request = event.request;
    const headers = request.headers;
    if (
    typeof headers.authorization === 'undefined' ||
    typeof headers.authorization.value === 'undefined'
    ) {
    return return401();
    }
    const encoded = headers.authorization.value.split(' ')[1];
    const decoded = Buffer.from(encoded, 'base64').toString();
    const userRequest = decoded.split(':')[0];
    const passRequest = decoded.split(':')[1];
    const exist = await kvsHandle.exists(userRequest);
    if (!exist) {
    return return401();
    }
    const passStore = await kvsHandle.get(userRequest);
    if (passStore !== passRequest) {
    return return401();
    }
    return request;
}
const return401 = () => {
    return {
    statusCode: 401,
    statusDescription: 'Unauthorized',
    headers: { 'www-authenticate': { value: 'Basic' } },
    };
};

※Terrformでのリソース作成時にKeyValueStoreのIDを設定できないため

②Webサイトへアクセス
・ユーザ名とパスワードが要求されることを確認
image.png

③正しいユーザで認証されることを確認1
image.png
image.png

④正しいユーザで認証されることを確認2
image.png
image.png

⑤未登録のユーザ・誤ったパスワードでの認証が失敗することを確認
image.png
image.png
image.png

参考(前回記事)

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0