Skip to content

Commit 369a621

Browse files
bkhouriFranzBusch
authored andcommitted
Add documentation for the Soundness API breakage check
Add docs/soundness-api-breakage-check.md describing the `api-breakage-check` job in the Soundness workflow, alongside the existing docs-check documentation. The document covers: - How the job works: checkout settings, baseline selection (explicit baseline or the PR base branch), and how the allowlist and additional tool arguments are passed to `swift package diagnose-api-breaking-changes` - Requirements, including the need for a `pull_request` trigger unless `api_breakage_check_baseline` is set - A reference table of the `api_breakage_check_*` inputs - Common scenarios: release-tag baseline, allowlist, additional tool arguments, custom container image, and disabling the check - Troubleshooting for common failures
1 parent f2b93cf commit 369a621

1 file changed

Lines changed: 125 additions & 0 deletions

File tree

Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
# API Breakage Check
2+
3+
The Soundness workflow can verify that a change to your Swift package does not introduce source-breaking changes to its public API. The **`api-breakage-check`** job runs on Linux, is enabled by default, and wraps [`swift package diagnose-api-breaking-changes`](https://github.com/swiftlang/swift-package-manager).
4+
5+
The job fails when the command reports API breakages that are not covered by an allowlist.
6+
7+
## How it works
8+
9+
1. Checks out the repository with full history, tags, and submodules (`fetch-depth: 0`, `fetch-tags: true`). Credentials are persisted because `diagnose-api-breaking-changes` clones the repository again, which would otherwise fail for private repositories.
10+
2. Marks the workspace as a safe git directory.
11+
3. Runs `linux_pre_build_command`, if provided.
12+
4. Determines the **baseline** to compare against:
13+
- if `api_breakage_check_baseline` is set, that tag or ref is used;
14+
- otherwise the pull request's base branch (`GITHUB_BASE_REF`) is fetched into a local `pull-base-ref` ref and used.
15+
5. Runs `swift package diagnose-api-breaking-changes <baseline>`, adding `--breakage-allowlist-path <path>` when `api_breakage_check_allowlist_path` is set, followed by any `api_breakage_check_additional_tool_arguments`.
16+
17+
The job has a 40 minute timeout.
18+
19+
## Requirements
20+
21+
1. **A SwiftPM package** with a `Package.swift` at the repository root.
22+
2. **At least one library product** whose public API can be compared.
23+
3. **A `pull_request` trigger**, unless you set `api_breakage_check_baseline`. The default baseline relies on `GITHUB_BASE_REF`, which GitHub only sets for pull request events.
24+
25+
## Enabling the check
26+
27+
The check is on by default, so calling the Soundness workflow is enough:
28+
29+
```yaml
30+
name: Pull request
31+
32+
on:
33+
pull_request:
34+
branches: [main]
35+
36+
jobs:
37+
soundness:
38+
name: Soundness
39+
uses: swiftlang/github-workflows/.github/workflows/soundness.yml@main
40+
```
41+
42+
## Configuration
43+
44+
| Input | Type | Default | Description |
45+
|---|---|---|---|
46+
| `api_breakage_check_enabled` | boolean | `true` | Enable or disable the job. |
47+
| `api_breakage_check_allowlist_path` | string | `""` | Path to a file passed as `--breakage-allowlist-path`. Relative paths are resolved from the repository root. |
48+
| `api_breakage_check_baseline` | string | `""` | Tag or ref to compare against. When empty, the pull request's base branch is used. |
49+
| `api_breakage_check_container_image` | string | `swift:6.3-noble` | Docker image used to run the check. |
50+
| `api_breakage_check_additional_tool_arguments` | string | `""` | Extra arguments appended to the `swift package diagnose-api-breaking-changes` invocation. |
51+
| `linux_pre_build_command` | string | `""` | Shell command to run before the check (e.g., installing system dependencies). Shared with other Soundness jobs. |
52+
53+
## Common scenarios
54+
55+
### Compare against a release tag
56+
57+
Useful for catching breakages relative to the last release rather than the PR base:
58+
59+
```yaml
60+
jobs:
61+
soundness:
62+
uses: swiftlang/github-workflows/.github/workflows/soundness.yml@main
63+
with:
64+
api_breakage_check_baseline: "1.2.0"
65+
```
66+
67+
### Allow known breakages
68+
69+
Create an allowlist file listing the breakages you intend to accept (one per line, in the format emitted by the tool) and point the job at it:
70+
71+
```yaml
72+
jobs:
73+
soundness:
74+
uses: swiftlang/github-workflows/.github/workflows/soundness.yml@main
75+
with:
76+
api_breakage_check_allowlist_path: ".github/api-breakage-allowlist.txt"
77+
```
78+
79+
### Pass additional arguments to the tool
80+
81+
Arguments are appended verbatim, so any flag supported by `swift package diagnose-api-breaking-changes` can be used. For example, to check only specific products:
82+
83+
```yaml
84+
jobs:
85+
soundness:
86+
uses: swiftlang/github-workflows/.github/workflows/soundness.yml@main
87+
with:
88+
api_breakage_check_additional_tool_arguments: "--products MyLibrary"
89+
```
90+
91+
The value is word-split by the shell, so it cannot contain arguments with embedded spaces.
92+
93+
### Use a different Swift toolchain or install dependencies
94+
95+
```yaml
96+
jobs:
97+
soundness:
98+
uses: swiftlang/github-workflows/.github/workflows/soundness.yml@main
99+
with:
100+
api_breakage_check_container_image: "swift:nightly-noble"
101+
linux_pre_build_command: "apt-get update && apt-get install -y libxml2-dev"
102+
```
103+
104+
### Disable the check
105+
106+
Packages that expose no public API (for example, executables only) can turn the job off:
107+
108+
```yaml
109+
jobs:
110+
soundness:
111+
uses: swiftlang/github-workflows/.github/workflows/soundness.yml@main
112+
with:
113+
api_breakage_check_enabled: false
114+
```
115+
116+
## Troubleshooting
117+
118+
| Symptom | Likely cause |
119+
|---|---|
120+
| `git fetch` fails with an empty ref name, or the baseline cannot be resolved. | The workflow was not triggered by a `pull_request` event, so `GITHUB_BASE_REF` is empty. Set `api_breakage_check_baseline` or trigger the workflow on `pull_request`. |
121+
| The baseline tag is not found. | The tag does not exist in the repository. Tags are fetched by the checkout step, so confirm the name matches exactly. |
122+
| Job fails on a breakage you intend to make. | Add the reported breakage to the allowlist file referenced by `api_breakage_check_allowlist_path`. |
123+
| Allowlist file is not found. | The path is resolved from the repository root, not from the workflow file's location. |
124+
| Build fails before the comparison runs. | A system dependency is missing. Install it with `linux_pre_build_command`. |
125+
| Job fails to clone the repository (private repositories). | The checkout step must persist credentials. The workflow already does this, so check that the calling workflow grants `contents: read`. |

0 commit comments

Comments
 (0)