前言
翻譯已與 raywenderlich 社區(qū)取得聯(lián)系(可翻譯10篇文章),原文鏈接
是否想過把參與過的多個項目中功能相近的代碼拆分成可復用的模塊,是否想過與其他開發(fā)者分享你寫的模塊?
也許你想像 iOS SDK 按功能來組織 API 一樣來模塊化你的代碼,也許也想像知名三方庫那樣發(fā)布自己的代碼。
通過這篇文章你將會學會如何創(chuàng)建 Framework 以及如何進行發(fā)布。
iOS 8,Xcode 6 中,蘋果提供了一種新的開發(fā)模板,Cocoa Touch Framework。這使得創(chuàng)建 Framework 更加容易。
Framework 有一下三個主要目的:
- 代碼封裝
- 代碼模塊化
- 代碼復用
你可以在你的其他 App 中,團隊成員,或 iOS 社區(qū)分享你的 Framework。swift 的訪問控制機制使得 framework 在代碼模塊之間提供了健壯可靠的接口。
swift 中,module 是作為一個編譯發(fā)布的代碼單元。framework 和 App 都是一種 module。
在這篇教程中,我們將會拆解一個已存在的 App 為例子,通過下面的步驟把部分代碼拆分出來打包成 framework :
- 為 rings widget 創(chuàng)建一個新的 framework
- 將代碼和測試單元移植到 framework 中
- 導入 framework 到 App 中
- 打包成 cocoapods
- 為你的 framework 設置代碼倉庫
完成上面步驟后,你已經(jīng)成功將該 App 中的部分代碼打包成了可移植的 framework。
開始
Phonercise 是一款簡單的呈現(xiàn)蘋果手表 Activity 應用數(shù)據(jù)的 App,另外還會記錄你手機的物理狀態(tài)。主界面的三個環(huán)分別代表移動,站立,運動。
該項目需要在真機上進行調(diào)試,并打開音量,開始吧。
移動手機,搖晃手機,保持站立來分別記錄移動,運動,站立的數(shù)據(jù)。
該 App 的邏輯如下:
- ActionViewController 包含 view 的生命周期管理和動作邏輯。
- 所有包含視圖邏輯的文件都在 Three Ring View 這個文件夾下。該文件夾下有管理視圖的 ThreeRingView.swift 類,管理音頻的 Fanfare.swift 類,和管理管理自定義視圖的其他類。
下面開始將環(huán)的控制打包成可復用的 framework。
創(chuàng)建 Framework
framework 是自包含,可復用的代碼和其他資源的組織單元。你可以將 framework 導入其他 App 中,甚至可以在 iOS,tvOS,watchOS 和 macOS 跨平臺使用。
如果你使用過其他編程語言,你應該聽過節(jié)點模塊,包,gems,jars 等等。framework 是 Xcode 對于包或者模塊的實現(xiàn)方式。比如 iOS SDK 中通用的 framework:Foundation, UIKit, AVFoundation, CloudKit 等。
設置 Framework
Xcode 6˙中開始新增了 Cocoa Touch Framework 代碼模板,這使得創(chuàng)建 framework 變得非常容易。首先創(chuàng)建 framework 的項目。
- Xcode 中,通過 File/New/Project 創(chuàng)建一個新項目。
- 選擇 iOS/Framework & Library/Cocoa Touch Framework 創(chuàng)建一個新的 framework。
- 點擊 Next
- 設置 Product Name 為 ThreeRingControl。使用你自己的 Organization Name 和 Organization Id恩替覅而。點擊 Include Unit Tests。這樣項目將會包含測試單元來確保項目中沒有 bug。
- 點擊 Next
- 在文件選擇框中,選擇在 Phonercise 項目同級目錄中創(chuàng)建項目。
- 點擊 Create
現(xiàn)在已成功創(chuàng)建了一個 framework。
添加代碼和資源
現(xiàn)在你的 framework 中還沒有代碼。從 Phonercise 項目中把以下八個文件拖拽到當前項目中:
- CircularGradient.swift
- coin07.mp3
- Fanfare.swift
- RingLayer.swift
- RingTip.swift
- ThreeRingView.swift
- Utilities.swift
- winning.mp3
點擊了 Copy items if needed,確保文件被拷貝進了新項目而不是只添加了文件的引用。framework 需要自己的源碼文件而不是文件引用。
編譯,確保編譯沒有任何警告和錯誤。
將 Framework 添加到項目中
回到 Phonercise 項目中。刪除 Three Ring View 組下的六個文件和 Helper Files 文件夾下兩個 MP3 文件。點擊 Move to Trash。
編譯,出現(xiàn) “Use of undeclared type 'ThreeRingView” 錯誤信息。
Phonercise 項目導航器中右鍵,點擊 Add Files to "Phonercise"。在文件選擇器中選擇 ThreeRingControl.xcodeproj。這樣把 ThreeRingControl.xcodeproj 作為子項目添加進來。
注意:也可以直接添加 ThreeRingControl.framework 到項目中。然而添加整個項目會讓同時開發(fā) framework 和 App 變得更容易。你對 framework 項目做的任何改變都將自動應用到 App 上。
雖然這兩個項目在同一工作空間中,Phonercise 仍然無法訪問 ThreeRingControl。
通過鏈接 framework 到 App 的 target 能夠解決這個問題。打開 ThreeRingControl 項目的 Products 文件夾,里面有一個 ThreeRingControl.framework 文件。該文件打包了二進制代碼,頭文件,資源等。
點擊 Phonercise 項目的項目導航器,點擊 Phonercise target,選擇 General tab。
滾動到 Embedded Binaries 選擇。把 ThreeRingControl.xcodeproj Products 文件夾下的 ThreeRingControl.framework 拖拽到該選項中。
這樣同時為 Embedded Binaries 和 Linked Frameworks and Binaries 添加了 framework 的入口。
這樣 App 就知道如何查找該 framework,編譯,出現(xiàn)更多相同錯誤。
訪問控制
此時雖然 framework 已經(jīng)是該項目的一部分了,但該項目代碼仍然無法訪問。
進入 ActionViewController.swift,在該文件的頂部添加如下代碼進行導入。
import ThreeRingControl
導入后仍然沒有解決錯誤信息。因為 swift 使用了訪問控制權(quán)限來讓開發(fā)者決定哪些東西可以暴露給其他用戶。
swift 默認使用 internal 訪問控制權(quán)限,這使得代碼僅在模塊內(nèi)可見。
雖然很麻煩,但訪問控制權(quán)限讓開發(fā)者能夠隱藏核心功能以防被修改,或者顯示的通過 internal 來暴露給其他用戶。
swift 有三個等級的訪問控制權(quán)限。通過下面的規(guī)則來進行選擇:
- Public: 對 App 或其他 framework 可見。
- Internal: 對該 framework 可見
- Fileprivate: 對該編譯文件可以見
- Private: 對該類可見
創(chuàng)建 Cocoapod 源
創(chuàng)建 Pod
在終端進入到 ThreeRingControl 目錄下。運行下面命令:
pod spec create ThreeRingControl
該命令會在當前目錄下創(chuàng)建 ThreeRingControl.podsepc 文件。該模板文件描述了 pod 以及如何進行編譯。通過 vi 打開。
該模板文件包含大量注釋和通用設置建議
- 使用下面代碼替換 Spec Metadata:
s.name = "ThreeRingControl"
s.version = "1.0.0"
s.summary = "A three-ring control like the Activity status bars"
s.description = "The three-ring is a completely customizable widget that can be used in any iOS app. It also plays a little victory fanfare."
s.homepage = "http://raywenderlich.com"
2.該 iOS framework 使用了 MIT 協(xié)議,使用下面的代碼替換 Spec License:
s.license = "MIT"
3.該 framework 僅用于 iOS 平臺,使用下面的代碼替換 Platform Specifics:
s.platform = :ios, "10.0"
4.使用下面代碼替換 Source Location。當你想通過 pod 進行發(fā)布,需要將這里替換成 GitHub repo 的地址和提交的 tag。
s.source = { :path => '.' }
5.使用下面代碼替換 Source Code:
s.source_files = "ThreeRingControl", "ThreeRingControl/**/*.{h,m,swift}"
6.添加 Resources 項:
s.resources = "ThreeRingControl/*.mp3"
這樣可以把音頻文件包含進 framework 的 bundle 中。
7.刪除 Project Linking 和 Project Setting 項。
8.指定該 pod 代碼使用的 swift 版本號。
s.pod_target_xcconfig = { 'SWIFT_VERSION' => '3' }
9.刪除多余的注釋(注釋以#開頭)
使用 Pod
這一節(jié)會帶領(lǐng)你完成最后一步,發(fā)布 pod 到 GitHub。
發(fā)布到 Pod
創(chuàng)建代碼倉庫
如果你還沒有 GitHub 賬號,創(chuàng)建賬號.
創(chuàng)建一個托管該 pod 代碼的新倉庫。把該倉庫命名為 ThreeRingControl,也可以使用任何其他名字。確保 .gitignore 選項為 swift license 為 MIT。
點擊創(chuàng)建倉庫。
克隆倉庫
回到終端創(chuàng)建一個新的文件夾。下面的命令會創(chuàng)建一個名為 repo 的文件夾。
mkdir repo
cd repo
克隆剛才創(chuàng)建的 GitHub 倉庫。替換下面命令中 URL 為 GitHub 倉庫的鏈接。
git clone URL
這會創(chuàng)建一個 Git 文件夾,并把之前創(chuàng)建的 README 和 LICENSE 文件克隆下來。
把代碼拷貝到克隆下來的文件夾中
把 ThreeRingControl 文件夾中的文件拷貝到 repo/ThreeRingControl 文件夾中。
打開拷貝的 ThreeRingControl.podsepc,更新 s.source 信息:
s.source = { :git => "URL", :tag => "1.0.0" }
把 URL 設置你的 GitHub 上代碼倉庫鏈接。
提交代碼
提交并把代碼 push 到 GitHub 上。
cd ThreeRingControl/
git add .
git commit -m "initial commit"
git push
打標記
運行下面命令給倉庫打上標記,以便 Podspec 能夠匹配。
git tag 1.0.0
git push --tags
歡迎關(guān)注我的簡書,我會定期做一些技術(shù)分享:)