迁移Xcode项目至Tuist时如何实现iOS与watchOS共享框架
Tuist 跨iOS/watchOS共享框架实现方案
1. 先调整项目目录结构
把所有跨端复用的代码从原有主App、Watch App、扩展组件的目录里抽离,单独放在独立的共享模块目录下,避免和平台特定代码混放,推荐结构如下:
项目根目录/ ├── Projects/ │ ├── MainApp/ # iOS主应用代码 │ ├── WatchApp/ # watchOS App、通知扩展代码 │ └── Shared/ # 跨平台共享代码 │ ├── Sources/ │ └── Resources/ ├── Tuist/ └── Project.swift
2. 定义多平台共享Target
在根目录的Project.swift里声明共享框架的Target,核心是用多平台配置让Tuist自动为iOS、watchOS分别编译适配的产物,示例配置:
import ProjectDescription let sharedKit = Target( name: "SharedKit", platform: .multiplatform, product: .framework, bundleId: "com.你的域名.sharedkit", infoPlist: .default, sources: ["Projects/Shared/Sources/**/*.swift"], resources: "Projects/Shared/Resources/**", deploymentTargets: .multiplatform( iOS: "16.0", // 和主App最低支持版本对齐 watchOS: "9.0" // 和Watch端最低支持版本对齐 ), dependencies: [ // 这里放跨平台通用的第三方依赖 ] )
如果共享代码里有平台差异逻辑,直接用系统条件编译宏包裹即可,不需要额外配置Tuist:
#if os(iOS) import UIKit // iOS特有的实现逻辑 #elseif os(watchOS) import WatchKit // watchOS特有的实现逻辑 #endif
3. 处理平台特定依赖
如果共享代码需要依赖iOS独有的能力(比如HealthKit的部分iOS专属接口、UIKit)或者watchOS独有的能力,不要全局引入对应依赖,通过条件依赖配置关联:
// 共享Target的dependencies段补充 dependencies: [ // 通用依赖正常写 .target( name: "SharedIOSpecific", condition: .when(platforms: [.iOS]) // 仅iOS平台链接该模块 ), .target( name: "SharedWatchSpecific", condition: .when(platforms: [.watchOS]) // 仅watchOS平台链接该模块 ) ]
如果平台特定代码量很少,不需要单独拆子模块,直接在代码里用条件编译导入对应系统库即可。
4. 给各业务模块关联共享框架
主iOS应用、Watch App、通知扩展三个Target,直接在各自的dependencies里声明对共享框架的依赖即可,Tuist会自动根据当前Target的平台,链接对应架构的共享框架产物,不需要做额外的平台判断:
let mainApp = Target( name: "MainApp", platform: .iOS, product: .app, bundleId: "com.你的域名.mainapp", infoPlist: .extendingDefault(with: [:]), sources: ["Projects/MainApp/Sources/**"], resources: ["Projects/MainApp/Resources/**"], dependencies: [ .target(name: "SharedKit") ] ) let watchApp = Target( name: "WatchApp", platform: .watchOS, product: .watch2App, bundleId: "com.你的域名.watchapp", infoPlist: .default, sources: ["Projects/WatchApp/App/**"], resources: ["Projects/WatchApp/Resources/**"], dependencies: [ .target(name: "WatchExtension"), .target(name: "SharedKit") ] ) let watchNotificationExt = Target( name: "WatchNotificationExt", platform: .watchOS, product: .watch2Extension, bundleId: "com.你的域名.watchapp.notification", infoPlist: .default, sources: ["Projects/WatchApp/NotificationExt/**"], dependencies: [ .target(name: "SharedKit") ] )
最后把所有Target组装到Project里,执行tuist generate就能生成可直接编译的工程。
迁移避坑
- 共享框架不要配置成
.staticFramework,watchOS对静态库嵌入限制很多,用动态.framework兼容性最好 - 共享框架的bundleId前缀要和主App、Watch App保持一致,避免签名报错
- 迁移按优先级逐步搬:先迁无平台依赖的通用代码(模型定义、工具类、通用网络封装),再迁带平台差异的代码,不要一次性全量移动
- 迁完记得删除原有各Target里重复的共享代码引用,避免编译时符号冲突
内容的提问来源于stack exchange,提问作者datinc
相关产品推荐
相关产品推荐

