テックブログ編集部の小川です。
春めきだつ今日このごろに今更感はありますが、社内のエンジニアを対象として、昨年 2021 年に「やらかした」ことを募ってみました。いただいた中から、いくつか紹介します。
存在しない URL にアクセスした場合、301 リダイレクトのループが発生することがある (N さん)
事象
OpenWork の一部のページにおいて、存在しない URL にアクセスすると 404 ではなく 301 リダイレクトのループが発生した。
原因
2021 年 2 月に実施した Symfony フレームワークのバージョンアップによる挙動の変更が原因。 Symfony 4.1 からは、存在しない URL にアクセスしたとき
- 末尾にスラッシュがない場合、スラッシュありの URL にリダイレクト ... (*)
- 末尾にスラッシュがある場合、スラッシュなしの URL にリダイレクト
という動作になる。
ここで、一部の Controller において、「末尾にスラッシュがついている場合、スラッシュなしの URL にリダイレクト」という処理があった。上記 (*) と組み合わされてしまうことで、リダイレクトの無限ループが発生するようになってしまった。
再発防止策
404 エラーページ用のテストを追加する。
編集部コメント
フレームワークのバージョンアップはこういった予期しない問題が出てくるので気が抜けないですね。
iOS 課金更新処理が失敗することがある (M さん)
事象
iOS アプリの課金更新処理が失敗することがある。エラー発生後も放置していると、ユーザーがクチコミを閲覧できなくなることがある。
原因
課金更新処理で利用している、以下の Apple の API が稀に 500 エラーを返すため。
https://developer.apple.com/documentation/appstorereceipts/verifyreceipt
再発防止策
外部 API の 500 を回避することはできないため、更新処理を一定時間後に再実行するように改修した。
編集部コメント
センシティブになりがちな課金系の案件です。こういった大事な処理で 500 を返されると凹みますね。リトライのデザインも奥深いので、社内でノウハウを集めていければと思います。
本番環境の EFS を設定変更した (O さん)
事象
開発環境の EFS を設定変更しようとしたところ、誤って本番環境のそれを変更してしまった。
具体的にはスループットモードをプロビジョンドからバーストに変更。すぐ気付けたため、バーストクレジットの枯渇前に設定を戻せたものの、サイトの UX に大きな影響が生じるところだった。
原因
操作ミス。 さらには、開発環境のリソースと本番環境のリソースが同じ AWS アカウント上にあること。
再発防止策
気合で間違えないようにする…はもちろんダメなので、AWS のアカウント分離が現実的。
編集部コメント
やらかしたと気付いた瞬間、いやな冷や汗がたくさん出る案件です。アカウント分離は面倒な割に目に見える効果がないため食指がなかなか動かないのですが、かといって分離されていないとこういう事故が起きてしまうので厄介です。
サービスが応答しなくなった (I さん)
事象
夜、最もアクセスが多い時間帯のこと。本番 DB の CPU が 100% に張り付き、サービスが応答を返さなくなった。
ちょうど同じタイミングでバッチもエラーを吐いて落ちた。
サービス自体は数分で復旧。落ちたバッチに関しては、DB とは関係のなさそうなエラー内容だったため、一時的な事象と判断しバッチを再実行。すると本番 DB の CPU が再び 100% に張り付き、サービスが応答しなくなった。
原因
原因不明。翌日昼にバッチを再実行した際は何も起きなかった。
再発防止策
原因がわからなかったことと、その後再発しなかったためあきらめていた。だがここ最近は再発の傾向があり、改めて調査をすすめている。
編集部コメント
バッチを実行しないとサービスに影響が出る、しかしバッチを実行するとサービスが止まる、というラスボスのような問題です。
再現性も低く苦戦していましたが、最近、特定のクエリとデータ更新が重なるとキャッシュが効かなくなるという仮説が見つかったため、対応を進めています。
謎のクエリが一ヶ月以上動き続けていた (O さん)
事象
本番 DB の CPU 利用率が、普段の 3 倍近くになっていた。
原因
調査をすすめたところ、Aurora MySQL ライターインスタンスのメトリクス RollbackSegmentHistoryListLength
の値が上昇していることがわかった。
インスタンス内で SHOW FULL PROCESSLIST
したところ、3 つ分のプロセスが 48 日間程度実行されていたため、KILL。結果、CPU 利用率、および RollbackSegmentHistoryListLength
が正常な値に戻った。
なぜクエリが長い間実行され続けたのかは不明。
再発防止策
48 日間もクエリが実行されていたことに気付けなかったのはよくない。Aurora の重要なメトリクスの監視が不十分だったため、設定する。
編集部コメント
クエリがやらかしてくれた案件です。
一定時間後にタイムアウトで落ちる想定だったのですがそうはいかないことがわかったので、防止策にもあるように悪いクエリをしっかり見つけられるよう監視を設定します。
最後に
やらかしたというより不可抗力で起きてしまった問題もありましたが、興味深かったので取り上げてみました。こうして振り返ってみると 2021 年もいろいろありました。記事化することで供養できればと思います。
さて、障害発生時、弊社で最も優先することが UX の回復です。これを前提とし、できるだけ早く障害から復旧ができるよう、各メンバーが自発的に障害対応にあたっています。(慣れていない人でも対応フローがまとめられているのでご安心ください。)
作業ミスやバグの発生を完全に防ぐことは不可能ですが、発生原因を分析して再発防止につなげることはできます。こうした問題を、個人ではなくチームで取り組んでいくのもオープンワークらしいかもしれません。
プロダクトの品質向上に興味のある方、募集しています。