iOS点击邮件URL跳转至APP后,如何获取原链接与上下文?
这两个问题都是iOS开发里处理深度链接的常见场景,我给你详细拆解解决方案:
问题1:获取邮件URL跳转至APP时的链接内容
不管你用的是URL Scheme还是Universal Links来实现跳转,iOS系统都会通过特定的回调方法把触发跳转的URL传递给APP,分两种场景处理:
场景1:APP冷启动(之前未打开)
如果APP是通过点击URL直接启动的,你需要在AppDelegate(iOS12及以下)或SceneDelegate(iOS13+)的启动回调里提取URL:
AppDelegate 实现
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { // 处理URL Scheme跳转 if let url = launchOptions?[.url] as? URL { handleIncomingURL(url) } // 处理Universal Links跳转 if let activityDict = launchOptions?[.userActivityDictionary] as? [String: Any], let userActivity = activityDict["UIApplicationLaunchOptionsUserActivityKey"] as? NSUserActivity, userActivity.activityType == NSUserActivityTypeBrowsingWeb, let url = userActivity.webpageURL { handleIncomingURL(url) } return true }
SceneDelegate 实现(iOS13+)
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { // 处理URL Scheme if let urlContext = connectionOptions.urlContexts.first { handleIncomingURL(urlContext.url) urlContext.urlHandler() // 标记URL已处理 } // 处理Universal Links if let userActivity = connectionOptions.userActivities.first, userActivity.activityType == NSUserActivityTypeBrowsingWeb, let url = userActivity.webpageURL { handleIncomingURL(url) } }
场景2:APP后台唤醒
如果APP已经在后台运行,点击URL会唤醒APP,此时要对应处理另一个回调:
AppDelegate 实现
// 处理URL Scheme唤醒 func application(_ app: UIApplication, open url: URL, options: [UIApplication.OpenURLOptionsKey : Any] = [:]) -> Bool { handleIncomingURL(url) return true } // 处理Universal Links唤醒 func application(_ application: UIApplication, continue userActivity: NSUserActivity, restorationHandler: @escaping ([UIUserActivityRestoring]?) -> Void) -> Bool { if userActivity.activityType == NSUserActivityTypeBrowsingWeb, let url = userActivity.webpageURL { handleIncomingURL(url) } return true }
SceneDelegate 实现(iOS13+)
// 处理URL Scheme唤醒 func scene(_ scene: UIScene, openURLContexts URLContexts: Set<UIOpenURLContext>) { if let urlContext = URLContexts.first { handleIncomingURL(urlContext.url) urlContext.urlHandler() } } // 处理Universal Links唤醒 func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { if userActivity.activityType == NSUserActivityTypeBrowsingWeb, let url = userActivity.webpageURL { handleIncomingURL(url) } }
通用URL解析方法
最后写一个统一的方法来解析URL里的参数(比如忘记密码的token):
func handleIncomingURL(_ url: URL) { // 示例:URL为 myapp://reset-password?token=abc123 或 https://yourapp.com/reset-password?token=abc123 let pathComponents = url.pathComponents if pathComponents.contains("reset-password") { // 提取token参数 let token = url.queryParameters?["token"] // 这里可以直接跳转到APP内的重置密码页面,传入token print("获取到重置密码token:\(token ?? "未找到")") } } // 给URL扩展一个便捷方法获取query参数 extension URL { var queryParameters: [String: String]? { guard let components = URLComponents(url: self, resolvingAgainstBaseURL: true), let queryItems = components.queryItems else { return nil } return queryItems.reduce(into: [String: String]()) { result, item in result[item.name] = item.value } } }
问题2:iOS9+自动跳转APP时检测链接并传递上下文
iOS9之后的自动跳转逻辑,本质上和用户主动点击链接是一样的——系统还是会通过上面提到的回调把URL传递给APP,核心注意点:
- 确保Universal Links配置正确:你的网站需要放置
apple-app-site-association文件,APP里也要配置对应的关联域名,这样系统才会把网站链接和APP绑定,实现自动跳转。 - 覆盖所有启动场景:不管APP是冷启动还是后台唤醒,都要在对应的回调里处理URL,不能只处理一种情况,否则会漏掉忘记密码这类场景的上下文。
- 解析URL参数传递上下文:比如忘记密码的链接里包含的token,你在
handleIncomingURL里解析后,直接传递给APP内的重置密码页面,就能实现和桌面端一样的无缝体验——用户跳转过来后直接进入重置流程,不用再输入额外信息。
内容的提问来源于stack exchange,提问作者Jason Galuten
相关产品推荐
相关产品推荐

