关于 -canOpenURL: 和 -openURL: 的那些事

最近工作中需要知道用户的 iPhone 上都安装了哪些应用,所以查阅了一些资料。总的来说主要还是通过使用 Apple 提供的 - canOpenURL: API 来测试相应 APP 的 scheme 是否有效来实现。

如何知道某个 APP 支持的所有 scheme

很显然,为了知道对应的 APP 是否在设备上,我们需要知道这个 APP 支持的所有 scheme(如果 APP 没有定义任何自己的 scheme,请看使用私有 API )。这里我总结了一下大概有两种方法。

  • 使用别人已经整理好的scheme。比如这个wiki页面,里面收录了一些比较有名的 APP 的 scheme。当然还有这个网站,你可以在这里查询 scheme 对应的 APP,你还可以帮助将你知道的 APP 的 scheme 添加进去,方便后面的人搜索。
  • 自己动手查看 APP 的 scheme。主要分下面几步:
    1. 获取 IPA 包。这里你可以使用 iTunes 下载 APP。 然后在~/Music/iTunes/iTunes Media/Mobile Applications这个目录下可以找到 iTunes 为我们下载的 IPA 包。
    2. 将 IPA 包的扩展名改成 zip,这样我们就可以解压了。
    3. 解压之后打开Payload文件夹,右键扩展名为 app 的文件夹,选择 显示包内容 就可以查看到内部的文件了
    4. 找到 Info.plist 文件,搜索 CFBundleURLSchemes 就可以看到这个 APP 给自己定义的 scheme 了。

如何使用 -canOpenURL:

iOS9 上面出于对用户隐私的保护,开发人员不能像以前一样随便 -canOpenURL: 了。 通常在 iOS9 及以后版本的系统中,使用 -canOpenURL: 分为如下几步。

  • 点击工程文件,选择相应的 Target,点击 Info 选项,展开 Custom iOS Target Properties
  • 找到或者添加 LSApplicationQueriesSchemes 到属性列表中。同时在这个数组下面添加相应的 scheme

当然你也可以直接编辑项目的 Info.plist 文件,在 LSApplicationQueriesSchemes 键下面添加你在 APP 中会使用到的 scheme。

通过将 scheme 添加到白名单中,我们就可以在代码中使用 -canOpenURL: 来测试对应 scheme 的 APP 是否被安装。如果你没有将 scheme 添加到白名单中却在 -canOpenURL: 中使用了,你的查询会失败,同时控制台会打印类似下面这样的信息:

-canOpenURL: failed for URL: "fb://" - error: "This app is not allowed to query for scheme fb"
-canOpenURL: failed for URL: "twitter://" - error: "This app is not allowed to query for scheme twitter"

正常的输出是这样的(如何 -canOpenURL: 测试 scheme 失败的话,成功的话控制台默认不会有任何输出
):

-canOpenURL: failed for URL: "fb://" - error: "(null)"

这里或许有个疑问就是为什么这样就能保护用户隐私呢? 毕竟我们可以添加很多的我们会测试的 scheme 到白名单中。 如果你无限制的添加 scheme 到白名单中, app store 审核时候可能会觉得你滥用了这个机制,从而不让你的 APP 审核通过。

要注意的是使用 iOS8 sdk 编译的代码跑在运行 iOS9 系统的设备上是没有问题的,但是一个 APP 可以测试的 scheme 有数量的限制,大概是50条。

关于 iOS9 上的 -openURL:

我测试了一下,在没有添加 scheme 到白名单的情况下,使用 -openURL: 会默认打开相应的应用,同时该函数返回 true(如果设备安装了),否则函数返回 false(也不会有任何提醒)。 而在添加了 scheme 到白名单的情况下,使用 -openURL: 会弹窗提示(有时候又没有弹窗😭,难道是第一次选择是跳转以后后面都默认跳转吗? 从这点可以看出 Apple 这个 API 做的用户体验并不好)用户是否需要打开相应的应用,选择是则打开,否则不打开,同时函数也会正确的返回 true 或者 false

<a name="private-api"></a>使用私有 API

私有 API 也就是 Apple 提供的 iOS SDK 中没有暴露给外部的接口类和方法。我们知道 OC 函数调用是运行时决定的,利用这个特性,通过一些手段获取到 Apple 的一些私有 API 的类名和方法名。我们就可以很容易的使用这些 API。对于本文主题,GitHub 上有一个很好的例子,大家可以下载这个 demo,了解如何使用私有 API 来获取设备上支持的所有 scheme,以及所有安装的 APP 信息。

需要注意的是, 如果你在项目中使用了私有 API,那么你可能需要做一些函数调用方式上的处理,以避免在 APP 审核的时候被发现导致被拒。

关于私有 API 更多的介绍可以看这个 StackOverflow 回答 What exactly is a private api and why will apple reject an ios app if one is us

关于 Apple 是如果检测应用是否使用了私有 API可以看这里 How does apple know you are using private api

参考资料

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

推荐阅读更多精彩内容

  • 很可能你的应用是与一个支持HTTPS传输数据的服务器交互,但是并没有使用TLS 1.2或更高。在这种情况下,你定义...
    Www刘阅读 3,039评论 0 5
  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 171,259评论 25 707
  • 原文地址 HashMap可以说是Java中最常用的集合类框架之一,是Java语言中非常典型的数据结构,我们总会在不...
    未央_2625阅读 250评论 0 2
  • 无论是哪种语言,作用域都是一个非常重要的概念,同样,作用域对JavaScript有许多影响。从功能的角度来看,作用...
    前端一小卒阅读 989评论 0 6
  • 自从用语言作为交流的主要工具,说话就从功能演化到了能力的范畴。 说话人人都会,会说话就不见得人人能行。 红楼梦里的...
    48岁的张昆阅读 239评论 2 4