前言
在移动端游戏开发时,我们常常会有获取一个唯一且固定不变的用户标识的需求
unity本身是提供了一个唯一标识(SystemInfo.deviceUniqueIdentifier)供我们使用的,在安卓设备上,我们只要保证应用的签名不变,这个标识基本就不会改变。但在IOS设备上这个标识却会随着用户更新系统或者重装应用而发生变化
当然网上有特别多的实现方案,在此仅分享一个博主常用且在线上产品验证有效的方案
IDFV
IOS官方文档
用来标识应用程序开发商的唯一标识符,且必然能获取到,无需请求用户权限。对于来自同一开发商并在同一设备上运行的应用,此属性的值相同。但卸载重装可能会可能导致该值发生变化
例如,应用A和应用B均来自同一个开发商,在某个IOS设备上安装或卸载这两个应用,以下不同情况会有不同结果
- 如果已安装A,A获取到的是IDFV_A,再安装B,B获取到的是IDFV_B,此时IDFV_A和IDFV_B相同
- 如果已安装A,A获取到的是IDFV_A,再安装B,B获取到的是IDFV_B,然后卸载重装A,A获取到的还是IDFV_A,且IDFV_A和IDFV_B相同
- 如果已安装A,A获取到的是IDFV_A,再安装B,B获取到的是IDFV_B,然后同时卸载A和B,接下来再重新安装A,A获取到的是IDFV_A_1,IDFV_A和IDFV_A_1不一定相同。此时如果再安装B,B获取到的是IDFV_B_1,IDFV_B_1和IDFV_A_1还是相同的
IOS钥匙串-Keychain
苹果官方提供的一种存储机制,主要用于存储一些敏感信息(如密码、密钥等),不会随应用卸载而被清除。当然实现方式也非常多,如果没有合适的实现方式,可以使用以下源码
实现源码
IOS唯一标识实现方案
本方案还是使用IDFV作为唯一标识,只不过并非每次重新启动应用都去获取。
在应用启动时,首先去PlayerPrefs中查询是否存储了该应用的IDFV。如果PlayerPrefs中存在,则直接使用,如果PlayerPrefs中不存在,则去Keychain中查询。如果Keychain中存在,则直接使用并将其存储到PlayerPrefs中,如果Keychain中不存在,则需要去获取IDFV并将其同时储存到PlayerPrefs和Keychain中
简单的源码实现
public static string GetUUID_IOS()
{
const string IdfvKey = "IdfvIOS";
KeychainWrapper keychainWrapper = new KeychainWrapper();
string uuid = PlayerPrefs.GetString(IdfvKey, "");
if (string.IsNullOrEmpty(uuid))
{
uuid = keychainWrapper.GetStringForKey(IdfvKey);
if (string.IsNullOrEmpty(uuid))
{
uuid = UnityEngine.iOS.Device.vendorIdentifier;
keychainWrapper.SetStringForKey(IdfvKey, uuid);
}
PlayerPrefs.SetString(IdfvKey, uuid);
}
else
{
//防止钥匙串中未存储
if (string.IsNullOrEmpty(keychainWrapper.GetStringForKey(IdfvKey)))
{
keychainWrapper.SetStringForKey(IdfvKey, uuid);
}
}
return uuid;
}
这样就能保证以后每次使用的均是首次启动应用时保存的IDFV。当然不排除一些极特殊的情况(比如刷机重装系统之类的)导致丢失的,但这不在我们本方案的考虑范围内,因为这发生的概率极低且并非我们能避免的。如果想要保证百分百唯一且不丢失,最好的方案还是引导用户绑定第三方账号