ci: Configure more steps more explicitly (#61401)

Also adds some Zizmor validations.

Release Notes:

- N/A
This commit is contained in:
Finn Evers authored and GitHub committed 2026-07-23 11:25:56 +00:00
1 parent 25632b979b
commit 146a568c79
39 files changed
+343 -124

No files matched your search

+3 -1
View File
@@ -5,7 +5,9 @@ runs:
using: "composite"
steps:
- name: Install nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c # nextest
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9 # 2.84.0
with:
tool: nextest
- name: Install Node
uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4
+3 -1
View File
@@ -12,7 +12,9 @@ runs:
steps:
- name: Install test runner
working-directory: ${{ inputs.working-directory }}
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c # nextest
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9 # 2.84.0
with:
tool: nextest
- name: Install Node
uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4
@@ -40,6 +40,9 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-members: read
permission-organization-projects: write
- if: steps.is-post-close-comment.outputs.result == 'true'
id: check-staff
+3 -1
View File
@@ -53,7 +53,7 @@ jobs:
version: '9'
- name: autofix_pr::run_autofix::install_cargo_machete
if: ${{ inputs.run_clippy }}
uses: taiki-e/install-action@02cc5f8ca9f2301050c0c099055816a41ee05507
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: cargo-machete@0.7.0
- name: autofix_pr::run_autofix::run_cargo_fix
@@ -104,6 +104,8 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
permission-workflows: write
- name: steps::checkout_repo
+4 -1
View File
@@ -23,6 +23,9 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -55,7 +58,7 @@ jobs:
echo "tag_suffix=$tag_suffix"
} >> "$GITHUB_OUTPUT"
- name: steps::install_cargo_edit
uses: taiki-e/install-action@02cc5f8ca9f2301050c0c099055816a41ee05507
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: cargo-edit
- id: bump-version
+14 -1
View File
@@ -21,6 +21,9 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: read
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -98,6 +101,10 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
permission-pull-requests: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -105,7 +112,7 @@ jobs:
ref: main
token: ${{ steps.generate-token.outputs.token }}
- name: steps::install_cargo_edit
uses: taiki-e/install-action@02cc5f8ca9f2301050c0c099055816a41ee05507
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: cargo-edit
- name: bump_zed_version::bump_main::bump_version
@@ -141,6 +148,9 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -196,6 +206,9 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
+3
View File
@@ -21,6 +21,9 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-members: read
permission-issues: write
- id: check-staff
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
+2
View File
@@ -33,6 +33,8 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
permission-workflows: write
permission-pull-requests: write
@@ -41,6 +41,8 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: write
- name: Set up Python
uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5.6.0
+7
View File
@@ -12,6 +12,9 @@
name: Community PR Board
on:
# zizmor: ignore[dangerous-triggers]
# Fork PRs must be supported, but this workflow only reads event metadata and
# checks out scripts from the trusted default branch; it never executes PR code.
pull_request_target:
types: [labeled, unlabeled, assigned, review_requested, edited]
issue_comment:
@@ -50,6 +53,10 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: read
permission-organization-projects: write
permission-pull-requests: read
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
@@ -32,6 +32,10 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: read
permission-organization-projects: write
permission-pull-requests: read
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
+1
View File
@@ -31,6 +31,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
cache: pnpm
cache-dependency-path: script/danger/pnpm-lock.yaml
- name: danger::danger_job::install_deps
+3 -1
View File
@@ -68,7 +68,9 @@ jobs:
- name: steps::download_wasi_sdk
run: ./script/download-wasi-sdk
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than 350 200
- name: deploy_collab::tests::run_collab_tests
+16 -19
View File
@@ -9,32 +9,25 @@ name: Documentation Suggestions
# 5. Keep this workflow focused on suggestions only until that stable workflow is added.
on:
# Run when PRs are merged to main
# Analyze merged PRs on main and cherry-picks to release branches. Each job
# further restricts the event actions and target branch that it handles.
pull_request:
types: [closed]
branches: [main]
paths:
- 'crates/**/*.rs'
- '!crates/**/*_test.rs'
- '!crates/**/tests/**'
# Run on cherry-picks to release branches
pull_request_target:
types: [opened, synchronize]
types: [closed, opened, synchronize]
branches:
- 'v0.*'
- main
- "v0.*"
paths:
- 'crates/**/*.rs'
- "crates/**/*.rs"
# Manual trigger for testing
workflow_dispatch:
inputs:
pr_number:
description: 'PR number to analyze'
description: "PR number to analyze"
required: true
type: string
mode:
description: 'Output mode'
description: "Output mode"
required: true
type: choice
options:
@@ -89,7 +82,6 @@ jobs:
fi
sleep $((i * 5))
done
echo "${HOME}/.local/bin" >> "$GITHUB_PATH"
env:
FACTORY_API_KEY: ${{ secrets.FACTORY_API_KEY }}
@@ -125,6 +117,8 @@ jobs:
FACTORY_API_KEY: ${{ secrets.FACTORY_API_KEY }}
PR_NUMBER: ${{ steps.pr.outputs.number }}
run: |
export PATH="${HOME}/.local/bin:${PATH}"
# Ensure gh CLI is authenticated (GH_TOKEN may not be auto-detected)
# Unset GH_TOKEN first to allow gh auth login to store credentials
echo "$GH_TOKEN" | (unset GH_TOKEN && gh auth login --with-token)
@@ -292,8 +286,10 @@ jobs:
group: docs-suggestions-${{ github.event.pull_request.number || inputs.pr_number || 'manual' }}
cancel-in-progress: true
if: |
(github.event_name == 'pull_request_target' &&
(github.event_name == 'pull_request' &&
contains(fromJSON('["opened","synchronize"]'), github.event.action) &&
startsWith(github.event.pull_request.base.ref, 'v0.') &&
github.event.pull_request.head.repo.full_name == github.repository &&
contains(fromJSON('["MEMBER","OWNER"]'),
github.event.pull_request.author_association)) ||
(github.event_name == 'workflow_dispatch' && inputs.mode == 'immediate')
@@ -303,7 +299,7 @@ jobs:
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
with:
fetch-depth: 0
ref: ${{ github.event_name == 'pull_request_target' && github.event.pull_request.base.ref || '' }}
ref: ${{ github.event_name == 'pull_request' && github.event.pull_request.base.ref || '' }}
persist-credentials: false
- name: Install Droid CLI
@@ -322,7 +318,6 @@ jobs:
fi
sleep $((i * 5))
done
echo "${HOME}/.local/bin" >> "$GITHUB_PATH"
env:
FACTORY_API_KEY: ${{ secrets.FACTORY_API_KEY }}
@@ -350,6 +345,8 @@ jobs:
FACTORY_API_KEY: ${{ secrets.FACTORY_API_KEY }}
PR_NUMBER: ${{ steps.pr.outputs.number }}
run: |
export PATH="${HOME}/.local/bin:${PATH}"
# Ensure gh CLI is authenticated (GH_TOKEN may not be auto-detected)
# Unset GH_TOKEN first to allow gh auth login to store credentials
echo "$GH_TOKEN" | (unset GH_TOKEN && gh auth login --with-token)
+11
View File
@@ -81,6 +81,10 @@ jobs:
with:
app-id: ${{ secrets.app-id }}
private-key: ${{ secrets.app-secret }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
permission-pull-requests: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -170,6 +174,9 @@ jobs:
with:
app-id: ${{ secrets.app-id }}
private-key: ${{ secrets.app-secret }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -222,6 +229,10 @@ jobs:
private-key: ${{ secrets.app-secret }}
owner: zed-industries
repositories: extensions
permission-contents: write
permission-issues: write
permission-members: read
permission-pull-requests: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
+3 -1
View File
@@ -99,7 +99,9 @@ jobs:
env:
PACKAGE_NAME: ${{ steps.get-package-name.outputs.package_name }}
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: extension_tests::run_nextest
run: 'cargo nextest run -p "$PACKAGE_NAME" --no-fail-fast --no-tests=warn --target "$(rustc -vV | sed -n ''s|host: ||p'')"'
env:
@@ -72,7 +72,7 @@ jobs:
.filter(repo => !repo.archived)
.map(repo => repo.name);
const filterInput = `${{ inputs.filter-repos }}`.trim();
const filterInput = process.env.FILTER_REPOS.trim();
if (filterInput.length > 0) {
const allowedNames = filterInput.split(',').map(s => s.trim()).filter(s => s.length > 0);
filteredRepos = filteredRepos.filter(name => allowedNames.includes(name));
@@ -82,6 +82,8 @@ jobs:
console.log(`Found ${filteredRepos.length} extension repos`);
return filteredRepos;
result-encoding: json
env:
FILTER_REPOS: ${{ inputs.filter-repos }}
- name: steps::cache_rust_dependencies_namespace
uses: namespacelabs/nscloud-cache-action@a90bb5d4b27522ce881c6e98eebd7d7e6d1653f9
with:
@@ -215,6 +217,8 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
@@ -34,6 +34,11 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: write
permission-members: read
permission-organization-projects: write
permission-pull-requests: read
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
@@ -7,6 +7,9 @@
name: Guild New PR Notification
on:
# zizmor: ignore[dangerous-triggers]
# Fork PRs must be supported, but this workflow only reads event metadata and
# checks out scripts from the trusted default branch; it never executes PR code.
pull_request_target:
types: [opened]
@@ -31,6 +34,11 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: write
permission-members: read
permission-organization-projects: write
permission-pull-requests: read
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
@@ -32,6 +32,11 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: write
permission-members: read
permission-organization-projects: write
permission-pull-requests: read
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
@@ -30,6 +30,11 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: read
permission-members: read
permission-organization-projects: read
permission-pull-requests: read
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1
+7
View File
@@ -12,6 +12,9 @@ name: PR Issue Labeler
on:
issues:
types: [opened]
# zizmor: ignore[dangerous-triggers]
# Fork PRs must be labeled, but this workflow only passes GitHub-provided event
# metadata to a pinned action; it never checks out or executes PR code.
pull_request_target:
types: [opened]
@@ -30,6 +33,10 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: write
permission-members: read
permission-pull-requests: read
- id: apply-authorship-label
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
@@ -42,6 +42,8 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::update_tag
uses: actions/github-script@f28e40c7f34bde8b3046d885e986cb6290c5673b
@@ -67,6 +69,11 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
permission-pull-requests: write
permission-workflows: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
@@ -121,6 +128,9 @@ jobs:
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: zed-industries
repositories: extensions
permission-contents: write
permission-pull-requests: write
permission-workflows: write
- id: short-sha
name: publish_extension_cli::get_short_sha
run: |
+29 -9
View File
@@ -33,8 +33,11 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than 350 200
- name: steps::setup_sccache
@@ -82,8 +85,11 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than 350 200
- name: steps::setup_sccache
@@ -128,6 +134,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than.ps1 350 200
shell: pwsh
@@ -254,13 +261,6 @@ jobs:
clean: false
- name: run_tests::check_scripts::run_shellcheck
run: ./script/shellcheck-scripts error
- id: get_actionlint
name: run_tests::check_scripts::download_actionlint
run: bash <(curl https://raw.githubusercontent.com/rhysd/actionlint/main/scripts/download-actionlint.bash)
- name: run_tests::check_scripts::run_actionlint
run: '"$ACTIONLINT_BIN" -color'
env:
ACTIONLINT_BIN: ${{ steps.get_actionlint.outputs.executable }}
- name: steps::cache_rust_dependencies_namespace
uses: namespacelabs/nscloud-cache-action@a90bb5d4b27522ce881c6e98eebd7d7e6d1653f9
with:
@@ -274,6 +274,19 @@ jobs:
echo "Please run 'cargo xtask workflows' locally and commit the changes"
exit 1
fi
- id: get_actionlint
name: run_tests::check_scripts::download_actionlint
run: bash <(curl https://raw.githubusercontent.com/rhysd/actionlint/main/scripts/download-actionlint.bash)
- name: run_tests::check_scripts::run_actionlint
run: '"$ACTIONLINT_BIN" -color'
env:
ACTIONLINT_BIN: ${{ steps.get_actionlint.outputs.executable }}
- name: run_tests::check_scripts::run_zizmor
uses: zizmorcore/zizmor-action@6599ee8b7a49aef6a770f63d261d214911a7ce02
with:
advanced-security: false
min-severity: high
version: latest
timeout-minutes: 60
create_draft_release:
if: (github.repository_owner == 'zed-industries' || github.repository_owner == 'zed-extensions')
@@ -285,6 +298,8 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
@@ -545,6 +560,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::setup_sentry
uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b
with:
@@ -596,6 +612,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::setup_sentry
uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b
with:
@@ -845,6 +862,9 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
with:
+8 -1
View File
@@ -64,8 +64,11 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than 350 200
- name: steps::setup_sccache
@@ -290,6 +293,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::setup_sentry
uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b
with:
@@ -345,6 +349,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::setup_sentry
uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b
with:
@@ -574,6 +579,8 @@ jobs:
with:
app-id: ${{ secrets.ZED_ZIPPY_APP_ID }}
private-key: ${{ secrets.ZED_ZIPPY_APP_PRIVATE_KEY }}
owner: ${{ github.repository_owner }}
repositories: ${{ github.event.repository.name }}
permission-contents: write
- name: steps::checkout_repo
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd
+2
View File
@@ -197,6 +197,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::setup_sentry
uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b
with:
@@ -247,6 +248,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::setup_sentry
uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b
with:
+23 -10
View File
@@ -344,6 +344,7 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than.ps1 350 200
shell: pwsh
@@ -402,8 +403,11 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than 350 200
- name: steps::setup_sccache
@@ -454,8 +458,11 @@ jobs:
with:
node-version: '24'
check-latest: true
package-manager-cache: false
- name: steps::cargo_install_nextest
uses: taiki-e/install-action@921e2c9f7148d7ba14cd819f417db338f63e733c
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: nextest
- name: steps::clear_target_dir_if_large
run: ./script/clear-target-dir-if-larger-than 350 200
- name: steps::setup_sccache
@@ -694,7 +701,7 @@ jobs:
cache: rust
path: ~/.rustup
- name: run_tests::check_dependencies::install_cargo_machete
uses: taiki-e/install-action@02cc5f8ca9f2301050c0c099055816a41ee05507
uses: taiki-e/install-action@a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9
with:
tool: cargo-machete@0.7.0
- name: run_tests::check_dependencies::run_cargo_machete
@@ -804,13 +811,6 @@ jobs:
clean: false
- name: run_tests::check_scripts::run_shellcheck
run: ./script/shellcheck-scripts error
- id: get_actionlint
name: run_tests::check_scripts::download_actionlint
run: bash <(curl https://raw.githubusercontent.com/rhysd/actionlint/main/scripts/download-actionlint.bash)
- name: run_tests::check_scripts::run_actionlint
run: '"$ACTIONLINT_BIN" -color'
env:
ACTIONLINT_BIN: ${{ steps.get_actionlint.outputs.executable }}
- name: steps::cache_rust_dependencies_namespace
uses: namespacelabs/nscloud-cache-action@a90bb5d4b27522ce881c6e98eebd7d7e6d1653f9
with:
@@ -824,6 +824,19 @@ jobs:
echo "Please run 'cargo xtask workflows' locally and commit the changes"
exit 1
fi
- id: get_actionlint
name: run_tests::check_scripts::download_actionlint
run: bash <(curl https://raw.githubusercontent.com/rhysd/actionlint/main/scripts/download-actionlint.bash)
- name: run_tests::check_scripts::run_actionlint
run: '"$ACTIONLINT_BIN" -color'
env:
ACTIONLINT_BIN: ${{ steps.get_actionlint.outputs.executable }}
- name: run_tests::check_scripts::run_zizmor
uses: zizmorcore/zizmor-action@6599ee8b7a49aef6a770f63d261d214911a7ce02
with:
advanced-security: false
min-severity: high
version: latest
timeout-minutes: 60
check_postgres_and_protobuf_migrations:
needs:
@@ -5,6 +5,9 @@
name: Notify Slack on community automation failure
on:
# zizmor: ignore[dangerous-triggers]
# The job validates that the completed run came from this repository, was
# started by an expected event, and failed before exposing the Slack secret.
workflow_run:
workflows:
- "Comment on potential duplicate bug/crash reports"
@@ -24,7 +27,9 @@ permissions:
jobs:
notify-slack:
if: >-
github.repository_owner == 'zed-industries'
github.repository == 'zed-industries/zed'
&& github.event.workflow_run.head_repository.full_name == github.repository
&& contains(fromJSON('["issues","issue_comment","pull_request","pull_request_target","schedule","workflow_dispatch"]'), github.event.workflow_run.event)
&& github.event.workflow_run.conclusion == 'failure'
runs-on: namespace-profile-2x4-ubuntu-2404
@@ -35,6 +35,9 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: read
permission-organization-projects: write
- name: Set up Python
uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5.6.0
@@ -74,6 +77,9 @@ jobs:
app-id: ${{ secrets.ZED_COMMUNITY_BOT_APP_ID }}
private-key: ${{ secrets.ZED_COMMUNITY_BOT_PRIVATE_KEY }}
owner: zed-industries
repositories: zed
permission-issues: read
permission-organization-projects: write
- name: Set up Python
uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5.6.0
@@ -91,6 +91,7 @@ jobs:
# mutations. Without `owner:`, the default token is repo-scoped and
# cannot write to org projects.
owner: zed-industries
repositories: zed
# Scope the token down to the minimum needed for this workflow.
# Even though the App may have broader permissions for other
# automations (e.g., Issues:Write for the dupe-bot), this token
+1
View File
@@ -0,0 +1 @@
rules: {}
@@ -65,7 +65,10 @@ fn run_bump_patch_version(branch: &WorkflowInput) -> steps::NamedJob {
.id("bump-version")
}
let (authenticate, token) = steps::authenticate_as_zippy().into();
let (authenticate, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([(steps::TokenPermissions::Contents, Level::Write)])
.into();
let channel_step = read_channel();
let tag_suffix = StepOutput::new(&channel_step, "tag_suffix");
let bump_version_step = bump_version();
@@ -88,7 +88,10 @@ fn resolve_versions() -> (steps::NamedJob, ResolvedOutputs) {
.id("versions")
}
let (authenticate, token) = steps::authenticate_as_zippy().into();
let (authenticate, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([(steps::TokenPermissions::Contents, Level::Read)])
.into();
let versions_step = extract_versions();
let next_version = StepOutput::new(&versions_step, "next_version");
let pr_branch = StepOutput::new(&versions_step, "pr_branch");
@@ -134,7 +137,13 @@ fn bump_main(
named::bash("cargo set-version -p zed --bump minor")
}
let (authenticate, token) = steps::authenticate_as_zippy().into();
let (authenticate, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([
(steps::TokenPermissions::Contents, Level::Write),
(steps::TokenPermissions::PullRequests, Level::Write),
])
.into();
named::job(
Job::default()
@@ -175,7 +184,10 @@ fn create_preview_branch(
named::bash("echo \"main_sha=$(git rev-parse HEAD)\" >> \"$GITHUB_OUTPUT\"").id("main-sha")
}
let (authenticate, token) = steps::authenticate_as_zippy().into();
let (authenticate, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([(steps::TokenPermissions::Contents, Level::Write)])
.into();
let main_sha_step = get_main_sha();
let main_sha = StepOutput::new(&main_sha_step, "main_sha");
@@ -225,7 +237,10 @@ fn promote_to_stable(
versions_job: &steps::NamedJob,
outputs: &ResolvedOutputs,
) -> steps::NamedJob {
let (authenticate, token) = steps::authenticate_as_zippy().into();
let (authenticate, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([(steps::TokenPermissions::Contents, Level::Write)])
.into();
let read_version_step = named::bash(indoc::indoc! {r#"
stable_version=$(script/get-crate-version zed)
@@ -7,8 +7,8 @@ use crate::tasks::workflows::{
steps::{
self, BASH_SHELL, CommonJobConditions, CommonPermissionSets,
DEFAULT_REPOSITORY_OWNER_GUARD, GitHubScriptStep, GitRef, NamedJob, RefSha,
RepositoryTarget, cache_rust_dependencies_namespace, checkout_repo, create_ref,
dependant_job, generate_token, named,
RepositoryTarget, TokenPermissions, cache_rust_dependencies_namespace, checkout_repo,
create_ref, dependant_job, generate_token, named,
},
vars::{
JobOutput, StepOutput, WorkflowInput, WorkflowSecret,
@@ -126,7 +126,10 @@ fn create_version_label(
app_secret: &WorkflowSecret,
) -> (NamedJob, StepOutput) {
let (generate_token, generated_token) =
generate_token(&app_id.to_string(), &app_secret.to_string()).into();
generate_token(&app_id.to_string(), &app_secret.to_string())
.for_repository(RepositoryTarget::current())
.with_permissions([(TokenPermissions::Contents, Level::Write)])
.into();
let (determine_tag_step, tag) = determine_tag(current_version);
let job = steps::dependant_job(dependencies)
.defaults(extension_job_defaults())
@@ -215,7 +218,13 @@ fn bump_extension_version(
app_secret: &WorkflowSecret,
) -> NamedJob {
let (generate_token, generated_token) =
generate_token(&app_id.to_string(), &app_secret.to_string()).into();
generate_token(&app_id.to_string(), &app_secret.to_string())
.for_repository(RepositoryTarget::current())
.with_permissions([
(TokenPermissions::Contents, Level::Write),
(TokenPermissions::PullRequests, Level::Write),
])
.into();
let (bump_version, _new_version, title, body, branch_name) =
bump_version(current_version, bump_type);
@@ -330,6 +339,12 @@ fn trigger_release(
let (generate_token, generated_token) =
generate_token(&app_id.to_string(), &app_secret.to_string())
.for_repository(extension_registry)
.with_permissions([
(TokenPermissions::Contents, Level::Write),
(TokenPermissions::Issues, Level::Write),
(TokenPermissions::Members, Level::Read),
(TokenPermissions::PullRequests, Level::Write),
])
.into();
let (get_extension_id, extension_id) = get_extension_id();
let (release_action, pull_request_number) = release_action(extension_id, tag, &generated_token);
@@ -67,7 +67,7 @@ fn fetch_extension_repos(filter_repos_input: &WorkflowInput) -> (NamedJob, JobOu
.filter(repo => !repo.archived)
.map(repo => repo.name);
const filterInput = `{filter_repos_input}`.trim();
const filterInput = process.env.FILTER_REPOS.trim();
if (filterInput.length > 0) {{
const allowedNames = filterInput.split(',').map(s => s.trim()).filter(s => s.length > 0);
filteredRepos = filteredRepos.filter(name => allowedNames.includes(name));
@@ -80,6 +80,7 @@ fn fetch_extension_repos(filter_repos_input: &WorkflowInput) -> (NamedJob, JobOu
.result_encoding(ResultEncoding::Json)
.custom_name("get_repositories")
.id("list-repos")
.env("FILTER_REPOS", filter_repos_input.to_string())
.into();
let filtered_repos = StepOutput::new(&step, "result");
@@ -86,7 +86,14 @@ fn publish_job() -> NamedJob {
fn update_sha_in_zed(publish_job: &NamedJob, message: &WorkflowInput) -> NamedJob {
let (generate_token, generated_token) =
generate_token(vars::ZED_ZIPPY_APP_ID, vars::ZED_ZIPPY_APP_PRIVATE_KEY).into();
generate_token(vars::ZED_ZIPPY_APP_ID, vars::ZED_ZIPPY_APP_PRIVATE_KEY)
.for_repository(RepositoryTarget::current())
.with_permissions([
(TokenPermissions::Contents, Level::Write),
(TokenPermissions::PullRequests, Level::Write),
(TokenPermissions::Workflows, Level::Write),
])
.into();
fn replace_sha() -> Step<Run> {
named::bash(indoc! {r#"
@@ -150,6 +157,11 @@ fn update_sha_in_extensions(publish_job: &NamedJob, message: &WorkflowInput) ->
let (generate_token, generated_token) =
generate_token(vars::ZED_ZIPPY_APP_ID, vars::ZED_ZIPPY_APP_PRIVATE_KEY)
.for_repository(extensions_repo)
.with_permissions([
(TokenPermissions::Contents, Level::Write),
(TokenPermissions::PullRequests, Level::Write),
(TokenPermissions::Workflows, Level::Write),
])
.into();
fn checkout_extensions_repo(token: &StepOutput) -> Step<Use> {
+5 -1
View File
@@ -427,7 +427,10 @@ fn auto_release_preview(deps: &[&NamedJob]) -> (NamedJob, JobOutput) {
.add_env(("GITHUB_TOKEN", token))
}
let (authenticate, token) = steps::authenticate_as_zippy().into();
let (authenticate, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([(steps::TokenPermissions::Contents, Level::Write)])
.into();
let auto_release_preview_step = auto_release_preview(&token);
let release_published = StepOutput::new(&auto_release_preview_step, "release_published");
@@ -498,6 +501,7 @@ fn create_draft_release() -> NamedJob {
}
let (authenticate_step, token) = steps::authenticate_as_zippy()
.for_repository(steps::RepositoryTarget::current())
.with_permissions([(TokenPermissions::Contents, Level::Write)])
.into();
+14 -2
View File
@@ -801,6 +801,17 @@ pub(crate) fn check_scripts(harden: bool) -> NamedJob {
named::bash("./script/shellcheck-scripts error")
}
fn run_zizmor() -> Step<Use> {
named::uses(
"zizmorcore",
"zizmor-action",
"6599ee8b7a49aef6a770f63d261d214911a7ce02", // v0.6.0
)
.add_with(("advanced-security", false))
.add_with(("min-severity", "high"))
.add_with(("version", "latest"))
}
fn check_xtask_workflows() -> Step<Run> {
named::bash(indoc::indoc! {r#"
cargo xtask workflows
@@ -818,10 +829,11 @@ pub(crate) fn check_scripts(harden: bool) -> NamedJob {
.when(harden, |this| this.add_step(steps::harden_runner()))
.add_step(steps::checkout_repo())
.add_step(run_shellcheck())
.add_step(cache_rust_dependencies_namespace())
.add_step(check_xtask_workflows())
.add_step(download_actionlint().id("get_actionlint"))
.add_step(run_actionlint())
.add_step(cache_rust_dependencies_namespace())
.add_step(check_xtask_workflows()),
.add_step(run_zizmor()),
)
}
+64 -62
View File
@@ -177,6 +177,7 @@ pub fn setup_node() -> Step<Use> {
)
.add_with(("node-version", "24"))
.add_with(("check-latest", true))
.add_with(("package-manager-cache", false))
}
pub fn setup_sentry() -> Step<Use> {
@@ -205,17 +206,13 @@ pub fn taiki_install_action(tool: &str) -> Step<Use> {
.uses(
"taiki-e",
"install-action",
"02cc5f8ca9f2301050c0c099055816a41ee05507", // v2
"a6b2e2dcd845ddd7f509ce4f3ed3d922b80cc5d9", // v2.84.0
)
.add_with(("tool", tool))
}
pub fn cargo_install_nextest() -> Step<Use> {
named::uses(
"taiki-e",
"install-action",
"921e2c9f7148d7ba14cd819f417db338f63e733c", // nextest
)
taiki_install_action("nextest")
}
pub fn setup_cargo_config(platform: Platform) -> Step<Run> {
@@ -784,6 +781,7 @@ pub fn download_artifact() -> DownloadArtifactStep {
pub(crate) enum TokenPermissions {
Contents,
Issues,
Members,
PullRequests,
Workflows,
}
@@ -793,38 +791,70 @@ impl TokenPermissions {
match self {
TokenPermissions::Contents => "permission-contents",
TokenPermissions::Issues => "permission-issues",
TokenPermissions::Members => "permission-members",
TokenPermissions::PullRequests => "permission-pull-requests",
TokenPermissions::Workflows => "permission-workflows",
}
}
}
pub(crate) struct GenerateAppToken<'a> {
pub(crate) struct Unset;
pub(crate) struct GenerateAppToken<'a, Target = Unset, Permissions = Unset> {
job_name: String,
app_id: &'a str,
app_secret: &'a str,
repository_target: Option<RepositoryTarget>,
permissions: Option<Vec<(TokenPermissions, Level)>>,
repository_target: Target,
permissions: Permissions,
}
impl<'a> GenerateAppToken<'a> {
pub fn for_repository(self, repository_target: RepositoryTarget) -> Self {
Self {
repository_target: Some(repository_target),
..self
}
}
pub fn with_permissions(self, permissions: impl Into<Vec<(TokenPermissions, Level)>>) -> Self {
Self {
permissions: Some(permissions.into()),
..self
impl<'a, Permissions> GenerateAppToken<'a, Unset, Permissions> {
pub fn for_repository(
self,
repository_target: RepositoryTarget,
) -> GenerateAppToken<'a, RepositoryTarget, Permissions> {
GenerateAppToken {
job_name: self.job_name,
app_id: self.app_id,
app_secret: self.app_secret,
repository_target,
permissions: self.permissions,
}
}
}
impl<'a> From<GenerateAppToken<'a>> for (Step<Use>, StepOutput) {
fn from(token: GenerateAppToken<'a>) -> Self {
impl<'a, Target> GenerateAppToken<'a, Target, Unset> {
pub fn with_permissions(
self,
permissions: impl Into<Vec<(TokenPermissions, Level)>>,
) -> GenerateAppToken<'a, Target, Vec<(TokenPermissions, Level)>> {
GenerateAppToken {
job_name: self.job_name,
app_id: self.app_id,
app_secret: self.app_secret,
repository_target: self.repository_target,
permissions: permissions.into(),
}
}
}
impl<'a> From<GenerateAppToken<'a, RepositoryTarget, Vec<(TokenPermissions, Level)>>>
for (Step<Use>, StepOutput)
{
fn from(token: GenerateAppToken<'a, RepositoryTarget, Vec<(TokenPermissions, Level)>>) -> Self {
let input = token.permissions.into_iter().fold(
Input::default()
.add("app-id", token.app_id)
.add("private-key", token.app_secret)
.add("owner", token.repository_target.owner)
.add("repositories", token.repository_target.repositories),
|input, (permission, level)| {
input.add(
permission.environment_name(),
serde_json::to_value(&level).unwrap_or_default(),
)
},
);
let step = Step::new(token.job_name)
.uses(
"actions",
@@ -832,35 +862,7 @@ impl<'a> From<GenerateAppToken<'a>> for (Step<Use>, StepOutput) {
"f8d387b68d61c58ab83c6c016672934102569859",
)
.id("generate-token")
.add_with(
Input::default()
.add("app-id", token.app_id)
.add("private-key", token.app_secret)
.when_some(
token.repository_target,
|input,
RepositoryTarget {
owner,
repositories,
}| {
input
.when_some(owner, |input, owner| input.add("owner", owner))
.when_some(repositories, |input, repositories| {
input.add("repositories", repositories)
})
},
)
.when_some(token.permissions, |input, permissions| {
permissions
.into_iter()
.fold(input, |input, (permission, level)| {
input.add(
permission.environment_name(),
serde_json::to_value(&level).unwrap_or_default(),
)
})
}),
);
.add_with(input);
let generated_token = StepOutput::new(&step, "token");
(step, generated_token)
@@ -868,23 +870,23 @@ impl<'a> From<GenerateAppToken<'a>> for (Step<Use>, StepOutput) {
}
pub(crate) struct RepositoryTarget {
owner: Option<String>,
repositories: Option<String>,
owner: String,
repositories: String,
}
impl RepositoryTarget {
pub fn new<T: ToString>(owner: T, repositories: &[&str]) -> Self {
Self {
owner: Some(owner.to_string()),
repositories: Some(repositories.join("\n")),
owner: owner.to_string(),
repositories: repositories.join("\n"),
}
}
pub fn current() -> Self {
Self {
owner: None,
repositories: None,
}
Self::new(
"${{ github.repository_owner }}",
&["${{ github.event.repository.name }}"],
)
}
}
@@ -907,8 +909,8 @@ fn generate_token_with_job_name<'a>(
job_name: function_name(1),
app_id: app_id_source,
app_secret: app_secret_source,
repository_target: None,
permissions: None,
repository_target: Unset,
permissions: Unset,
}
}