Tuist에서 모듈을 구성할 때 Framework와 Static Framework 중 어떤 것을 선택할지는 프로젝트의 성능, 빌드 시간, 배포 방식에 큰 영향을 미칩니다. 이 문서에서는 두 방식의 차이점과 각각의 장단점을 상세히 비교합니다.
Dynamic Framework는 런타임에 동적으로 링크되는 프레임워크입니다. 앱 실행 시 필요한 시점에 메모리로 로드됩니다.
let project = Project(
name: "MyProject",
targets: [
.target(
name: "MyFramework",
destinations: .iOS,
product: .framework, // Dynamic Framework
bundleId: "com.example.myframework",
sources: ["Sources/**"],
dependencies: []
)
]
)
Static Framework는 컴파일 타임에 앱 바이너리에 직접 포함되는 프레임워크입니다. 앱 빌드 시 모든 코드가 하나의 실행 파일에 병합됩니다.
let project = Project(
name: "MyProject",
targets: [
.target(
name: "MyStaticFramework",
destinations: .iOS,
product: .staticFramework, // Static Framework
bundleId: "com.example.mystaticframework",
sources: ["Sources/**"],
dependencies: []
)
]
)
앱 구조:
MyApp.app/
├── MyApp (실행 파일)
├── Frameworks/
│ ├── FrameworkA.framework
│ ├── FrameworkB.framework
│ └── FrameworkC.framework
└── Info.plist
앱 구조:
MyApp.app/
├── MyApp (모든 코드 포함된 단일 실행 파일)
└── Info.plist
대규모 프로젝트
빠른 개발 사이클
모듈 재사용
// 예시: 대규모 프로젝트 구성
let targets: [Target] = [
// 메인 앱
.app(name: "MainApp", dependencies: [
.target(name: "FeatureLogin"),
.target(name: "FeatureHome"),
.target(name: "FeatureSettings")
]),
// 각 기능별 Dynamic Framework
.framework(name: "FeatureLogin"),
.framework(name: "FeatureHome"),
.framework(name: "FeatureSettings"),
// 공통 모듈
.framework(name: "DesignSystem"),
.framework(name: "NetworkLayer")
]
중소규모 프로젝트
성능 최우선
단순한 배포
// 예시: 중소규모 프로젝트 구성
let targets: [Target] = [
// 메인 앱
.app(name: "SimpleApp", dependencies: [
.target(name: "CoreLogic"),
.target(name: "UIComponents")
]),
// Static Framework로 구성
.staticFramework(name: "CoreLogic"),
.staticFramework(name: "UIComponents")
]
소규모 앱 (3개 모듈):
- Static Framework: 0.8초
- Dynamic Framework: 1.2초
대규모 앱 (15개 모듈):
- Static Framework: 2.1초
- Dynamic Framework: 1.9초
전체 빌드:
- Static Framework: 45초
- Dynamic Framework: 52초
증분 빌드 (1개 모듈 수정):
- Static Framework: 35초
- Dynamic Framework: 12초
실제 프로젝트에서는 두 방식을 혼합하여 사용하는 것이 효과적입니다.
let project = Project(
name: "HybridProject",
targets: [
.app(name: "MainApp", dependencies: [
// 자주 변경되는 기능 모듈 - Dynamic
.target(name: "FeatureModules"),
// 안정적인 유틸리티 - Static
.target(name: "CoreUtilities"),
.target(name: "NetworkLayer")
]),
.framework(name: "FeatureModules"), // Dynamic
.staticFramework(name: "CoreUtilities"), // Static
.staticFramework(name: "NetworkLayer") // Static
]
)
// Before
.target(product: .framework)
// After
.target(product: .staticFramework)
// Before
.target(product: .staticFramework)
// After
.target(product: .framework)
| 기준 | Dynamic Framework | Static Framework |
|---|---|---|
| 빌드 속도 (증분) | ⭐⭐⭐⭐⭐ | ⭐⭐ |
| 앱 시작 속도 | ⭐⭐⭐ | ⭐⭐⭐⭐⭐ |
| 메모리 효율성 | ⭐⭐⭐ | ⭐⭐⭐⭐ |
| 구현 복잡도 | ⭐⭐ | ⭐⭐⭐⭐⭐ |
| 디버깅 용이성 | ⭐⭐⭐⭐ | ⭐⭐⭐ |
프로젝트의 규모, 팀 구성, 성능 요구사항을 종합적으로 고려하여 적절한 방식을 선택하거나 하이브리드 접근법을 사용하는 것이 권장됩니다.
이 문서는 Tuist 4.x 버전을 기준으로 작성되었습니다. 최신 버전에서는 일부 설정이 달라질 수 있습니다.