Edited at

安易にiOSのUUIDをアカウント認証ロジックに使ってはいけない

More than 1 year has passed since last update.

この記事は Akatsuki Advent Calendar 2016 の5日目です。


はじめに

iOS端末のUUIDとソーシャルゲームアプリのアカウント認証にまつわる話です。


経緯

UUIDをアプリのアカウント認証のロジックに使用していたら、

iCloudバックアップ後にログインできなくなってしまった。


UUIDとは


UUID(Universally Unique IDentifier)とは、全世界で2つ以上のアイテムが同じ値を持つことがない一意な識別子のこと。

何らかの組織やシステムなどが管理・割り当てを行うわけではなく、誰でもいつでも自由に生成することができるが、他のUUIDと重複することは起きないようになっている。


出典: IT用語辞典 UUID

UUIDは絶対に被らないユニークなIDです。

iOSでもUUIDを取得するメソッドが提供されています。

例: [[UIDevice currentDevice].identifierForVendor UUIDString]

このUUIDをアプリのアカウント認証のロジックに使用するケースがあります。


iCloudによるバックアップ

iCloudとはApple社が提供するサービスで、バックアップやiPhoneを探すが有名かと思います。便利ですね。

iCloudを使って端末のバックアップを取ると、新しくiOS端末を購入したとしても、

すぐに元の端末の状態に戻すことができます。

ソーシャルゲームアプリのデータとかもiCloudの容量があればバックアップすることができます。

本当に便利ですね。しかし、ここでほいほいバックアップから復元すると、ある問題が起きます。


何が起きたのか

iCloudからのバックアップでiOS端末内のデータは丸ごと復元されますが、

端末が違うためUUIDが変更されています。

UUIDをゲーム認証ロジックに使用していた場合、アプリデータ自体は残っているため、

そのままアプリを起動すると認証に失敗してしまいます。(ゲーム内のIDは正しいが、端末が違う…)

よって、ユーザは新規アカウントで始めることを余儀なくされます。

前端末で遊んでいたデータを自己修復する術はないため、

ディベロッパーのカスタマーサポートにアカウント復旧をお願いするほかありません。

ユーザはアカウント復旧を待たなくてはいけないし、

開発者はアカウント復旧に頭を抱えてしまいます。


どうすればいいの?


1. UUIDを端末内部に保存する


  • 端末からUUIDを取得した時点でUUIDを端末内部に保存しておく

  • もし取得したUUIDが違っていた場合(iCloudからのバックアップ、etc.)、保存してあるUUIDを用いて認証を行う

  • 認証に成功した時点で、保存してあるUUIDを新しいものに書きかえる


2. UUIDを使わずに端末を特定するIDを発行する


  • 端末から取得したUUIDではなく、サーバ側で発行したUUIDを用いて認証を行う

  • 端末側ではそのUUIDをセキュアな場所に保存しておく


3. iCloudでバックアップするときは注意してください、と呼びかける


  • 諦めの一手

  • iCloudによるバックアップを行う前に、アプリ内の引き継ぎを行っておくように、とアプリ内でアナウンスする


結論

1や2を用いることでiCloudバックアップ対策になると思います。

3は冗談交じりですが、既に動いているサービスだと

なかなか全ユーザの認証の仕組みを変えるのにはリスクがあると思うので、手段としては有りかと。


まとめ


UUIDは絶対に変更されないもの。

変更されるときは機種変更のときだけだからその時はアプリ内のデータ引き継ぎはやってくれるだろう。


という前提は捨てましょうm(__)m