Adding test target to Swift Package (--type executable)

👋 Hi, I'm Javal Nanda, a Mobile Application Developer based in India. I've been in the world of mobile app development since 2010, and this blog is my space to share experiences and thoughts.
Search for a command to run...

👋 Hi, I'm Javal Nanda, a Mobile Application Developer based in India. I've been in the world of mobile app development since 2010, and this blog is my space to share experiences and thoughts.
Having a genuine trader to guide you on your investment is the best decision to make, if you're looking for a genuine trader to guide you on your investment look no further than adelynn_richardson.fx at lñstagràm I'm making a huge profits through her mentorship
We often need to modify the SwiftUI view in some way or the other. There are three ways in which we can achieve customization of the SwiftUI View: View Extensions ViewModifiers Custom Views We can almost produce the same results with the above a...

One of the main rules for writing clean code is that it should clearly show what it's meant to do. There are a few things to keep in mind when doing this. It means giving variables and function names that make sense, making sure each part of the code...

Pull requests are the standard way to request a change to be merged into the main or stable branch. Having fellow developers or maintainers review the change is crucial to ensure its quality, although exceptions may apply for teams using pair program...

Ideally, you would not require conditional logic in your production code to check if tests are running or the main app target is running. But, there are situations where you can't get around it in case of Integration tests or UI Tests. There are vari...

If you have used SPM to create the command line application before Swift 5.9.0, the project structure used to be as follows:
Package.swift
README.md
.gitignore
Sources/
Sources/SamplePackage/main.swift
Tests/
Tests/LinuxMain.swift
Tests/SamplePackageTests/
Tests/SamplePackageTests/SamplePackageTests.swift
Tests/SamplePackageTests/XCTestManifests.swift
The test target and the basic scaffolding for it were available on the package creation.
With the recent changes to simplify the templating of the package --type , test target is only added to the package --type library and not to --type tool and --type executable.
tool is the newly added type that creates the package of type executable with the dependency for SwiftArgumentParser already added to the package.
The new file structure looks as follows:
// --type executable
./executable
./executable/.gitignore
./executable/Package.swift
./executable/Sources
./executable/Sources/executable.swift
// --type tool
./tool
./tool/.gitignore
./tool/Package.swift
./tool/Sources
./tool/Sources/tool.swift
// --type empty
./empty
./empty/Package.swift
// --type library
./library
./library/Tests
./library/Tests/libraryTests
./library/Tests/libraryTests/libraryTests.swift
./library/.gitignore
./library/Package.swift
./library/Sources
./library/Sources/library
./library/Sources/library/library.swift
You can find more details about the change in this PR.
Now, if you want to add the test target to the package of --type tool or --type executable with newer tool-chain of Swift 5.9.0, you can follow these steps:
Create the package:
$ mkdir SamplePackage
$ cd SamplePackage
$ swift package init --type executable
Creating executable package: SamplePackage
Creating Package.swift
Creating .gitignore
Creating Sources/
Creating Sources/main.swift
Open Package.swift. It should look like this:
// swift-tools-version: 5.9
// The swift-tools-version declares the minimum version of Swift required to build this package.
import PackageDescription
let package = Package(
name: "SamplePackage",
targets: [
// Targets are the basic building blocks of a package, defining a module or a test suite.
// Targets can depend on other targets in this package and products from dependencies.
.executableTarget(
name: "SamplePackage"),
]
)
Update Package.swift as below:
// swift-tools-version: 5.9
// The swift-tools-version declares the minimum version of Swift required to build this package.
import PackageDescription
let package = Package(
name: "SamplePackage",
targets: [
// Targets are the basic building blocks of a package, defining a module or a test suite.
// Targets can depend on other targets in this package and products from dependencies.
.executableTarget(
name: "SamplePackage",
path: "Sources"
),
.testTarget(
name: "SamplePackageTests",
dependencies: ["SamplePackage"],
path: "Tests"
)
]
)
Add .testTarget to the array of targets and add the main target SamplePackage to its dependencies list. Also, add the path to the Tests folder.
Add a sample test file with @testable import <main module> to validate that the tests can resolve the main module.
Example test file:
import XCTest
@testable import SamplePackage
class ExampleTests: XCTestCase {
func testExample() {
}
}
The updated file structure should look as below:
SamplePackage
SamplePackage/.gitignore
SamplePackage/Package.swift
SamplePackage/Sources
SamplePackage/Sources/main.swift
SamplePackage/Tests/ExampleTests.swift
Validate if tests are running successfully via Xcode ⌘ + U and via the command line swift test
Let me know if you found this helpful. Feel free to tweet me on Twitter if you have any additional tips or feedback.
Thanks.