SwiftPM and Library Unit Testing

CocoaPods has test specs that provide the specifications for CocoaPods to create an Xcode target for building and running unit tests. How would you do something comparable in SwiftPM?

When you initialize a package from scratch, it includes a sample test:

mkdir Sample
cd Sample
swift package init

See the resulting Package.swift and Tests directory for the relevant code.

Run the all tests in one go like this:

swift test

(See swift test --help for more fine‐grained options.)

If you want work with the package—including tests—in Xcode, generate an Xcode project:

swift package generate-xcodeproj
open *.xcodeproj

(These instructions are for the current stable releases. Available Xcode Betas introduce new kinds of integration with SwiftPM from the Xcode side.)


Both of these approaches seem to run the tests on macOS only, even if I add platforms: [ .iOS(.v9) ], to Package.swift.

Is there a way to test on iOS targets using swift test and/or swift package generate-xcodeproj?

While SPM is now supported for dependency management for iOS, it still does not support defining or creating iOS projects.

1 Like

Yes. See here:

Those instructions are for Xcode 10. I think Xcode 11 can infer more of the arguments on its own now, but I cannot remember which off the top of my head.

1 Like

It has indirectly supported frameworks for iOS for a long time through generate-xcodeproj. The iOS‐related portions of the generated Xcode project have been in working condition since at least Swift 4.0.

Two important things it cannot do are (a) directly cross‐compile without outside help such as Xcode and (b) specify resources, or by extension application bundles. But these are nothing specific to iOS.

Technically what it doesn’t support yet is declaring a project to be limited to any specific platform. You cannot make an iOS project, because what you end up with is a cross‐platform macOS‐Linux‐iOS‐watchOS‐tvOS‐Android‐Windows project, though it may contain code that doesn’t actually compile successfully for all of them.


That's a fair correction to my over simplification!