Release branches
If you maintain older versions on branches such as release/1.x, those branches
ship to your customers too. fremforge scans each protected release branch
with the same scanners as your default branch. Its findings are listed per
branch, and none of them is counted in your default branch’s numbers.
Which branches are scanned
A branch is scanned as a release branch when both of these hold:
- it matches one of your organisation’s protected-branch patterns (Repos ›
Branch protection defaults,
main,master,release/*by default), or one of the repository’s own branch protection rules; - it is not the repository’s default branch.
Which branch is the default is what Forgejo records for the repository, never a setting in the scan. If you rename the default branch, the new name counts as the default from the next scan, and the old name is treated as a release branch from then on, if it is still protected.
When they are scanned
- On push. A push to a release branch requests a scan of that branch. Several pushes close together give one scan of the latest commit.
- Weekly. Each release branch is rescanned at least once a week, so new advisories reach branches that nobody pushes to. A branch is scanned at once the first time it is found.
- Deleted or unprotected branches are forgotten. Deleting a branch removes its findings. A branch that no longer matches a protection pattern is removed at the next weekly pass.
Scanning a release branch costs the same runner time as scanning your default branch, per push and once a week. Release branches are not included in the daily image rescan or the weekly secret-history sweep.
Kept apart from your default branch
Release-branch findings are stored on their own. Your default branch’s numbers are unchanged: the overview, the findings lists and their counts, SLA breaches and SLA metrics, and the finding lifecycle.
- Fix-by date, no SLA metrics. Each release-branch finding shows a fix-by date from your fix-by SLA for its severity, counted from when the finding was first seen on that branch, or No SLA where the severity has none. These dates are shown for planning. They are not counted in SLA breaches, the SLA tile or any SLA metric.
- Alerts and the weekly digest list release branches in a section of their own: new and open critical and high findings per branch. The default branch’s counts in them are unchanged.
In the console
Security › Findings › All shows a branch row once a release branch has been scanned: Default branch, then one chip per release branch with its open findings. Choosing a branch lists only that branch’s findings, with a Fix by column. The type and severity filters work as usual.
Each row’s menu has:
- Dismiss on this branch: see Dismissals.
- Propose a fix PR into this branch, on a dependency finding with a fixed version: see Security fixes. While a fix is queued or its pull request is open, the row links to it instead.
Dismissals
A dismissal on a release branch applies to that branch only. It is an entry in
the same Exceptions list as every other dismissal, with
the id branch.<finding id> and the scope branch, and it names the branch.
Revoke it there, and the finding is open again. Your organisation’s exception
settings apply, including the maximum expiry.
Limitation: where dismissals require approval,
only an approver can dismiss a release-branch finding. The request-and-approve
queue does not cover release branches yet. A dismissal by someone else is refused
(403 approval-required over the API, a notice in the console) and the finding
stays open.
Security fixes
A dependency finding with a fixed version can get a security fix pull request into its release branch. Everything about the fix works as it does on your default branch, with these differences:
- The pull request targets the release branch, from its own branch
security-fix/<branch>/<package>-<version>, for examplesecurity-fix/release-1.x/lodash-4.17.21. - It fixes every open finding on that package on that branch, with the lowest version that fixes all of them.
- One live fix per package per branch. The same package on your default
branch and on
release/1.xgets two separate fixes. Your organisation’s limits count all branches together. - A pull request that the run opens against any other branch is closed, with
the reason
scope_base. - A fix counts as resolved when the release branch’s next scan no longer reports its findings.
It is never merged automatically, as on the default branch.
Pull requests into a release branch
The checks on a pull request into a release branch compare it with that branch’s last scan, not the default branch’s. A pull request is blocked only by findings it introduces. A pull request that changes only configuration is not blocked by findings already on the release branch.
API
| Call | What it does |
|---|---|
GET /orgs/{org}/security/release-branches | The scanned release branches, each with its number of open findings. |
GET /orgs/{org}/security/findings?branch=release/1.x | That branch’s findings, in the same shape as the default branch’s, plus branch and fix_by. An unknown branch is 404 unknown-branch. |
POST /orgs/{org}/security/release-findings/{id}/dismiss | Dismiss on that branch: reason, optional expires_at. |
POST /orgs/{org}/security/release-findings/{id}/autofix | Queue a security fix into that branch. The answer carries base_branch. |
curl -sS "https://frem.sh/_app/api/v1/orgs/acme/security/findings?branch=release%2F1.x" \
-H "Authorization: Bearer $FREMFORGE_TOKEN"Reads need findings:read, and dismissals and fixes need findings:write. See
the API reference for every field.
If Forgejo cannot be reached
To file a scan, fremforge must know whether the scanned branch is the default. When Forgejo cannot say, the scan is not dropped, and it is not guessed at either. It is held and filed as soon as Forgejo answers, normally within minutes. Until then, that branch’s findings show the previous scan.