S3, Cloudfront, Route 53을 통한 정적 사이트 호스팅

gompro·2020년 4월 24일
9
post-thumbnail

안녕하세요. 곰프로입니다.

오늘은 S3, Route 53, Cloudfront 그리고 Certificate Manager를 이용해 도메인 구입부터 ssl 인증서를 연결하는 방법까지 알아보도록 하겠습니다.

도메인 구입

웹사이트 호스팅을 생각하고 있다면 가장 먼저 해야할 일은 도메인을 구입하는 일입니다.

도메인은 굳이 AWS가 아니더라도 가비아, 후이즈, 카페24 등을 통해 진행하실 수 있습니다.

다만 이번 튜토리얼에서는 처음부터 끝까지 AWS 서비스만을 활용할 예정이기 때문에 해당 내용은 포함되지 않았다는 점 주의해주시기 바랍니다. (AWS를 통해 도메인 구입을 진행하지 않은 경우 해당 도메인의 네임서버 변경 작업이 추가로 필요합니다)

이제 도메인을 등록해봅시다.

먼저 Route 53의 도메인 등록 메뉴로 이동합니다.

register-domain

적당한 도메인명을 선택한 뒤 확인을 눌러 계속 진행합니다.

buy-domain

연락처 세부 정보 확인 단계를 넘어가

맨 마지막 확인 및 구매 단계에서 도메인 자동 갱신에 대한 응답을 선택해줍니다. (기본값은 활성화이며, 저는 비활성화를 선택했습니다.)

confirm

도메인 구입을 마치셨다면 이제 등록된 도메인 메뉴에 도메인 명이 뜰 것입니다.

코드 작성

신나는 코드 작성 시간입니다 😄

이번 시간에는 Vue.js로 만든 헬로월드 앱을 호스팅하게 될텐데요, 일반적인 html 페이지나 다른 프레임워크를 사용하시더라도 동일하게 진행할 수 있습니다. 각자 취향에 맞게 선택해주세요.

혹시라도 node.js가 설치되지 않으신 분들은 홈페이지로 가셔서 다운로드 받아주세요.

이번 튜토리얼에서는 처음부터 개발환경을 설정하는 대신 vue-cli를 사용하도록 하겠습니다.

npm install -g @vue/cli

vue create [project-name] -- project-name은 아무 이름이나 입력해주시면 됩니다!

cd ~/[project-name]

npm run dev

위 명령어를 실행시키면 새로운 vue 프로젝트를 생성하고 개발환경에서 실행시키게 됩니다.

hello-world

이제 프로젝트를 빌드하여 업로드할 준비를 해줍시다.

npm run build 명령어를 실행시키고, dist 디렉토리가 정상적으로 생성된 것을 확인하셨다면 이제 다음 단계로 넘어가봅시다.

S3 버킷 생성/설정

S3는 각종 파일을 저장할 수 있는 스토리지로 빌드 과정을 통해 생성된 파일을 호스팅하기 위해 사용합니다.

먼저 파일을 업로드하기 전에 버킷을 생성해줍니다.

S3 메뉴로 이동해서 우측 버킷만들기를 선택해줍니다.

s3

다음은 버킷 설정입니다.

여기서 주의할 점은 버킷 이름을 도메인 명과 일치하게끔 맞춰주셔야된다는건데요, 나중에 Route 53 연결 작업을 할 때 필요한 설정입니다. 잊지 말고 이름을 맞춰주세요!

리전은 어느 리전이든 상관 없습니다.

그리고 다음으로 퍼블릭 엑세스 차단을 해제해줍니다.

퍼블릭 엑세스 차단을 해제해야 S3 버킷에 저장된 파일 (index.html 등)에 대해 사용자들이 엑세스를 할 수 있습니다.

s3-setting

고급 설정은 기본값으로 두셔도 좋습니다.

계속해서 버킷 설정으로 넘어가봅시다.

enable-web-hosting

위와 같이 속성 - 정적 웹사이트 호스팅 메뉴를 설정해줍니다.

다음은 권한 설정입니다.

policy

권한 - 버킷 정책 탭에서 아래 코드를 붙여넣어줍니다.

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "PublicReadAccess",
            "Effect": "Allow",
            "Principal": "*",
            "Action": "s3:GetObject",
            "Resource": "arn:aws:s3:::my-domain.com/*" // my-domain.com 부분을 버킷 이름으로 바꿔줍니다!
        }
    ]
}

다음으로 dist 폴더를 버킷에 업로드 해봅시다.

  1. 콘솔을 사용하는 경우

    버킷 개요 메뉴 아래 업로드 버튼을 누른 뒤 아래와 같이 dist 폴더에 있는 모든 파일을 끌어다놓습니다.

    upload

    2단계 권한 설정에서 퍼블릭 읽기 엑세스 권한을 허용해준 뒤 다음 버튼을 눌러 끝까지 진행해줍니다.

    allow-public-access

  2. aws-cli가 설치/설정된 경우

    프로젝트의 루트 디렉토리에서 아래 명령어를 입력해서 업로드를 진행할 수 있습니다.

    aws s3 sync ./dist s3://[bucket-name]

Route 53 설정

이제 버킷을 도메인 주소와 연결할 차례입니다.

Route 53 - 호스팅 영역 - 해당 도메인명 으로 이동해줍니다.

상단의 레코드 세트 생성을 눌러 특정 도메인 주소가 버킷에 있는 파일을 바라보도록 설정해줍시다.

create-record-set

레코드 세트 생성 버튼을 누르면 우측에 위와 같은 메뉴가 보일 겁니다.

이름에는 서브 도메인을 입력하거나 혹은 공란으로 비워둡니다. (ex sub.example.com)

유형은 IPv4주소인 경우 A레코드를, IPv6주소인 경우 AAAA레코드를 선택해줍니다.

이제 별칭에 예를 선택하고 별칭대상의 S3 웹 사이트 엔드포인트에 보이는 버킷을 골라줍니다.

주의
만약 S3 웹 사이트 엔드포인트에 "사용 가능한 대상 없음"으로 표시된다면 버킷의 이름이 도메인명과 정확히 일치하거나 혹은 서브 도메인 형식인지 확인해보시기 바랍니다. S3 웹 사이트 엔드포인트를 Route 53에 연결하기 위해서는 반드시 (sub.)domain.com과 같은 형식의 이름이여야 합니다. 참고

만약 이미 버킷을 생성하신 뒤라면 해당 버킷의 파일을 모두 삭제하신 다음 버킷을 삭제해주시고, S3 버킷 생성/설정 과정을 참고하여 새로운 버킷을 생성해주시기 바랍니다.

나머지 설정은 건드리지 말고 아래 레코드 세트 저장 버튼을 눌러 저장해줍니다.

no-ssl

이 단계까지 오셨다면 해당 도메인을 통해 사이트 접속이 가능합니다. 하지만 아직 https가 활성화되지 않은 상태입니다.

인증서 발급

Https는 암호화되지 않은 프로토콜인 http보다 보안적으로 안전할 뿐만 아니라 빠르기도 합니다. 참고

또한 위에서 보았듯 대부분의 모던 브라우저는 http로 연결된 웹사이트에 대해 Not Secure (안전하지 않음) 표시를 통해 사이트 이용자들에게 경고를 제공하고 있습니다.

그러므로 https를 연결하지 말아야할 별다른 이유가 없다면 웬만한 사이트에는 https 연결이 권장되고 있습니다.

AWS에서는 어떤 식으로 인증서를 관리할 수 있을까요?

AWS는 내부 리소스에 사용되는 SSL/TLS 인증서를 발급, 관리하는 서비스인 Certificate Manager를 운영하고 있습니다.

create-cert

콘솔을 통해 Certificate Manager로 이동한 뒤 인증서 생성을 위해 인증서 프로비저닝 메뉴 - 시작하기 버튼을 눌러줍니다.

certificate1

공인 인증서 요청을 선택한 뒤 다음으로 넘어갑니다.

certificate2

위와 같이 도메인 혹은 서브 도메인 이름을 추가해줍니다. (서브 도메인을 선택할 경우 해당 서브 도메인 이름으로 된 버킷이 더 필요합니다.)

certificate3

검증 방법은 기본인 DNS 검증으로 선택합니다. (이번 튜토리얼에서는 이메일 검증 방법에 대해서는 다루지 않습니다.)

이후 단계는 모두 다음을 눌러주시고, 5단계 검증 단계까지 진행합니다.

verify

이제 도메인 명을 확장하시면 아래와 같이 CNAME 레코드가 하나 등장합니다. 현재 저는 my-domain.com 도메인의 소유주가 아니기 때문에 추가적으로 Route 53에 추가와 같은 버튼이 보이지 않지만 해당 도메인을 소유하고 있다면 버튼이 보일 겁니다.

verify-2

Route 53에 추가 버튼을 눌러 자동으로 해당 레코드를 Route 53 설정에 추가해주시거나 아래와 같이 레코드 세트 생성 버튼을 누르고

add-cname-record

위와 같이 CNAME 레코드를 추가해줍니다.

모든 절차를 완료했다면 아래와 같은 창이 뜹니다.

last-step

5분 정도 기다려주시면 검증 완료 상태가 될텐데요, 그 때까지 잠깐 기다려주시면 됩니다!

주의
혹시 아무리 기다려도 해당 단계가 완료되지 않는다면 CNAME 레코드를 Route 53에 추가해줬는지 다시 확인해주세요.
위 화면에서 DNS 구성을 파일로 내보냅니다 버튼을 누르면 csv 파일을 다운로드 받을 수 있습니다.
거기에 적힌 RecordName 및 RecordType을 참고하여 Route 53 레코드 세트에 추가해줍니다.

Cloudfront 설정

이제 Cloudfront를 설정해줄 차례입니다.

갑자기 Cloudfront가 등장한 것에 대해 궁금하신 분들이 있으실텐데요, 이는 S3 버킷에는 직접적으로 SSL 인증서를 추가할 수가 없기 때문입니다.

또 Cloudfront는 전 세계에 엣지 로케이션(Edge location)을 가지고 있는 훌륭한 CDN 서비스입니다. 웹 사이트 로드 속도를 줄이기 위해서도 꼭 필요하죠.

Cloudfront로 이동하셔서

create-distribution

Create Distribution 버튼을 눌러 distribution을 생성해줍니다.

web

두 유형 중에서는 Web을 선택해줍니다.

configuration-1

먼저 Origin Domain Name을 선택한 뒤 S3 버킷 주소를 선택해줍니다.

Viewer Protocol PolicyRedirect HTTP to HTTPS를 선택해줍니다.

아래로 스크롤을 내리다보면 Distribution Settings 메뉴가 보입니다.

여기서 Altername Domain Names에 구매한 도메인 명을 넣어주고, Cutom SSL Certificate를 선택한 다음, 생성해둔 인증서를 넣어줍니다. 마지막으로 Default Root Object에 index.html를 명시해줍니다.

주의
Default Root Object 설정이 누락될 경우 403 에러가 발생합니다. 이는 Cloudfront가 해당 버킷의 엔트리 포인트를 찾지 못하기 때문에 발생하는 에러입니다.

configuration-2

이제 홈으로 이동해서 상태가 아래와 같이 Deployed(배포됨)이 될 때까지 충분히 기다려줍니다.

주의
Route 53에서 Clodfront Distribution을 인식하지 못할 경우 대부분 상태가 In Progress(진행중) 입니다.
그러므로 충분히 기다려서 상태가 배포됨이 된 걸 확인해주시고 다음 단계를 진행해주세요

cloudfront-status

Cloudfront distribution 생성/배포가 완료되었다면 다시 Route 53으로 이동하여 기존에 S3 버킷을 바라보고 있던 레코드 세트를 선택한 다음 별칭 대상을 CloudFront 배포 아래에 있는 주소로 변경해줍니다.

route53-cloudfront

수고하셨습니다! 이제 https을 통해 페이지를 보여주고 있다는 자물쇠 표시가 보이네요.

https

Q&A

  1. 주소에 접속했더니 403 에러가 발생합니다. 어떻게 해야 되나요?

    403

    이 경우 버킷의 정책이 아래와 같이 설정되어 있는지 확인해주세요.

    {
        "Version": "2012-10-17",
        "Statement": [
            {
                "Sid": "PublicReadAccess",
                "Effect": "Allow",
                "Principal": "*",
                "Action": "s3:GetObject",
                "Resource": "arn:aws:s3:::my-domain.com/*" // my-domain.com 부분을 버킷 이름으로 바꿔줍니다!
            }
        ]
    }

    혹은 CloudfrontDefault Root Object 설정이 누락된 것은 아닌지 확인해야 합니다.

    해당 distribution으로 들어가신 뒤 Edit 버튼을 누르면 설정을 변경할 수 있습니다.

    스크롤을 내리다보면 Default Root Object 탭을 찾을 수 있습니다.

    여기에 해당 사이트의 진입점이 되는 파일명을 입력해주세요. (일반적으로 index.html)

    cloudfront-edit

    setting

  2. 해당 설정을 모두 마쳤을 때 어느 정도의 비용이 발생하나요?

    ec2나 빈스톡 인스턴스를 띄운 것이 아니기 때문에 트래픽이 높지 않을 경우 비용은 거의 발생하지 않습니다.

    제 경우 약 한 달에 Cloudfront로부터 0.02 달러 정도 꾸준히 발생하고 있습니다.

  3. 아무리 기다려도 Cloudfront의 상태가 Deployed(배포됨)으로 변경되지 않습니다.

    이 경우 해당 distribution을 삭제하고 새로 생성하길 추천드립니다.

  4. Route 53 레코드 세트 추가에서 별칭 대상에 S3 웹 사이트 엔드포인트가 보이지 않습니다.

    먼저 S3 버킷의 정적 호스팅 옵션을 켰는지를 확인해주시고, 버킷의 이름이 반드시 도메인 혹은 서브 도메인과 같은 형식으로 되어있는지 확인해주시기 바랍니다.


다른 질문 사항이 있다면 코멘트로 적어주시기 바랍니다. 감사합니다 🙂

profile
다양한 것들을 시도합니다

3개의 댓글

comment-user-thumbnail
2020년 8월 3일

안녕하세요. 작성해 주신 글과 다른 블로그 글들을 참고하여 AWS 도메인 연결을 마쳤는데, 한 가지 이슈가 있어 질문 드립니다.

현재 AWS 버킷에 도메인을 연결하는 작업까지 모두 마무리 했습니다.
버킷은 SSL 작업을 위해 ssl.example.kr, www.example.kr 버킷을 각각 따로 생성했습니다.
ssl.example.kr 버킷은 CloudFront와 연결하여 진행하였으며, Route 53로 "example.kr"로 연결시켰습니다.

www.example.kr 버킷은 사용자가 www.example.kr로 입력했을 경우
example.kr로 리다이렉트되도록 정적 웹사이트 경로를 변경했습니다.

현재 URL 주소 입력창에 다음 주소를 기입하면 정상적으로 사이트 접속은 가능합니다.

여기서 문제는 "https://www.example.kr"로 입력시 사이트에 연결할 수 없다고 뜨는데,
AWS에서 어느 부분을 수정해야 해당 문제를 해결할 수 있는지 질문 드립니다.

1개의 답글
comment-user-thumbnail
2020년 12월 16일

포스팅 정말 감사드립니다!

저의 경우 다른 점이 있었는데 cloudfront의 origin domain name 등록 시에
Dropdown 목록에서가 아닌 s3의 접근 주소를 입력해야 정상 작동 하였습니다!

관련 레퍼 중에서도 그렇게 하셨다는 분이 계셔서 댓글 남깁니다!!

답글 달기