iOS info.plist應(yīng)用權(quán)限配置

iOS APP審核比較嚴(yán)格阵难,十分注重保護(hù)用戶隱私岳枷。沒有用戶對APP授權(quán),很多涉及數(shù)據(jù)采集的功能都無法使用。這里記錄一些常用的權(quán)限配置及權(quán)限狀態(tài)檢查嫩舟,后面會陸續(xù)補(bǔ)充付呕。

一箱熬、常見隱私權(quán)限
1.基本格式 Privacy - xxxx :詳細(xì)描述摹闽,如圖:
樣例一.png
ps:詳細(xì)描述要寫的與具體功能相關(guān)亚再,否則APP審核可能會被打回误堡。
2.隱私權(quán)限清單
Privacy - Camera Usage Description : 使用相機(jī)(拍照或錄制)
Privacy - Face ID Usage Description : 使用FaceID
Privacy - NFC Scan Usage Description : 使用NFC掃描
Privacy - Microphone Usage Description :使用麥克風(fēng)(錄音)
Privacy - Bluetooth Always Usage Description :使用手機(jī)藍(lán)牙
//定位
Privacy - Location When In Use Usage Description : APP使用期間獲取定位信息(僅限應(yīng)用在前臺)
Privacy - Location Always and When In Use Usage Description :允許一直獲取定位信息(包括前臺和后臺)
//圖庫
Privacy - Photo Library Usage Description :允許從圖庫讀取圖片或視頻
Privacy - Photo Library Additions Usage Description :向圖庫添加圖片或視頻
二豆茫、檢查權(quán)限狀態(tài)伸蚯,及主動申請
這一部分是最基本的容錯(cuò)撬码,調(diào)用方法前去獲取設(shè)備硬件狀態(tài)或權(quán)限是否授權(quán)维蒙。進(jìn)而去規(guī)避一些由于用戶沒有授權(quán)權(quán)限掰吕,直接調(diào)用對應(yīng)方法而導(dǎo)致的崩潰。

1.相機(jī)
這里用到的是AVCaptureDevice來檢查權(quán)限狀態(tài)颅痊,后續(xù)會添加使用其他方法狀態(tài)獲取的方式殖熟。

    private func isPrepareOfAVCaptureVideoDevice(_ completionHandler: @escaping (Bool) -> Void) {
        let videoStatus = AVCaptureDevice.authorizationStatus(for: .video)

        if videoStatus == .notDetermined{
            AVCaptureDevice.requestAccess(for: .video) {
                completionHandler($0)
            }
            return
        }
        completionHandler(videoStatus == .authorized)
    }

2.麥克風(fēng)
同相機(jī)獲取權(quán)限狀態(tài)的方式,后續(xù)也會添加斑响。

    private func isPrepareOfAVCaptureAudioDevice(_ completionHandler: @escaping (Bool) -> Void) {
        let audioStatus = AVCaptureDevice.authorizationStatus(for: .audio)
        if audioStatus == .notDetermined {
            AVCaptureDevice.requestAccess(for: .audio) {
                completionHandler($0)
            }
            return
        }
        completionHandler(audioStatus == .authorized)
    }

3.圖庫
PhotoLibrary權(quán)限在iOS14.0進(jìn)行了細(xì)化:
a)獲取圖庫讀寫權(quán)限


        if #available(iOS 14, *) {
            let readWriteStatus = PHPhotoLibrary.authorizationStatus(for: .readWrite)
            print(readWriteStatus)
            PHPhotoLibrary.requestAuthorization(for: .readWrite) { (status) in
                self.handleRequestStatus(status: status)
            }
        } else {
            let readWriteStatus = PHPhotoLibrary.authorizationStatus()
            print(readWriteStatus)
            PHPhotoLibrary.requestAuthorization { (status) in
                self.handleRequestStatus(status: status)
            }
        }
    }

    func handleRequestStatus(status:PHAuthorizationStatus){
        switch status {
        case .notDetermined:
            print("The user hasn't determined this app's access.")
        case .restricted:
            print("The system restricted this app's access.")
        case .denied:
            print("The user explicitly denied this app's access.")
        case .authorized:
            print("The user authorized this app to access Photos data.")
        case .limited:
            print("The user authorized this app for limited Photos access.")
        @unknown default:
            fatalError()
        }
    }

b)僅向圖庫添加菱属,為了對稱添加了iOS14版本以下的

    func checkPhotosLibraryAddtionStatus(){
        if #available(iOS 14, *) {
            let readWriteStatus = PHPhotoLibrary.authorizationStatus(for: .addOnly)
            print(readWriteStatus)
            PHPhotoLibrary.requestAuthorization(for: .addOnly) { [self] (status) in
                handleRequestStatus(status: status)
            }
        } else {
            let readWriteStatus = PHPhotoLibrary.authorizationStatus()
            print(readWriteStatus)
            PHPhotoLibrary.requestAuthorization { (status) in
                self.handleRequestStatus(status: status)
            }
        }
    }
    
    func handleRequestStatus(status:PHAuthorizationStatus){
        switch status {
        case .notDetermined:
            print("The user hasn't determined this app's access.")
        case .restricted:
            print("The system restricted this app's access.")
        case .denied:
            print("The user explicitly denied this app's access.")
        case .authorized:
            print("The user authorized this app to access Photos data.")
        case .limited:
            print("The user authorized this app for limited Photos access.")
        @unknown default:
            fatalError()
        }
    }

4.藍(lán)牙

  //藍(lán)牙狀態(tài)獲取是通過delegate方法centralManagerDidUpdateState來實(shí)現(xiàn)的
  func centralManagerDidUpdateState(_ central: CBCentralManager) {
        switch central.state {
        case .resetting:
            print("服務(wù)連接中斷,正在重連")
        case .unsupported:
            print("設(shè)備不支持")
        case .unauthorized:
            if #available(iOS 13.0, *) {
                switch central.authorization {
                case .restricted:
                    print("設(shè)備藍(lán)牙有問題舰罚,被限制使用")
                case .denied:
                    print("被用戶拒絕了")
                default:
                    print("啥也不是~~~~~")
                }
            } else {
                print("用戶未授權(quán)")
            }
        case .poweredOff:
            print("藍(lán)牙未打開")
        case .poweredOn:
            print("藍(lán)牙已打開")
            
        default:
            print("啥也不是~~~~~")
        }

5.定位

    func checkLocationStatus(){
        let locationManager = CLLocationManager()
        if #available(iOS 14.0, *) {
            let status = locationManager.authorizationStatus
            self.requestLocationAuthor(status: status)
        } else {
            let status = CLLocationManager.authorizationStatus()
            self.requestLocationAuthor(status: status)
        }
    }
    
    func requestLocationAuthor(status:CLAuthorizationStatus){
        let locationManager = CLLocationManager()

        switch status {
        case .authorizedAlways:
            print("The user authorized this app is authorizedAlways.")
        case .authorizedWhenInUse:
            print("The user authorized this app is authorizedWhenInUse.")
        case .denied:
            print("The user authorized this app is denied.")
        case .notDetermined://根據(jù)需求二選一
//            locationManager.requestAlwaysAuthorization()
            locationManager.requestWhenInUseAuthorization()
            
        case .restricted:
            print("The user authorized this app is restricted.")

        default:
            fatalError()
        }
    }

6.NFC
要使用NFC功能開發(fā)需要在證書中添加NFC開發(fā)選項(xiàng)纽门,配置證書后然后在項(xiàng)目中添加Capability。


NFC Capability配置.png

獲取狀態(tài)是否可用比較簡單营罢,內(nèi)部封裝好的api直接調(diào)用即可赏陵。

//MARK: NFC相關(guān)
import CoreNFC
extension ViewController{
    func checkNFCReaderAvailable() -> Bool{
       return NFCNDEFReaderSession.readingAvailable
    }
}

7.FaceID
請求設(shè)備本地解鎖認(rèn)證(密碼,faceID饲漾,TouchID)蝙搔,LAPolicy有兩種枚舉類型,deviceOwnerAuthenticationWithBiometrics僅調(diào)用設(shè)備設(shè)置的touchid或faceID進(jìn)行認(rèn)證考传,deviceOwnerAuthentication會根據(jù)設(shè)備設(shè)置的解鎖方式進(jìn)行請求吃型,默認(rèn)是設(shè)備密碼認(rèn)證,即使在沒有設(shè)置生物學(xué)識別信息(指紋伙菊、面部特征)的情況下也可以使用

import LocalAuthentication
var context = LAContext()
extension ViewController{

    func requetAuthor(){
        /*
         canEvaluatePolicy()方法用來檢查認(rèn)證方式是否可用败玉,也可用來標(biāo)記狀態(tài)
         evaluatePolicy()方法用來進(jìn)行認(rèn)證方法調(diào)用
        */
            context = LAContext()
            context.localizedCancelTitle = "設(shè)置title"

            var error: NSError?
            if context.canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: &error) {
                let reason = "設(shè)置具體描述"
                context.evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: reason ) { success, error in
                    if success {
                        DispatchQueue.main.async { [unowned self] in
                           print("認(rèn)證成功")
                        }

                    } else {
                        print(error?.localizedDescription ?? "認(rèn)證失敗")
                    }
                }
            } else {
                print(error?.localizedDescription ?? "無法調(diào)用系統(tǒng)認(rèn)證方式")
            }
        }
}

8.消息通知
檢查消息通知狀態(tài)

  func checkNotificationAvailable(){
        if #available(iOS 10, *) {
            UNUserNotificationCenter.current().getNotificationSettings { (settings) in
                print(settings.authorizationStatus)
                switch settings.authorizationStatus{
                case .authorized:
                    print("已授權(quán)")
                case .denied:
                    print("用戶拒絕消息通知")
                case .notDetermined:
                    print("未確定消息權(quán)限")
                //這兩個(gè)是新的,沒有做深入探究
                case .ephemeral:
                    print("ephemeral")
                case .provisional:
                    print("provisional")

                default:
                    break
                }
            }
        }else{
            let isRegistered = UIApplication.shared.isRegisteredForRemoteNotifications
            print(isRegistered)
        }
    }
附:iOS 網(wǎng)絡(luò)通信配置

iOS 9.0 以后APP網(wǎng)絡(luò)請求需要在info.plist中配置NSAppTransportSecurity镜硕,具體配置如下圖:
網(wǎng)絡(luò)通信配置2.png
Apple官方文檔:ProtectedResources
Demo:Demo鏈接
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末运翼,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子兴枯,更是在濱河造成了極大的恐慌血淌,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,270評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異悠夯,居然都是意外死亡癌淮,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,489評論 3 395
  • 文/潘曉璐 我一進(jìn)店門沦补,熙熙樓的掌柜王于貴愁眉苦臉地迎上來乳蓄,“玉大人,你說我怎么就攤上這事夕膀⌒榈梗” “怎么了?”我有些...
    開封第一講書人閱讀 165,630評論 0 356
  • 文/不壞的土叔 我叫張陵产舞,是天一觀的道長魂奥。 經(jīng)常有香客問我,道長易猫,這世上最難降的妖魔是什么耻煤? 我笑而不...
    開封第一講書人閱讀 58,906評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮准颓,結(jié)果婚禮上哈蝇,老公的妹妹穿的比我還像新娘。我一直安慰自己瞬场,他們只是感情好买鸽,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,928評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著贯被,像睡著了一般眼五。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上彤灶,一...
    開封第一講書人閱讀 51,718評論 1 305
  • 那天看幼,我揣著相機(jī)與錄音,去河邊找鬼幌陕。 笑死诵姜,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的搏熄。 我是一名探鬼主播棚唆,決...
    沈念sama閱讀 40,442評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼心例!你這毒婦竟也來了宵凌?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,345評論 0 276
  • 序言:老撾萬榮一對情侶失蹤止后,失蹤者是張志新(化名)和其女友劉穎瞎惫,沒想到半個(gè)月后溜腐,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,802評論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡瓜喇,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,984評論 3 337
  • 正文 我和宋清朗相戀三年挺益,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片乘寒。...
    茶點(diǎn)故事閱讀 40,117評論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡望众,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出肃续,到底是詐尸還是另有隱情黍檩,我是刑警寧澤,帶...
    沈念sama閱讀 35,810評論 5 346
  • 正文 年R本政府宣布始锚,位于F島的核電站,受9級特大地震影響喳逛,放射性物質(zhì)發(fā)生泄漏瞧捌。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,462評論 3 331
  • 文/蒙蒙 一润文、第九天 我趴在偏房一處隱蔽的房頂上張望姐呐。 院中可真熱鬧,春花似錦典蝌、人聲如沸曙砂。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,011評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽鸠澈。三九已至,卻和暖如春截驮,著一層夾襖步出監(jiān)牢的瞬間笑陈,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,139評論 1 272
  • 我被黑心中介騙來泰國打工葵袭, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留涵妥,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,377評論 3 373
  • 正文 我出身青樓坡锡,卻偏偏與公主長得像蓬网,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個(gè)殘疾皇子鹉勒,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,060評論 2 355

推薦閱讀更多精彩內(nèi)容