swift-spm

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Swift Package Manager Skill

Swift Package Manager 技能指南

Dependency management, package creation, and distribution with Swift Package Manager.
使用Swift Package Manager进行依赖管理、包创建与分发。

Prerequisites

前置要求

  • Swift 5.5+ toolchain
  • Xcode 14+ or VS Code with Swift extension
  • Git for version control
  • Swift 5.5+ 工具链
  • Xcode 14+ 或带有Swift扩展的VS Code
  • 用于版本控制的Git

Parameters

参数

yaml
parameters:
  swift_tools_version:
    type: string
    default: "5.9"
  platforms:
    type: array
    items: [iOS, macOS, watchOS, tvOS, visionOS, linux]
    default: [iOS, macOS]
  package_type:
    type: string
    enum: [library, executable, plugin]
    default: library
yaml
parameters:
  swift_tools_version:
    type: string
    default: "5.9"
  platforms:
    type: array
    items: [iOS, macOS, watchOS, tvOS, visionOS, linux]
    default: [iOS, macOS]
  package_type:
    type: string
    enum: [library, executable, plugin]
    default: library

Topics Covered

涵盖主题

Package.swift Structure

Package.swift 结构

ElementPurpose
name
Package name
platforms
Supported platforms/versions
products
Libraries/executables exposed
dependencies
External packages
targets
Build targets
元素用途
name
包名称
platforms
支持的平台/版本
products
对外暴露的库/可执行文件
dependencies
外部依赖包
targets
构建目标

Dependency Specification

依赖声明格式

FormatExample
Version range
.upToNextMajor(from: "1.0.0")
Exact version
.exact("1.2.3")
Branch
.branch("main")
Commit
.revision("abc123")
Path
.package(path: "../LocalPkg")
格式示例
版本范围
.upToNextMajor(from: "1.0.0")
精确版本
.exact("1.2.3")
分支
.branch("main")
提交记录
.revision("abc123")
本地路径
.package(path: "../LocalPkg")

Target Types

Target类型

TypePurpose
.target
Library code
.executableTarget
Command-line tool
.testTarget
Unit tests
.plugin
Build tool plugin
.macro
Swift macro
类型用途
.target
库代码
.executableTarget
命令行工具
.testTarget
单元测试
.plugin
构建工具插件
.macro
Swift宏

Code Examples

代码示例

Complete Package.swift

完整的Package.swift示例

swift
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
    name: "NetworkKit",
    platforms: [
        .iOS(.v15),
        .macOS(.v12),
        .watchOS(.v8),
        .tvOS(.v15)
    ],
    products: [
        .library(
            name: "NetworkKit",
            targets: ["NetworkKit"]
        ),
        .library(
            name: "NetworkKitMocks",
            targets: ["NetworkKitMocks"]
        )
    ],
    dependencies: [
        .package(url: "https://github.com/apple/swift-log.git", from: "1.5.0"),
        .package(url: "https://github.com/apple/swift-collections.git", from: "1.0.0")
    ],
    targets: [
        .target(
            name: "NetworkKit",
            dependencies: [
                .product(name: "Logging", package: "swift-log"),
                .product(name: "OrderedCollections", package: "swift-collections")
            ],
            resources: [
                .process("Resources")
            ],
            swiftSettings: [
                .enableExperimentalFeature("StrictConcurrency")
            ]
        ),
        .target(
            name: "NetworkKitMocks",
            dependencies: ["NetworkKit"]
        ),
        .testTarget(
            name: "NetworkKitTests",
            dependencies: [
                "NetworkKit",
                "NetworkKitMocks"
            ],
            resources: [
                .copy("Fixtures")
            ]
        )
    ]
)
swift
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
    name: "NetworkKit",
    platforms: [
        .iOS(.v15),
        .macOS(.v12),
        .watchOS(.v8),
        .tvOS(.v15)
    ],
    products: [
        .library(
            name: "NetworkKit",
            targets: ["NetworkKit"]
        ),
        .library(
            name: "NetworkKitMocks",
            targets: ["NetworkKitMocks"]
        )
    ],
    dependencies: [
        .package(url: "https://github.com/apple/swift-log.git", from: "1.5.0"),
        .package(url: "https://github.com/apple/swift-collections.git", from: "1.0.0")
    ],
    targets: [
        .target(
            name: "NetworkKit",
            dependencies: [
                .product(name: "Logging", package: "swift-log"),
                .product(name: "OrderedCollections", package: "swift-collections")
            ],
            resources: [
                .process("Resources")
            ],
            swiftSettings: [
                .enableExperimentalFeature("StrictConcurrency")
            ]
        ),
        .target(
            name: "NetworkKitMocks",
            dependencies: ["NetworkKit"]
        ),
        .testTarget(
            name: "NetworkKitTests",
            dependencies: [
                "NetworkKit",
                "NetworkKitMocks"
            ],
            resources: [
                .copy("Fixtures")
            ]
        )
    ]
)

Library with Multiple Targets

多Target库示例

swift
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
    name: "FeatureKit",
    platforms: [.iOS(.v16), .macOS(.v13)],
    products: [
        // Main library
        .library(name: "FeatureKit", targets: ["FeatureKit"]),
        // Individual features for selective import
        .library(name: "AuthFeature", targets: ["AuthFeature"]),
        .library(name: "ProfileFeature", targets: ["ProfileFeature"])
    ],
    dependencies: [
        .package(url: "https://github.com/pointfreeco/swift-composable-architecture", from: "1.0.0")
    ],
    targets: [
        // Core shared code
        .target(
            name: "Core",
            dependencies: []
        ),

        // Auth feature
        .target(
            name: "AuthFeature",
            dependencies: [
                "Core",
                .product(name: "ComposableArchitecture", package: "swift-composable-architecture")
            ]
        ),

        // Profile feature
        .target(
            name: "ProfileFeature",
            dependencies: [
                "Core",
                .product(name: "ComposableArchitecture", package: "swift-composable-architecture")
            ]
        ),

        // Umbrella target
        .target(
            name: "FeatureKit",
            dependencies: ["AuthFeature", "ProfileFeature"]
        ),

        // Tests
        .testTarget(
            name: "AuthFeatureTests",
            dependencies: ["AuthFeature"]
        ),
        .testTarget(
            name: "ProfileFeatureTests",
            dependencies: ["ProfileFeature"]
        )
    ]
)
swift
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
    name: "FeatureKit",
    platforms: [.iOS(.v16), .macOS(.v13)],
    products: [
        // 主库
        .library(name: "FeatureKit", targets: ["FeatureKit"]),
        // 可单独导入的独立功能模块
        .library(name: "AuthFeature", targets: ["AuthFeature"]),
        .library(name: "ProfileFeature", targets: ["ProfileFeature"])
    ],
    dependencies: [
        .package(url: "https://github.com/pointfreeco/swift-composable-architecture", from: "1.0.0")
    ],
    targets: [
        // 核心共享代码
        .target(
            name: "Core",
            dependencies: []
        ),

        // 认证功能
        .target(
            name: "AuthFeature",
            dependencies: [
                "Core",
                .product(name: "ComposableArchitecture", package: "swift-composable-architecture")
            ]
        ),

        // 个人资料功能
        .target(
            name: "ProfileFeature",
            dependencies: [
                "Core",
                .product(name: "ComposableArchitecture", package: "swift-composable-architecture")
            ]
        ),

        // 聚合Target
        .target(
            name: "FeatureKit",
            dependencies: ["AuthFeature", "ProfileFeature"]
        ),

        // 测试用例
        .testTarget(
            name: "AuthFeatureTests",
            dependencies: ["AuthFeature"]
        ),
        .testTarget(
            name: "ProfileFeatureTests",
            dependencies: ["ProfileFeature"]
        )
    ]
)

Command-Line Tool

命令行工具示例

swift
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
    name: "swift-format-tool",
    platforms: [.macOS(.v13)],
    products: [
        .executable(name: "swift-format-tool", targets: ["swift-format-tool"])
    ],
    dependencies: [
        .package(url: "https://github.com/apple/swift-argument-parser", from: "1.2.0"),
        .package(url: "https://github.com/apple/swift-syntax", from: "509.0.0")
    ],
    targets: [
        .executableTarget(
            name: "swift-format-tool",
            dependencies: [
                .product(name: "ArgumentParser", package: "swift-argument-parser"),
                .product(name: "SwiftSyntax", package: "swift-syntax"),
                .product(name: "SwiftParser", package: "swift-syntax")
            ]
        )
    ]
)
swift
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
    name: "swift-format-tool",
    platforms: [.macOS(.v13)],
    products: [
        .executable(name: "swift-format-tool", targets: ["swift-format-tool"])
    ],
    dependencies: [
        .package(url: "https://github.com/apple/swift-argument-parser", from: "1.2.0"),
        .package(url: "https://github.com/apple/swift-syntax", from: "509.0.0")
    ],
    targets: [
        .executableTarget(
            name: "swift-format-tool",
            dependencies: [
                .product(name: "ArgumentParser", package: "swift-argument-parser"),
                .product(name: "SwiftSyntax", package: "swift-syntax"),
                .product(name: "SwiftParser", package: "swift-syntax")
            ]
        )
    ]
)

Local Development Package

本地开发包示例

swift
// In your app's Package.swift or Xcode project
// Use local path during development

// Package.swift with local override
let package = Package(
    name: "MyApp",
    dependencies: [
        // Production: Use remote
        // .package(url: "https://github.com/company/SharedKit", from: "1.0.0")

        // Development: Use local
        .package(path: "../SharedKit")
    ],
    targets: [
        .target(name: "MyApp", dependencies: ["SharedKit"])
    ]
)
swift
// 在你的应用Package.swift或Xcode项目中
// 开发阶段使用本地路径

// 带有本地依赖的Package.swift
let package = Package(
    name: "MyApp",
    dependencies: [
        // 生产环境:使用远程依赖
        // .package(url: "https://github.com/company/SharedKit", from: "1.0.0")

        // 开发环境:使用本地路径
        .package(path: "../SharedKit")
    ],
    targets: [
        .target(name: "MyApp", dependencies: ["SharedKit"])
    ]
)

Swift Macro Package

Swift Macro包示例

swift
// swift-tools-version: 5.9
import PackageDescription
import CompilerPluginSupport

let package = Package(
    name: "MacroKit",
    platforms: [.macOS(.v10_15), .iOS(.v13)],
    products: [
        .library(name: "MacroKit", targets: ["MacroKit"])
    ],
    dependencies: [
        .package(url: "https://github.com/apple/swift-syntax", from: "509.0.0")
    ],
    targets: [
        // Macro implementation
        .macro(
            name: "MacroKitMacros",
            dependencies: [
                .product(name: "SwiftSyntaxMacros", package: "swift-syntax"),
                .product(name: "SwiftCompilerPlugin", package: "swift-syntax")
            ]
        ),

        // Library that exposes the macro
        .target(
            name: "MacroKit",
            dependencies: ["MacroKitMacros"]
        ),

        // Tests for the macro
        .testTarget(
            name: "MacroKitTests",
            dependencies: [
                "MacroKitMacros",
                .product(name: "SwiftSyntaxMacrosTestSupport", package: "swift-syntax")
            ]
        )
    ]
)
swift
// swift-tools-version: 5.9
import PackageDescription
import CompilerPluginSupport

let package = Package(
    name: "MacroKit",
    platforms: [.macOS(.v10_15), .iOS(.v13)],
    products: [
        .library(name: "MacroKit", targets: ["MacroKit"])
    ],
    dependencies: [
        .package(url: "https://github.com/apple/swift-syntax", from: "509.0.0")
    ],
    targets: [
        // 宏实现
        .macro(
            name: "MacroKitMacros",
            dependencies: [
                .product(name: "SwiftSyntaxMacros", package: "swift-syntax"),
                .product(name: "SwiftCompilerPlugin", package: "swift-syntax")
            ]
        ),

        // 对外暴露宏的库
        .target(
            name: "MacroKit",
            dependencies: ["MacroKitMacros"]
        ),

        // 宏测试用例
        .testTarget(
            name: "MacroKitTests",
            dependencies: [
                "MacroKitMacros",
                .product(name: "SwiftSyntaxMacrosTestSupport", package: "swift-syntax")
            ]
        )
    ]
)

CLI Commands

CLI命令

bash
undefined
bash
undefined

Create new package

创建新包

swift package init --type library swift package init --type executable swift package init --type macro
swift package init --type library swift package init --type executable swift package init --type macro

Build

构建

swift build swift build -c release
swift build swift build -c release

Test

测试

swift test swift test --filter MyTests
swift test swift test --filter MyTests

Update dependencies

更新依赖

swift package update swift package update PackageName
swift package update swift package update PackageName

Resolve dependencies

解析依赖

swift package resolve
swift package resolve

Show dependencies

查看依赖

swift package show-dependencies swift package show-dependencies --format json
swift package show-dependencies swift package show-dependencies --format json

Generate Xcode project (deprecated but useful)

生成Xcode项目(已废弃但仍有用)

swift package generate-xcodeproj
swift package generate-xcodeproj

Clean

清理

swift package clean swift package reset
swift package clean swift package reset

Dump package description

导出包描述

swift package dump-package
undefined
swift package dump-package
undefined

Troubleshooting

问题排查

Common Issues

常见问题

IssueCauseSolution
"No such module"Missing dependencyAdd to target dependencies
Version conflictIncompatible requirementsUse version that satisfies all
Build fails on CIDifferent Swift versionPin swift-tools-version
Resources not foundWrong resource ruleUse .process or .copy correctly
Xcode not seeing changesCache staleClean derived data
问题原因解决方案
"No such module"(找不到模块)缺少依赖添加到Target依赖中
版本冲突依赖版本不兼容使用满足所有要求的版本
CI环境构建失败Swift版本不一致固定swift-tools-version
资源找不到资源规则错误正确使用.process或.copy
Xcode不识别更改缓存过期清理Derived Data

Debug Tips

调试技巧

bash
undefined
bash
undefined

Verbose build

详细构建日志

swift build -v
swift build -v

Check resolved versions

查看已解析的版本

cat Package.resolved
cat Package.resolved

Dependency tree

依赖树可视化

swift package show-dependencies --format dot | dot -Tpng -o deps.png
swift package show-dependencies --format dot | dot -Tpng -o deps.png

Rebuild from scratch

从头重新构建

rm -rf .build Package.resolved swift package resolve swift build
undefined
rm -rf .build Package.resolved swift package resolve swift build
undefined

Validation Rules

验证规则

yaml
validation:
  - rule: pin_versions
    severity: warning
    check: Use version ranges, not branch/revision in production
  - rule: semantic_versioning
    severity: error
    check: Follow semver for your packages
  - rule: platform_support
    severity: info
    check: Declare minimum platform versions
yaml
validation:
  - rule: pin_versions
    severity: warning
    check: Use version ranges, not branch/revision in production
  - rule: semantic_versioning
    severity: error
    check: Follow semver for your packages
  - rule: platform_support
    severity: info
    check: Declare minimum platform versions

Usage

使用方法

Skill("swift-spm")
Skill("swift-spm")

Related Skills

相关技能

  • swift-fundamentals
    - Language basics
  • swift-testing
    - Package testing
  • swift-architecture
    - Package design
  • swift-fundamentals
    - 语言基础
  • swift-testing
    - 包测试
  • swift-architecture
    - 包设计