合成檔案
Tuist 可以在生成時產生檔案和程式碼,讓管理和使用 Xcode 專案更方便。本頁將介紹此功能,以及如何在你的專案中使用。
目標資源#
Xcode 專案支援向目標加入資源。不過,這會為團隊帶來一些挑戰,特別是在處理模組化專案時,因為來源與資源經常被移動:
- 執行階段存取不一致:資源在最終產品中的位置及存取方式取決於目標產品類型。例如,如果你的目標代表應用程式,資源會被複製到應用程式套件中。這會導致存取資源的程式碼對套件結構作出假設,並不理想,因為這令程式碼更難理解,亦令資源難以移動。
- 不支援資源的產品:某些產品(例如靜態函式庫)並非套件,因此不支援資源。為此,你必須改用其他產品類型(例如框架),但這可能為你的專案或應用程式帶來額外負擔。例如,靜態框架會以靜態方式連結至最終產品,並需要一個建置階段來只將資源複製到最終產品。或者使用動態框架,Xcode 會將二進位檔和資源都複製到最終產品,但由於框架需要動態載入,會增加應用程式的啟動時間。
- 容易出現執行階段錯誤:資源透過名稱和副檔名(字串)來識別。因此,任何拼寫錯誤都會在嘗試存取資源時導致執行階段錯誤。這並不理想,因為編譯時期無法偵測到,可能在發行版本中引發崩潰。
Tuist 透過合成統一介面來存取套件和資源,抽象化實作細節,從而解決上述問題。
雖然並非必須透過 Tuist 合成的介面來存取資源,但我們建議這樣做,因為這令程式碼更易理解,亦令資源更易移動。
資源#
Tuist 提供介面,讓你在 Swift 中宣告如 Info.plist 或權限等檔案的內容。這有助於確保跨目標和專案的一致性,並利用編譯器在編譯時期捕捉問題。你也可以建立自己的抽象層來建模內容,並在目標和專案之間共用。
當你的專案生成時,Tuist 會合成這些檔案的內容,並將它們寫入相對於定義它們的專案目錄的 Derived 目錄中。
我們建議將 Derived 目錄加入你專案的 .gitignore 檔案中。
套件存取器#
Tuist 會合成一個介面,用以存取包含目標資源的套件。
Swift#
目標會包含一個 Bundle 類型的擴充功能,用於公開套件:
let bundle = Bundle.module
Objective-C#
在 Objective-C 中,你會獲得一個 {Target}Resources 介面來存取套件:
NSBundle *bundle = [MyFeatureResources bundle];
目前,Tuist 不會為僅包含 Objective-C 來源的內部目標生成資源套件存取器。這是已知限制,可在 issue #6456 中追蹤。
如果目標產品(例如函式庫)不支援資源,Tuist 會將資源包含在產品類型為 bundle 的目標中,確保其出現在最終產品中,且介面指向正確的套件。這些合成的套件會自動標記為 tuist:synthesized,並繼承其父目標的所有標籤,讓你能在 快取設定檔中針對它們。
資源存取器#
資源透過名稱和副檔名(字串)來識別。這並不理想,因為編譯時期無法偵測到,可能在發行版本中引發崩潰。為防止此情況,Tuist 將 SwiftGen 整合到專案生成過程中,以合成存取資源的介面。藉此,你可以放心地存取資源,並利用編譯器捕捉任何問題。
Tuist 預設包含 範本,用於為以下資源類型合成存取器:
| 資源類型 | 合成檔案 |
|---|---|
| 圖片和顏色 | Assets+{Target}.swift |
| 字串 | Strings+{Target}.swift |
| Plist | {NameOfPlist}.swift |
| 字型 | Fonts+{Target}.swift |
| 檔案 | Files+{Target}.swift |
注意:你可以透過將
disableSynthesizedResourceAccessors選項傳遞給專案選項,以每個專案為基礎停用資源存取器的生成功能。
自訂範本#
如果你想提供自己的範本來為其他資源類型合成存取器(必須由 SwiftGen 支援),你可以在 Tuist/ResourceSynthesizers/{name}.stencil 建立它們,其中名稱是資源的駝峰式大小寫版本。
| 資源 | 範本名稱 |
|---|---|
| 字串 | Strings.stencil |
| 資產 | Assets.stencil |
| Plist | Plists.stencil |
| 字型 | Fonts.stencil |
| CoreData | CoreData.stencil |
| InterfaceBuilder | InterfaceBuilder.stencil |
| JSON | JSON.stencil |
| YAML | YAML.stencil |
| 檔案 | Files.stencil |
如果你想設定要為哪些資源類型合成存取器,可以使用 Project.resourceSynthesizers 屬性,並傳入你想使用的資源合成器清單:
let project = Project(resourceSynthesizers: [.string(), .fonts()])
你可以查看 此範例,了解如何使用自訂範本來合成資源存取器。