自定義 URL Scheme 指南

本文由 Migrant 翻譯自 The Complete Tutorial on iOS/iPhone Custom URL Schemes,轉(zhuǎn)載請(qǐng)注明出處。

注意: 自從自定義 URL 的引入,本文始終是我博客中閱讀量最大的文章。雖然大多數(shù)都相同,但仍然有一些細(xì)微差別的變化。本文是原帖的重寫版,更新為最新的 iOS 和 Xcode 版本。

iPhone / iOS SDK 最酷的特性之一就是應(yīng)用將其自身”綁定”到一個(gè)自定義 URL scheme 上,該 scheme 用于從瀏覽器或其他應(yīng)用中啟動(dòng)本應(yīng)用。

注冊(cè)自定義 URL Scheme

注冊(cè)自定義 URL Scheme 的第一步是創(chuàng)建 URL Scheme — 在 Xcode Project Navigator 中找到并點(diǎn)擊工程 info.plist 文件。當(dāng)該文件顯示在右邊窗口,在列表上點(diǎn)擊鼠標(biāo)右鍵,選擇 Add Row:

向下滾動(dòng)彈出的列表并選擇 URL types。

點(diǎn)擊左邊剪頭打開(kāi)列表,可以看到 Item 0,一個(gè)字典實(shí)體。展開(kāi) Item 0,可以看到 URL Identifier,一個(gè)字符串對(duì)象。該字符串是你自定義的 URL scheme 的名字。建議采用反轉(zhuǎn)域名的方法保證該名字的唯一性,比如 com.yourCompany.yourApp

點(diǎn)擊 Item 0 新增一行,從下拉列表中選擇 URL Schemes,敲擊鍵盤回車鍵完成插入。

注意 URL Schemes 是一個(gè)數(shù)組,允許應(yīng)用定義多個(gè) URL schemes。

展開(kāi)該數(shù)據(jù)并點(diǎn)擊 Item 0。你將在這里定義自定義 URL scheme 的名字。只需要名字,不要在后面追加 :// — 比如,如果你輸入 iOSDevApp,你的自定義 url 就是 iOSDevApp://

此時(shí),整個(gè)定義如下圖:

iOS Custom URL Scheme

雖然我贊同 Xcode 使用描述性的名字的目的,不過(guò)看到創(chuàng)建的實(shí)際的 key 也是非常有用的。這里有一個(gè)方便的技巧,右鍵點(diǎn)擊 plist 并選擇 Show Raw Keys/Values,就能看到以下效果:

還有另一種有用的輸出格式,XML,因?yàn)榭梢苑浅H菀椎目吹阶值浜驮紨?shù)組及其包括的實(shí)體的結(jié)構(gòu)。點(diǎn)擊 plist 并選擇 Open As – Source Code:

從 Safari 中調(diào)用自定義 URL Scheme

定義了 URL scheme,我們可以運(yùn)行一個(gè)快速測(cè)試來(lái)驗(yàn)證應(yīng)用是否如我們所期望的被調(diào)用。在這之前,我創(chuàng)建了一個(gè)準(zhǔn) UI 以辨別帶有自定義 URL 的應(yīng)用。該應(yīng)用只有一個(gè) UILabel,帶有文本 “App With Custom URL”。下載源代碼

使用模擬器調(diào)用應(yīng)用的步驟:

  • 在 Xcode 中運(yùn)行應(yīng)用
  • 一旦應(yīng)用被安裝,自定義 URL scheme 就會(huì)被注冊(cè)
  • 通過(guò)模擬器的硬件菜單中選擇 Home 來(lái)關(guān)閉應(yīng)用
  • 啟動(dòng) Safari
  • 在瀏覽器地址欄輸入之前定義的 URL scheme(如下)

此時(shí) Safari 將會(huì)關(guān)閉,應(yīng)用會(huì)被帶回到前臺(tái)。祝賀你剛剛使用自定義 URL scheme 調(diào)用了一個(gè) iPhone 應(yīng)用。

從另一個(gè) iPhone 應(yīng)用中調(diào)用自定義 URL Scheme

讓我們看看如何從另一個(gè)應(yīng)用中調(diào)用自定義 URL scheme。我又創(chuàng)建了一個(gè)非常簡(jiǎn)單的 iPhone 應(yīng)用,它只有一個(gè) UILabel 和一個(gè) UIButton — 前者顯示了一段信息,告訴你這個(gè)應(yīng)用將要通過(guò)自定義 URL scheme 來(lái)調(diào)用另一個(gè)應(yīng)用,按鈕則開(kāi)始這個(gè)行為。下載源代碼

buttonPressed 方法中的代碼處理 URL 調(diào)用:

- (void)buttonPressed:(UIButton *)button{
         NSString *customURL = @"iOSDevTips://"; 
        if ([[UIApplication sharedApplication] canOpenURL:[NSURL URLWithString:customURL]]) { 
              [[UIApplication sharedApplication] openURL:[NSURL URLWithString:customURL]];
        } else { 
              UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"URL error" message:[NSString stringWithFormat: @"No custom URL defined for %@", customURL] delegate:self cancelButtonTitle:@"Ok" otherButtonTitles:nil]; 
              [alert show]; 
       }
}

第 5 行代碼檢查自定義 URL 是否被定義,如果定義了,則使用 shared application 實(shí)例來(lái)打開(kāi) URL (第 8 行)。openURL: 方法啟動(dòng)應(yīng)用并將 URL 傳入應(yīng)用。在此過(guò)程中,當(dāng)前的應(yīng)用被退出。

通過(guò)自定義 URL Scheme 向應(yīng)用傳遞參數(shù)

有時(shí)你需要通過(guò)自定義 URL 向應(yīng)用中傳遞參數(shù)。讓我們看看該如何完成這個(gè)工作。

NSURL 作為從一個(gè)應(yīng)用調(diào)用另一個(gè)的基礎(chǔ),遵循 RFC 1808 (Relative Uniform Resource Locators) 標(biāo)準(zhǔn)。 因此你所熟悉的基于網(wǎng)頁(yè)內(nèi)容的 URL 格式在這里也適用。

在自定義了 URL scheme 的應(yīng)用中,app delegate 必須實(shí)現(xiàn)以下方法:

- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation

從一個(gè)應(yīng)用傳遞參數(shù)到另一個(gè)的訣竅是通過(guò) URL。例如,假設(shè)我們使用以下的 URL scheme,想傳遞一個(gè)名為 “token”的參數(shù)和一個(gè)標(biāo)識(shí)注冊(cè)狀態(tài)的標(biāo)志,我們可以像這樣創(chuàng)建一個(gè) URL:


NSString *customURL = @"iOSDevTips://?token=123abct&registered=1";

在 web 開(kāi)發(fā)中,字符串 ?token=123abct&registered=1 被稱作查詢?cè)兇?query string).
在被調(diào)用(設(shè)置了自定義 URL)的應(yīng)用的 app delegate 中,獲取參數(shù)的代碼如下:


- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation{ 
                NSLog(@"Calling Application Bundle ID: %@", sourceApplication); 
                NSLog(@"URL scheme:%@", [url scheme]);
                NSLog(@"URL query: %@", [url query]);
                return YES;
}

以上代碼在應(yīng)用被調(diào)用時(shí)的輸出為:


Calling Application Bundle ID: com.3Sixty.CallCustomURL
URL scheme:iOSDevTips
URL query: token=123abct&registered=1

注意 “Calling Application Bundle ID”,你可以用這個(gè)來(lái)確保只有你定義的應(yīng)用可以與你的應(yīng)用直接交互。

讓我們改變一下代碼,來(lái)驗(yàn)證發(fā)起調(diào)用的應(yīng)用的 Bundle ID 是否合法:

- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation{ 
// Check the calling application Bundle ID
         if ([sourceApplication isEqualToString:@"com.3Sixty.CallCustomURL"]) { 
                      NSLog(@"Calling Application Bundle ID: %@", sourceApplication);
                      NSLog(@"URL scheme:%@", [url scheme]); 
                      NSLog(@"URL query: %@", [url query]); 
                      return YES; 
        } else {
                      return NO;
        }
}

有一點(diǎn)要特別注意,你不能阻止其他應(yīng)用通過(guò)自定義 URL scheme 調(diào)用你的應(yīng)用,然而你可以跳過(guò)后續(xù)的操作并返回 NO,就像上面的代碼那樣。也就是說(shuō),如果你想阻止其它應(yīng)用調(diào)用你的應(yīng)用,創(chuàng)建一個(gè)與眾不同的 URL scheme。盡管這不能保證你的應(yīng)用不會(huì)被調(diào)用,但至少大大降低了這種可能性。

自定義 URL Scheme 示例工程

我意識(shí)到按照本文的每一步做下來(lái)還是有一點(diǎn)復(fù)雜的。我做好了兩個(gè)非常基礎(chǔ)的 iOS 應(yīng)用,一個(gè)自定義了 URL scheme,另一個(gè)則去調(diào)用它,并傳遞了一個(gè)比較短的參數(shù)列表(query string)。這些是體驗(yàn)自定義 URL 的很好的入門點(diǎn)。
Download Xcode project for app with Custom URL scheme
Download Xcode project for app to call custom URL scheme

其它資源

How to Properly Validate URL Parameters
URL Scheme Reference Docs

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 一、URL Scheme 簡(jiǎn)介和作用 相信大家都知道 URL,例如 http://www.itdecent.cn/...
    伯牙呀閱讀 23,675評(píng)論 -1 19
  • Spring Cloud為開(kāi)發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見(jiàn)模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,563評(píng)論 19 139
  • 廣大漫迷們,漫長(zhǎng)的動(dòng)漫連載熱劇是否讓你望眼欲穿,遙遙無(wú)期的愛(ài)豆力作是否讓你心心念念,制作精良的動(dòng)漫新番是否讓你翹首...
    萌呷動(dòng)漫閱讀 672評(píng)論 0 0
  • 記不清有多久沒(méi)有寫東西了,一直以來(lái)很喜歡欣賞美文,自以為由工作忙沒(méi)時(shí)間,而不斷使自己惰性增加,今夜終于不用加班...
    萱萱美女媽閱讀 886評(píng)論 1 2
  • 只有身懷絕技,才能披荊斬棘,走人不能走之路,成功不一定在于堅(jiān)持,還在于選擇。
    紫夜天天萌閱讀 233評(píng)論 0 0

友情鏈接更多精彩內(nèi)容