iOS获取手机唯一标识符来判断不同终端登录(IDFA和UUID分析)

11.13更新

广告标示符,适用于对外:例如广告推广,换量等跨应用的用户追踪等。

是iOS 6中另外一个新的方法,提供了一个方法advertisingIdentifier,通过调用该方法会返回一个NSUUID实例,最后可以获得一个UUID,由系统存储着的。不过即使这是由系统存储的,但是有几种情况下,会重新生成广告标示符。如果用户完全重置系统((设置程序 -> 通用 -> 还原 -> 还原位置与隐私) ,这个广告标示符会重新生成。另外如果用户明确的还原广告(设置程序-> 通用 -> 关于本机 -> 广告 -> 还原广告标示符) ,那么广告标示符也会重新生成。关于广告标示符的还原,有一点需要注意:如果程序在后台运行,此时用户“还原广告标示符”,然后再回到程序中,此时获取广 告标示符并不会立即获得还原后的标示符。必须要终止程序,然后再重新启动程序,才能获得还原后的广告标示符。

在同一个设备上的所有App都会取到相同的值,是苹果专门给各广告提供商用来追踪用户而设的,用户可以在 设置|隐私|广告追踪 里重置此id的值,或限制此id的使用,故此id有可能会取不到值,但好在Apple默认是允许追踪的,而且一般用户都不知道有这么个设置,所以基本上用来监测推广效果,是戳戳有余了。

注意:由于idfa会出现取不到的情况,故绝不可以作为业务分析的主id,来识别用户。
因此,IDFA就是用来跟踪广告推广的,而UUID虽然每次不同,但是可以自己手动存入Keychain来进行唯一性的确保,这么说来IDFA就是如果广告商投放的时候使用,而UUID就是自己后台来判断用户是否换了设备,或者信息不一致需要重新登录的业务
知乎上看到一个非常详细介绍IDFA的文章
IDFA看这个就够了

IDFA

可以理解为广告id,apple公司提供的用于追踪用户的广告标识符。缺点:如果用户完全重置系统((设置程序 -> 通用 -> 还原 -> 还原位置与隐私) ,这个广告标示符会重新生成。
另外如果用户明确的还原广告(设置程序-> 通用 -> 关于本机 -> 广告 -> 还原广告标示符) ,那么广告标示符也会重新生成

这是iOS 6中另外一个新的方法,advertisingIdentifier是新框架AdSupport.framework的一部分。ASIdentifierManager单例提供了一个方法advertisingIdentifier,通过调用该方法会返回一个上面提到的NSUUID实例。

// 获取
//需要导入AdSupport.framework这个库
#import <AdSupport/AdSupport.h>
NSString *idfa = [[[ASIdentifierManager sharedManager] advertisingIdentifier] UUIDString];

// 判断是否开启
// 判断是否开启  限制广告跟踪选项(该选项在设置-隐私-广告-限制广告隐私)
Boolean on = [[ASIdentifierManager sharedManager] isAdvertisingTrackingEnabled];

ios10之前开关限制广告追踪选项的确没什么用,ios10之后,如果手机开启限制广告追踪的话就不能再得到广告标识符,得到的是下面的0。这个开关是一个简单的boolean标志,当将广告标示符发到任意的服务器端时,你最好判断一下这个值,然后再做决定。

//开启的时候
2016-01-05 15:22:19.218 sss[1773:60b] 41B2FD07-695A-4A27-8D26-C30ECE6F7EAD
2016-01-05 15:22:19.233 sss[1773:60b] 0

//关闭的时候
2016-01-05 15:19:57.502 sss[1763:60b] 7773E145-26FF-4304-A60F-60C948D52B40
2016-01-05 15:19:57.516 sss[1763:60b] 1

开启和关闭切换的话,idfa会变,如果不切换,保持开启状态,每次都是不会变的,当切换了下之后就会变,或者还原的话会变

// 获取IDFA的方法
+ (NSString *)getIDFA
{
    SEL advertisingIdentifierSel = sel_registerName("advertisingIdentifier");
    SEL UUIDStringSel = sel_registerName("UUIDString");

    ASIdentifierManager *manager = [ASIdentifierManager sharedManager];
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Warc-performSelector-leaks"
    if([manager respondsToSelector:advertisingIdentifierSel]) {

        id UUID = [manager performSelector:advertisingIdentifierSel];

        if([UUID respondsToSelector:UUIDStringSel]) {

            return [UUID performSelector:UUIDStringSel];

        }

    }
#pragma clang diagnostic pop
    return nil;
}

UUID

CFUUID—>2.0出现
NSUUID—>6.0出现
这两个一个是CF框架下的,一个更加面向对象,获取的时候更方便而已,其实获取到的都是同一个东西
针对CFUUID需要注意的是:获得的这个CFUUID值系统并没有存储。每次调用CFUUIDCreate,系统都会返回一个新的唯一标示符。如果你希望存储这个标示符,那么需要自己将其存储到NSUserDefaults, Keychain, Pasteboard或其它地方。

由于我们后台判断App登录时根据uuid来判断的在不同终端登录的,虽然上面提到UUID是获取的时候一直在变化的,而且不是系统级别的存储,那么我们就需要自己存储到系统,用到SSKeyChain,我们自己来保证一个手机理论状态下对应一个UUID

+ (NSString *)getUUID{
    NSString  *openUUID = [[NSUserDefaults standardUserDefaults] objectForKey:OpenSessionID];
//    NSLog(@"openUUID 一: %@",openUUID);
    if (openUUID == nil) {

        CFUUIDRef puuid = CFUUIDCreate(kCFAllocatorDefault);
        CFStringRef uuidString = CFUUIDCreateString(kCFAllocatorDefault,puuid);
        NSString *udidStr = (NSString *)CFBridgingRelease(CFStringCreateCopy( NULL, uuidString));
        CFRelease(puuid);
        CFRelease(uuidString);
        openUUID =  [udidStr MD5Hash];

//        NSLog(@"openUUID 二: %@",openUUID);
        NSString *uniqueKeyItem = [SSKeychain  passwordForService:kUniqueIdentifier account:kUniqueIdentifierValue];
        if (uniqueKeyItem == nil || [uniqueKeyItem length] == 0) {
            uniqueKeyItem = openUUID;
            [SSKeychain  setPassword:openUUID forService:kUniqueIdentifier account:kUniqueIdentifierValue];
        }
        [[NSUserDefaults standardUserDefaults] setObject:uniqueKeyItem forKey:OpenSessionID];
        [[NSUserDefaults  standardUserDefaults] synchronize];
//        NSLog(@"uniqueKeyItem: %@",uniqueKeyItem);
        openUUID = uniqueKeyItem;
    }
//    NSLog(@"openUUID 三: %@",openUUID);
    return openUUID;
}

1.首先从沙盒获取,没有的话就调用CF方法获取,然后再去keychain获取,如果没获取到,把刚才获取到的UUID存储到Keychain,由于keychain你不刷机,存储的东西会一直存在,因此保证了唯一性,每次获取的都是从keychain获取到的第一次存储进去的值,那么请求的时候,后台根据用户主键盘点uuid是否更改从而判断是否换了终端登录,进行弹框提示

总结:
1.idfa在用户重置广告标志符的时候会变化,所以可以把第一次生成的idfa存放到keychain里面,以后就直接读取keychain值就可以了,这样就能避免用户重置广告标志符造成idfa的变化,而keychain的值只有在用户重置系统的时候才会删除,所以很适合用idfa+keychain的方案
2.那么第二种方法也可以用,UUID+Keychain的方式也行,上面介绍了,我们就用的第二种,总之,keychain是个好东西,根据app的键,来存储对应的用户信息,密码等重要信息还是不错的,这里简单记录下之前一直疑惑的知识点,方便以后查阅

IDFA提交Appstore选项相关

如何确定是否需要选择IDFA???先看看下面的终端使用判断是否需要勾选
iOS审核中如何正确填写APP广告标识符IDFA

1、在 App 内投放广告

2、将此 App 安装归因于先前投放的特定广告

3、将此 App 中发生的操作归因于先前投放的特定广告

4、对使用广告标识符做确认

1.serve advertisements within the app

服务应用中的广告。如果你的应用中集成了广告的时候,你需要勾选这一项。

2.Attribute this app installation to a previously served advertisement.

跟踪广告带来的安装。如果你使用了第三方的工具来跟踪广告带来的激活以及一些其他事件,但是应用里并没有展示广告你需要勾选这一项。

3.Attribute an action taken within this app to a previously served advertisement

跟踪广告带来的用户的后续行为。如果你使用了第三方的工具来跟踪广告带来的激活以及一些其他事件,但是应用里并没有展示广告你需要勾选第2项和第3项。

下边还有一项

4.Limit Ad Tracking setting in iOS

这一项下的内容其实就是对你的应用使用idfa的目的做下确认,只要你选择了采集idfa,那么这一项都是需要勾选的。

总结一下,

(1)如果你的应用里只是集成了广告,不追踪广告带来的激活行为,那么选择1和4;

(2)如果你的应用里没有集成广告,但是需要追踪广告带来的激活行为,那么选择2,3和4;

(3)如果你的应用里集成了广告,而且使用了sdk等用来追踪广告带来的激活行为,需要选择1,2,3和4 。

个人理解:当你有用到IDFA的时候,你是必须要勾选YES的,14年的时候很严格,剩下四个选项如果你选错了很容易悲剧,现在感觉如果你选了YES,然后在找个合适的理由勾选,基本上没问题了,例如你集成了UMENG的IDFA SDK,然后你有启动广告,你选1和4,一样OK了

参考博客,还介绍了其他标识符

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,324评论 5 476
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,303评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,192评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,555评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,569评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,566评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,927评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,583评论 0 257
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,827评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,590评论 2 320
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,669评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,365评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,941评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,928评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,159评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,880评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,399评论 2 342

推荐阅读更多精彩内容