天天看點

iOS開發之App間賬号共享與SDK封裝

本篇部落格就先封裝一個LoginSDK, 讓後将該SDK植入到兩個App中(一個暫且叫做“App One”, 另一個暫且稱為“App Two”)。當App One登入成功後,當你在打開App Tow進行登入時,我們封裝的LoginSDK會從KeyChain中取出App One的賬号進行登入。前提是這兩個App設定了Keychain Share。廢話少說,進入今天的主題。

一、功能總述

在部落格開始的第一部分,我們先來看一下我們最終要實作的效果。下圖中所表述的就是我們今天部落格中要做的事情,下方的App One和App Two都植入了我們将要封裝的LoginSDK, 兩個App中都設定了Keychain Share。當App One通過我們的LoginSDK登入後,在啟動App Two時,會去檢索是否有賬号以及在分享的Keychain中存儲了,如果有的話,那麼不會彈出“登入”界面,直接進行隐式登入。當然上述這些工作都是在我們的LoginSDK中進行做的事情。

iOS開發之App間賬号共享與SDK封裝

本部分算是本篇部落格的一個綜述吧,從下方截圖中,我們能清楚的看到上述的兩個App中都植入了我們接下來要封裝的SDK。LoginSDK.framework就是我們封裝的登入靜态庫,其中提供了使用者所調用的API。

  

iOS開發之App間賬号共享與SDK封裝

下方這個截圖中的内容就是使用者所調用LoginSDK的API。因為我們做的隻是一個Demo,是以下方的API接口比較簡單,如果你要和現實App中真正的需求和業務邏輯整合到一塊,那麼封裝一個登入用的SDK是非常麻煩的。因為我考慮過把我們團隊所開發的幾個App中的登入子產品封裝成SDK, 仔細考慮了一下,東西還是蠻多的。扯遠了,不過今天這個Demo還是可以提供一個大體思路的。

下方API的對象是通過單例來擷取的,如果是首次登入的話,就需要調用getLoginViewController這個方法來擷取登入頁面,并且這個函數需要提供一個Block參數,這個Block參數用來處理登入成功後的事件。而登入失敗等事件就在我們SDK中自行處理了。

checkHaveLogin方法是用來檢查是否已經有賬号登入過,該方法需要提供兩個Block,一個是登入成功要執行的Block,一個是沒有已登入賬号時執行的Block。當執行該方法時,如果之前有賬号登入過的話,就直接進行隐式登入,登入成功後執行loginSuccessBlock。之前如果沒有賬号在此裝置上登入就執行noAccountBlock, 來處理首次登入的事件。

iOS開發之App間賬号共享與SDK封裝

該部分先聊這麼多,接下來會根據上述的知識點詳細的展開。

二、LoginSDK的封裝

在封裝LoginSDK之前呢,SDK的源代碼以及所依賴的資源得準備好對吧。下方截圖就是我們LoginSDK的源代碼,下方綠框中的部分是留給使用者使用的API, 而黃框中的部分就是我們這個SDK所依賴的資源了,雖然此處隻用一個Storyboard,我們還是有必要将該資源檔案打包成Bundle檔案提供給使用者的。而其他源代碼SDK的使用者是看不到的。源碼準備好,測試完畢後,接下來我們就要進行SDK的封裝了。

iOS開發之App間賬号共享與SDK封裝

1.建立iOS Framework工程

首先我們需要建立一個iOS的CocoaTouch工程,點選Next,輸入我們Framework的名字即可。下方我們暫且将該Framework的名字命名為“CreateLoginSDKFramework”。如下所示:

iOS開發之App間賬号共享與SDK封裝
iOS開發之App間賬号共享與SDK封裝

2.設定相容版本

建立完工程後,我們要選擇“Deployment Target”, 此處我們選擇的是8.0。也就是說此處我們封裝的SDK所支援的iOS系統版本是iOS8.0+。

iOS開發之App間賬号共享與SDK封裝

3.選擇“靜态庫”

我們建立的framework預設是動态庫,是以我們要講Mach-O Type設定為靜态庫“Static Library”,如下所示。

iOS開發之App間賬号共享與SDK封裝

4.引入源代碼并進行編譯

配置好上述選項後,接下來我們就需要将我們事先準備好的SDK源代碼引入到我們的Framework的工程中進行編譯了,在編譯之前我們要選擇SDK使用者可以看到的檔案。下方截圖中就是在Build Phases下的Headers中進行設定的。将使用者可以看到的頭檔案房子Public中,使用者看不到的放在Project中。如下所示。

iOS開發之App間賬号共享與SDK封裝

5.編譯

上述設定和配置完畢後,我們就要對我們的Framework工程進行編譯了。先選擇模拟器進行編譯,然後選擇真機進行編譯。編譯完後,在Products下會生成相應的Framework, 然後通過Show in Finder進行檢視即可。檢視時,如果想看“模拟器”和“真機”的framework的話,在Show in finder後,需要前往上層檔案夾檢視。具體如下所示。

iOS開發之App間賬号共享與SDK封裝

6.Framework的合并

因為在模拟器下編譯會生成模拟器下使用的Framework,在真機下編譯會生成真機使用的Framework。如果想我們生成的Framework既可以在真機下使用,也可以在模拟器下使用,那麼我們需要将兩個Framework進行合并。

下方截圖中,這兩個framework一個是真機生成的,另一個是模拟器生成的,我們做的事情就是将下方綠框中的兩個檔案進行合并。然後使用合并後的檔案将下方的檔案替換即可。替換後的framework就可以在模拟器和真機下進行使用了。

iOS開發之App間賬号共享與SDK封裝

我們使用“lipo -create 模拟器framework路徑  真機framework路徑 -output 新的檔案”指令将上述兩個檔案進行合并。下方就是合并上述兩個檔案的執行指令, 執行完下方指令後會生成合并後的檔案,将上述檔案進行替換即可。經過上述步驟,我們的Framework至此就封裝完畢了。

iOS開發之App間賬号共享與SDK封裝

三、封裝Bundle

封裝完Framework後,接下來我們要對Framework依賴的資源檔案進行打包了。因為我們SDK中的界面是使用Storyboard做的,是以需要将Storyboard打包成Bundle資源檔案與上述的Framework一起使用。如果我們SDK中需要一些圖檔資源的話,也可以進行一并打包。接下來我們就要對資源檔案進行打包。

1.Bundle工程的建立

首先我們像建立Framework工程一樣建立一個Bundle工程,因為iOS工程下方沒有Bundle類型的工程,是以我們需要在OS X -> Framework & Library -> Bundle下面來建立我們的Bundle工程。選擇完後,輸出我們的Bundle檔案的名稱即可,如下所示:

iOS開發之App間賬号共享與SDK封裝
iOS開發之App間賬号共享與SDK封裝

2. Bundle工程的配置

建立完Bundle工程後,我們要對其進行相應的配置。因為我們是選擇OS X建立的Bundle,預設的Bundle是不能在iOS中使用的,是以我們得将Base SDK進行設定,選擇相應的iOS版本即可,如下所示。選擇完Base SDK後,我們還要像上面Framework的封裝一樣,設定一下要相容的iOS版本(iOS Deployment Target), 在此就不做過多贅述了。

iOS開發之App間賬号共享與SDK封裝

3.引入資源,進行編譯

進行上述配置完後,接下來就是引入資源檔案進行編譯了,下方引入的資源檔案就是我們的LoginSDK.storyboard。引入資源後,進行編譯,編譯後會在Products下面生成相應的Bundle資源檔案,該檔案就可以和我們的Framework進行使用了。

iOS開發之App間賬号共享與SDK封裝

4.Bundle資源的加載

生成完Bundle資源檔案後,我們在SDK的源代碼中,要從Bundle資源檔案中進行資源的加載。下方代碼就是加載相應Bundle的代碼。通過下方的宏定義,就可以通過“Bundle”的名字來加載Bundle。下方的LOGIN_SDK_BUNDLE就是我們要使用的Bundle資源檔案的對象。

下方代碼就是從上述Bundle對象中加載相應的Storyboard。與我們之前的代碼不同,之前我們是從MainBundle中加載的Storyboard,而現在我們是從指定的Bundle中來加載Storyboard。具體代碼如下所示。

iOS開發之App間賬号共享與SDK封裝

四、SDK的引入

SDK已經依賴的資源檔案封裝完畢後,接下來就是在其他App中使用了。在第一部分中的App One和App Two都引入了上述我們封裝的LoginSDK。引入SDK步驟也是比較簡單的,這和引入友盟,個推,微信支付,支付寶等等SDK的步驟差不多。下方就是我們引入SDK的步驟。

1.導入SDK并進行相關配置

導入SDK到我們的App工程後,我們要對其進行相應的配置。首先我們要對Framework Search Paths進行配置,也就是說告訴編譯器我們的第三方SDK所在的位置。下方這個配置項在引入SDK後就預設存在的,如果沒有的話就進行配置即可。

iOS開發之App間賬号共享與SDK封裝

配置完路徑後,接下來我們要在Other Linker Flags添加上-Objc和-all_load選項。這兩個選項在之前的部落格中也不止一次的提到過。-Objc這個flag告訴連結器把庫中定義的Objective-C類和Category都加載進來。而-all_load會強制連結器把目标檔案都加載進來,即使沒有objc代碼。根據上面介紹的,下方即使不添加-Objc這個選項,下方的工程也是可以正常運作的。

iOS開發之App間賬号共享與SDK封裝

2.SDK的使用

配置完畢後,接下來就是在我們App中使用該SDK了。下方代碼就是我們上述LoginSDK的使用方式,首先擷取單例,然後檢查是否登入,登入成功後根據Block回調跳轉到首頁,如果未登入,就通過LoginAPI擷取登入頁面進行登入。具體如下所示。

iOS開發之App間賬号共享與SDK封裝

五、Keychain共享

iOS開發之App間賬号共享與SDK封裝

經過上面的所有步驟,我們封裝了一個簡單的LoginSDK, 并在多個App中進行植入,并且進行了賬号共享。依照之前的風格,将本篇部落格所涉及的所有内容都會在Github上進行分享,下方就是github分享位址。歡迎交流,上述内容有什麼不足之處,歡迎批評指正,謝謝。