iOS SDK - 支持深度链接

添加深度链接支持

深度链接 将用户引导至您应用中的特定内容。当用户在已安装您应用的设备上点击深度链接时, 应用会直接打开并跳转至预期的内容,例如产品页面或特定的体验。

Singular 跟踪链接同时支持标准深度链接(用于已安装的应用)和延迟深度链接 (用于新安装)。如需完整信息,请参阅 深度链接常见问题 Singular Links FAQ


要求

先决条件

要为您的应用启用深度链接,请完成 Singular Links 先决条件

必需的配置步骤:

  • Associated Domains: 在 Xcode 中,将 Singular 自定义子域添加到 Signing & Capabilities > Associated Domains
  • URL Types: Info > URL Types 中将应用 scheme 添加到您的 URL Types
  • Singular 平台: 在 Singular 平台的 Apps 页面中添加您的 Apple Developer Team ID Scheme

注意:

  • 如果应用已配置为使用 iOS Universal Links, Universal Link 域名 已存在于 Associated Domains 中,可以保留。如下方高级章节所述, 此域名应添加到 Supported Domains 配置选项
  • 您还必须包含 Singular 自定义链接域名 , 这样 Singular 才能从营销活动中跟踪归因, 并处理来自这些活动的深度链接

实现 Singular Links 处理程序

当应用打开时,SingularLinkHandler 提供回调机制以从 Singular 跟踪链接 检索深度链接、延迟深度链接和 passthrough 参数。

可用参数:

  • Deep Link: 点击链接的用户在您应用中的目标 URL
  • Deferred Deep Link: 点击链接后安装应用的用户的目标 URL
  • Passthrough: 通过跟踪链接传递的自定义数据,用于提供附加上下文
  • URL Parameters: 跟踪链接 URL 中的所有查询参数

SDK 配置

将 SingularLinkHandler 添加到 Config

在 SDK 初始化期间配置 SingularLinkHandler,以处理传入的深度链接和延迟 深度链接数据。

Swift Objective-C
func getConfig() -> SingularConfig? {
    // Create config with API credentials
    guard let config = SingularConfig(apiKey: "SDK_KEY", andSecret: "SDK_SECRET") else {
        return nil
    }
    
    // Set deep link handler
    config.singularLinksHandler = { params in
        self.handleDeeplink(params: params)
    }
    
    return config
}

func handleDeeplink(params: SingularLinkParams?) {
    // Get Deeplink data from Singular Link
    let deeplink = params?.getDeepLink()
    let passthrough = params?.getPassthrough()
    let isDeferred = params?.isDeferred()
    let urlParams = params?.getUrlParameters()
    
    print("Deeplink: \(deeplink ?? "null")")
    print("Passthrough: \(passthrough ?? "null")")
    print("Is Deferred: \(isDeferred ?? false)")
    
    // Handle deep link routing
    if let url = deeplink {
        handleDeepLinkRouting(url: url, isDeferred: isDeferred ?? false)
    }
}

注意: SingularLinkHandler 仅在应用通过 Singular Link 打开时才会触发。 如需更多信息,请参阅 Singular Links FAQ


处理程序行为

SingularLinkHandler 的行为会因应用是新安装还是已安装而有所不同。

新安装(延迟深度链接)

在新安装的情况下,应用启动时不存在 Open URL。Singular 完成归因以 确定跟踪链接是否包含深度链接或延迟深度链接值。

延迟深度链接流程:

  1. 用户点击配置有深度链接值的 Singular 跟踪链接
  2. 用户首次安装并打开应用
  3. Singular SDK 将首次会话发送到 Singular 服务器
  4. 归因完成并从跟踪链接中识别出深度链接
  5. 深度链接值连同 isDeferred = true 一起返回到 SingularLinkHandler

测试延迟深度链接:

  1. 从测试设备卸载应用(如果当前已安装)
  2. 在设备上重置 IDFA(Settings > Privacy > Apple Advertising > Reset Advertising Identifier)
  3. 从设备点击 Singular 跟踪链接(确保已配置深度链接值)
  4. 安装并打开应用

归因应成功完成,且延迟深度链接值将被传递给 SingularLinkHandler。

专业提示: 当使用具有不同 bundle 标识符的开发版本(例如, com.example.dev 而不是 com.example.prod )测试深度链接时, 请专门为开发应用的 bundle 标识符配置跟踪链接。点击测试链接后,通过 Xcode 或 TestFlight 直接将开发版本安装到设备上,而不是从 App Store 下载生产应用。


已安装(即时深度链接)

当应用已安装时,点击 Singular Link 会使用 iOS Universal Links 技术 立即打开应用。

即时深度链接流程:

  1. 用户点击 Singular 跟踪链接
  2. iOS 提供包含完整 Singular 跟踪链接的 Open URL
  3. 在 SDK 初始化期间,Singular 解析 NSUserActivity 或 URL
  4. Singular 提取深度链接和 passthrough 值
  5. 这些值连同 isDeferred = false 一起通过 SingularLinkHandler 返回

Passthrough 参数

使用 passthrough 参数从跟踪链接点击中捕获额外数据。

如果跟踪链接中包含 passthrough 参数,SingularLinkHandler 的 passthrough 参数会包含相应的数据。可用于捕获活动Meta数据、用户分段数据, 或您在应用中需要的任何自定义信息。

Swift Objective-C
func handleDeeplink(params: SingularLinkParams?) {
    // Extract passthrough data
    if let passthroughData = params?.getPassthrough() {
        // Parse JSON passthrough data
        if let data = passthroughData.data(using: .utf8),
           let jsonData = try? JSONSerialization.jsonObject(with: data) as? [String: Any] {
            
            let campaignId = jsonData["campaign_id"] as? String
            let userSegment = jsonData["segment"] as? String
            
            print("Campaign ID: \(campaignId ?? "unknown")")
            print("User Segment: \(userSegment ?? "unknown")")
        }
    }
}

URL 参数

使用 getUrlParameters() 方法从跟踪链接 URL 捕获所有查询参数。

SingularLinkHandler 提供对跟踪链接所有 URL 参数的访问, 让您可以完全访问自定义参数和 UTM 标签。

Swift Objective-C
func handleDeeplink(params: SingularLinkParams?) {
    // Get all URL parameters
    if let urlParams = params?.getUrlParameters() {
        for (key, value) in urlParams {
            print("Parameter: \(key) = \(value)")
        }
        
        // Access specific parameters
        if let utmSource = urlParams["utm_source"] as? String {
            print("UTM Source: \(utmSource)")
        }
        
        if let promoCode = urlParams["promo"] as? String {
            print("Promo Code: \(promoCode)")
        }
    }
}

跟踪链接示例:
https://yourapp.sng.link/A1b2c/abc123?_dl=myapp://product/123&utm_source=facebook&promo=SALE2024

SingularLinkHandler 将通过 getUrlParameters() 方法提供对所有参数的访问,包括 utm_source promo


高级配置

支持来自第三方合作伙伴(如 Google Ads 和 Facebook)的 Universal Links 用于归因跟踪。

对于 Singular iOS SDK 12.0.3 及更高版本,默认支持非 Singular Universal Links。

已弃用功能: supportedDomains 归因和 startSession:...andSupportedDomains: 重载在当前 SDK 中被标注为 __attribute__((deprecated)) 。以下代码块仅针对旧版 SDK(低于 12.0.3)显示; 请升级 SDK,而不是在新代码中继续设置 supportedDomains

要在旧版 SDK 中支持第三方深度链接:

  • 每次初始化 Singular SDK 时,将所有关联域( sng.link 除外) 添加到 Config 对象的 supportedDomains 配置选项中
  • 这允许第三方深度链接行为,但不允许对深度链接进行归因。 要进行归因,您仍必须使用 Singular 跟踪链接
  • supportedDomains 功能假定您已为 Universal Links 配置了应用, 并且目前在您自己的域上托管 AASA 文件
Swift Objective-C
func getConfig() -> SingularConfig? {
    guard let config = SingularConfig(apiKey: "SDK_KEY", andSecret: "SDK_SECRET") else {
        return nil
    }
    
    // Add supported domains for third-party Universal Links
    config.supportedDomains = [
        "subdomain.mywebsite.com",
        "anothersubdomain.myotherwebsite.com"
    ]
    
    return config
}

为电子邮件活动归因启用由电子邮件服务提供商 (ESP) 提供的 Universal Links。

ESP 域必须启用 HTTPS。Apple 要求 iOS 应用从启用了 HTTPS 且无再营销的端点拉取 apple-app-site-association 文件。请与您的 ESP 确认他们如何为您的应用托管此文件, 因为可能需要在您站点的 DNS 上进行 DNS 配置。

要支持 ESP 域,请每次初始化 Singular SDK 时将自定义跟踪域添加到 config 对象的 espDomains 配置选项中。

Swift Objective-C
func getConfig() -> SingularConfig? {
    guard let config = SingularConfig(apiKey: "SDK_KEY", andSecret: "SDK_SECRET") else {
        return nil
    }
    
    // Add ESP domains for email campaign tracking
    config.espDomains = ["links.mywebsite.com"]
    
    return config
}