Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions .github/ISSUE_TEMPLATE/bug_report.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,9 @@ body:
- type: input
id: version
attributes:
label: aurtomator version or commit SHA
description: Tagged release or short SHA of the commit you are running.
placeholder: "v0.2.2 or abc1234"
label: aurtomator version
description: "The version your calling workflows pin, from the `# vX.Y.Z` comment after the SHA."
placeholder: "v0.8.0"
validations:
required: true

Expand All @@ -37,7 +37,7 @@ body:
attributes:
label: Workflow run URL
description: If this is a CI-related bug, link to the failing workflow run.
placeholder: "https://github.com/<you>/<fork>/actions/runs/1234567890"
placeholder: "https://github.com/<you>/<repository>/actions/runs/1234567890"

- type: input
id: strategy
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/check-updates.yml
Original file line number Diff line number Diff line change
Expand Up @@ -617,7 +617,7 @@ jobs:
[[ -d "$STATUS_DIR" ]] || exit 0

# gh issue list fails in a repository with Issues turned off. A
# fork like that gets a notice, and any other failure of the
# repository like that gets a notice, and any other failure of the
# list still fails the step.
if grep -qsE '^(check_failed|update_failed|held|newer):' "$STATUS_DIR"/* || [[ -s "$STATUS_DIR/_alerts" ]]; then
has_issues=$(gh api "repos/$GITHUB_REPOSITORY" --jq .has_issues)
Expand Down
6 changes: 4 additions & 2 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# Contributing to aurtomator

aurtomator is a template repository: you fork it and run your own instance. Upstream contributions are welcome and optional.
aurtomator holds the scripts, the strategies and the reusable workflows. A user repository, created from the template [staticwire/aurtomator-seed](https://github.com/staticwire/aurtomator-seed), holds the package YAMLs and calls the workflows of aurtomator at a pinned SHA, see [docs/SETUP.md](docs/SETUP.md#the-calling-workflows). A run takes the scripts and the strategies from aurtomator at that SHA, so a fix or a new strategy comes here by pull request.

## Before opening a PR

Expand Down Expand Up @@ -44,6 +44,8 @@ bats tests/ --recursive

CI runs the suite under bashcov, as `bashcov -- tests/helpers/bashcov-bats.sh tests/ --recursive`. bashcov passes `errexit`, `nounset` and `pipefail` to every script a test starts, so a mock has to work under `set -euo pipefail`.

`ci.yml` also calls the reusable workflows of the same commit: the job `validate` calls `validate.yml`, and the job `pipeline` calls `check-updates.yml` with aurtomator itself as the repository of the packages, see [docs/WORKFLOW.md section 6.4](docs/WORKFLOW.md#64-validate-and-pipeline-jobs). A pull request from a fork of aurtomator gets a read-only token, so `pipeline` runs only for a push and for a pull request from a branch of aurtomator.

## PR workflow

PRs are squash-merged. The squash commit subject on `main` must follow Conventional Commits with a scope, so write the PR title and the commit subjects that way. A PR titled `fix strategy bug` is renamed to something like `fix(strategy): handle empty release list from github-release` before it is merged.
Expand All @@ -52,7 +54,7 @@ Keep PRs focused: one logical change per PR. Unrelated refactors go in a separat

## Releases

aurtomator follows semantic versioning, and `VERSION` holds the version of the code. After a merge to `main`, release-please (`.github/workflows/release-please.yml`) opens or updates a release PR from the commit types since the last release: `fix` raises the patch number, `feat` the minor one, and before 1.0.0 a breaking change raises the minor one too. A `docs`, `ci`, `chore` or `test` commit opens no release PR and goes out with the next release. The release PR writes the new version to `VERSION` and to the version line of the package table in `README.md`. Its merge tags `vX.Y.Z` and publishes the release with the notes GitHub generates from the merged PRs. A line `Release-As: X.Y.Z` in the body of a squash commit sets another number.
aurtomator follows semantic versioning, and `VERSION` holds the version of the code. After a merge to `main`, release-please (`.github/workflows/release-please.yml`) opens or updates a release PR from the commit types since the last release: `fix` raises the patch number, `feat` the minor one, and before 1.0.0 a breaking change raises the minor one too. A `!` after the type and scope marks a breaking change, as in `feat(workflow)!: run as a reusable workflow`. A `docs`, `ci`, `chore` or `test` commit opens no release PR and goes out with the next release. The release PR writes the new version to `VERSION` and to the version line of the package table in `README.md`. Its merge tags `vX.Y.Z` and publishes the release with the notes GitHub generates from the merged PRs. A line `Release-As: X.Y.Z` in the body of a squash commit sets another number.

The workflow runs release-please with the token of a GitHub App installed on the repository, with read and write access to contents, issues and pull requests. It creates the token from the variable `RELEASE_APP_CLIENT_ID` and the secret `RELEASE_APP_PRIVATE_KEY`. With the workflow token instead, GitHub would run the CI of the release PR only after someone with write access approves it.

Expand Down
26 changes: 14 additions & 12 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
[![Lint & Test](https://github.com/staticwire/aurtomator/actions/workflows/ci.yml/badge.svg)](https://github.com/staticwire/aurtomator/actions/workflows/ci.yml) [![codecov](https://codecov.io/github/staticwire/aurtomator/graph/badge.svg)](https://codecov.io/github/staticwire/aurtomator) [![Bash](https://img.shields.io/badge/bash-5%2B-green)](https://www.gnu.org/software/bash/) [![AUR](https://img.shields.io/badge/AUR-automation-orange)](https://aur.archlinux.org/) [![License](https://img.shields.io/badge/license-BSD--3--Clause-blue)](LICENSE)

Automated AUR package updates from a single GitHub repo.
[Fork it](https://github.com/staticwire/aurtomator/fork), drop in your packages, let CI handle the rest.
Create a repository from the template [staticwire/aurtomator-seed](https://github.com/staticwire/aurtomator-seed) and drop in your packages. Its workflows call the pipeline of aurtomator at a pinned commit.

## Packages

Expand All @@ -22,7 +22,8 @@ aurtomator 0.7.1 <!-- x-release-please-version -->

```mermaid
graph LR
A[GitHub Actions<br/>on schedule] -->|for each package| K[check job, read-only token<br/>run strategy<br/>decide the run]
U[your repository<br/>package YAMLs<br/>calling workflow on schedule] --> R[aurtomator at the pinned SHA<br/>reusable check-updates.yml]
R -->|for each package| K[check job, read-only token<br/>run strategy<br/>decide the run]
K -->|new version| B[prepare job, no secrets<br/>clone AUR repo<br/>sed pkgver<br/>updpkgsums<br/>makepkg --printsrcinfo]
B --> V[verify job, no secrets<br/>download the sources<br/>check the checksums]
V --> C[publish job<br/>check the prepared files<br/>git push to AUR]
Expand All @@ -32,17 +33,18 @@ graph LR
C --> D
```

Each package has a YAML config pointing to an upstream source. A first job runs the strategies and decides what the run does. When a new version is detected, aurtomator clones the existing AUR repo, bumps `pkgver`, regenerates checksums and `.SRCINFO`, and pushes. A PKGBUILD is code, so these steps run in a job without secrets, and the jobs after it take the statuses from the first job. A second job without secrets downloads the sources and checks the checksums, and the job that pushes checks the result once more. It does not generate PKGBUILDs or modify anything else. A package that starts failing gets a GitHub Issue, and so does a failed run of the workflow.
Each package has a YAML config pointing to an upstream source. Your repository holds these configs and calls the pipeline of aurtomator. A first job runs the strategies and decides what the run does. When a new version is detected, aurtomator clones the existing AUR repo, bumps `pkgver`, regenerates checksums and `.SRCINFO`, and pushes. A PKGBUILD is code, so these steps run in a job without secrets, and the jobs after it take the statuses from the first job. A second job without secrets downloads the sources and checks the checksums, and the job that pushes checks the result once more. It does not generate PKGBUILDs or modify anything else. A package that starts failing gets a GitHub Issue, and so does a failed run of the workflow.

## Quick start

1. Fork this repo (or use as template)
2. Enable Actions and Issues in your fork's Settings ([why?](docs/SETUP.md#after-forking))
3. Run `./scripts/setup.sh` ([detailed guide](docs/SETUP.md))
4. Add a package: `cp packages/example.yml.sample packages/<name>.yml`, where `<name>` is the pkgbase on the AUR
5. Edit the copy: set `name: <name>`, a `strategy` and its `upstream` fields, see [Strategies](#strategies)
6. Validate: `./scripts/validate-pkg.sh <name>`
7. Push and let CI handle the rest
1. Create a repository from [staticwire/aurtomator-seed](https://github.com/staticwire/aurtomator-seed) with "Use this template"
2. Make sure Issues are on in the Settings of the new repository ([why?](docs/SETUP.md#after-creating-the-repository))
3. Clone aurtomator for the scripts, at the tag the calling workflows pin: `git clone https://github.com/staticwire/aurtomator ~/src/aurtomator` and `git -C ~/src/aurtomator checkout vX.Y.Z`, where `vX.Y.Z` is the version in the `# vX.Y.Z` comment of those workflows
4. Clone the new repository and run `~/src/aurtomator/scripts/setup.sh` from inside it ([detailed guide](docs/SETUP.md))
5. Add a package: `cp ~/src/aurtomator/packages/example.yml.sample packages/<name>.yml`, where `<name>` is the pkgbase on the AUR
6. Edit the copy: set `name: <name>`, a `strategy` and its `upstream` fields, see [Strategies](#strategies)
7. Validate from inside the new repository: `~/src/aurtomator/scripts/validate-pkg.sh <name>`
8. Push and let CI handle the rest

The setup script configures your identity (git author for AUR commits), SSH access, and GitHub Secrets. With [gh CLI](https://cli.github.com/) it sets the secrets itself. Without it, the script prints manual instructions. GPG commit signing is optional.

Expand Down Expand Up @@ -99,7 +101,7 @@ Some upstreams name a release asset with more than the version and rebuild a rel

## Updates of aurtomator

`VERSION` holds the version of aurtomator a repository runs, and the package table shows it. When a newer aurtomator release is out, a run links it under the table and opens an issue, which closes once the fork has merged the release. Details are in [docs/WORKFLOW.md section 5.8](docs/WORKFLOW.md#58-version-of-aurtomator).
The line under the package table shows the version a run uses, which is `VERSION` of aurtomator at the SHA the calling workflows pin. Dependabot opens the pull request that moves the pin. A newer release also gets an issue and a link on that line. A run closes the issue once the pin of the calling workflows names that release, or once a newer release is out. Details are in [docs/WORKFLOW.md section 5.8](docs/WORKFLOW.md#58-version-of-aurtomator).

## Resource usage

Expand All @@ -119,7 +121,7 @@ All packages run in one workflow run. `check` and `issues` run every time, `prep
| [lilac] | Large repos (archlinuxcn) | Full build bot, needs own infra |
| [aur-auto-update] | Centralized service | Requires bot co-maintainer on AUR |
| [Renovate] | Multi-ecosystem | Enterprise-grade, heavy config |
| **aurtomator** | Individual maintainers | Fork and go |
| **aurtomator** | Individual maintainers | Template and a pinned workflow |

[nvchecker]: https://github.com/lilydjwg/nvchecker
[lilac]: https://github.com/archlinuxcn/lilac
Expand Down
12 changes: 6 additions & 6 deletions SECURITY.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
| latest release | yes |
| older releases | no |

There are no backports. A fork is expected to merge fixes from upstream as they land. Unreleased `main` is not supported.
There are no backports. A user repository calls the workflows of aurtomator at a pinned SHA, the SHA of a release tag. It is expected to move the pin to the latest release, and Dependabot opens the pull request that moves it, see [docs/SETUP.md](docs/SETUP.md#the-calling-workflows). Unreleased `main` is not supported.

## Reporting a vulnerability

Expand All @@ -26,14 +26,14 @@ In scope:

- `scripts/`: any defect that allows arbitrary code execution, secret exfiltration, or writes outside the working tree.
- `strategies/`: injection through crafted upstream responses, YAML parsing issues, or command injection through package configuration.
- `.github/workflows/`: misconfiguration that leaks the `AUR_SSH_KEY`, `GPG_SIGNING_KEY`, `AUR_GIT_NAME` or `AUR_GIT_EMAIL` secrets into logs, artifacts, forks, pull requests or third-party actions.
- Anything else in this repository that can make a fork push a compromised package to the AUR without the fork maintainer's intent.
- `.github/workflows/`: misconfiguration that leaks the `AUR_SSH_KEY`, `GPG_SIGNING_KEY`, `AUR_GIT_NAME` or `AUR_GIT_EMAIL` secrets into logs, artifacts, pull requests or third-party actions. A user repository passes these secrets to the reusable workflows when it calls them.
- Anything else in this repository that can make a user repository push a compromised package to the AUR without the intent of its maintainer.

Out of scope:

- Vulnerabilities in external tools that aurtomator calls (`makepkg`, `yq`, `curl`, `git`, `namcap`, `shellcheck`, `shfmt`, `bats`). Report those upstream.
- The contents of AUR packages published by forks. Each fork maintainer is responsible for the packages they publish.
- The fork model itself, for example that a malicious fork can push a bad package.
- The contents of AUR packages published from user repositories. The maintainer of each user repository is responsible for the packages they publish.
- The model itself: a user repository runs the workflows with its own AUR key, and a pin that is not the SHA of a release tag runs the code of the commit it names.
- Issues in third-party GitHub Actions. Report them to the action's maintainer. aurtomator pins every action by commit SHA.

## Known limitations
Expand All @@ -42,4 +42,4 @@ Publish compares a line of the prepared `.SRCINFO` other than `pkgver`, `pkgrel`

## Disclosure

Once a reported issue is fixed, the advisory is published on the repository's Security tab. A CVE assigned through GitHub's CNA is referenced in the published advisory. A fork gets the fix with its next merge from upstream. Watching this repository's releases gives a notification when a fix ships.
Once a reported issue is fixed, the advisory is published on the repository's Security tab. A CVE assigned through GitHub's CNA is referenced in the published advisory. A user repository gets the fix once the pin of its calling workflows moves to a release that holds the fix. Watching this repository's releases gives a notification when a fix ships.
Loading
Loading