From 39ee61dd7d9ce34fe4566faee785e8c69c3c593f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=9B=B6Rei?= Date: Thu, 12 Mar 2026 08:44:35 -0700 Subject: [PATCH 1/3] chore: Add Renovate configuration for automated dependency updates Configures Renovate to manage Cargo and GitHub Actions dependencies with dashboard approval, 7-day minimum release age, and automerge for patches and dev dependencies. Co-Authored-By: Claude Opus 4.6 --- renovate.json | 49 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) create mode 100644 renovate.json diff --git a/renovate.json b/renovate.json new file mode 100644 index 0000000..d638770 --- /dev/null +++ b/renovate.json @@ -0,0 +1,49 @@ +{ + "$schema": "https://docs.renovatebot.com/renovate-schema.json", + "extends": [":dependencyDashboardApproval"], + "enabledManagers": ["cargo", "github-actions"], + "minimumReleaseAge": "7 days", + "schedule": [], + "updateNotScheduled": false, + "semanticCommitScope": "", + "semanticCommitType": "deps", + "packageRules": [ + { + "matchManagers": ["github-actions"], + "dependencyDashboardCategory": "GitHub Actions updates" + }, + { + "matchManagers": ["cargo"], + "dependencyDashboardCategory": "Rust updates" + }, + { + "matchDepTypes": ["devDependencies"], + "semanticCommitScope": "dev", + "semanticCommitType": "deps", + "automerge": true + }, + { + "matchUpdateTypes": ["patch"], + "automerge": true + }, + { + "matchUpdateTypes": ["lockFileMaintenance"], + "automerge": true + } + ], + "lockFileMaintenance": { + "enabled": true + }, + "prBodyTemplate": "{{{header}}}{{{table}}}{{{warnings}}}{{{notes}}}{{{changelogs}}}", + "prBodyColumns": ["Package", "Change"], + "ignorePresets": ["mergeConfidence:all-badges"], + "vulnerabilityAlerts": { + "groupName": null, + "dependencyDashboardApproval": true, + "rangeStrategy": "update-lockfile", + "commitMessageSuffix": "[security]", + "branchTopic": "{{{datasource}}}-{{{depNameSanitized}}}-vulnerability", + "prCreation": "immediate", + "vulnerabilityFixStrategy": "lowest" + } +} From 6322acc6a920fd4b2567464b853897de9bdaa109 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=9B=B6Rei?= Date: Thu, 12 Mar 2026 14:18:49 -0700 Subject: [PATCH 2/3] ci: Add release workflow and documentation for publishing to crates.io Co-Authored-By: Claude Opus 4.6 --- .github/workflows/release.yml | 114 ++++++++++++++++++++++++++++++++++ RELEASE.md | 44 +++++++++++++ 2 files changed, 158 insertions(+) create mode 100644 .github/workflows/release.yml create mode 100644 RELEASE.md diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..9e3b88a --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,114 @@ +name: Release + +on: + push: + tags: + - "v*" + +permissions: + contents: write + +jobs: + test: + name: Test before release + runs-on: ubuntu-latest + steps: + - name: Step Security + uses: step-security/harden-runner@58077d3c7e43986b6b15fba718e8ea69e387dfcc # v2.15.1 + with: + disable-sudo-and-containers: true + egress-policy: block + allowed-endpoints: > + api.github.com:443 + objects.githubusercontent.com:443 + release-assets.githubusercontent.com:443 + github.com:443 + index.crates.io:443 + static.crates.io:443 + static.rust-lang.org:443 + proxy.golang.org:443 + + - name: Checkout + uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + + - name: Install Go + uses: actions/setup-go@4b73464bb391d4059bd26b0524d20df3927bd417 # v6.3.0 + with: + go-version: stable + + - name: Install Rust + uses: dtolnay/rust-toolchain@efa25f7f19611383d5b0ccf2d1c8914531636bf9 + with: + toolchain: stable + + - name: cargo build + run: cargo build --locked --verbose + env: + CARGO_TERM_COLOR: always + + - name: cargo test + run: cargo test --locked --verbose + env: + CARGO_TERM_COLOR: always + + - name: go test + run: | + go generate ./... + go test ./... + + - name: run snapshot tests + run: cargo test --locked --verbose --test cli + + publish: + name: Publish to crates.io + needs: test + runs-on: ubuntu-latest + steps: + - name: Step Security + uses: step-security/harden-runner@58077d3c7e43986b6b15fba718e8ea69e387dfcc # v2.15.1 + with: + disable-sudo-and-containers: true + egress-policy: block + allowed-endpoints: > + crates.io:443 + index.crates.io:443 + static.crates.io:443 + static.rust-lang.org:443 + github.com:443 + + - name: Checkout + uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + + - name: Install Rust + uses: dtolnay/rust-toolchain@efa25f7f19611383d5b0ccf2d1c8914531636bf9 + with: + toolchain: stable + + - name: Publish + run: cargo publish -p arcjet-gravity --locked + env: + CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }} + CARGO_TERM_COLOR: always + + github-release: + name: Create GitHub Release + needs: publish + runs-on: ubuntu-latest + steps: + - name: Step Security + uses: step-security/harden-runner@58077d3c7e43986b6b15fba718e8ea69e387dfcc # v2.15.1 + with: + disable-sudo-and-containers: true + egress-policy: block + allowed-endpoints: > + api.github.com:443 + github.com:443 + uploads.github.com:443 + + - name: Checkout + uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + + - name: Create GitHub Release + env: + GH_TOKEN: ${{ github.token }} + run: gh release create "${{ github.ref_name }}" --generate-notes diff --git a/RELEASE.md b/RELEASE.md new file mode 100644 index 0000000..99f91f2 --- /dev/null +++ b/RELEASE.md @@ -0,0 +1,44 @@ +# Release + +Publishing to crates.io is automated via GitHub Actions but requires a manual +tag push to initiate. + +## Prerequisites + +A `CARGO_REGISTRY_TOKEN` secret must be configured in the repository's GitHub +settings (Settings → Secrets and variables → Actions). This token must have +publish permissions for the `arcjet-gravity` crate on crates.io. + +## Process + +It looks like this: + +1. Update the version in `cmd/gravity/Cargo.toml` and land the change on `main`. +2. Tag the release commit and push the tag: + ```sh + git tag v0.1.0 + git push origin v0.1.0 + ``` +3. The [Release workflow](.github/workflows/release.yml) runs automatically: + 1. **Test** — runs the full test suite (cargo test, go test, snapshot tests). + 2. **Publish** — publishes `arcjet-gravity` to crates.io. + 3. **GitHub Release** — creates a GitHub Release with auto-generated notes. +4. Verify the release on [crates.io](https://crates.io/crates/arcjet-gravity) + and on the repository's + [Releases page](https://github.com/arcjet/gravity/releases). + +## Versioning + +This project follows [Semantic Versioning](https://semver.org/). While the +project is in early development (`0.x`), minor version bumps may include +breaking changes. + +## Troubleshooting + +- **Publish fails with permission error**: check that the `CARGO_REGISTRY_TOKEN` + secret is set and the token has not expired. +- **Publish fails with version conflict**: the version in `Cargo.toml` must be + greater than the latest published version on crates.io. You cannot re-publish + a version that has already been published. +- **Tests fail**: the release is aborted. Fix the issue on `main`, delete the + tag (`git push origin :refs/tags/v0.1.0`), and start again. From db294d3d558e7d5d421c0674b4c4e7627ceedda1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=9B=B6Rei?= <212411920+arcjet-rei@users.noreply.github.com> Date: Wed, 29 Apr 2026 22:29:45 -0700 Subject: [PATCH 3/3] ci: switch release workflow to crates.io Trusted Publishing - Replace CARGO_REGISTRY_TOKEN secret with rust-lang/crates-io-auth-action, which exchanges a GitHub OIDC token for a short-lived crates.io token - Wrap the publish job in a `release` GitHub Environment so the secret / approval policy can be configured per-environment, matching the pattern used by arcjet-py and arcjet-js - Tighten top-level permissions to `contents: read` and grant `contents: write` only to the github-release job that needs it - Add `id-token: write` on the publish job for OIDC - Allow token.actions.githubusercontent.com:443 in the publish job's hardened egress list (needed for the OIDC token exchange) - Bump pinned action SHAs to match what is on main - Update RELEASE.md prerequisites and troubleshooting to describe the Trusted Publisher + environment setup instead of token-based publishing Co-Authored-By: Claude Opus 4.7 (1M context) --- .github/workflows/release.yml | 27 +++++++++++++++++++-------- RELEASE.md | 34 ++++++++++++++++++++++++++-------- 2 files changed, 45 insertions(+), 16 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 9e3b88a..6c58f60 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -6,7 +6,7 @@ on: - "v*" permissions: - contents: write + contents: read jobs: test: @@ -14,7 +14,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Step Security - uses: step-security/harden-runner@58077d3c7e43986b6b15fba718e8ea69e387dfcc # v2.15.1 + uses: step-security/harden-runner@6c3c2f2c1c457b00c10c4848d6f5491db3b629df # v2.18.0 with: disable-sudo-and-containers: true egress-policy: block @@ -32,12 +32,12 @@ jobs: uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Install Go - uses: actions/setup-go@4b73464bb391d4059bd26b0524d20df3927bd417 # v6.3.0 + uses: actions/setup-go@4a3601121dd01d1626a1e23e37211e3254c1c06c # v6.4.0 with: go-version: stable - name: Install Rust - uses: dtolnay/rust-toolchain@efa25f7f19611383d5b0ccf2d1c8914531636bf9 + uses: dtolnay/rust-toolchain@3c5f7ea28cd621ae0bf5283f0e981fb97b8a7af9 with: toolchain: stable @@ -63,9 +63,13 @@ jobs: name: Publish to crates.io needs: test runs-on: ubuntu-latest + environment: + name: release + permissions: + id-token: write steps: - name: Step Security - uses: step-security/harden-runner@58077d3c7e43986b6b15fba718e8ea69e387dfcc # v2.15.1 + uses: step-security/harden-runner@6c3c2f2c1c457b00c10c4848d6f5491db3b629df # v2.18.0 with: disable-sudo-and-containers: true egress-policy: block @@ -75,28 +79,35 @@ jobs: static.crates.io:443 static.rust-lang.org:443 github.com:443 + token.actions.githubusercontent.com:443 - name: Checkout uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Install Rust - uses: dtolnay/rust-toolchain@efa25f7f19611383d5b0ccf2d1c8914531636bf9 + uses: dtolnay/rust-toolchain@3c5f7ea28cd621ae0bf5283f0e981fb97b8a7af9 with: toolchain: stable + - name: Authenticate with crates.io + id: auth + uses: rust-lang/crates-io-auth-action@bbd81622f20ce9e2dd9622e3218b975523e45bbe # v1.0.4 + - name: Publish run: cargo publish -p arcjet-gravity --locked env: - CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }} + CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }} CARGO_TERM_COLOR: always github-release: name: Create GitHub Release needs: publish runs-on: ubuntu-latest + permissions: + contents: write steps: - name: Step Security - uses: step-security/harden-runner@58077d3c7e43986b6b15fba718e8ea69e387dfcc # v2.15.1 + uses: step-security/harden-runner@6c3c2f2c1c457b00c10c4848d6f5491db3b629df # v2.18.0 with: disable-sudo-and-containers: true egress-policy: block diff --git a/RELEASE.md b/RELEASE.md index 99f91f2..58e49fa 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -5,14 +5,28 @@ tag push to initiate. ## Prerequisites -A `CARGO_REGISTRY_TOKEN` secret must be configured in the repository's GitHub -settings (Settings → Secrets and variables → Actions). This token must have -publish permissions for the `arcjet-gravity` crate on crates.io. +The release workflow uses [crates.io Trusted Publishing][trusted-publishing] +to authenticate via OIDC, so no long-lived `CARGO_REGISTRY_TOKEN` is required. +The following one-time setup must be in place: + +1. The repository's `release` GitHub Environment exists (Settings → + Environments). Required reviewers can be configured here to gate the + publish step on a manual approval. +2. A Trusted Publisher entry exists on + [crates.io for `arcjet-gravity`](https://crates.io/crates/arcjet-gravity/settings) + with: + - Repository owner: `arcjet` + - Repository name: `gravity` + - Workflow filename: `release.yml` + - Environment: `release` + + This must be added by a crate owner. Members of the `arcjet/rust-team` + GitHub team inherit owner access via the team owner on the crate. + +[trusted-publishing]: https://crates.io/docs/trusted-publishing ## Process -It looks like this: - 1. Update the version in `cmd/gravity/Cargo.toml` and land the change on `main`. 2. Tag the release commit and push the tag: ```sh @@ -21,7 +35,9 @@ It looks like this: ``` 3. The [Release workflow](.github/workflows/release.yml) runs automatically: 1. **Test** — runs the full test suite (cargo test, go test, snapshot tests). - 2. **Publish** — publishes `arcjet-gravity` to crates.io. + 2. **Publish** — authenticates to crates.io via Trusted Publishing and + publishes `arcjet-gravity`. If required reviewers are configured on the + `release` environment, this step waits for approval first. 3. **GitHub Release** — creates a GitHub Release with auto-generated notes. 4. Verify the release on [crates.io](https://crates.io/crates/arcjet-gravity) and on the repository's @@ -35,8 +51,10 @@ breaking changes. ## Troubleshooting -- **Publish fails with permission error**: check that the `CARGO_REGISTRY_TOKEN` - secret is set and the token has not expired. +- **Publish fails with an authentication error**: confirm the Trusted Publisher + entry on crates.io matches the repository, workflow filename, and environment + name exactly. The `permissions: id-token: write` block must be present on + the `publish` job. - **Publish fails with version conflict**: the version in `Cargo.toml` must be greater than the latest published version on crates.io. You cannot re-publish a version that has already been published.