当前位置: 移动技术网 > 移动技术>移动开发>IOS > iOS 获取设备唯一标示符的方法详解

iOS 获取设备唯一标示符的方法详解

2019年07月24日  | 移动技术网移动技术  | 我要评论

在开发中会遇到应用需要记录设备标示,即使应用卸载后再安装也可重新识别的情况,在这写一种实现方式——读取设备的uuid(universally unique identifier)并通过keychain记录。

首先ios中获取设备唯一标示符的方法一直随版本的更新而变化。ios 2.0版本以后uidevice提供一个获取设备唯一标识符的方法uniqueidentifier,通过该方法我们可以获取设备的序列号,这个也是目前为止唯一可以确认唯一的标示符。好景不长,因为该唯一标识符与手机一一对应,苹果觉得可能会泄露用户隐私,所以在 ios 5.0之后该方法就被废弃掉了;ios 6.0系统新增了两个用于替换uniqueidentifier的接口,分别是:identifierforvendor,advertisingidentifier,但这两个接口会在应用重新安装时改变数值,并不是唯一的标示符,所以开发者改为使用wifi的mac地址来取代;ios 7中苹果又封杀mac地址,所以开发者再次改变思路使用keychain来保存获取到的udid,这样以后即使app删了再装回来,也可以从keychain中读取回来。

首先保存设备的uuid,可以使用类方法+ (id)uuid 是一个类方法,调用该方法可以获得一个uuid。通过下面的代码可以获得一个uuid字符串:

 nsstring *uuid = [[nsuuid uuid] uuidstring];

也可以保存在ios 6中新增的vindor标示符 (idfv-identifierforvendor),获取这个idfv的新方法被添加在已有的uidevice类中。跟advertisingidentifier一样,该方法返回的是一个nsuuid对象。

nsstring *idfv = [[[uidevice currentdevice] identifierforvendor] uuidstring];

如果用户卸载了同一个vendor对应的所有程序,然后在重新安装同一个vendor提供的程序,此时identifierforvendor会被重置,所以这里要用到keychain来保存。

keychain(钥匙串)是使用苹果设备经常使用的,通常要调试的话,都得安装证书之类的,这些证书就是保存在keychain中,还有我们平时浏览网页记录的账号密码也都是记录在keychain中。ios中的keychain相比os x比较简单,整个系统只有一个keychain,每个程序都可以往keychain中记录数据,而且只能读取到自己程序记录在keychain中的数据。ios中security.framework框架提供了四个主要的方法来操作keychain:

  • secitemcopymatching(cfdictionaryref query, cftyperef *result);//查询osstatus
  • secitemadd(cfdictionaryref attributes, cftyperef *result); //添加osstatus
  • secitemupdate(cfdictionaryref query, cfdictionaryref attributestoupdate);//更新keychain中的itemosstatus
  • secitemdelete(cfdictionaryref query)//删除keychain中的itemosstatus

这四个方法参数比较复杂,一旦传错就会导致操作keychain失败,文档中介绍的比较详细,大家可以查查官方文档。而苹果提供的keychain使用起来略麻烦,所以这里推荐一个第三方库samkeychains.samkeychains对苹果安全框架api进行了简单封装,支持对存储在钥匙串中密码、账户进行访问,包括读取、删除和设置。samkeychains使用简单,通过实例代码便可掌握。

//保存一个uuid字符串到钥匙串:
cfuuidref uuid = cfuuidcreate(null);
assert(uuid != null);
cfstringref uuidstr = cfuuidcreatestring(null, uuid);
 [samkeychain setpassword: [nsstring stringwithformat:@"%@", uuidstr]
 forservice:@"com.yourapp.yourcompany"account:@"user"];

//从钥匙串读取uuid:
nsstring *retrieveuuid = [samkeychain passwordforservice:@"com.yourapp.yourcompany"account:@"user"];

**注意: setpassword和passwordforsevice方法中的**services 和 accounts 参数应该是一致的。

更多详细用法说明可以看samkeychains documentation

基本的实现思路便是这样,下面是具体的一种具体实现代码,仅供参考。

+ (nsstring *)getdeviceid
{
  nsstring * currentdeviceuuidstr = [samkeychain passwordforservice:@" "account:@"uuid"];
  if (currentdeviceuuidstr == nil || [currentdeviceuuidstr isequaltostring:@""])
  {
    nsuuid * currentdeviceuuid = [uidevice currentdevice].identifierforvendor;
    currentdeviceuuidstr = currentdeviceuuid.uuidstring;
    currentdeviceuuidstr = [currentdeviceuuidstr stringbyreplacingoccurrencesofstring:@"-" withstring:@""];
    currentdeviceuuidstr = [currentdeviceuuidstr lowercasestring];
    [samkeychain setpassword: currentdeviceuuidstr forservice:@" "account:@"uuid"];
  }
  return currentdeviceuuidstr;
}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持移动技术网。、

如对本文有疑问, 点击进行留言回复!!

相关文章:

验证码:
移动技术网