[AWS] SES: 이메일 수신 서버 구성하기
SES는 보통 이메일을 전송할때 많이 쓰지만, 수신용으로도 사용할 수 있다.
보통은 그냥 gmail 같은 메일서비스를 쓰는게 일반적이라서 고려되지 않을 뿐이다.
직접 메일 서버를 구현할 때의 이점은, 이메일의 ID 영역까지 자유롭게 통제할 수 있다는 것이다.
aaa@foo.com, bbbb@foo.com, cccc@foo.com처럼 별도의 수신 이메일 주소를 동적으로 만들어서 관리할 수 있다. 사실상 진짜 이메일 서비스처럼 되는 것이다.
아무튼 여기서는 SES를 사용해서 확장 가능하고 관리가 용이한 메일 서버를 구성하는 방법을 다뤄본다.
이걸 하려면 도메인도 필요하다. 다른 도메인 제공자도 되지만 Route53에 있는게 편하다.
사전 지식
https://blog.naver.com/sssang97/224163430397
아키텍쳐
그림으로 그리면 대강 이런 모양이 된다.
우선 MX 도메인 레코드가 가장 앞단에 있는데, 거기서는 AWS의 내부 메일 서버 도메인을 알려준다.
그러면 메일 클라이언트는 AWS의 메일 서버로 전송을 할 것이다.
그 다음에는 AWS SES 수신자가 메일서버로 들어온 메일을 가로채서 SNS에 전송하고, SNS는 SQS에 메일 데이터를 적재한다. 그러면 서버는 SQS에서 데이터를 꺼내서 적절히 쓰면 되는 것이다.
이 구조의 장점은 매우 높은 부하에도 유연하게 대응하기 쉽고, 비용도 그렇게 비싸지는 않다는 것이다.
단, 몇가지 제한사항은 있다.
SNS, SQS는 페이로드의 크기 제한이 있다. 1MB 정도가 한계다.
하지만 사실 메일 클라이언트들도 이런걸 대응하는 방어로직이 있어서 현실적으로 저 제한을 넘을 일은 잘 없다.
그리고 SQS는 보존 기한이 있다. 최대 14일이 지나기 전에는 읽어서 소비해야 유실을 피할 수 있다.
비용
주요 비용 발생 지점은 SES의 수신 비용, SNS의 게시 비용, SQS의 저장 비용, SQS의 읽기 비용이다.
SES => SNS와 SNS => SQS 전송은 리전내 전송이므로 데이터 전송 자체에는 트래픽 비용이 발생하지 않는다.
대신 횟수에 따른 요청당 비용만 발생한다.
만약 10KB짜리 이메일을 100만개 받는다고 하면, 발생하는 비용은 다음과 같다.
SES $100 ($0.10/1,000건 + $0.09/256KB 초과당)
SNS $0.5 ($0.5/100만건)
SQS $0.4 ($0.4/100만건)
SES 수신 비용이 가장 크고, SNS와 SQS의 적재 비용은 매우 작은 편이다.
게다가 월에 100만건은 무료 사용량이라서 작은 규모에서는 비용이 아예 발생하지 않을 것이다.
SES 자격 증명 (identities) 생성
먼저 내가 이메일에 쓸 도메인을 안전하다는 의미로서 검증을 해야 한다.
SES의 자격 증명 탭에 들어가서 도메인 타입으로 하나 만들어준다.

Route53의 도메인을 쓴다면 자동으로 확인해서 검증해준다. 이런게 편하다.


도메인에 MX 레코드 등록
가장 중요한 것은 MX 레코드를 추가해서 이메일 클라이언트가 메일서버를 찾을 수 있게 하는 것이다.
AWS SES의 이메일 서버로 보내게 해야하는데, 이건 우리가 만드는게 아니라 리전마다 고정으로 제공된다.
다음과 같이 중간에 리전만 채워서 만들어주면 된다.
10 inbound-smtp.{리전}.amazonaws.com

그리고 도메인 조회에서 다음과 같이 등록한 값이 잘 조회되면 이건 끝이다.

이메일 수신 구성
이제 SES로 가서 구성을 추가해주자.
SES 메일서버로 전송하게 해뒀으니, 이건 그걸 꺼내올 수 있게 하는 설정이다.
이걸 쓰면 도메인을 기반으로 수신자를 찾아서 메일을 어딘가로 전송해줄 수 있다.

이름 짓고
보안 옵션 다 켜서 규칙도 추가해준 다음에
수신자 조건에 내 이메일 도메인을 넣어주면 된다.
아까 MX 레코드로 등록한 도메인과 동일하게 넣어준다.
그 다음에는 받은 메일을 어디로 쏠지 결정할 수 있다.
내 경우에는 SNS를 통해서 SQS로 포워딩하는 방식을 택했다.
저 콘솔에서 즉시 SNS를 만들 수 있는데

만들어서 적당히 연결해주면 된다.
그리고 인코딩은 Base64와 UTF-8을 선택할 수 있는데, 보통은 UTF-8로도 충분하고 쓰기 편하다.
UTF8을 추천한다.
SQS 생성
SQS는 요구사항에 맞는걸로 적당히 넣어도 되는데, 비용적으로 좋은건 표준 큐다.
만들고
아까 만들었던 SNS 주제에 SQS를 연결한다.

원시 메세지는 웬만하면 켜는걸 추천한다.
안그러면 쓸데없는 메타데이터를 잔뜩 넣어서 SQS에 넣는데, 그거만 해도 1KB는 넘는데다 파싱하기도 불편하다.
메일 전송해보기
이러면 이제 기본 세팅은 다 된 것이다.
지메일을 열어서 메일을 날려보자.
ID 영역에는 뭘 넣어도 된다. 중요한건 도메인이다.
전송하면 대략 몇초 뒤에 바로 SQS에 메세지가 쌓일텐데


까보면 이런 식으로 JSON 데이터가 들어있을 것이다.
타이틀이나 수신자는 그냥 들어있어서 보면 되는데, content는 MIME (Multipurpose Internet Mail Extensions)라는 포맷으로 인코딩되어있어서 파싱을 거쳐야 한다.
다음은 파이썬으로 파싱을 수행하는 간단한 코드다.
넣어서 돌려보면
방금 메일에 썼던 내용이 보일 것이다.
이렇게 쓰면 된다.
참조
https://docs.aws.amazon.com/ko_kr/ses/latest/dg/receiving-email.html