オンライン上で9月2日~4日にわたって開催の「CEDEC2020」。ここでは、9月3日に行われたセッション「SINoALICE -シノアリス- それは緊急の”障害対応”」の内容をお届けする。
この講演では、「SINoALICE -シノアリス-」(以下、「シノアリス」) のサービス開始から3年の間に起こった、人為的なミスや自然的とも言えるインフラ障害、発生原因の特定が困難な障害等の今までに発生した障害から、全体への影響範囲が大きかったものをピックアップして振り返った。
ソーシャルゲームにおける補填作業などで注意すべきポイントや避けるべき実装方法が実例と共に紹介されたので、そのレポートをお届けしよう。
プレゼントボックスの改善
「シノアリス」とは、スクウェア・エニックスとポケラボによる、童話をモチーフにしたスマートフォン向けアプリ。魅力的なキャラクターとヨコオタロウ氏原案によるダークな世界観が、本作にしかない特有の魅力を生み出している。
そして「シノアリス」では特に、毎日行われているギルドバトルが目玉コンテンツのひとつとなっている。コロシアムの開催時間は、8:00~8:20、12:30~12:50、18:00~18:20、19:00~19:20、20:00~20:20、21:00~21:20、22:00~22:20、23:00~23:20までの間で選ぶことが可能(選択権はギルドマスターのみ)。
「シノアリス」で実際に起こった障害のひとつとして挙げられたのは、2019年12月16日から開催されたクリスマスイベント「聖夜の旅路」。メディアでも大々的に宣伝したイベントだったこともあり、イベントのメンテ明けから想定以上のアクセスがあった。DBのCPU使用率が70%にまで上昇している。
一方で、このアクセス集中が起こる1日前にもグラフでCPUの使用率が一瞬跳ね上がっている。これは前述のコロシアムが終わったあとに、コロシアムを遊んでいた人たちがプレゼントボックスに報酬を受け取りにくるためだそう。今のこのアクセス集中状態がずっと続くと、コロシアムが始まった時に障害が起こってしまう。
だが、DBスペックアップを行うためにはメンテナンスが必要で、コロシアムが中止になってしまう。できるだけコロシアムは止めたくないので、メンテナンスを行うことができない。
一方でフェイルオーバー(異常を検知した時に、正常なサーバーに切り替える)を発生させる道もあったが、そうすると数十秒の接続障害が発生し、リアルタイムバトルを売りにしている「シノアリス」では致命的だった。
「シノアリス」ではNewRelicでパフォーマンスを見ているが、通常よりもプレゼントボックスの受け取り処理が遅くなっていることが確認出来ていた。
そこでやむを得ず、ゲームを止めないためにプレゼントボックスの受け取りを確率で通す処理を行った。そしてこの緊急対応を行ってから、なんとかサーバーの負荷はギリギリのところで抑えられた。
もちろんこれは緊急的な措置のため、恒久対応を行わなければならない。負荷が上昇したのはユーザーデータDBのwriter群。長期運用によるサーバー削減やデータ増加により、writerへのSELECTが徐々に負荷として顕著化し、今回のイベントでその負荷が表面化することとなった。
そこで負荷を下げるために「武器を〇種類集める」ミッションの判定について改修をいれることとなった。
未所持武器は、受け取りごとに図鑑登録され、武器収集ミッションの判定が行われる。この流れはミッションの実装としては正しく、一般的にもよく使われているのだが、この処理がリリース時と比べてコストが高くなっていた。
そこで呼び出しを少なくするために、処理をAPI単位で分離。ミッション確認画面で武器収集カウントのセレクトを行うように、ミッション達成度更新を行うようにした。
ユーザーにとっては特に変わった部分はわからないが、サーバーの負荷には効果覿面だったという。特にイベント直後は新武器が実装されるため、ユーザーがプレゼントボックスに集中するが、この対応によってreaderのほうに負荷を逃がすことが出来た。
大規模データの改善
次は、2020年3月10日に、モノガタリでチャットが使用不能になった障害。モノガタリが進行不能になってしまったのだ。
この案件ではサーバー、DBの負荷には問題がなく、チャットのデータも正常で、モノガタリ以外のチャットは使用できたため、これまで出会ったことのない障害だったという。
ベテランのエンジニアに相談したところ、チャットのint最大値を超えたあたりから障害が発生しているのでは、という指摘があった。
intとは、データベースで数値を扱うための型。リリース時より、アプリ側はサーバーからのレスポンスでチャットのIDをint型で受け取って使用していたが、3年が経ちチャットのIDがintを超えてしまったため、アプリが誤作動を起こしていたのだ。
恒久対応を行うためにはアプリの修正が必要のため、まずはサーバー側で暫定的な対応を行った。
まずチャットデータへINSERTするIDを修正。そして不要なチャットデータを退避させ、空き領域にインサートするように緊急対応すると、アプリの誤作動は収まった。
だが、そもそも「シノアリス」では大量のデータを扱うにあたっての対策として、DBのshardingや、不要データの削除(退避)、primary keyのようなauto incrementするカラムの型のサイズの妥当性検証などは行っていた。
特に不要なデータが肥大化しやすいテーブルは、バトルデータ、チャットデータ、プレゼントデータ。よって「シノアリス」では毎日深夜に、3日前のデータを削除(退避)している。
ここまでしていても、何故障害は起こってしまったのか。その原因は、データのシリアライズはMesseagePackで、レスポンスの型はサーバーサイドエンジニア・クライアントエンジニアが手動で入力しているが、コミュニケーションミスがあり、型の差が生まれてしまったことだった。
よって再発防止策として、スキーマ定義からサーバとのクライアントのコードを同時に生成する仕組みを作れば良いのでは、と考えているという。また、根本的な解決として、スキーマ情報をもったIDLと、DBスキーマ情報からクライアントのコードをチェックする仕組みを導入予定だという。
最後に山口氏は「ゲームを運用していく上で課題は日々変わっていく。課題に対する最適な解を模索、選択することで、未来につながる。今後も色々な課題な浮彫になってくるのかもしれないが、お客様に安定したサービスを届けるためにも、良い勉強の機会とするためにも、しっかり取り組んでいきたい」と本セッションを締めくくった。
(C) 2017-2020 Pokelabo Inc./SQUARE ENIX CO., LTD. All Rights Reserved.
※画面は開発中のものです。
本コンテンツは、掲載するECサイトやメーカー等から収益を得ている場合があります。





















































