關於如何檢測iOS 14本地網絡權限的一些思路

前戲

蘋果iOS 14針對本地局域作了一些權限限制,詳情見連接:developer.apple.com/videos/play…html

wwdc翻譯過來湊字數的

什麼是本地網絡?

這裏的本地網絡其實就是咱們常說的局域網,是將設備接入路由器之後造成的網絡,設備能夠經過這張網絡互相通訊,如咱們的設備發現、設備綁定、局域網優先等功能都是使用的本地網絡。git

從 iOS 13 開始,應用想要得到當前鏈接到的 Wi-Fi 名稱,那就必需要得到定位權限。由於經過識別 Wi-Fi 名稱, 應用就能輕鬆地在你和周圍的人之間創建大數據網絡。可是不給定位權限不表明應用就沒有辦法跟蹤你了,由於應用能夠經過本地網絡裏的設備進行跟蹤。github

爲何須要向用戶申請權限?

和iOS 13獲取WiFi名稱須要經過定位權限相似,蘋果增強了對用戶隱私安全權限,這裏也是相似的問題。在過去的 iOS 版本中,應用能夠隨意掃描本地網絡中的設備,所以應用就能夠很輕鬆地獲得本地網絡裏全部設備的名稱和 MAC 地址。MAC 地址是一種確認網絡設備位置的地址,每一個網卡都有一個惟一的 MAC 地址,加上 MAC 地址也具備惟一性,設備廠商會按照必定的規律分配 MAC,因此不一樣的局域網都是獨一無二能夠識別的。比方說,你從線下渠道買了個新相機,拍完照片利用相機自帶的 Wi-Fi 將照片導入到手機上。這時候帶有某個推廣模塊的應用對局域網發起了一次掃描,識別到了一個新的設備,推廣模塊會將相機的 MAC 地址上傳了雲端,進行簡單的識別對比之後,很容易知道這個 MAC 地址屬於相機。這樣帶有推廣模塊的應用都會在畫像裏給你加上「相機用戶」這樣的標籤,當你下次打開帶有同一個推廣模塊的購物應用時,你就會看到推薦了一堆和相機有關的東西。安全

那些應用須要使用本地網絡?

  • 利用本地網絡進行設備發現
  • 利用本地網絡進行數據傳輸
  • 網絡調試工具

影響範圍

主要影響沒法使用Socket或者Bonjour作一些局域網的發現,數據傳輸。markdown

對局域網應用如:智能家居類,局域網遊戲,網絡測試工具等等。本人測試了下其實也沒有那麼大,由於發現這個開關,App下次啓動後可能不會生效,暫時未定位緣由。網絡

怎麼解決?

相信不少人都很奇怪爲何不整個權限申請或狀態查詢的接口,在翻了一些資料後發現,竟然真的沒有。 連接:developer.apple.com/forums/tags…app

很無奈!ide

大部分應用使用局域通常使用Socket或者Bonjour作一些局域的發現,數據傳輸。說在調用的時候會出現code:65 desc:no route to host。這是其實就是所謂的無本地網絡權限。可是我在測試時發現有時候即便是關掉本地網絡權限的開關,也能正常的使用UDP、TCP。簡直不敢信!難道iOS 14也會想iOS 13一開始出來同樣各類坑滿天飛?工具

這裏的思路是oop

  • 經過接口獲取本機的IP地址
  • 使用(SimplePing)來ping手機的IP

整個流程的大概耗時在0.13-0.2秒之間,大部分在0.17秒左右。可能耗時還能接受。可是不知道某些路由器是否能夠設置禁止ping。若是有那就炸裂了。 下面上簡單的代碼

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view.
    NSDictionary *router = [LDSRouterInfo getRouterInfo];
    pinger = [[SimplePing alloc] initWithHostName:router[@"ip"]];
    pinger.delegate = self;
    [self->pinger start];
    
}
- (void)simplePing:(SimplePing *)pinger didStartWithAddress:(NSData *)address {
    if (timer) {
        return;
    }
    timer = dispatch_source_create(DISPATCH_SOURCE_TYPE_TIMER, 0, 0, dispatch_get_main_queue());
    dispatch_source_set_timer(timer, DISPATCH_TIME_NOW, 2 * NSEC_PER_SEC, 0 * NSEC_PER_SEC);
    dispatch_source_set_event_handler(timer, ^{
        [pinger sendPingWithData:nil];
    });
    dispatch_resume(timer);
}

- (void)simplePing:(SimplePing *)pinger didSendPacket:(NSData *)packet sequenceNumber:(uint16_t)sequenceNumber {
    NSLog(@"可使用局域網");
}

- (void)simplePing:(SimplePing *)pinger didFailToSendPacket:(NSData *)packet sequenceNumber:(uint16_t)sequenceNumber error:(NSError *)error {
    if (error.code == 65) {//no route to host
        NSLog(@"不可使用局域網");
    }
}
複製代碼

友情提示

  • 調上面接口能夠觸發首次啓動本地網絡權限的系統彈窗
  • 不知道某些路由器是否能夠設置禁止ping
  • 整理流程在iPhone 6sp耗時130-200毫秒之間。平均值在160毫秒左右
  • 上面代碼未正式上線,本人也在測試中,請酌情使用。

demo

相關文章
相關標籤/搜索