1. 为什么你的App需要一个“专属传送门”?

最近在复盘我们团队上线的几个项目数据时,发现一个挺有意思的现象:每次版本更新后,App Store里的新功能介绍页面,用户点击查看的比例其实并不低,但真正触发更新的用户却少了一大截。这中间就存在一个“断点”——用户看到了新功能,但需要手动返回、搜索、再进入App详情页才能更新,操作路径太长,很多用户可能就懒得动了,或者干脆忘了。

这其实就是我们今天要聊的 App Store深度链接(Universal Links) 能解决的痛点。你可以把它理解成给你的App在App Store里安装了一个“专属传送门”。当你的App有版本更新或者有新的推广活动时,你可以在App Store里创建一个“App内活动”。用户只要点击这个活动卡片,就能直接跳转到你的App内部,完成更新或者查看活动详情,整个过程丝滑流畅,没有任何多余的步骤。

我刚开始接触这个功能时,也觉得它可能只是个“锦上添花”的东西。但实际用下来,尤其是在一个用户基数不小的海外游戏项目上部署后,效果非常直接:新版本发布后一周内的主动更新率提升了近20%,而且通过活动卡片进来的用户,其后续的活跃度和付费意愿都有明显提升。这背后的逻辑很简单:你为用户省去了麻烦,提供了便利,用户的响应就会更积极。

所以,无论你是想提升老用户的更新体验,还是想通过App Store更有效地推广新功能、新活动,这个“传送门”都值得你花点时间配置一下。它不是什么黑科技,而是苹果官方提供的一套成熟、稳定的深度链接方案。接下来,我就手把手带你从零开始,把这个“传送门”给搭建起来,过程中我踩过的坑、总结的技巧,都会毫无保留地分享给你。

2. 动手之前:搞懂原理与备齐“粮草”

在开始敲代码和改配置之前,我们得先花几分钟把Universal Links的工作原理和需要准备的东西搞清楚。这样后面操作起来,你才知道每一步是在做什么,出了问题也知道该往哪个方向排查。

Universal Links的核心原理其实很巧妙。它本质上是一个由你的网站(必须是HTTPS)和你的iOS应用之间建立的、经过苹果验证的信任关系。当用户在设备上点击一个指向你网站的链接(比如在Safari、信息或邮件里),iOS系统会先检查这个链接的域名是否关联了某个已安装的App。如果关联了,并且该App支持处理这个链接,那么系统就会直接打开你的App,并将链接信息传递给它;如果没有安装App,则会正常在Safari中打开网页。

为了实现这个验证,你需要准备一个关键的“信物”——一个名为 apple-app-site-association (AASA) 的JSON文件。这个文件里写明了你的App ID(团队ID+包名)以及你的App可以处理的网站路径。你必须把这个文件放到你网站的特定位置(根目录或.well-known目录下),并且确保能通过HTTPS访问。当用户安装你的App时,iOS系统会悄悄地去你网站的这个地址下载并验证这个文件,从而建立关联。

所以,在动手前,请确保你备齐了以下“粮草”:

  1. 一个受信任的HTTPS域名:这是硬性要求。必须是你App的官方网站或你拥有控制权的域名,并且配置了有效的SSL证书(不能是自签名证书)。很多开发者第一次失败就栽在这里,用了HTTP或者证书无效的域名。
  2. 苹果开发者账号和对应的App ID:你需要在开发者后台为你的App明确启用“Associated Domains”能力。
  3. 开发环境:一台Mac电脑,安装好最新稳定版的Xcode。我写这篇文章时用的是Xcode 15.0.1,但核心步骤在后续版本中基本一致。
  4. 服务器访问权限:你需要能将上面提到的AASA文件上传到你的网站服务器。如果你有后端同事,这一步沟通好就行;如果是个人开发者,你需要知道如何管理你的服务器或静态托管服务(比如GitHub Pages、Vercel等,但需确保支持HTTPS和静态文件服务)。

把这些准备好,我们就能进入实战环节了。整个过程就像搭积木,一步一个脚印,跟着做准没错。

3. 第一步:配置开发者证书与编写“关联文件”

这是整个流程的基石,也是最容易出错的环节之一。我们需要双线操作:一边在苹果开发者后台修改证书配置,一边编写那个关键的AASA文件。

3.1 在开发者后台启用关联域名能力

首先,登录你的 Apple Developer 账号。别急着去证书列表,我们先去管理你的App ID。

  1. 进入“Certificates, Identifiers & Profiles”页面。
  2. 在左侧边栏选择“Identifiers”,然后找到你的App对应的App ID(类型为“App IDs”的)。点击进入其详情页面。
  3. 你会看到一列“Capabilities”(功能)。找到 “Associated Domains” 这一项,把旁边的复选框勾选上。这个操作的意思是,告诉苹果,我这个App将要使用关联域名功能。
  4. 勾选后,记得点击页面右下角的 “Save” 按钮进行保存。

这里有个非常重要的点:仅仅在这里勾选是不够的。对于已经存在的描述文件(Provisioning Profile),它并不会自动更新这个新能力。因此,你需要为你所有的开发、分发描述文件(Development和Distribution)重新生成(Edit -> Generate)。我建议直接“Revoke”旧的,然后创建新的,确保万无一失。很多人在Xcode里配置后报错“Associated Domains entitlement is not enabled”,根源就是用了旧的、未包含此能力的描述文件。

完成这一步后,记下你的 Team ID 和 Bundle Identifier。Team ID是一个10字符的字符串,你可以在开发者账号的会员资格页面找到。Bundle ID就是你的App包名,比如com.yourcompany.yourapp。这两个信息马上就会用到。

3.2 编写 apple-app-site-association 文件

现在,打开你电脑上的文本编辑器(推荐VS Code、Sublime Text或甚至系统的文本编辑应用),创建一个新文件。注意,这个文件的名字必须严格、完全地命名为 apple-app-site-association,没有.json后缀,没有.txt后缀,什么都没有! 这是苹果的硬性规定,名字错一个字母都不行。

文件的内容格式如下,非常简洁:

{
    "applinks": {
        "apps": [],
        "details": [
            {
                "appID": "ABCDE12345.com.yourcompany.yourapp",
                "paths": ["*"]
            }
        ]
    }
}

我来解释一下每个字段:

  • applinks: 固定节点,表示这是用于App Links的配置。
  • apps: 必须是一个空数组 [],照写就行。
  • details: 一个数组,里面可以包含多个App的配置。通常我们只配置自己的App。
    • appID: 这里填写 “TeamID.BundleID”。把刚才记下的Team ID和Bundle ID用点号连接起来。例如,你的Team ID是ABCDE12345,Bundle ID是com.awesome.game,那么这里就填ABCDE12345.com.awesome.game。这是最容易填错的地方,务必核对清楚。
    • paths: 一个数组,指定你的App可以处理网站上的哪些路径。["*"]表示处理该域名下的所有路径。你也可以更精细地控制,比如["/news/*", "/promotion/2024/*"],表示只处理/news/和/promotion/2024/下的链接。初期建议用*通配符,简单省事。

重要提醒:这个JSON文件必须是一个有效的、格式标准的JSON。不能有任何注释(// 或 /* */),不能有多余的逗号(比如最后一个元素后面加逗号)。写完以后,可以把它粘贴到任何一个在线的JSON验证工具里检查一下格式是否正确。文件内容就这些,保存好,我们进入下一步。

4. 第二步:部署关联文件到服务器

现在,我们需要把这个“信物”放到你的网站上,让苹果和用户的iOS设备能够找到并验证它。这一步对服务器的配置有点要求。

4.1 文件放置位置与访问链接

你有两个标准位置可以放置这个apple-app-site-association文件:

  1. 网站的根目录:直接放在你域名对应的网站根目录下。例如,你的网站是https://www.yourapp.com,那么文件的访问地址就是 https://www.yourapp.com/apple-app-site-association。
  2. .well-known 目录:在网站根目录下创建一个名为.well-known的文件夹(注意前面有个点),把文件放进去。那么访问地址就是 https://www.yourapp.com/.well-known/apple-app-site-association。

苹果官方推荐使用 .well-known 目录,因为这是一个用于存放网站元数据的标准目录,更规范。我个人也习惯用这个位置。

关键点来了:无论你放在哪里,你必须确保这个链接能够通过 HTTPS 被公开访问,并且服务器返回的 Content-Type 头是 application/json。很多开发者用浏览器访问能看到JSON内容就以为成功了,但其实服务器可能返回的是 text/plain,这可能会导致验证失败。你可以用命令行工具 curl 来检查:

curl -I https://www.yourapp.com/.well-known/apple-app-site-association

在返回的HTTP头信息里,查找 Content-Type: application/json。如果没有,你需要配置你的Web服务器(如Nginx, Apache)为这个特定的文件路径设置正确的MIME类型。以Nginx为例,你可以在配置文件中添加:

location /.well-known/apple-app-site-association {
    types { } default_type "application/json";
}

4.2 验证文件是否生效

部署完成后,强烈建议使用苹果提供的官方验证工具进行测试。在Mac上,你可以使用终端命令:

# 将网址替换成你的AASA文件实际地址
xcrun diagnostic-links validate -u https://www.yourapp.com/.well-known/apple-app-site-association

如果一切配置正确,这个命令会返回成功的验证信息,并列出它找到的App ID。这是最可靠的验证方式。

此外,你也可以直接在Safari浏览器中输入你的AASA文件地址。如果配置正确,浏览器会直接下载这个文件(而不是显示内容)。如果你看到的是纯文本的JSON代码显示在页面上,这通常也意味着服务器没有正确设置Content-Type头,需要按上述方法调整。

5. 第三步:在Xcode项目中集成配置

服务器端搞定后,我们回到客户端,在Xcode里完成最后的配置。这一步相对直观。

  1. 用Xcode打开你的iOS项目。
  2. 在项目导航器中,点击你的项目文件,然后选择你的App Target。
  3. 切换到 “Signing & Capabilities” 标签页。
  4. 点击左上角的 “+ Capability” 按钮,在弹出的列表中搜索并添加 “Associated Domains”。添加后,你会看到下方出现了一个“Domains”列表。
  5. 在Domains列表中,点击“+”号,添加你的域名。格式有严格要求:applinks: + 你的域名。
    • 例如,你的域名是 www.yourapp.com,那么就添加:applinks:www.yourapp.com
    • 如果你的AASA文件放在根目录,域名前不要加www也可以,但为了保险,我建议和你AASA文件访问地址里使用的域名完全一致。比如你访问用的是https://yourapp.com/...,这里就填applinks:yourapp.com;如果用的是https://www.yourapp.com/...,这里就填applinks:www.yourapp.com。
  6. 添加完成后,Xcode会自动更新你的App ID配置和描述文件。确保你当前构建使用的描述文件是包含了“Associated Domains”能力的最新文件(可以在该页面顶部查看)。

这一步做完,编译并运行你的App到真机上。当App第一次启动时,iOS系统就会去你配置的域名下获取并验证那个AASA文件。你可以在Xcode的控制台日志中搜索“swcd”来查看关联域进程的日志,但更简单的测试方法在下一步。

6. 第四步:在App中处理深度链接

关联建立后,当用户点击一个指向你域名的Universal Link时,系统会尝试打开你的App。我们需要在App内写代码来接收和处理这个链接。

在iOS中,处理Universal Links主要是在 AppDelegate 或 SceneDelegate(如果你的项目支持多场景)中,实现特定的回调方法。这里以AppDelegate为例,方法非常固定:

// 在 AppDelegate.m 中
- (BOOL)application:(UIApplication *)application continueUserActivity:(NSUserActivity *)userActivity restorationHandler:(void (^)(NSArray<id<UIUserActivityRestoring>> * _Nullable))restorationHandler {
    
    // 检查是否是网页浏览活动(即来自Universal Link)
    if ([userActivity.activityType isEqualToString:NSUserActivityTypeBrowsingWeb]) {
        NSURL *url = userActivity.webpageURL;
        NSLog(@"Universal Link 触发,URL: %@", url.absoluteString);
        
        // 在这里解析URL,根据不同的路径执行不同的操作
        // 例如:跳转到特定页面、展示更新弹窗、领取活动奖励等
        [self handleUniversalLink:url];
        
        return YES; // 表示我们已经处理了这个链接
    }
    
    // 如果不是网页链接,返回NO,让系统尝试其他处理方式
    return NO;
}

// 一个简单的处理函数示例
- (void)handleUniversalLink:(NSURL *)url {
    NSString *path = url.path; // 获取路径部分,如 “/promotion/update”
    NSString *host = url.host; // 获取域名,如 “www.yourapp.com”
    
    // 根据路径决定跳转到哪个界面
    if ([path containsString:@"/promotion/update"]) {
        // 跳转到应用内更新提示页面
        [self navigateToUpdateViewController];
    } else if ([path containsString:@"/event/gift"]) {
        // 解析URL中的查询参数,例如 ?code=ABCD123
        NSURLComponents *components = [NSURLComponents componentsWithURL:url resolvingAgainstBaseURL:NO];
        NSString *giftCode = nil;
        for (NSURLQueryItem *item in components.queryItems) {
            if ([item.name isEqualToString:@"code"]) {
                giftCode = item.value;
                break;
            }
        }
        // 跳转到礼物兑换页面,并填入兑换码
        [self navigateToGiftRedeemViewControllerWithCode:giftCode];
    }
    // ... 可以处理更多路径
}

对于SwiftUI项目,你可以在主要的App结构体中,使用 onOpenURL 修饰符来处理,原理是相通的。

如何测试? 配置完成后,最直接的测试方法是:

  1. 将App安装到真机(模拟器对Universal Links的支持不完整,强烈建议用真机)。
  2. 确保设备已联网。
  3. 在设备的 备忘录(Notes) App里,创建一个新笔记,输入你配置的完整Universal Link,例如 https://www.yourapp.com/promotion/update。
  4. 点击这个链接。如果一切正常,它会直接打开你的App(如果已安装),而不是在Safari中打开。如果是在Safari中打开,并且顶部出现一个“在XXX中打开”的横幅,你点击横幅也能跳转,但这属于“智能横幅”,说明Universal Link可能没有完全生效,需要回头检查前面的步骤,尤其是AASA文件的验证和Xcode中的域名配置。

7. 在App Store Connect中创建“App内活动”

前面所有步骤,都是为了给你的App装上接收“传送门”信号的装置。现在,我们要在App Store里创建那个吸引用户点击的“门”本身,这就是 “App内活动”。

  1. 登录 App Store Connect。
  2. 选择你的App,在左侧边栏找到 “App内活动” 并点击进入。
  3. 点击右上角的“+”按钮创建一个新活动。
  4. 填写活动详情:
    • 参考名称:给活动起个名字,仅后台可见。
    • 活动类型:选择“更新”,或者其他适合的类型如“挑战”、“活动”等。
    • 活动链接:这是最关键的一步!在这里填入你准备好的Universal Link。例如,你想让用户点击后跳转到App内的更新介绍页,就填入 https://www.yourapp.com/promotion/update-v2.0。这个链接必须是你已经在AASA文件中声明、并且在App内处理好的路径。
    • 活动内容:设置活动在App Store中展示的标题、副标题、图片或视频素材。这里的设计要吸引人,清晰传达“点击我能得到什么好处”(例如:立即更新,体验全新功能!)。
    • 调度:设置活动的开始和结束日期。活动会在开始日期自动在App Store产品页面上线。

创建并提交活动后,苹果会进行审核。审核通过后,当活动处于有效期内,它就会显示在你的App Store产品页面上。用户点击这个活动卡片,就会通过你配置的Universal Link,直接跳转到你的App内部,完成你预设的引导动作(如弹出更新弹窗、跳转到活动页面等)。

一个实战技巧:你可以为不同的场景创建不同的活动,并配置不同的Universal Link路径。比如,一个大版本更新用一个链接(/update/major),一个节日限时活动用另一个链接(/event/christmas)。这样在App内就能精准地区分用户来自哪个入口,实现个性化的引导和运营。

更多推荐