iOS10以及XCode8适配问题汇总

升级iOS10以后,遇到了很多新的的问题。经过一段时间的适配,暴露的问题基本都已经解决。这里把这些问题作一个统一的汇总,方便其他同学再遇到类似的问题时,进行查阅。
这些问题,大致分为下面几类:

一、权限crash闪退

iOS 10 开始对隐私权限更加严格,如果你不设置就会直接崩溃,现在很多遇到崩溃问题了,一般解决办法都是在info.plist文件添加对应的Key-Value就可以了。如下图:

特别注意:value值不能为空,否则AppStore提交会审核被拒。

二、系统版本方法判断失效

由于iOS系统已经升级到iOS10,版本号由1位数变成了2位数,在之前处理版本号相关的代码需要重新检查确认没有使用错误,Firefly iOS组便发现此前使用的版本号判断方法上存在缺陷。
项目组在此之前通过使用compare来对iOS系统的版本进行比较,具体代码如下:

[[[UIDevicecurrentDevice] systemVersion] compare:@"9.0"] != NSOrderedAscending;

上述的代码的意图是判断当前iOS系统与9.0的关系,本来是要将字符串转化成数字之后与9.0进行比较,然后得出结果。但在compare时存在缺陷,直接使用compare函数在比较时是将两者当成字符串进行字典比较,并非按预想根据数值比较。在iOS10版本之前,这行代码返回的结果是对的,因为数字1-9在字典中的顺序与数字顺序一致,所以并未出错。但当iOS升级到10后,版本获取返回的”10.0”与”9.0”比较时,会按字符串进行字典比较,进而先将”1”与”9”比较,结果发现”1”在”9”前面,从而认为”10.0”小于”9.0”,得出错误结果,导致许多依赖版本的方法运行出错。该方法有点类似于当年的千年虫,缺陷会在某个时间才会暴露出来,iOS升级到10便触发这个bug的原因。版本判断正确的方法是使用带options的compare函数,如下所示:

[[[UIDevicecurrentDevice] systemVersion] compare:@"9.0" options:NSNumericSearch] != NSOrderedAscending;
  • 之前如果存在类似的代码:
#define IOS10_OR_LATER ( [[[UIDevice currentDevice] systemVersion] compare:@"10.0"] != NSOrderedAscending )
#define IOS9_OR_LATER ( [[[UIDevice currentDevice] systemVersion] compare:@"9.0" ] != NSOrderedAscending )
  • iOS10以后要采用更加严谨的判断方法:
#define IOS10_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"10.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS9_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"9.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS8_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"8.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS7_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"7.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS6_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"6.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS5_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"5.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS4_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"4.0" options:NSNumericSearch] != NSOrderedAscending )
#define IOS3_OR_LATER  ( [[[UIDevice currentDevice] systemVersion] compare:@"3.0" options:NSNumericSearch] != NSOrderedAscending )
三、控制台多余log

XCode8新建一个工程,运行。会发现控制台输出很多系统级别的log,如果不想看到这些log,解决办法是设置OS_ACTIVITY_MODE : disable。
具体的途径是:【product】-【scheme】-【Edit Scheme】-【Run】-【Argument】-【Environment Variable】添加keyValue【OS_ACTIVITY_MODE disable】可以停止输出打印此日志。

四、IDFA获取失败

首先关于IDFA的说明文档,有这么一句话:

Important
In iOS 10.0 and later, the value of advertisingIdentifier is all zeroes when the user has limited ad tracking.

ios10更新之后一旦开启了 设置->隐私->广告->限制广告跟踪之后 获取到的idfa将会是一串00000 ,而且每次开启在关闭之后 相应的idfa也会重新生成,相当于还原了一次广告标识符。
针对这种修改,目前Firefly_iOS采用的解决方案是:
设备标识首先采用IDFA,获取时增加判断[[ASIdentifierManager sharedManager] isAdvertisingTrackingEnabled],如果获取不到,就返回vender ID。
同时,新增一个用户设备指纹接口,专门标识用户的使用设备是否发生变化。采用的方案是verder id + keychain。第一次将verder id存入keychain,之后都从keychain获取。
相关代码实现:

+ (NSString *)deviceIdentifier
{
    static NSString *_identify = nil;
    static  dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        if (_identify == nil)
        {
            // iOS10以后IDFA可能会由于设置获取不到
            if ([[ASIdentifierManager sharedManager] isAdvertisingTrackingEnabled])
            {
                _identify = [[[ASIdentifierManager sharedManager] advertisingIdentifier] UUIDString];
            }
            else
            {
                _identify = [[[UIDevice currentDevice] identifierForVendor] UUIDString];
            }
        }
    });
    
    return _identify;
}

+ (NSString *)verifyCode
{
    static NSString *_identify = nil;
    static  dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        if (_identify == nil)
        {
            _identify = [FireflyKeychain passwordForService:kFireflyAppIdentifyService
                                                   username:kFireflyAppIdentifyUser];
            if (_identify == nil)
            {
                _identify = [[[UIDevice currentDevice] identifierForVendor] UUIDString];
                [FireflyKeychain setPassword:_identify
                                  forService:kFireflyAppIdentifyService
                                    username:kFireflyAppIdentifyUser];
            }
        }
    });
    
    return _identify;
}
五、模拟器环境,RSA公钥获取不到,导致crash

具体的原因和keychain的权限问题有关,将工程配置里的keychain开关打开即可。

六、推送修改

首先,工程设置的开关一定要记得打开:

具体的使用规则,先简单记录如下,后续会继续完善:
iOS 9 以前的通知

  • 1.在调用方法时,有些方法让人很难区分,容易写错方法,这让开发者有时候很苦恼。
  • 2.应用在运行时和非运行时捕获通知的路径还不一致。
  • 3.应用在前台时,是无法直接显示远程通知,还需要进一步处理。
  • 4.已经发出的通知是不能更新的,内容发出时是不能改变的,并且只有简单文本展示方式,扩展性根本不是很好。

iOS 10 开始的通知

  • 1.所有相关通知被统一到了UserNotifications.framework框架中。
  • 2.增加了撤销、更新、中途还可以修改通知的内容。
  • 3.通知不在是简单的文本了,可以加入视频、图片,自定义通知的展示等等。
  • 4.iOS 10相对之前的通知来说更加好用易于管理,并且进行了大规模优化,对于开发者来说是一件好事。
  • 5.iOS 10开始对于权限问题进行了优化,申请权限就比较简单了(本地与远程通知集成在一个方法中)。
七、ATS问题
  • 1.在iOS 9的时候,默认非HTTS的网络是被禁止的,我们可以在info.plist文件中添加NSAppTransportSecurity字典,将NSAllowsArbitraryLoads设置为YES来禁用ATS;
  • 2.从2017年1月1日起,所有新提交的 app 默认不允许使用NSAllowsArbitraryLoads来绕过ATS的限制,默认情况下你的 app 可以访问加密足够强的(TLS V1.2以上)HTTPS内容;
  • 3.可以选择使用NSExceptionDomains设置白名单的方式对特定的域名开放HTTP内容来通过审核,比如说你的应用集成了第三方的登录分享SDK,可以通过这种方式来做。
    下面以新浪SDK作为示范:
<key>NSAppTransportSecurity</key>
<dict>
 <key>NSExceptionDomains</key>
 <dict>
  <key>sina.cn</key>
  <dict>
   <key>NSThirdPartyExceptionMinimumTLSVersion</key>
   <string>TLSv1.0</string>
   <key>NSThirdPartyExceptionRequiresForwardSecrecy</key>
   <false>
   <key>NSIncludesSubdomains</key>
   <true>
  </true></false></dict>
  <key>weibo.cn</key>
  <dict>
   <key>NSThirdPartyExceptionMinimumTLSVersion</key>
   <string>TLSv1.0</string>
   <key>NSThirdPartyExceptionRequiresForwardSecrecy</key>
   <false>
   <key>NSIncludesSubdomains</key>
   <true>
  </true></false></dict>
 </dict>
</dict>
八、NSAllowsArbitraryLoadsInWebContent键

在iOS 10 中info.plist文件新加入了NSAllowsArbitraryLoadsInWebContent键,允许任意web页面加载,同时苹果会用 ATS 来保护你的app。

九、安全传输不再支持SSLv3,

建议尽快停用SHA1和3DES算法。

参考:
http://www.cnblogs.com/oc-bowen/p/5916630.html
http://www.2cto.com/kf/201609/547127.html

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

推荐阅读更多精彩内容

  • 随着iOS10发布的临近,大家的App都需要适配iOS10,下面是我总结的一些关于iOS10适配方面的问题,如果有...
    Eternaldream阅读 58,541评论 58 333
  • 一、证书管理用Xcode8打开工程后,比较明显的就是下图了,这个是苹果的新特性,可以帮助我们自动管理证书。建议大家...
    seventhboy阅读 1,497评论 0 2
  • 随着iOS10发布的临近,大家的App都需要适配iOS10,下面是我总结的一些关于iOS10适配方面的问题,如果有...
    杨二哥阅读 508评论 4 2
  • 随着iOS10发布的临近,大家的App都需要适配iOS10,下面是我总结的一些关于iOS10适配方面的问题,如果有...
    心淡然如水阅读 483评论 0 0
  • 原文链接:http://www.jianshu.com/p/f8151d556930 随着iOS10发布的临近,大...
    Ywaiting阅读 341评论 0 0