マルチモジュールマスターになろう。
開発環境
> xcodebuild -version Xcode 14.1 Build version 14B47b
モチベーション
マルチモジュールなアプリに対して日々追加開発を行っているが、自分でマルチモジュール化したわけではないのでマルチモジュールの理解が乏しい。理解したい!
マルチモジュール化のやり方
マルチモジュールといっても、構成の手段にはいくつかのバリエーションが見受けられた。
- Embedded Frameworkを利用するやり方
- Swift Packageを利用するやり方
今回はEmbedded Frameworkを利用したマルチモジュールなアプリを構成してみた。
つくったもの
以下気になったところのメモ。
Frameworkを作成すると同名のModuleも作成される
Framework内に定義したSwiftコードはそのFrameworkをEmbedしたProject内で import {Framework名}
を宣言すれば利用できるため、Frameworkを作成すると同名のModuleも作成される、という理解。
Frameworkを追加して、
Framework内のSwiftコードに構造体を書いて、
public struct Dog { public init() {} public func bark() { print("ワオーン") } }
Project内でFrameworkのコードを利用する。
import FeatureDog import UIKit final class ViewController: UIViewController { override func viewDidLoad() { super.viewDidLoad() let dog = Dog() dog.bark() // "ワオーン" } }
Moduleの意味合いはimportできる単位のため、FeatureDog
Moduleが存在することが分かる。
import FeatureDog import UIKit final class ViewController: UIViewController { override func viewDidLoad() { super.viewDidLoad() let dog = FeatureDog.Dog() dog.bark() // "ワオーン" let originalDog = Dog() originalDog.bark() // "waoooooonn" } } struct Dog { func bark() { print("waoooooonn") } }
Framework追加時にEmbedしないとどうなるか
Framework追加時にEmbedしないと、Frameworkが "Frameworks, Libraries, and Embedded Content" に存在しない。この状態だとFramework内のSwiftコードがアプリ側で利用できない。赤枠内左下の「+」から追加すれば使えるようになる。
差分ビルドでアプリのビルド時間の削減
FrameworkがEmbedされたアプリをビルドするときに、EmbedしたFrameworkに変更がなければFramework自体はビルドされない。変更があればビルドされる。(正確な説明は"Frameworkが持つSwiftコードがコンパイルされない/される")コードの責務分割の観点でのマルチモジュールの良さは書いていて掴めていたが、ビルド時間削減の観点でもメリットがあることが分かって良い。
おわりに
本記事でマルチモジュールを知っていく第一歩を踏み出した。記事を書き始めた当初は「マルチモジュール?モジュールどこから来た?」と疑問だったが、Framework自体が同名のModuleを持つため、複数のFrameworkを持つ==複数のModuleを持つ→マルチモジュール、という意味合いだろうと理解した。とはいえ、まだ理解していない項目が多く、Swift Packageを使ったマルチモジュール化やXCFrameworkなども今後身につけていく。
参考
- Sansan iOS アプリのマルチモジュール化推進方法 - Sansan Tech Blog
- 記事内で参考されている記事も参考
- 大規模なマルチモジュール開発をSwiftPackageに移行して運用してみた - Timee Product Team Blog
- Swift Package中心のプロジェクト構成とその実践 by Daiki Matsudate | トーク | iOSDC Japan 2021 #iosdc - fortee.jp
- https://developer.apple.com/library/archive/documentation/General/Conceptual/DevPedia-CocoaCore/Framework.html