【问题标题】:How can I programmatically determine if a URL is a Universal Link or just a regular web URL?如何以编程方式确定 URL 是通用链接还是常规 Web URL?
【发布时间】:2017-01-10 22:14:17
【问题描述】:

在 iOS 上,我如何以编程方式确定 URL 是通用链接还是只是常规 Web URL?

假设您即将从您自己的 iOS 应用程序中启动 URL http://www.yelp.com。 (http://www.yelp.com 是完全注册的通用链接。)

案例一)用户没有安装应用程序 -> 您想在 IN-APP 网页视图中向他们展示网站。

案例二)用户确实安装了应用程序 -> 您想要启动您的应用程序并使用 [[UIApplication sharedApplication] openURL:URL] 直接深层链接到 yelp 应用程序;而不是在应用中呈现 webview。

问题出在: 您可以使用的只是字符串 url:“http://www.yelp.com 如果安装了 yelp 应用程序,您的目标是启动,但如果未安装 yelp,则显示应用程序内 web 视图。

注意1:本题只针对通用链接。请不要给出使用 URL Schemes 的答案。

注意 2:这个问题不是关于专门启动 yelp 应用程序。该解决方案应该适用于任何 url,以确定它是否是已安装应用程序的通用链接。

你能做到吗?

【问题讨论】:

  • 使用 canOpenURL 方法检查 URL 的 scheme 是否可以被系统处理,如果不能(yelp app 未安装),则显示 webview 屏幕。
  • 在什么情况下 canOpenURL 会为给定的 url http://www.yelp.com 返回 false ? (顺便说一句,这个问题没有讨论任何方案)

标签: ios ios-universal-links


【解决方案1】:

使用UIApplicationOpenURLOptionUniversalLinksOnly检测链接是否通用

解决方法如下:

[[UIApplication sharedApplication] openURL:url
                                       options:@{UIApplicationOpenURLOptionUniversalLinksOnly: @YES}
                             completionHandler:^(BOOL success){
                                 if(!success) {
                                     // present in app web view, the app is not installed 
                                 }
                             }];

【讨论】:

  • 如果应用调用也是通用链接的目的地,这将不起作用。
【解决方案2】:

我在下面的 Swift 4 课程中解决了这个问题。如果可能,它还使用嵌入式 Safari 浏览器。您也可以在您的情况下采用类似的方法。

import UIKit
import SafariServices

class OpenLink {
    static func inAnyNativeWay(url: URL, dontPreferEmbeddedBrowser: Bool = false) { // OPEN AS UNIVERSAL LINK IF EXISTS else : EMBEDDED or EXTERNAL
        if #available(iOS 10.0, *) {
            // Try to open with owner universal link app
            UIApplication.shared.open(url, options: [UIApplication.OpenExternalURLOptionsKey.universalLinksOnly : true]) { (success) in
                if !success {
                    if dontPreferEmbeddedBrowser {
                        withRegularWay(url: url)
                    } else {
                        inAnyNativeBrowser(url: url)
                    }
                }
            }
        } else {
            if dontPreferEmbeddedBrowser {
                withRegularWay(url: url)
            } else {
                inAnyNativeBrowser(url: url)
            }
        }
    }
    private static func isItOkayToOpenUrlInSafariController(url: URL) -> Bool {
        return url.host != nil && (url.scheme == "http" || url.scheme == "https") //url.host!.contains("twitter.com") == false
    }
    static func inAnyNativeBrowser(url: URL) { // EMBEDDED or EXTERNAL BROWSER
        if isItOkayToOpenUrlInSafariController(url: url) {
            inEmbeddedSafariController(url: url)
        } else {
            withRegularWay(url: url)
        }
    }
    static func inEmbeddedSafariController(url: URL) { // EMBEDDED BROWSER ONLY
        let vc = SFSafariViewController(url: url, entersReaderIfAvailable: false)
        if #available(iOS 11.0, *) {
            vc.dismissButtonStyle = SFSafariViewController.DismissButtonStyle.close
        }
        mainViewControllerReference.present(vc, animated: true)
    }
    static func withRegularWay(url: URL) { // EXTERNAL BROWSER ONLY
        if #available(iOS 10.0, *) {
            UIApplication.shared.open(url, options: [UIApplication.OpenExternalURLOptionsKey(rawValue: "no"):"options"]) { (good) in
                if !good {
                    Logger.log(text: "There is no application on your device to open this link.")
                }
            }
        } else {
            UIApplication.shared.openURL(url)
        }
    }
}

【讨论】:

    猜你喜欢
    • 2011-07-20
    • 2010-10-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-29
    相关资源
    最近更新 更多