Amazon Aurora に移行を決めた3つの理由と移行方法

みんなのウェディングのインフラエンジニア横山です。

みんなのウェディングでは先日、データベースを RDS for MySQL から Amazon Aurora (以下 Aurora )へ移行しました。
この記事では移行の経緯や移行手順、移行後の感想についてまとめたいと思います。

移行の経緯

みんなのウェディングでは結婚式場口コミサイトのみんなのウェディングを運営しています。
本サービスではサービス開始当初から MySQL を利用しており、 AWS 移行時にも RDS for MySQL を選択していました。
今回、 Aurora 移行を決めた理由は以下の3つのメリットがあったからです。

1. リーダーエンドポイントによるリードレプリカの冗長化

Aurora にはリーダーエンドポイントという読み込み専用エンドポイントがあります。
https://aws.amazon.com/jp/blogs/news/new-reader-endpoint-for-amazon-aurora-load-balancing-higher-availability/
これは、複数台の Aurora レプリカでラウンドロビンで負荷分散、冗長化を行ってくれるエンドポイントです。
RDS for MySQL の際は、 HAProxy を使って冗長化を図っていましたが、リーダーエンドポイントの利用によって HAProxy の運用工数削減が期待できました。
また、 HAProxy 自体の冗長化も考えなくて済みます。

2. 高い耐障害性

Aurora のデータベースボリュームは、同一のデータが3つのアベイラビリティーゾーンにかけて、6個レプリケーションされる構造になっています。
これにより RDS for MySQL よりも高い耐障害性を持っていることも移行理由の一つでした。

3. ゼロダウンタイムパッチによる無停止アップデート

以下の記事にある通り、 Amazon Aurora では無停止のままパッチが適用できます。
https://aws.amazon.com/jp/blogs/news/amazon-aurora-update-spatial-indexing-and-zero-downtime-patching/
この点は、24時間365日稼働するサービスを運営していく上で非常に魅力的でした。

デメリットは、 Aurora は RDS for MySQL と比較して若干高いことぐらいでした。 他にも考慮した点はありましたが、上記3つのメリットと料金の上昇を天秤にかけ、移行することを決定しました。

移行手順

まずは移行可能か確認するため、アプリとバッチの動作確認を行いました。
その結果、 MySQL 互換とアナウンスされている通り、アプリ・バッチ共に移行のための変更が必要ないことがわかりました。

次に移行方法です。
アプリケーション無停止で移行することも可能でしたが、安全策を取って夜間にメンテナンス時間を取って移行することにしました。
メンテナンス時間の調整には営業など各部署への調整が必要でしたが、滞りなく作業を進めることができました。
今回スムーズに作業が進められたのは、私たちが日々安定運用してきたからこそ生まれた信頼関係があるからだと思っています。

移行前の構成は以下の図の通りです。switch_pointを利用することで、DBアクセスをマスター( M )とリードレプリカ( R )に分割するようにしています。

移行作業には、 RDS for MySQL から Aurora リードレプリカを作る、以下の機能を利用しました。この機能のおかげで簡単に移行することができました。
http://docs.aws.amazon.com/ja_jp/AmazonRDS/latest/UserGuide/Aurora.Migration.RDSMySQL.html

具体的な手順は以下の通りです。

  • メンテナンス前に本番環境の RDS for MySQL から Aurora リードレプリカを作成

  • サービスをメンテナンスモードに切り替えて RDS for MySQL へのアクセスを停止

  • RDS for MySQL へのアクセスがないことを確認した上で、 Aurora リードレプリカをマスターに昇格

  • 昇格した Aurora インスタンスをマスターとする、読み込み専用の Aurora レプリカを作成。

  • アプリケーションサーバの接続先を変更して、メンテナンスを解除し、サービスを再開

切り替え後しばらくは注視していましたが、特に大きな問題も起こらず無事に作業を終えることができました。

移行後の感想

移行後の感想について述べていきます。

実クエリを用いて性能テストするべきだった

今回、移行による性能向上はあまり期待していませんでしたが、一部のクエリでは逆に実行時間が長くなる事象が発生しました。 とあるクエリでは30〜40秒→5~6分と、実行時間がおよそ10倍になりました。
幸いにもインデックスの追加削除などのチューニングで改善することができ、 現在はこちらのクエリは10秒程度で完了するようになりました。
「 Aurora は MySQL と比較して最大で 5 倍のパフォーマンスを提供する」とAWSがアナウンスしていますが、 このようなケースがあることも考慮して、実クエリを用いて性能テストすべきだったなーとちょっと後悔しています。

リーダーエンドポイントについて

当初は予定通りリーダーエンドポイントを利用していたのですが、サービスのレスポンスが悪化する事象が発生しました。
原因は、リーダーエンドポイントを利用することでバッチサーバとサービス側のクエリが同一のDBで実行されることになり、 バッチサーバのクエリの影響を受けてサービス側のクエリ実行時間が長くなっていためでした。
複数台の Aurora レプリカを分割した振り分け先DBグループを作り、バッチサーバとサービス側で振り分け先DBグループを分けるなどができると良いのですが、 現状のリーダーエンドポイントにはそのような機能は残念ながらありません。すべての Aurora レプリカに均等に分散されてしまいます。
現状、問題の回避のためにリーダーエンドポイントを利用せずインスタンスエンドポイントを利用しています。
今後は、バッチサーバから発行されるクエリの性能改善を行い、サービスへの影響を減らすことができたらリーダーエンドポイントの利用を再開したいと思っています。
また、振り分け先DBグループのような機能が追加されると、すぐにリーダーエンドポイント利用に戻せるのでそのような機能が追加されたら嬉しいです。

不満点ばかり上げてしまいましたが、決して Aurora 自体に問題があるわけではありません。
バッチサーバから発行されるクエリの改善が必要であるなど、サービスの改善点が見つけられたという意味では意義のある移行でした。 また、すぐに目に見えてくる部分ではないところ(データのレプリケーションによる可用性向上やパッチの無停止アップデートなど)の恩恵もこれから受けることになります。
現時点だけでなく、数年後を見据えた時に意味のある移行だったと確信しています。

まとめ

今回は RDS for MySQL から Aurora への移行についてお話ししました。
Aurora は今後の機能拡張が非常に楽しみなサービスです。
移行後は多少苦労する点もありましたが、総合すると今後につながる意味のある移行だと考えています。 今後も新機能が追加されたらそれを利用することで、より効率的・安定的なインフラ運用を目指していきたいです。


みんなのウェディングでは一緒に働く仲間を募集中です。
サービスの成長に携わっていきたい方や、0からサービスを作りたい、チームでサービスをもっと成長させてみたいエンジニアやデザイナーの方は、ぜひお気軽に遊びに来て下さい!

ただいま夏インターンの参加者を大募集中です!(19卒限定)
このブログを読んで興味を持っていただけたら以下からご応募ください!お待ちしております!