iOS14 隱私適配及部分解決方案

原文鏈接 淘系技術(shù):iOS14 隱私適配及部分解決方案

簡介: 在剛剛結(jié)束的線上 WWDC 2020 發(fā)布會上蘋果向我們展示了新的 iOS14 系統(tǒng)。iOS14 的適配,很重要的一環(huán)就集中在用戶隱私和安全方面。 最近在調(diào)研 iOS14的適配方案,本文主要分享一下 iOS14 上對于隱私授權(quán)的變更和部分適配方案,歡迎補(bǔ)充指正。

滾動.gif

在剛剛結(jié)束的線上 WWDC 2020 發(fā)布會上蘋果向我們展示了新的 iOS14 系統(tǒng)。iOS14 的適配,很重要的一環(huán)就集中在用戶隱私和安全方面。

在 iOS13 及以前,當(dāng)用戶首次訪問應(yīng)用程序時,會被要求開放大量權(quán)限,比如相冊、定位、聯(lián)系人,實(shí)際上該應(yīng)用可能僅僅需要一個選擇圖片功能,卻被要求開放整個照片庫的權(quán)限,這確實(shí)是不合理的。對于相冊,在 iOS14 中引入了 “LimitedPhotos Library” 的概念,用戶可以授予應(yīng)用訪問其一部分的照片,對于應(yīng)用來說,僅能讀取到用戶選擇讓應(yīng)用來讀取的照片,讓我們看到了 Apple 對于用戶隱私的尊重。這僅僅是一部分,在iOS14 中,可以看到諸多類似的保護(hù)用戶隱私的措施,也需要我們升級適配。

最近在調(diào)研 iOS14的適配方案,本文主要分享一下 iOS14 上對于隱私授權(quán)的變更和部分適配方案,歡迎補(bǔ)充指正。

適配點(diǎn)

? 相冊

? iOS14 新增了“Limited Photo Library Access” 模式,在授權(quán)彈窗中增加了 Select Photo 選項(xiàng)。用戶可以在 App 請求調(diào)用相冊時選擇部分照片讓 App 讀取。從 App 的視?來看,你的相冊里就只有這幾張照片,App 無法得知其它照片的存在。

image.png

? iOS14 中當(dāng)用戶選擇
“PHAuthorizationStatusLimited” 時,如果未進(jìn)行適配,有可能會在每次觸發(fā)相冊功能時都進(jìn)行彈窗詢問用戶是否需要修改照片權(quán)限。

? 對于這種情況可通過在 Info.plist 中設(shè)置
“PHPhotoLibraryPreventAutomaticLimitedAccessAlert”的值為 YES 來阻止該彈窗反復(fù)彈出,并且可通過下面這個 API 來主動控制何時彈出PHPickerViewController 進(jìn)行照片選擇。

[[PHPhotoLibrary sharedPhotoLibrary] presentLimitedLibraryPickerFromViewController:self];

? 在 iOS14 中官方推薦使用 PHPicker 來替代原 API 進(jìn)行圖片選擇。PHPicker 為獨(dú)立進(jìn)程,會在視圖最頂層進(jìn)行展示,應(yīng)用內(nèi)無法對其進(jìn)行截圖也無法直接訪問到其內(nèi)的數(shù)據(jù)。

  • UIImagePickerController -> PHPickerViewController, UIImagePickerViewController 功能受限,每次只能選擇一張圖片,將逐漸被廢棄。
image.png
  • PHPicker 支持多選,支持搜索,支持按 image,video,livePhotos 等進(jìn)行選擇。


    image.png

? 新API及遷移demo:

image.png
@interface ViewController () <PHPickerViewControllerDelegate>

  @property (weak, nonatomic) IBOutlet UIImageView *imageView;
@property (nonatomic, strong) NSArray<NSItemProvider *> *itemProviders;

@end

@implementation ViewController

  - (void)viewDidLoad {
      [super viewDidLoad];
      // Do any additional setup after loading the view.
}

  - (IBAction)button:(id)sender {
      // 以下 API 僅為 iOS14 only
      PHPickerConfiguration *configuration = [[PHPickerConfiguration alloc] init];
      configuration.filter = [PHPickerFilter videosFilter]; // 可配置查詢用戶相冊中文件的類型,支持三種
    configuration.selectionLimit = 0; // 默認(rèn)為1,為0時表示可多選。

      PHPickerViewController *picker = [[PHPickerViewController alloc] initWithConfiguration:configuration];
      picker.delegate = self;
      // picker vc,在選完圖片后需要在回調(diào)中手動 dismiss
    [self presentViewController:picker animated:YES completion:^{

      }];
  }

#pragma mark - Delegate

  - (void)picker:(PHPickerViewController *)picker didFinishPicking:(NSArray<PHPickerResult *> *)results {
      [picker dismissViewControllerAnimated:YES completion:nil];
      if (!results || !results.count) {
          return;
      }
      NSItemProvider *itemProvider = results.firstObject.itemProvider;
      if ([itemProvider canLoadObjectOfClass:UIImage.class]) {
          __weak typeof(self) weakSelf = self;
          [itemProvider loadObjectOfClass:UIImage.class completionHandler:^(__kindof id<NSItemProviderReading>  _Nullable object, NSError * _Nullable error) {
              if ([object isKindOfClass:UIImage.class]) {
                  __strong typeof(self) strongSelf = weakSelf;
                  dispatch_async(dispatch_get_main_queue(), ^{
                      strongSelf.imageView.image = (UIImage *)object;
                  });
              }
          }]; 
      }
    }

? 需要注意的是,在 limit Photo 模式下,AssetsLibrary 訪問相冊會失??;在 writeOnly 模式下,AssetLibrary 也會有顯示問題。建議還在使用 AssetsLibrary 的同學(xué)盡快遷移到新 API。

? 授權(quán)相關(guān):舊 API 廢棄,增加 PHAccessLevel 參數(shù)。如果再使用以前的API來獲取權(quán)限狀態(tài),
PHAuthorizationStatusLimited 狀態(tài)下也會返回
PHAuthorizationStatusAuthorized

image.png
typedef NS_ENUM(NSInteger, PHAccessLevel) {
  PHAccessLevelAddOnly = 1, // 僅允許添加照片
  PHAccessLevelReadWrite = 2, // 允許訪問照片,limitedLevel 必須為 readWrite
} API_AVAILABLE(macos(10.16), ios(14), tvos(14));

// 查詢權(quán)限
PHAccessLevel level = PHAccessLevelReadWrite;
PHAuthorizationStatus status = [PHPhotoLibrary authorizationStatusForAccessLevel:level];
  switch (status) {
      case PHAuthorizationStatusLimited:
          NSLog(@"limited");
          break;
      case PHAuthorizationStatusDenied:
          NSLog(@"denied");
          break;
      case PHAuthorizationStatusAuthorized:
          NSLog(@"authorized");
          break;
      default:
          break;
}

// 請求權(quán)限,需注意 limited 權(quán)限盡在 accessLevel 為 readAndWrite 時生效
[PHPhotoLibrary requestAuthorizationForAccessLevel:level handler:^(PHAuthorizationStatus status) {
  switch (status) {
      case PHAuthorizationStatusLimited:
          NSLog(@"limited");
          break;
      case PHAuthorizationStatusDenied:
          NSLog(@"denied");
          break;
      case PHAuthorizationStatusAuthorized:
          NSLog(@"authorized");
          break;
      default:
          break; 
  }
}];

? 定位

? 在 iOS13 及以前,App 請求用戶定位授權(quán)時為如下形態(tài):一旦用戶同意應(yīng)用獲取定位信息,當(dāng)前應(yīng)用就可以獲取到用戶的精確定位。

image.png

? iOS14 新增用戶大致位置選項(xiàng)可供用戶選擇,原因是大多數(shù) App 實(shí)際上并不需要獲取用戶到用戶最準(zhǔn)確的定位信息。iOS14 授權(quán)彈窗新增的 Precise的開關(guān)默認(rèn)會選中精確位置。用戶通過這個開關(guān)可以進(jìn)行更改,當(dāng)把這個值設(shè)為 On 時,地圖上會顯示精確位置;切換為Off時,將顯示用戶的大致位置。

? 對于對用戶位置敏感度不高的 App 來說,這個似乎無影響,但是對于強(qiáng)依賴精確位置的 App 適配工作就顯得非常重要了。可以通過用戶在 “隱私設(shè)置” 中設(shè)置來開啟精確定位,但是可能用戶寧可放棄使用這個應(yīng)用也不愿意開啟。這個時候,iOS14 在 CLLocationManager 新增兩個方法可用于向用戶申請臨時開啟一次精確位置權(quán)限。

image.png

使用方式也很簡單,需要首先在 Info.plist 中配置“NSLocationTemporaryUsageDescriptionDictionary”字典中需要配置 key 和 value 表明使用位置的原因,以及具體的描述。

image.png

在本例中,key 即為獲取用戶權(quán)限時傳的 "purposeKey",最終呈現(xiàn)給用戶的就是左圖,右圖為當(dāng)App主動關(guān)閉精確定位權(quán)限申請。

image.png

? 對于地理位置不敏感的App 來說,iOS14 也可以通過直接在 info.plist 中添加 NSLocationDefaultAccuracyReduced 為 true 默認(rèn)請求大概位置。

image.png

? 這樣設(shè)置之后,即使用戶想要為該 App 開啟精確定位權(quán)限,也無法開啟。

? 也可以直接通過API來根據(jù)不同的需求設(shè)置不同的定位精確度。

image.png

? 需要注意的是,當(dāng) App 在 Background 模式下,如果并未獲得精確位置授權(quán),那么 Beacon 及其他位置敏感功能都將受到限制。

? Local Network

? iOS14 當(dāng) App 要使用 Bonjour 服務(wù)時或者訪問本地局域網(wǎng),使用 mDNS 服務(wù)等,都需要授權(quán),開發(fā)者需要在 Info.plist 中詳細(xì)描述使用的為哪種服務(wù)以及用途。下圖為需要無需申請權(quán)限與需要授權(quán)的服務(wù):

image.png

? 在 "隱私設(shè)置" 中也可以查看和修改具體有哪些 App 正在使用 LocalNetwork

image.png

? 如果應(yīng)用中需要使用 LocalNetwork 需要在 Info.plist 中配置兩個選項(xiàng),詳細(xì)描述為什么需要使用該權(quán)限,以及需要列出具體使用 LocalNetwork 的服務(wù)列表。

image.png

? 對于使用了下列包含 Bonjour 的 framework,都需要更新描述.

image.png

? Wi-Fi Address

? iOS8 - iOS13 ,用戶在不同的網(wǎng)絡(luò)間切換和接入時,mac 地址都不會改變,這也就使得網(wǎng)絡(luò)運(yùn)營商還是可以通過 mac 地址對用戶進(jìn)行匹配和用戶信息收集,生成完整的用戶信息。iOS14 提供 Wifi 加密服務(wù),每次接入不同的 WiFi 使用的 mac 地址都不同。每過 24 小時,mac 地址還會更新一次。需要關(guān)注是否有使用用戶網(wǎng)絡(luò) mac 地址的服務(wù)。

? 下圖為 iOS13 及之前用戶接入網(wǎng)絡(luò)時 mac 地址并不會進(jìn)行改變

image.png

? 下圖為 iOS14 用戶接入 Wi-Fi 時 mac 地址的變化情況

image.png

? 并且用戶也可以自行選擇是否開啟 private Wi-Fi address

image.png

? 剪切板

? 在 iOS14 中,讀取用戶剪切板的數(shù)據(jù)會彈出提示。

image.png

? 彈出提示的原因是使用 UIPasteboard 訪問用戶數(shù)據(jù),訪問以下數(shù)據(jù)都會彈出 toast 提示。

image.png

? 兼容方案:如果應(yīng)用訪問剪切板僅僅用于判斷是否為URL格式,則 iOS14 新增了兩個 API 可以用于規(guī)避該提示。如果應(yīng)用想直接訪問剪切板的數(shù)據(jù),暫時可能無法做到規(guī)避該提示。iOS14 新增兩種
UIPasteboardDetectionPattern。

image.png

? 上面的兩個 API 可用于規(guī)避提示,但只能用于判斷剪切板中是否有 URL,并不是真正的訪問剪貼板數(shù)據(jù),也拿不到剪切板的真實(shí)數(shù)據(jù)。下面兩個 API 可以獲得具體的 URL 信息,但是會觸發(fā)剪切板提示。并且實(shí)測當(dāng)用戶剪切板中包含多個 URL 時只會返回第一個。

image.png

? 使用示例

NSSet *patterns = [[NSSet alloc] initWithObjects:UIPasteboardDetectionPatternProbableWebURL, nil];
[[UIPasteboard generalPasteboard] detectPatternsForPatterns:patterns completionHandler:^(NSSet<UIPasteboardDetectionPattern> * _Nullable result, NSError * _Nullable error) {
    if (result && result.count) {
            // 當(dāng)前剪切板中存在 URL
    }
}];

? 相機(jī)和麥克風(fēng)

? iOS14 中 App 使用相機(jī)和麥克風(fēng)時會有圖標(biāo)提示以及綠點(diǎn)和黃點(diǎn)提示,并且會顯示當(dāng)前是哪個 App 在使用此功能。我們無法控制是否顯示該提示。

image.png

? 會觸發(fā)錄音小黃點(diǎn)的代碼示例:

AVAudioRecorder *recorder = [[AVAudioRecorder alloc] initWithURL:recorderPath settings:nil error:nil];
[recorder record];

? 觸發(fā)相機(jī)小綠點(diǎn)的代碼示例:

AVCaptureDeviceInput *videoInput = [[AVCaptureDeviceInput alloc] initWithDevice:videoCaptureDevice error:nil];
AVCaptureSession *session = [[AVCaptureSession alloc] init];
if ([session canAddInput:videoInput]) {
    [session addInput:videoInput];
}
[session startRunning];

? IDFA

? IDFA 全稱為 Identity for Advertisers ,即廣告標(biāo)識符。用來標(biāo)記用戶,目前最廣泛的用途是用于投放廣告、個性化推薦等。

? 在 iOS13 及以前,系統(tǒng)會默認(rèn)為用戶開啟允許追蹤設(shè)置,我們可以簡單的通過代碼來獲取到用戶的 IDFA 標(biāo)識符。

if ([[ASIdentifierManager sharedManager] isAdvertisingTrackingEnabled]) {
    NSString *idfaString = [[ASIdentifierManager sharedManager] advertisingIdentifier].UUIDString;
    NSLog(@"%@", idfaString);
}

? 但是在 iOS14 中,這個判斷用戶是否允許被追蹤的方法已經(jīng)廢棄。

image.png

? iOS14 中,系統(tǒng)會默認(rèn)為用戶關(guān)閉廣告追蹤權(quán)限。

image.png

? 對于這種情況,我們需要去請求用戶權(quán)限。首先需要在 Info.plist 中配置" NSUserTrackingUsageDescription " 及描述文案,接著使用 AppTrackingTransparency 框架中的 ATTrackingManager 中的 requestTrackingAuthorizationWithCompletionHandler 請求用戶權(quán)限,在用戶授權(quán)后再去訪問 IDFA 才能夠獲取到正確信息。

#import <AppTrackingTransparency/AppTrackingTransparency.h>
#import <AdSupport/AdSupport.h>

- (void)testIDFA {
    if (@available(iOS 14, *)) {
        [ATTrackingManager requestTrackingAuthorizationWithCompletionHandler:^(ATTrackingManagerAuthorizationStatus status) {
            if (status == ATTrackingManagerAuthorizationStatusAuthorized) {
                NSString *idfaString = [[ASIdentifierManager sharedManager] advertisingIdentifier].UUIDString;
            }
        }];
    } else {
        // 使用原方式訪問 IDFA
    }
}

對于用戶拒絕授權(quán) UserTracking 的情況,可以考慮接入蘋果的 SKAdNetwork 框架進(jìn)行廣告分析。感興趣的同學(xué)可進(jìn)一步了解:https://developer.apple.com/documentation/storekit/skadnetwork

? 上傳 AppStore

更加嚴(yán)格的隱私審核,可以讓用戶在下載 App 之前就知道此 App 將會需要哪些權(quán)限。目前蘋果商店要求所有應(yīng)用在上架時都必須提供一份隱私政策。如果引入了第三方收集用戶信息等SDK,都需要向蘋果說明是這些信息的用途。

image.png
image.png

總結(jié)

對于這次 iOS14 的隱私權(quán)限大升級和新嘗試,體現(xiàn)了蘋果對于用戶隱私的尊重。

從用戶角度來說,近年來越來越精準(zhǔn)的廣告投放讓我們越來越感覺自己被”監(jiān)視“著,此次升級后,我們有了更多保護(hù)自己隱私的方式以及避免廣告騷擾的方法,蘋果此舉無疑會加大我們對其的好感度和信任感。但從另一個角度來說,對于 IDFA 的限制,可能會導(dǎo)致之前許多依靠廣告投放收入的免費(fèi) App 難以繼續(xù)維持生計(jì),也可能也會導(dǎo)致免費(fèi) App 的數(shù)量有所降低。從開發(fā)者的角度來說,除了對 iOS14 隱私升級的積極適配外,也讓我們感受到了 iOS14 中對于用戶隱私的重視無疑會提高獲取用戶行為信息的成本。

沖擊最大的應(yīng)該就是廣告行業(yè),對于目前的推薦算法和用戶拉新都會受到影響,如何在充分尊重用戶隱私的前提下進(jìn)行廣告的精準(zhǔn)投放對于開發(fā)者和廣告商來說都是一個不小的機(jī)遇和挑戰(zhàn)。

下一期,我們聊聊 【Metal 新特性詳解|帶來的技術(shù)啟發(fā)和思考】,敬請持續(xù)關(guān)注~

參考資料

  • WWDC 2020 Apple Developer
  • Developer Documentation
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容