Amazon SES+mailxの証明書エラーに2パターンで対応

Amazon SESを試すことがあり、例を調べているとpostfix+mailxを使ったものが多かったのですが、証明書のところでちょっとだけ調べることがあったので備忘します。

学べること

Amazon SESの証明書エラー対応方法

  • コマンドのオプションで対応
  • ルート証明書インポートで対応

問題

SESの準備をしたあと、実際にメール送信できるか以下のmailxコマンドで試しました。
ちなみにコマンドはEC2で実行しており、VPC Endpoint経由でSESにアクセスしています。

echo "This is the message body and contains the message" | mailx -v -r "送信元メアド" -s "This is the subject" -S smtp="vpce-xxxxxxxxxxx.email-smtp.ap-northeast-1.vpce.amazonaws.com:587" -S smtp-use-starttls -S smtp-auth=login -S smtp-auth-user="AKIxxxxxxxxxxxxxxxx" -S smtp-auth-password="BBBxxxxxxxxxxxxxxxxxxxxxx" -S nss-config-dir=/etc/pki/nssdb/ 送信先メアド

するとError in certificate: Peer’s certificate issuer is not recognized という証明書エラーが発生しました。

>>> STARTTLS
220 Ready to start TLS
Error in certificate: Peer's certificate issuer is not recognized.
Comparing DNS name: "email-smtp-fips.ap-northeast-1.amazonaws.com"
Comparing DNS name: "*.email-smtp.ap-northeast-1.vpce.amazonaws.com"
SSL parameters: cipher=AES-256-GCM, keysize=256, secretkeysize=256,
issuer=CN=Amazon,OU=Server CA 1B,O=Amazon,C=US
subject=CN=email-smtp.ap-northeast-1.amazonaws.com

これはAmazon SESが使うSSL証明書のIssuerが信頼できるかどうか判断できない為、エラーが発生しています。

今回EC2で実行しているので、こういった問題は起きないかなと思っていたんですが、コマンドの引数で’nss-config-dir=etc/pki/nssdb/’というものを指定する必要があり、これがmozilla系?の証明書ストアみたいで、デフォルトでEC2に入っている証明書郡(/etc/pki/tls/certs/以下とか)とはまた別の仕組みなので自分で対応する必要があります。

ちなみに

FQDNではなくIPでSESのエンドポイントを指定してメール送信もできますが、host certificate does not match “10.100.1.41” といったエラーが当然ながら発生します。

echo "This is the message body and contains the message" | mailx -v -r "送信元メアド" -s "This is the subject" -S smtp="10.100.10.41:587" -S smtp-use-starttls -S smtp-auth=login -S smtp-auth-user="AKIxxxxxxxxxxxxxxxx" -S smtp-auth-password="BBBxxxxxxxxxxxxxxxxxxxxxx" -S nss-config-dir=/etc/pki/nssdb/ 送信先メアド
>>> STARTTLS                     
220 Ready to start TLS                                                                                                                  
Comparing DNS name: "email-smtp-fips.ap-northeast-1.amazonaws.com"                                                                      
Comparing DNS name: "*.email-smtp.ap-northeast-1.vpce.amazonaws.com"                                                                    
Comparing DNS name: "email-smtp.ap-northeast-1.amazonaws.com"                                                                           
Comparing common name: "email-smtp.ap-northeast-1.amazonaws.com"                                                                        
host certificate does not match "10.100.1.41"                                                                                           
Continue (y/n)? "/home/ec2-user/dead.letter" 11/372                             
. . . message not sent.

対応方法

①コマンドオプションで対応

mailxコマンドのオプションに’ssl-verify=ignore’をつけることでSSL関連のエラーを無視してメール送信することが可能です。接続先や経路が信頼できる場合はこちらでも良いかと思います。
IPで指定する場合もこちらになります。

echo "This is the message body and contains the message" | mailx -v -r "送信元メアド" -s "This is the subject" -S smtp="vpce-xxxxxxxxxxx.email-smtp.ap-northeast-1.vpce.amazonaws.com:587" -S smtp-use-starttls -S smtp-auth=login -S smtp-auth-user="AKIxxxxxxxxxxxxxxxx" -S smtp-auth-password="BBBxxxxxxxxxxxxxxxxxxxxxx" -S nss-config-dir=/etc/pki/nssdb/ -S ssl-verify=ignore 送信先メアド

コマンドを実行すると、Error in certificate: Peer’s certificate issuer is not recognized といったエラーは継続してでますが、そこで処理が終わることなくメール送信までできます。

②ルート証明書インポートで対応

然るべき証明書をnssdbにインポートすることで正常にTLS通信を行うことができます。基本的にはこちらの方が推奨されるかと思います。エンドポイントをIPで指定している場合はこちらではなく、①のssl-verify=ignoreで対応します。

以下のコマンドでAmazonのルート証明書をダウンロードし、nssdbにインポートしています

wget https://www.amazontrust.com/repository/AmazonRootCA1.pem
sudo certutil -A -n "amazon ca" -t "TC,C,C" -i AmazonRootCA1.pem -d /etc/pki/nssdb/

インポートされているか確認。

$ certutil -L -d /etc/pki/nssdb/
Certificate Nickname                                         Trust Attributes
                                                             SSL,S/MIME,JAR/XPI

amazon ca                                                    CT,C,C

この後にmailxコマンドを実行すると特にエラーなく実行できていることが確認できるかと思います。

Appendix

他のAmazonの証明書類はこちらからダウンロードできます。

 https://www.amazontrust.com/repository/

certutilコマンドの-t引数でインポートする証明書をどの程度信頼するか指定しています。以下のサイトで確認できますが、スクショも貼っておきます。


https://developer.mozilla.org/en-US/docs/Mozilla/Projects/NSS/Reference/NSS_tools_:_certutil

ちなみに-t “c,c,c”でインポートした場合は、以下のように別のエラーが発生しました。

>>> STARTTLS
220 Ready to start TLS
Error in certificate: Peer's certificate issuer has been marked as not trusted by the.
Comparing DNS name: "email-smtp-fips.ap-northeast-1.amazonaws.com"
Comparing DNS name: "*.email-smtp.ap-northeast-1.vpce.amazonaws.com"
SSL parameters: cipher=AES-256-GCM, keysize=256, secretkeysize=256,
issuer=CN=Amazon,OU=Server CA 1B,O=Amazon,C=US
subject=CN=email-smtp.ap-northeast-1.amazonaws.com

starttlsではなく、SMTPSを使う場合もこれまで書いたことと同じことが言えます。
mailxでsmtpsを使うには以下の用にsmtp=”smtps://endpoint:465″といった具合に明示的にsmtpsを指定します。

echo "This is the message body and contains the message" | mailx -v -r "送信元メアド" -s "This is the subject" -S smtp="smtps://vpce-xxxxxxxxxxx.email-smtp.ap-northeast-1.vpce.amazonaws.com:465" -S smtp-use-starttls -S smtp-auth=login -S smtp-auth-user="AKIxxxxxxxxxxxxxxxx" -S smtp-auth-password="Bxxxxxxxxxxxxxxxxxxxxxx" -S nss-config-dir=/etc/pki/nssdb/ 送信先メアド