From b1922b7156e80d95f872953dbd930974c6d4f34e Mon Sep 17 00:00:00 2001 From: Conrad Irwin Date: Tue, 28 Oct 2025 13:57:23 -0600 Subject: [PATCH] Move Nightly release to gh-workflow (#41349) Follow up to #41304 to move nightly release over Release Notes: - N/A --------- Co-authored-by: Ben Kunkle --- .github/workflows/danger.yml | 2 +- .github/workflows/nix_build.yml | 14 +- .github/workflows/release_nightly.yml | 660 ++++++++++-------- .github/workflows/run_bundling.yml | 14 +- Cargo.lock | 4 +- Cargo.toml | 2 +- ci/Dockerfile.namespace | 21 + tooling/xtask/src/tasks/workflows.rs | 4 +- .../xtask/src/tasks/workflows/nix_build.rs | 128 ++-- .../src/tasks/workflows/release_nightly.rs | 270 +++++++ .../xtask/src/tasks/workflows/run_bundling.rs | 35 +- tooling/xtask/src/tasks/workflows/runners.rs | 25 +- tooling/xtask/src/tasks/workflows/steps.rs | 79 ++- tooling/xtask/src/tasks/workflows/vars.rs | 46 +- 14 files changed, 880 insertions(+), 424 deletions(-) create mode 100644 ci/Dockerfile.namespace create mode 100644 tooling/xtask/src/tasks/workflows/release_nightly.rs diff --git a/.github/workflows/danger.yml b/.github/workflows/danger.yml index 0cdaf104d00acf4808d9300f21db5108a5f35a9c..1134167e05e29ffebfcf176b4f8c6cfc1b9e862d 100644 --- a/.github/workflows/danger.yml +++ b/.github/workflows/danger.yml @@ -18,7 +18,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: steps::setup_pnpm uses: pnpm/action-setup@fe02b34f77f8bc703788d5817da081398fad5dd2 with: diff --git a/.github/workflows/nix_build.yml b/.github/workflows/nix_build.yml index 386aa42a775c71895bf0a99db1779ebe315b79a2..cc6bac824f8374cd60bb5ce5dcfb19439ecdc22d 100644 --- a/.github/workflows/nix_build.yml +++ b/.github/workflows/nix_build.yml @@ -10,9 +10,9 @@ on: cachix-filter: type: string jobs: - nix-build-linux-x86: + build_nix_linux_x86_64: if: github.repository_owner == 'zed-industries' - runs-on: namespace-profile-16x32-ubuntu-2204 + runs-on: namespace-profile-32x64-ubuntu-2004 env: ZED_CLIENT_CHECKSUM_SEED: ${{ secrets.ZED_CLIENT_CHECKSUM_SEED }} ZED_MINIDUMP_ENDPOINT: ${{ secrets.ZED_SENTRY_MINIDUMP_ENDPOINT }} @@ -22,7 +22,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: nix_build::install_nix uses: cachix/install-nix-action@02a151ada4993995686f9ed4f1be7cfbb229e56f with: @@ -32,14 +32,14 @@ jobs: with: name: zed authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} - pushFilter: ${{ inputs.cachix-filter }} cachixArgs: -v + pushFilter: ${{ inputs.cachix-filter }} - name: nix_build::build run: nix build .#${{ inputs.flake-output }} -L --accept-flake-config shell: bash -euxo pipefail {0} timeout-minutes: 60 continue-on-error: true - nix-build-mac-arm: + build_nix_mac_aarch64: if: github.repository_owner == 'zed-industries' runs-on: self-mini-macos env: @@ -51,7 +51,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: nix_build::set_path run: | echo "/nix/var/nix/profiles/default/bin" >> "$GITHUB_PATH" @@ -62,8 +62,8 @@ jobs: with: name: zed authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} - pushFilter: ${{ inputs.cachix-filter }} cachixArgs: -v + pushFilter: ${{ inputs.cachix-filter }} - name: nix_build::build run: nix build .#${{ inputs.flake-output }} -L --accept-flake-config shell: bash -euxo pipefail {0} diff --git a/.github/workflows/release_nightly.yml b/.github/workflows/release_nightly.yml index fba1f8b67501b2d16d0bfcceb7528df15d144288..bc31296d2bc05920dfc38f7ead8946ba0a7753ef 100644 --- a/.github/workflows/release_nightly.yml +++ b/.github/workflows/release_nightly.yml @@ -1,93 +1,107 @@ -name: Release Nightly - -on: - schedule: - # Fire every day at 7:00am UTC (Roughly before EU workday and after US workday) - - cron: "0 7 * * *" - push: - tags: - - "nightly" - +# Generated from xtask::workflows::release_nightly +# Rebuild with `cargo xtask workflows`. +name: release_nightly env: CARGO_TERM_COLOR: always - CARGO_INCREMENTAL: 0 - RUST_BACKTRACE: 1 + CARGO_INCREMENTAL: '0' + RUST_BACKTRACE: '1' ZED_CLIENT_CHECKSUM_SEED: ${{ secrets.ZED_CLIENT_CHECKSUM_SEED }} ZED_MINIDUMP_ENDPOINT: ${{ secrets.ZED_SENTRY_MINIDUMP_ENDPOINT }} DIGITALOCEAN_SPACES_ACCESS_KEY: ${{ secrets.DIGITALOCEAN_SPACES_ACCESS_KEY }} DIGITALOCEAN_SPACES_SECRET_KEY: ${{ secrets.DIGITALOCEAN_SPACES_SECRET_KEY }} - +on: + push: + tags: + - nightly + schedule: + - cron: 0 7 * * * jobs: - style: - timeout-minutes: 60 - name: Check formatting and Clippy lints + check_style: if: github.repository_owner == 'zed-industries' - runs-on: - - self-hosted - - macOS + runs-on: self-mini-macos steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - fetch-depth: 0 - - - name: Run style checks - uses: ./.github/actions/check_style - - - name: Run clippy - run: ./script/clippy - - tests: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + fetch-depth: 0 + - name: steps::cargo_fmt + run: cargo fmt --all -- --check + shell: bash -euxo pipefail {0} + - name: ./script/clippy + run: ./script/clippy + shell: bash -euxo pipefail {0} timeout-minutes: 60 - name: Run tests + run_tests_mac: if: github.repository_owner == 'zed-industries' - runs-on: - - self-hosted - - macOS - needs: style + runs-on: self-mini-macos steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Run tests - uses: ./.github/actions/run_tests - - windows-tests: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_cargo_config + run: | + mkdir -p ./../.cargo + cp ./.cargo/ci-config.toml ./../.cargo/config.toml + shell: bash -euxo pipefail {0} + - name: steps::setup_node + uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 + with: + node-version: '20' + - name: steps::cargo_install_nextest + run: cargo install cargo-nextest --locked + shell: bash -euxo pipefail {0} + - name: steps::clear_target_dir_if_large + run: ./script/clear-target-dir-if-larger-than 300 + shell: bash -euxo pipefail {0} + - name: steps::cargo_nextest + run: cargo nextest run --workspace --no-fail-fast --failure-output immediate-final + shell: bash -euxo pipefail {0} + - name: steps::cleanup_cargo_config + if: always() + run: | + rm -rf ./../.cargo + shell: bash -euxo pipefail {0} timeout-minutes: 60 - name: Run tests on Windows + run_tests_windows: if: github.repository_owner == 'zed-industries' - runs-on: [self-32vcpu-windows-2022] + runs-on: self-32vcpu-windows-2022 steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Configure CI - run: | - New-Item -ItemType Directory -Path "./../.cargo" -Force - Copy-Item -Path "./.cargo/ci-config.toml" -Destination "./../.cargo/config.toml" - - - name: Run tests - uses: ./.github/actions/run_tests_windows - - - name: Limit target directory size - run: ./script/clear-target-dir-if-larger-than.ps1 1024 - - - name: Clean CI config file - if: always() - run: Remove-Item -Recurse -Path "./../.cargo" -Force -ErrorAction SilentlyContinue - - bundle-mac: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_cargo_config + run: | + New-Item -ItemType Directory -Path "./../.cargo" -Force + Copy-Item -Path "./.cargo/ci-config.toml" -Destination "./../.cargo/config.toml" + shell: pwsh + - name: steps::setup_node + uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 + with: + node-version: '20' + - name: steps::cargo_install_nextest + run: cargo install cargo-nextest --locked + shell: pwsh + - name: steps::clear_target_dir_if_large + run: ./script/clear-target-dir-if-larger-than.ps1 250 + shell: pwsh + - name: steps::cargo_nextest + run: cargo nextest run --workspace --no-fail-fast --failure-output immediate-final + shell: pwsh + - name: steps::cleanup_cargo_config + if: always() + run: | + Remove-Item -Recurse -Path "./../.cargo" -Force -ErrorAction SilentlyContinue + shell: pwsh timeout-minutes: 60 - name: Create a macOS bundle + bundle_mac_nightly: + needs: + - check_style + - run_tests_mac if: github.repository_owner == 'zed-industries' - runs-on: - - self-mini-macos - needs: tests + runs-on: self-mini-macos env: MACOS_CERTIFICATE: ${{ secrets.MACOS_CERTIFICATE }} MACOS_CERTIFICATE_PASSWORD: ${{ secrets.MACOS_CERTIFICATE_PASSWORD }} @@ -95,161 +109,120 @@ jobs: APPLE_NOTARIZATION_KEY_ID: ${{ secrets.APPLE_NOTARIZATION_KEY_ID }} APPLE_NOTARIZATION_ISSUER_ID: ${{ secrets.APPLE_NOTARIZATION_ISSUER_ID }} steps: - - name: Install Node - uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4 - with: - node-version: "18" - - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Set release channel to nightly - run: | - set -eu - version=$(git rev-parse --short HEAD) - echo "Publishing version: ${version} on release channel nightly" - echo "nightly" > crates/zed/RELEASE_CHANNEL - - - name: Setup Sentry CLI - uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b #v2 - with: - token: ${{ SECRETS.SENTRY_AUTH_TOKEN }} - - - name: Create macOS app bundle - run: script/bundle-mac - - - name: Upload Zed Nightly - run: script/upload-nightly macos - - bundle-linux-x86: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_node + uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 + with: + node-version: '20' + - name: steps::setup_sentry + uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b + with: + token: ${{ secrets.SENTRY_AUTH_TOKEN }} + - name: steps::clear_target_dir_if_large + run: ./script/clear-target-dir-if-larger-than 300 + shell: bash -euxo pipefail {0} + - name: release_nightly::set_release_channel_to_nightly + run: | + set -eu + version=$(git rev-parse --short HEAD) + echo "Publishing version: ${version} on release channel nightly" + echo "nightly" > crates/zed/RELEASE_CHANNEL + shell: bash -euxo pipefail {0} + - name: ./script/bundle-mac + run: ./script/bundle-mac + shell: bash -euxo pipefail {0} + - name: release_nightly::upload_zed_nightly + run: script/upload-nightly macos + shell: bash -euxo pipefail {0} timeout-minutes: 60 - name: Create a Linux *.tar.gz bundle for x86 + bundle_linux_nightly_x86_64: + needs: + - check_style + - run_tests_mac if: github.repository_owner == 'zed-industries' - runs-on: - - namespace-profile-16x32-ubuntu-2004 # ubuntu 20.04 for minimal glibc - needs: tests + runs-on: namespace-profile-32x64-ubuntu-2004 steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Add Rust to the PATH - run: echo "$HOME/.cargo/bin" >> "$GITHUB_PATH" - - - name: Install Linux dependencies - run: ./script/linux && ./script/install-mold 2.34.0 - - - name: Setup Sentry CLI - uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b #v2 - with: - token: ${{ SECRETS.SENTRY_AUTH_TOKEN }} - - - name: Limit target directory size - run: script/clear-target-dir-if-larger-than 100 - - - name: Set release channel to nightly - run: | - set -euo pipefail - version=$(git rev-parse --short HEAD) - echo "Publishing version: ${version} on release channel nightly" - echo "nightly" > crates/zed/RELEASE_CHANNEL - - - name: Create Linux .tar.gz bundle - run: script/bundle-linux - - - name: Upload Zed Nightly - run: script/upload-nightly linux-targz - - bundle-linux-arm: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_sentry + uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b + with: + token: ${{ secrets.SENTRY_AUTH_TOKEN }} + - name: release_nightly::add_rust_to_path + run: echo "$HOME/.cargo/bin" >> "$GITHUB_PATH" + shell: bash -euxo pipefail {0} + - name: ./script/linux + run: ./script/linux + shell: bash -euxo pipefail {0} + - name: ./script/install-mold + run: ./script/install-mold + shell: bash -euxo pipefail {0} + - name: steps::clear_target_dir_if_large + run: ./script/clear-target-dir-if-larger-than 100 + shell: bash -euxo pipefail {0} + - name: release_nightly::set_release_channel_to_nightly + run: | + set -eu + version=$(git rev-parse --short HEAD) + echo "Publishing version: ${version} on release channel nightly" + echo "nightly" > crates/zed/RELEASE_CHANNEL + shell: bash -euxo pipefail {0} + - name: ./script/bundle-linux + run: ./script/bundle-linux + shell: bash -euxo pipefail {0} + - name: release_nightly::upload_zed_nightly + run: script/upload-nightly linux-targz + shell: bash -euxo pipefail {0} timeout-minutes: 60 - name: Create a Linux *.tar.gz bundle for ARM + bundle_linux_nightly_aarch64: + needs: + - check_style + - run_tests_mac if: github.repository_owner == 'zed-industries' - runs-on: - - namespace-profile-8x32-ubuntu-2004-arm-m4 # ubuntu 20.04 for minimal glibc - needs: tests + runs-on: namespace-profile-8x32-ubuntu-2004-arm-m4 steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Install Linux dependencies - run: ./script/linux - - - name: Setup Sentry CLI - uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b #v2 - with: - token: ${{ SECRETS.SENTRY_AUTH_TOKEN }} - - - name: Limit target directory size - run: script/clear-target-dir-if-larger-than 100 - - - name: Set release channel to nightly - run: | - set -euo pipefail - version=$(git rev-parse --short HEAD) - echo "Publishing version: ${version} on release channel nightly" - echo "nightly" > crates/zed/RELEASE_CHANNEL - - - name: Create Linux .tar.gz bundle - run: script/bundle-linux - - - name: Upload Zed Nightly - run: script/upload-nightly linux-targz - - freebsd: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_sentry + uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b + with: + token: ${{ secrets.SENTRY_AUTH_TOKEN }} + - name: release_nightly::add_rust_to_path + run: echo "$HOME/.cargo/bin" >> "$GITHUB_PATH" + shell: bash -euxo pipefail {0} + - name: ./script/linux + run: ./script/linux + shell: bash -euxo pipefail {0} + - name: steps::clear_target_dir_if_large + run: ./script/clear-target-dir-if-larger-than 100 + shell: bash -euxo pipefail {0} + - name: release_nightly::set_release_channel_to_nightly + run: | + set -eu + version=$(git rev-parse --short HEAD) + echo "Publishing version: ${version} on release channel nightly" + echo "nightly" > crates/zed/RELEASE_CHANNEL + shell: bash -euxo pipefail {0} + - name: ./script/bundle-linux + run: ./script/bundle-linux + shell: bash -euxo pipefail {0} + - name: release_nightly::upload_zed_nightly + run: script/upload-nightly linux-targz + shell: bash -euxo pipefail {0} timeout-minutes: 60 - if: false && github.repository_owner == 'zed-industries' - runs-on: github-8vcpu-ubuntu-2404 - needs: tests - name: Build Zed on FreeBSD - steps: - - uses: actions/checkout@v4 - - name: Build FreeBSD remote-server - id: freebsd-build - uses: vmactions/freebsd-vm@c3ae29a132c8ef1924775414107a97cac042aad5 # v1.2.0 - with: - # envs: "MYTOKEN MYTOKEN2" - usesh: true - release: 13.5 - copyback: true - prepare: | - pkg install -y \ - bash curl jq git \ - rustup-init cmake-core llvm-devel-lite pkgconf protobuf # ibx11 alsa-lib rust-bindgen-cli - run: | - freebsd-version - sysctl hw.model - sysctl hw.ncpu - sysctl hw.physmem - sysctl hw.usermem - git config --global --add safe.directory /home/runner/work/zed/zed - rustup-init --profile minimal --default-toolchain none -y - . "$HOME/.cargo/env" - ./script/bundle-freebsd - mkdir -p out/ - mv "target/zed-remote-server-freebsd-x86_64.gz" out/ - rm -rf target/ - cargo clean - - - name: Upload Zed Nightly - run: script/upload-nightly freebsd - - bundle-nix: - name: Build and cache Nix package - needs: tests - secrets: inherit - uses: ./.github/workflows/nix_build.yml - - bundle-windows-x64: - timeout-minutes: 60 - name: Create a Windows installer for x86_64 + bundle_windows_nightly_x86_64: + needs: + - check_style + - run_tests_windows if: github.repository_owner == 'zed-industries' - runs-on: [self-32vcpu-windows-2022] - needs: windows-tests + runs-on: self-32vcpu-windows-2022 env: AZURE_TENANT_ID: ${{ secrets.AZURE_SIGNING_TENANT_ID }} AZURE_CLIENT_ID: ${{ secrets.AZURE_SIGNING_CLIENT_ID }} @@ -259,40 +232,39 @@ jobs: ENDPOINT: ${{ vars.AZURE_SIGNING_ENDPOINT }} FILE_DIGEST: SHA256 TIMESTAMP_DIGEST: SHA256 - TIMESTAMP_SERVER: "http://timestamp.acs.microsoft.com" + TIMESTAMP_SERVER: http://timestamp.acs.microsoft.com steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Set release channel to nightly - working-directory: ${{ env.ZED_WORKSPACE }} - run: | - $ErrorActionPreference = "Stop" - $version = git rev-parse --short HEAD - Write-Host "Publishing version: $version on release channel nightly" - "nightly" | Set-Content -Path "crates/zed/RELEASE_CHANNEL" - - - name: Setup Sentry CLI - uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b #v2 - with: - token: ${{ SECRETS.SENTRY_AUTH_TOKEN }} - - - name: Build Zed installer - working-directory: ${{ env.ZED_WORKSPACE }} - run: script/bundle-windows.ps1 -Architecture x86_64 - - - name: Upload Zed Nightly - working-directory: ${{ env.ZED_WORKSPACE }} - run: script/upload-nightly.ps1 -Architecture x86_64 - - bundle-windows-arm64: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_sentry + uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b + with: + token: ${{ secrets.SENTRY_AUTH_TOKEN }} + - name: release_nightly::set_release_channel_to_nightly + run: | + $ErrorActionPreference = "Stop" + $version = git rev-parse --short HEAD + Write-Host "Publishing version: $version on release channel nightly" + "nightly" | Set-Content -Path "crates/zed/RELEASE_CHANNEL" + shell: pwsh + working-directory: ${{ env.ZED_WORKSPACE }} + - name: release_nightly::build_zed_installer + run: script/bundle-windows.ps1 -Architecture x86_64 + shell: pwsh + working-directory: ${{ env.ZED_WORKSPACE }} + - name: release_nightly::upload_zed_nightly_windows + run: script/upload-nightly.ps1 -Architecture x86_64 + shell: pwsh + working-directory: ${{ env.ZED_WORKSPACE }} timeout-minutes: 60 - name: Create a Windows installer for aarch64 + bundle_windows_nightly_aarch64: + needs: + - check_style + - run_tests_windows if: github.repository_owner == 'zed-industries' - runs-on: [self-32vcpu-windows-2022] - needs: windows-tests + runs-on: self-32vcpu-windows-2022 env: AZURE_TENANT_ID: ${{ secrets.AZURE_SIGNING_TENANT_ID }} AZURE_CLIENT_ID: ${{ secrets.AZURE_SIGNING_CLIENT_ID }} @@ -302,66 +274,134 @@ jobs: ENDPOINT: ${{ vars.AZURE_SIGNING_ENDPOINT }} FILE_DIGEST: SHA256 TIMESTAMP_DIGEST: SHA256 - TIMESTAMP_SERVER: "http://timestamp.acs.microsoft.com" + TIMESTAMP_SERVER: http://timestamp.acs.microsoft.com steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - clean: false - - - name: Set release channel to nightly - working-directory: ${{ env.ZED_WORKSPACE }} - run: | - $ErrorActionPreference = "Stop" - $version = git rev-parse --short HEAD - Write-Host "Publishing version: $version on release channel nightly" - "nightly" | Set-Content -Path "crates/zed/RELEASE_CHANNEL" - - - name: Setup Sentry CLI - uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b #v2 - with: - token: ${{ SECRETS.SENTRY_AUTH_TOKEN }} - - - name: Build Zed installer - working-directory: ${{ env.ZED_WORKSPACE }} - run: script/bundle-windows.ps1 -Architecture aarch64 - - - name: Upload Zed Nightly - working-directory: ${{ env.ZED_WORKSPACE }} - run: script/upload-nightly.ps1 -Architecture aarch64 - - update-nightly-tag: - name: Update nightly tag + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: steps::setup_sentry + uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b + with: + token: ${{ secrets.SENTRY_AUTH_TOKEN }} + - name: release_nightly::set_release_channel_to_nightly + run: | + $ErrorActionPreference = "Stop" + $version = git rev-parse --short HEAD + Write-Host "Publishing version: $version on release channel nightly" + "nightly" | Set-Content -Path "crates/zed/RELEASE_CHANNEL" + shell: pwsh + working-directory: ${{ env.ZED_WORKSPACE }} + - name: release_nightly::build_zed_installer + run: script/bundle-windows.ps1 -Architecture aarch64 + shell: pwsh + working-directory: ${{ env.ZED_WORKSPACE }} + - name: release_nightly::upload_zed_nightly_windows + run: script/upload-nightly.ps1 -Architecture aarch64 + shell: pwsh + working-directory: ${{ env.ZED_WORKSPACE }} + timeout-minutes: 60 + build_nix_linux_x86_64: + needs: + - check_style + - run_tests_mac if: github.repository_owner == 'zed-industries' - runs-on: namespace-profile-2x4-ubuntu-2404 + runs-on: namespace-profile-32x64-ubuntu-2004 + env: + ZED_CLIENT_CHECKSUM_SEED: ${{ secrets.ZED_CLIENT_CHECKSUM_SEED }} + ZED_MINIDUMP_ENDPOINT: ${{ secrets.ZED_SENTRY_MINIDUMP_ENDPOINT }} + ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON: ${{ secrets.ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON }} + GIT_LFS_SKIP_SMUDGE: '1' + steps: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: nix_build::install_nix + uses: cachix/install-nix-action@02a151ada4993995686f9ed4f1be7cfbb229e56f + with: + github_access_token: ${{ secrets.GITHUB_TOKEN }} + - name: nix_build::cachix_action + uses: cachix/cachix-action@0fc020193b5a1fa3ac4575aa3a7d3aa6a35435ad + with: + name: zed + authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} + cachixArgs: -v + - name: nix_build::build + run: nix build .#default -L --accept-flake-config + shell: bash -euxo pipefail {0} + timeout-minutes: 60 + continue-on-error: true + build_nix_mac_aarch64: needs: - - bundle-mac - - bundle-linux-x86 - - bundle-linux-arm - - bundle-windows-x64 - - bundle-windows-arm64 + - check_style + - run_tests_mac + if: github.repository_owner == 'zed-industries' + runs-on: self-mini-macos + env: + ZED_CLIENT_CHECKSUM_SEED: ${{ secrets.ZED_CLIENT_CHECKSUM_SEED }} + ZED_MINIDUMP_ENDPOINT: ${{ secrets.ZED_SENTRY_MINIDUMP_ENDPOINT }} + ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON: ${{ secrets.ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON }} + GIT_LFS_SKIP_SMUDGE: '1' steps: - - name: Checkout repo - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4 - with: - fetch-depth: 0 - - - name: Update nightly tag - run: | - if [ "$(git rev-parse nightly)" = "$(git rev-parse HEAD)" ]; then - echo "Nightly tag already points to current commit. Skipping tagging." - exit 0 - fi - git config user.name github-actions - git config user.email github-actions@github.com - git tag -f nightly - git push origin nightly --force - - - name: Create Sentry release - uses: getsentry/action-release@526942b68292201ac6bbb99b9a0747d4abee354c # v3 - env: - SENTRY_ORG: zed-dev - SENTRY_PROJECT: zed - SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} - with: - environment: production + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + - name: nix_build::set_path + run: | + echo "/nix/var/nix/profiles/default/bin" >> "$GITHUB_PATH" + echo "/Users/administrator/.nix-profile/bin" >> "$GITHUB_PATH" + shell: bash -euxo pipefail {0} + - name: nix_build::cachix_action + uses: cachix/cachix-action@0fc020193b5a1fa3ac4575aa3a7d3aa6a35435ad + with: + name: zed + authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} + cachixArgs: -v + - name: nix_build::build + run: nix build .#default -L --accept-flake-config + shell: bash -euxo pipefail {0} + - name: nix_build::limit_store + run: |- + if [ "$(du -sm /nix/store | cut -f1)" -gt 50000 ]; then + nix-collect-garbage -d || true + fi + shell: bash -euxo pipefail {0} + timeout-minutes: 60 + continue-on-error: true + update_nightly_tag: + needs: + - bundle_mac_nightly + - bundle_linux_nightly_x86_64 + - bundle_linux_nightly_aarch64 + - bundle_windows_nightly_x86_64 + - bundle_windows_nightly_aarch64 + if: github.repository_owner == 'zed-industries' + runs-on: namespace-profile-2x4-ubuntu-2404 + steps: + - name: steps::checkout_repo + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + clean: false + fetch-depth: 0 + - name: release_nightly::update_nightly_tag + run: | + if [ "$(git rev-parse nightly)" = "$(git rev-parse HEAD)" ]; then + echo "Nightly tag already points to current commit. Skipping tagging." + exit 0 + fi + git config user.name github-actions + git config user.email github-actions@github.com + git tag -f nightly + git push origin nightly --force + shell: bash -euxo pipefail {0} + - name: release_nightly::create_sentry_release + uses: getsentry/action-release@526942b68292201ac6bbb99b9a0747d4abee354c + with: + environment: production + env: + SENTRY_ORG: zed-dev + SENTRY_PROJECT: zed + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} + timeout-minutes: 60 diff --git a/.github/workflows/run_bundling.yml b/.github/workflows/run_bundling.yml index 95700fae48d343c392433cd882f9c71cd88a6ccb..d78298e69a9c14c8412d789a10b5b2139f76e693 100644 --- a/.github/workflows/run_bundling.yml +++ b/.github/workflows/run_bundling.yml @@ -28,7 +28,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: steps::setup_node uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 with: @@ -38,10 +38,8 @@ jobs: with: token: ${{ secrets.SENTRY_AUTH_TOKEN }} - name: steps::clear_target_dir_if_large - run: script/clear-target-dir-if-larger-than ${{ env.MAX_SIZE }} + run: ./script/clear-target-dir-if-larger-than 300 shell: bash -euxo pipefail {0} - env: - MAX_SIZE: ${{ runner.os == 'macOS' && 300 || 100 }} - name: ./script/bundle-mac run: ./script/bundle-mac shell: bash -euxo pipefail {0} @@ -65,7 +63,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: steps::setup_sentry uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b with: @@ -99,7 +97,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: steps::setup_sentry uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b with: @@ -140,7 +138,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: steps::setup_sentry uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b with: @@ -174,7 +172,7 @@ jobs: - name: steps::checkout_repo uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 with: - clean: 'false' + clean: false - name: steps::setup_sentry uses: matbour/setup-sentry-cli@3e938c54b3018bdd019973689ef984e033b0454b with: diff --git a/Cargo.lock b/Cargo.lock index 53ef3873b3d9704555bcf9035dcae7136618dbf7..ceeb849fe5d009067913558c0bdf9b71acc4ebc3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6957,7 +6957,7 @@ dependencies = [ [[package]] name = "gh-workflow" version = "0.8.0" -source = "git+https://github.com/zed-industries/gh-workflow?rev=fe5fd50664bfe164277cab5c86537a2361eddbbd#fe5fd50664bfe164277cab5c86537a2361eddbbd" +source = "git+https://github.com/zed-industries/gh-workflow?rev=0090c6b6ef82fff02bc8616645953e778d1acc08#0090c6b6ef82fff02bc8616645953e778d1acc08" dependencies = [ "async-trait", "derive_more 2.0.1", @@ -6974,7 +6974,7 @@ dependencies = [ [[package]] name = "gh-workflow-macros" version = "0.8.0" -source = "git+https://github.com/zed-industries/gh-workflow?rev=fe5fd50664bfe164277cab5c86537a2361eddbbd#fe5fd50664bfe164277cab5c86537a2361eddbbd" +source = "git+https://github.com/zed-industries/gh-workflow?rev=0090c6b6ef82fff02bc8616645953e778d1acc08#0090c6b6ef82fff02bc8616645953e778d1acc08" dependencies = [ "heck 0.5.0", "quote", diff --git a/Cargo.toml b/Cargo.toml index 4c5975bd050afd774a8cd6c47006b146919c6b38..369082ff16736f9f682ad8c5bd09634c03434609 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -508,7 +508,7 @@ fork = "0.2.0" futures = "0.3" futures-batch = "0.6.1" futures-lite = "1.13" -gh-workflow = { git = "https://github.com/zed-industries/gh-workflow", rev = "fe5fd50664bfe164277cab5c86537a2361eddbbd" } +gh-workflow = { git = "https://github.com/zed-industries/gh-workflow", rev = "0090c6b6ef82fff02bc8616645953e778d1acc08" } git2 = { version = "0.20.1", default-features = false } globset = "0.4" handlebars = "4.3" diff --git a/ci/Dockerfile.namespace b/ci/Dockerfile.namespace new file mode 100644 index 0000000000000000000000000000000000000000..f370dae194a0a3e614354ba70f65237e27c3382e --- /dev/null +++ b/ci/Dockerfile.namespace @@ -0,0 +1,21 @@ +ARG NAMESPACE_BASE_IMAGE_REF="" + +# Your image must build FROM NAMESPACE_BASE_IMAGE_REF +FROM ${NAMESPACE_BASE_IMAGE_REF} AS base + +# Remove problematic git-lfs packagecloud source +RUN sudo rm -f /etc/apt/sources.list.d/*git-lfs*.list +# Install git and SSH for cloning private repositories +RUN sudo apt-get update && \ + sudo apt-get install -y git openssh-client + +# Clone the Zed repository +RUN git clone https://github.com/zed-industries/zed.git ~/zed + +# Run the Linux installation script +WORKDIR /home/runner/zed +RUN ./script/linux + +# Clean up unnecessary files to reduce image size +RUN sudo apt-get clean && sudo rm -rf \ + /home/runner/zed diff --git a/tooling/xtask/src/tasks/workflows.rs b/tooling/xtask/src/tasks/workflows.rs index 063279b818ecf07983d76597b22c76179c0eca93..b86f31cbd26321998d1b1c26d94459d512e7d817 100644 --- a/tooling/xtask/src/tasks/workflows.rs +++ b/tooling/xtask/src/tasks/workflows.rs @@ -5,9 +5,8 @@ use std::path::Path; mod danger; mod nix_build; -// mod release; +mod release_nightly; mod run_bundling; -// mod run_tests; mod runners; mod steps; @@ -23,6 +22,7 @@ pub fn run_workflows(_: GenerateWorkflowArgs) -> Result<()> { ("danger.yml", danger::danger()), ("nix_build.yml", nix_build::nix_build()), ("run_bundling.yml", run_bundling::run_bundling()), + ("release_nightly.yml", release_nightly::release_nightly()), // ("run_tests.yml", run_tests::run_tests()), // ("release.yml", release::release()), ]; diff --git a/tooling/xtask/src/tasks/workflows/nix_build.rs b/tooling/xtask/src/tasks/workflows/nix_build.rs index 73a73e523c3b03b78c99cf5669172568e73962b9..1406f2a1e12518c39d65d208205d6abd3ea38bb4 100644 --- a/tooling/xtask/src/tasks/workflows/nix_build.rs +++ b/tooling/xtask/src/tasks/workflows/nix_build.rs @@ -1,23 +1,14 @@ +use crate::tasks::workflows::{ + runners::{Arch, Platform}, + steps::NamedJob, +}; + use super::{runners, steps, steps::named, vars}; use gh_workflow::*; -use indexmap::IndexMap; use indoc::indoc; /// Generates the nix.yml workflow pub fn nix_build() -> Workflow { - let env: IndexMap<_, _> = [ - ("ZED_CLIENT_CHECKSUM_SEED", vars::ZED_CLIENT_CHECKSUM_SEED), - ("ZED_MINIDUMP_ENDPOINT", vars::ZED_SENTRY_MINIDUMP_ENDPOINT), - ( - "ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON", - vars::ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON, - ), - ("GIT_LFS_SKIP_SMUDGE", "1"), // breaks the livekit rust sdk examples which we don't actually depend on - ] - .into_iter() - .map(|(key, value)| (key.into(), value.into())) - .collect(); - // todo(ci) instead of having these as optional YAML inputs, // should we just generate two copies of the job (one for release-nightly // and one for CI?) @@ -37,44 +28,80 @@ pub fn nix_build() -> Workflow { }, ); + let linux_x86 = build_nix( + Platform::Linux, + Arch::X86_64, + &input_flake_output, + Some(&input_cachix_filter), + &[], + ); + let mac_arm = build_nix( + Platform::Mac, + Arch::ARM64, + &input_flake_output, + Some(&input_cachix_filter), + &[], + ); + named::workflow() .on(Event::default().workflow_call( WorkflowCall::default() .add_input(flake_output.0, flake_output.1) .add_input(cachix_filter.0, cachix_filter.1), )) - .add_job( - "nix-build-linux-x86", - Job::default() - .timeout_minutes(60u32) - .continue_on_error(true) - .cond(Expression::new( - "github.repository_owner == 'zed-industries'", - )) - .runs_on(runners::LINUX_DEFAULT) - .envs(env.clone()) - .add_step(steps::checkout_repo().add_with(("clean", "false"))) - .add_step(install_nix()) - .add_step(cachix_action(&input_cachix_filter)) - .add_step(build(&input_flake_output)), - ) - .add_job( - "nix-build-mac-arm", - Job::default() - .timeout_minutes(60u32) - .continue_on_error(true) - .cond(Expression::new( - "github.repository_owner == 'zed-industries'", - )) - .runs_on(runners::MAC_DEFAULT) - .envs(env) - .add_step(steps::checkout_repo().add_with(("clean", "false"))) - .add_step(set_path()) - .add_step(cachix_action(&input_cachix_filter)) - .add_step(build(&input_flake_output)) - .add_step(limit_store()), - ) + .add_job(linux_x86.name, linux_x86.job) + .add_job(mac_arm.name, mac_arm.job) +} + +pub(crate) fn build_nix( + platform: Platform, + arch: Arch, + flake_output: &str, + cachix_filter: Option<&str>, + deps: &[&NamedJob], +) -> NamedJob { + let runner = match platform { + Platform::Windows => unimplemented!(), + Platform::Linux => runners::LINUX_X86_BUNDLER, + Platform::Mac => runners::MAC_DEFAULT, + }; + let mut job = Job::default() + .timeout_minutes(60u32) + .continue_on_error(true) + .cond(Expression::new( + "github.repository_owner == 'zed-industries'", + )) + .runs_on(runner) + .add_env(("ZED_CLIENT_CHECKSUM_SEED", vars::ZED_CLIENT_CHECKSUM_SEED)) + .add_env(("ZED_MINIDUMP_ENDPOINT", vars::ZED_SENTRY_MINIDUMP_ENDPOINT)) + .add_env(( + "ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON", + vars::ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON, + )) + .add_env(("GIT_LFS_SKIP_SMUDGE", "1")) // breaks the livekit rust sdk examples which we don't actually depend on + .add_step(steps::checkout_repo()); + + if deps.len() > 0 { + job = job.needs(deps.iter().map(|d| d.name.clone()).collect::>()); + } + + job = if platform == Platform::Linux { + job.add_step(install_nix()) + .add_step(cachix_action(cachix_filter)) + .add_step(build(&flake_output)) + } else { + job.add_step(set_path()) + .add_step(cachix_action(cachix_filter)) + .add_step(build(&flake_output)) + .add_step(limit_store()) + }; + + NamedJob { + name: format!("build_nix_{platform}_{arch}"), + job, + } } + // on our macs we manually install nix. for some reason the cachix action is running // under a non-login /bin/bash shell which doesn't source the proper script to add the // nix profile to PATH, so we manually add them here @@ -94,16 +121,19 @@ pub fn install_nix() -> Step { .add_with(("github_access_token", vars::GITHUB_TOKEN)) } -pub fn cachix_action(cachix_filter: &str) -> Step { - named::uses( +pub fn cachix_action(cachix_filter: Option<&str>) -> Step { + let mut step = named::uses( "cachix", "cachix-action", "0fc020193b5a1fa3ac4575aa3a7d3aa6a35435ad", // v16 ) .add_with(("name", "zed")) .add_with(("authToken", vars::CACHIX_AUTH_TOKEN)) - .add_with(("pushFilter", cachix_filter)) - .add_with(("cachixArgs", "-v")) + .add_with(("cachixArgs", "-v")); + if let Some(cachix_filter) = cachix_filter { + step = step.add_with(("pushFilter", cachix_filter)); + } + step } pub fn build(flake_output: &str) -> Step { diff --git a/tooling/xtask/src/tasks/workflows/release_nightly.rs b/tooling/xtask/src/tasks/workflows/release_nightly.rs new file mode 100644 index 0000000000000000000000000000000000000000..18134fd153244d192207bc7fac011b8854b9ab0a --- /dev/null +++ b/tooling/xtask/src/tasks/workflows/release_nightly.rs @@ -0,0 +1,270 @@ +use crate::tasks::workflows::{ + nix_build::build_nix, + runners::{Arch, Platform}, + steps::NamedJob, + vars::{mac_bundle_envs, windows_bundle_envs}, +}; + +use super::{runners, steps, steps::named, vars}; +use gh_workflow::*; +use indexmap::IndexMap; + +/// Generates the release_nightly.yml workflow +pub fn release_nightly() -> Workflow { + let env: IndexMap<_, _> = [ + ("CARGO_TERM_COLOR", "always"), + ("CARGO_INCREMENTAL", "0"), + ("RUST_BACKTRACE", "1"), + ("ZED_CLIENT_CHECKSUM_SEED", vars::ZED_CLIENT_CHECKSUM_SEED), + ("ZED_MINIDUMP_ENDPOINT", vars::ZED_SENTRY_MINIDUMP_ENDPOINT), + ( + "DIGITALOCEAN_SPACES_ACCESS_KEY", + vars::DIGITALOCEAN_SPACES_ACCESS_KEY, + ), + ( + "DIGITALOCEAN_SPACES_SECRET_KEY", + vars::DIGITALOCEAN_SPACES_SECRET_KEY, + ), + ] + .into_iter() + .map(|(key, value)| (key.into(), value.into())) + .collect(); + + let style = check_style(); + let tests = run_tests(Platform::Mac); + let windows_tests = run_tests(Platform::Windows); + let bundle_mac = bundle_mac_nightly(&[&style, &tests]); + let linux_x86 = bundle_linux_nightly(Arch::X86_64, &[&style, &tests]); + let linux_arm = bundle_linux_nightly(Arch::ARM64, &[&style, &tests]); + let windows_x86 = bundle_windows_nightly(Arch::X86_64, &[&style, &windows_tests]); + let windows_arm = bundle_windows_nightly(Arch::ARM64, &[&style, &windows_tests]); + + let nix_linux_x86 = build_nix( + Platform::Linux, + Arch::X86_64, + "default", + None, + &[&style, &tests], + ); + let nix_mac_arm = build_nix( + Platform::Mac, + Arch::ARM64, + "default", + None, + &[&style, &tests], + ); + let update_nightly_tag = update_nightly_tag_job(&[ + &bundle_mac, + &linux_x86, + &linux_arm, + &windows_x86, + &windows_arm, + ]); + + named::workflow() + .on(Event::default() + // Fire every day at 7:00am UTC (Roughly before EU workday and after US workday) + .schedule([Schedule::new("0 7 * * *")]) + .push(Push::default().add_tag("nightly"))) + .envs(env) + .add_job(style.name, style.job) + .add_job(tests.name, tests.job) + .add_job(windows_tests.name, windows_tests.job) + .add_job(bundle_mac.name, bundle_mac.job) + .add_job(linux_x86.name, linux_x86.job) + .add_job(linux_arm.name, linux_arm.job) + .add_job(windows_x86.name, windows_x86.job) + .add_job(windows_arm.name, windows_arm.job) + .add_job(nix_linux_x86.name, nix_linux_x86.job) + .add_job(nix_mac_arm.name, nix_mac_arm.job) + .add_job(update_nightly_tag.name, update_nightly_tag.job) +} + +fn check_style() -> NamedJob { + let job = release_job(&[]) + .runs_on(runners::MAC_DEFAULT) + .add_step( + steps::checkout_repo() + .add_with(("clean", false)) + .add_with(("fetch-depth", 0)), + ) + .add_step(steps::cargo_fmt()) + .add_step(steps::script("./script/clippy")); + + named::job(job) +} + +fn release_job(deps: &[&NamedJob]) -> Job { + let job = Job::default() + .cond(Expression::new( + "github.repository_owner == 'zed-industries'", + )) + .timeout_minutes(60u32); + if deps.len() > 0 { + job.needs(deps.iter().map(|j| j.name.clone()).collect::>()) + } else { + job + } +} + +fn run_tests(platform: Platform) -> NamedJob { + let runner = match platform { + Platform::Windows => runners::WINDOWS_DEFAULT, + Platform::Linux => runners::LINUX_DEFAULT, + Platform::Mac => runners::MAC_DEFAULT, + }; + NamedJob { + name: format!("run_tests_{platform}"), + job: release_job(&[]) + .runs_on(runner) + .add_step(steps::checkout_repo()) + .add_step(steps::setup_cargo_config(platform)) + .add_step(steps::setup_node()) + .add_step(steps::cargo_install_nextest(platform)) + .add_step(steps::clear_target_dir_if_large(platform)) + .add_step(steps::cargo_nextest(platform)) + .add_step(steps::cleanup_cargo_config(platform)), + } +} + +fn bundle_mac_nightly(deps: &[&NamedJob]) -> NamedJob { + let platform = Platform::Mac; + let job = release_job(deps) + .runs_on(runners::MAC_DEFAULT) + .envs(mac_bundle_envs()) + .add_step(steps::checkout_repo()) + .add_step(steps::setup_node()) + .add_step(steps::setup_sentry()) + .add_step(steps::clear_target_dir_if_large(platform)) + .add_step(set_release_channel_to_nightly(platform)) + .add_step(steps::script("./script/bundle-mac")) + .add_step(upload_zed_nightly(platform, Arch::ARM64)); + named::job(job) +} + +fn bundle_linux_nightly(arch: Arch, deps: &[&NamedJob]) -> NamedJob { + let platform = Platform::Linux; + let mut job = release_job(deps) + .runs_on(arch.linux_bundler()) + .add_step(steps::checkout_repo()) + .add_step(steps::setup_sentry()) + .add_step(add_rust_to_path()) + .add_step(steps::script("./script/linux")); + + // todo(ci) can we do this on arm too? + if arch == Arch::X86_64 { + job = job.add_step(steps::script("./script/install-mold")); + } + job = job + .add_step(steps::clear_target_dir_if_large(platform)) + .add_step(set_release_channel_to_nightly(platform)) + .add_step(steps::script("./script/bundle-linux")) + .add_step(upload_zed_nightly(platform, arch)); + NamedJob { + name: format!("bundle_linux_nightly_{arch}"), + job, + } +} + +fn bundle_windows_nightly(arch: Arch, deps: &[&NamedJob]) -> NamedJob { + let platform = Platform::Windows; + NamedJob { + name: format!("bundle_windows_nightly_{arch}"), + job: release_job(deps) + .runs_on(runners::WINDOWS_DEFAULT) + .envs(windows_bundle_envs()) + .add_step(steps::checkout_repo()) + .add_step(steps::setup_sentry()) + .add_step(set_release_channel_to_nightly(platform)) + .add_step(build_zed_installer(arch)) + .add_step(upload_zed_nightly_windows(arch)), + } +} + +fn update_nightly_tag_job(deps: &[&NamedJob]) -> NamedJob { + NamedJob { + name: "update_nightly_tag".to_owned(), + job: release_job(deps) + .runs_on(runners::LINUX_CHEAP) + .add_step(steps::checkout_repo().add_with(("fetch-depth", 0))) + .add_step(update_nightly_tag()) + .add_step(create_sentry_release()), + } +} + +fn set_release_channel_to_nightly(platform: Platform) -> Step { + match platform { + Platform::Linux | Platform::Mac => named::bash(indoc::indoc! {r#" + set -eu + version=$(git rev-parse --short HEAD) + echo "Publishing version: ${version} on release channel nightly" + echo "nightly" > crates/zed/RELEASE_CHANNEL + "#}), + Platform::Windows => named::pwsh(indoc::indoc! {r#" + $ErrorActionPreference = "Stop" + $version = git rev-parse --short HEAD + Write-Host "Publishing version: $version on release channel nightly" + "nightly" | Set-Content -Path "crates/zed/RELEASE_CHANNEL" + "#}) + .working_directory("${{ env.ZED_WORKSPACE }}"), + } +} + +fn add_rust_to_path() -> Step { + named::bash(r#"echo "$HOME/.cargo/bin" >> "$GITHUB_PATH""#) +} + +fn upload_zed_nightly(platform: Platform, arch: Arch) -> Step { + match platform { + Platform::Linux => named::bash("script/upload-nightly linux-targz"), + Platform::Mac => named::bash("script/upload-nightly macos"), + Platform::Windows => { + let cmd = match arch { + Arch::X86_64 => "script/upload-nightly.ps1 -Architecture x86_64", + Arch::ARM64 => "script/upload-nightly.ps1 -Architecture aarch64", + }; + named::pwsh(cmd).working_directory("${{ env.ZED_WORKSPACE }}") + } + } +} + +fn build_zed_installer(arch: Arch) -> Step { + let cmd = match arch { + Arch::X86_64 => "script/bundle-windows.ps1 -Architecture x86_64", + Arch::ARM64 => "script/bundle-windows.ps1 -Architecture aarch64", + }; + named::pwsh(cmd).working_directory("${{ env.ZED_WORKSPACE }}") +} + +fn upload_zed_nightly_windows(arch: Arch) -> Step { + let cmd = match arch { + Arch::X86_64 => "script/upload-nightly.ps1 -Architecture x86_64", + Arch::ARM64 => "script/upload-nightly.ps1 -Architecture aarch64", + }; + named::pwsh(cmd).working_directory("${{ env.ZED_WORKSPACE }}") +} + +fn update_nightly_tag() -> Step { + named::bash(indoc::indoc! {r#" + if [ "$(git rev-parse nightly)" = "$(git rev-parse HEAD)" ]; then + echo "Nightly tag already points to current commit. Skipping tagging." + exit 0 + fi + git config user.name github-actions + git config user.email github-actions@github.com + git tag -f nightly + git push origin nightly --force + "#}) +} + +fn create_sentry_release() -> Step { + named::uses( + "getsentry", + "action-release", + "526942b68292201ac6bbb99b9a0747d4abee354c", // v3 + ) + .add_env(("SENTRY_ORG", "zed-dev")) + .add_env(("SENTRY_PROJECT", "zed")) + .add_env(("SENTRY_AUTH_TOKEN", vars::SENTRY_AUTH_TOKEN)) + .add_with(("environment", "production")) +} diff --git a/tooling/xtask/src/tasks/workflows/run_bundling.rs b/tooling/xtask/src/tasks/workflows/run_bundling.rs index d2e657a9ac045269870bee1f7493c4d0377b61cf..45e4940e32ef35f8890d17a03b41466f301c9411 100644 --- a/tooling/xtask/src/tasks/workflows/run_bundling.rs +++ b/tooling/xtask/src/tasks/workflows/run_bundling.rs @@ -1,4 +1,7 @@ -use crate::tasks::workflows::steps::named; +use crate::tasks::workflows::{ + steps::named, + vars::{mac_bundle_envs, windows_bundle_envs}, +}; use super::{runners, steps, vars}; use gh_workflow::*; @@ -21,14 +24,14 @@ pub fn run_bundling() -> Workflow { .add_env(("ZED_MINIDUMP_ENDPOINT", vars::ZED_SENTRY_MINIDUMP_ENDPOINT)) .add_job("bundle_mac", bundle_mac()) .add_job("bundle_linux_x86_64", bundle_linux(runners::Arch::X86_64)) - .add_job("bundle_linux_arm64", bundle_linux(runners::Arch::AARCH64)) + .add_job("bundle_linux_arm64", bundle_linux(runners::Arch::ARM64)) .add_job( "bundle_windows_x86_64", bundle_windows_job(runners::Arch::X86_64), ) .add_job( "bundle_windows_arm64", - bundle_windows_job(runners::Arch::AARCH64), + bundle_windows_job(runners::Arch::ARM64), ) } @@ -44,21 +47,11 @@ fn bundle_job() -> Job { fn bundle_mac() -> Job { bundle_job() .runs_on(runners::MAC_DEFAULT) - .add_env(("MACOS_CERTIFICATE", vars::MACOS_CERTIFICATE)) - .add_env(( - "MACOS_CERTIFICATE_PASSWORD", - vars::MACOS_CERTIFICATE_PASSWORD, - )) - .add_env(("APPLE_NOTARIZATION_KEY", vars::APPLE_NOTARIZATION_KEY)) - .add_env(("APPLE_NOTARIZATION_KEY_ID", vars::APPLE_NOTARIZATION_KEY_ID)) - .add_env(( - "APPLE_NOTARIZATION_ISSUER_ID", - vars::APPLE_NOTARIZATION_ISSUER_ID, - )) + .envs(mac_bundle_envs()) .add_step(steps::checkout_repo()) .add_step(steps::setup_node()) .add_step(steps::setup_sentry()) - .add_step(steps::clear_target_dir_if_large()) + .add_step(steps::clear_target_dir_if_large(runners::Platform::Mac)) .add_step(steps::script("./script/bundle-mac")) .add_step(steps::upload_artifact( "Zed_${{ github.event.pull_request.head.sha || github.sha }}-aarch64.dmg", @@ -101,15 +94,7 @@ fn bundle_windows_job(arch: runners::Arch) -> Job { use vars::GITHUB_SHA; bundle_job() .runs_on(runners::WINDOWS_DEFAULT) - .add_env(("AZURE_TENANT_ID", vars::AZURE_SIGNING_TENANT_ID)) - .add_env(("AZURE_CLIENT_ID", vars::AZURE_SIGNING_CLIENT_ID)) - .add_env(("AZURE_CLIENT_SECRET", vars::AZURE_SIGNING_CLIENT_SECRET)) - .add_env(("ACCOUNT_NAME", vars::AZURE_SIGNING_ACCOUNT_NAME)) - .add_env(("CERT_PROFILE_NAME", vars::AZURE_SIGNING_CERT_PROFILE_NAME)) - .add_env(("ENDPOINT", vars::AZURE_SIGNING_ENDPOINT)) - .add_env(("FILE_DIGEST", "SHA256")) - .add_env(("TIMESTAMP_DIGEST", "SHA256")) - .add_env(("TIMESTAMP_SERVER", "http://timestamp.acs.microsoft.com")) + .envs(windows_bundle_envs()) .add_step(steps::checkout_repo()) .add_step(steps::setup_sentry()) .add_step(bundle_windows(arch)) @@ -122,7 +107,7 @@ fn bundle_windows_job(arch: runners::Arch) -> Job { fn bundle_windows(arch: runners::Arch) -> Step { let step = match arch { runners::Arch::X86_64 => named::pwsh("script/bundle-windows.ps1 -Architecture x86_64"), - runners::Arch::AARCH64 => named::pwsh("script/bundle-windows.ps1 -Architecture aarch64"), + runners::Arch::ARM64 => named::pwsh("script/bundle-windows.ps1 -Architecture aarch64"), }; step.working_directory("${{ env.ZED_WORKSPACE }}") } diff --git a/tooling/xtask/src/tasks/workflows/runners.rs b/tooling/xtask/src/tasks/workflows/runners.rs index edd8594682e38c43c3f10f9ed2cac90bc4613f98..02263ef42bb54dc31c10bfa07a4dde76010fdd85 100644 --- a/tooling/xtask/src/tasks/workflows/runners.rs +++ b/tooling/xtask/src/tasks/workflows/runners.rs @@ -19,14 +19,14 @@ impl Into for Runner { #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub enum Arch { X86_64, - AARCH64, + ARM64, } impl std::fmt::Display for Arch { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { match self { Arch::X86_64 => write!(f, "x86_64"), - Arch::AARCH64 => write!(f, "aarch64"), + Arch::ARM64 => write!(f, "aarch64"), } } } @@ -35,14 +35,31 @@ impl Arch { pub fn triple(&self) -> &'static str { match self { Arch::X86_64 => "x86_64-unknown-linux-gnu", - Arch::AARCH64 => "aarch64-unknown-linux-gnu", + Arch::ARM64 => "aarch64-unknown-linux-gnu", } } pub fn linux_bundler(&self) -> Runner { match self { Arch::X86_64 => LINUX_X86_BUNDLER, - Arch::AARCH64 => LINUX_ARM_BUNDLER, + Arch::ARM64 => LINUX_ARM_BUNDLER, + } + } +} + +#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] +pub enum Platform { + Windows, + Linux, + Mac, +} + +impl std::fmt::Display for Platform { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + match self { + Platform::Windows => write!(f, "windows"), + Platform::Linux => write!(f, "linux"), + Platform::Mac => write!(f, "mac"), } } } diff --git a/tooling/xtask/src/tasks/workflows/steps.rs b/tooling/xtask/src/tasks/workflows/steps.rs index 957ba2eacc7afc09a186ec57a8fca8c99be3b069..235fcd64b1e40c8809c4c237f4bbcdcb37874acd 100644 --- a/tooling/xtask/src/tasks/workflows/steps.rs +++ b/tooling/xtask/src/tasks/workflows/steps.rs @@ -1,6 +1,6 @@ use gh_workflow::*; -use crate::tasks::workflows::vars; +use crate::tasks::workflows::{runners::Platform, vars}; const BASH_SHELL: &str = "bash -euxo pipefail {0}"; // https://docs.github.com/en/actions/reference/workflows-and-actions/workflow-syntax#jobsjob_idstepsshell @@ -44,6 +44,48 @@ pub fn setup_sentry() -> Step { .add_with(("token", vars::SENTRY_AUTH_TOKEN)) } +pub fn cargo_fmt() -> Step { + named::bash("cargo fmt --all -- --check") +} + +pub fn cargo_install_nextest(platform: Platform) -> Step { + named::run(platform, "cargo install cargo-nextest --locked") +} + +pub fn cargo_nextest(platform: Platform) -> Step { + named::run( + platform, + "cargo nextest run --workspace --no-fail-fast --failure-output immediate-final", + ) +} + +pub fn setup_cargo_config(platform: Platform) -> Step { + match platform { + Platform::Windows => named::pwsh(indoc::indoc! {r#" + New-Item -ItemType Directory -Path "./../.cargo" -Force + Copy-Item -Path "./.cargo/ci-config.toml" -Destination "./../.cargo/config.toml" + "#}), + + Platform::Linux | Platform::Mac => named::bash(indoc::indoc! {r#" + mkdir -p ./../.cargo + cp ./.cargo/ci-config.toml ./../.cargo/config.toml + "#}), + } +} + +pub fn cleanup_cargo_config(platform: Platform) -> Step { + let step = match platform { + Platform::Windows => named::pwsh(indoc::indoc! {r#" + Remove-Item -Recurse -Path "./../.cargo" -Force -ErrorAction SilentlyContinue + "#}), + Platform::Linux | Platform::Mac => named::bash(indoc::indoc! {r#" + rm -rf ./../.cargo + "#}), + }; + + step.if_condition(Expression::new("always()")) +} + pub fn upload_artifact(name: &str, path: &str) -> Step { Step::new(format!("@actions/upload-artifact {}", name)) .uses( @@ -55,9 +97,12 @@ pub fn upload_artifact(name: &str, path: &str) -> Step { .add_with(("path", path)) } -pub fn clear_target_dir_if_large() -> Step { - named::bash("script/clear-target-dir-if-larger-than ${{ env.MAX_SIZE }}") - .add_env(("MAX_SIZE", "${{ runner.os == 'macOS' && 300 || 100 }}")) +pub fn clear_target_dir_if_large(platform: Platform) -> Step { + match platform { + Platform::Windows => named::pwsh("./script/clear-target-dir-if-larger-than.ps1 250"), + Platform::Linux => named::bash("./script/clear-target-dir-if-larger-than 100"), + Platform::Mac => named::bash("./script/clear-target-dir-if-larger-than 300"), + } } pub fn script(name: &str) -> Step { @@ -68,6 +113,11 @@ pub fn script(name: &str) -> Step { } } +pub(crate) struct NamedJob { + pub name: String, + pub job: Job, +} + // (janky) helper to generate steps with a name that corresponds // to the name of the calling function. pub(crate) mod named { @@ -94,6 +144,18 @@ pub(crate) mod named { Step::new(function_name(1)).run(script).shell(PWSH_SHELL) } + /// Runs the command in either powershell or bash, depending on platform. + /// (You shouldn't inline this function into the workflow definition, you must + /// wrap it in a new function.) + pub(crate) fn run(platform: Platform, script: &str) -> Step { + match platform { + Platform::Windows => Step::new(function_name(1)).run(script).shell(PWSH_SHELL), + Platform::Linux | Platform::Mac => { + Step::new(function_name(1)).run(script).shell(BASH_SHELL) + } + } + } + /// Returns a Workflow with the same name as the enclosing module. pub(crate) fn workflow() -> Workflow { Workflow::default().name( @@ -105,6 +167,15 @@ pub(crate) mod named { ) } + /// Returns a Job with the same name as the enclosing function. + /// (note job names may not contain `::`) + pub(crate) fn job(job: Job) -> NamedJob { + NamedJob { + name: function_name(1).split("::").last().unwrap().to_owned(), + job, + } + } + /// Returns the function name N callers above in the stack /// (typically 1). /// This only works because xtask always runs debug builds. diff --git a/tooling/xtask/src/tasks/workflows/vars.rs b/tooling/xtask/src/tasks/workflows/vars.rs index adcb0707749671b6f9e1814114a1ccdfea372046..6220e3960b091dc04798283ff7239a56ffef5eb0 100644 --- a/tooling/xtask/src/tasks/workflows/vars.rs +++ b/tooling/xtask/src/tasks/workflows/vars.rs @@ -1,4 +1,4 @@ -use gh_workflow::WorkflowCallInput; +use gh_workflow::{Env, WorkflowCallInput}; macro_rules! secret { ($secret_name:ident) => { @@ -16,20 +16,22 @@ pub fn input(name: &str, input: WorkflowCallInput) -> (String, (&str, WorkflowCa return (format!("${{{{ inputs.{name} }}}}"), (name, input)); } -secret!(GITHUB_TOKEN); -secret!(CACHIX_AUTH_TOKEN); -secret!(ZED_CLIENT_CHECKSUM_SEED); -secret!(ZED_SENTRY_MINIDUMP_ENDPOINT); -secret!(ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON); -secret!(MACOS_CERTIFICATE); -secret!(MACOS_CERTIFICATE_PASSWORD); +secret!(APPLE_NOTARIZATION_ISSUER_ID); secret!(APPLE_NOTARIZATION_KEY); secret!(APPLE_NOTARIZATION_KEY_ID); -secret!(APPLE_NOTARIZATION_ISSUER_ID); -secret!(SENTRY_AUTH_TOKEN); -secret!(AZURE_SIGNING_TENANT_ID); secret!(AZURE_SIGNING_CLIENT_ID); secret!(AZURE_SIGNING_CLIENT_SECRET); +secret!(AZURE_SIGNING_TENANT_ID); +secret!(CACHIX_AUTH_TOKEN); +secret!(DIGITALOCEAN_SPACES_ACCESS_KEY); +secret!(DIGITALOCEAN_SPACES_SECRET_KEY); +secret!(GITHUB_TOKEN); +secret!(MACOS_CERTIFICATE); +secret!(MACOS_CERTIFICATE_PASSWORD); +secret!(SENTRY_AUTH_TOKEN); +secret!(ZED_CLIENT_CHECKSUM_SEED); +secret!(ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON); +secret!(ZED_SENTRY_MINIDUMP_ENDPOINT); // todo(ci) make these secrets too... var!(AZURE_SIGNING_ACCOUNT_NAME); @@ -37,3 +39,25 @@ var!(AZURE_SIGNING_CERT_PROFILE_NAME); var!(AZURE_SIGNING_ENDPOINT); pub const GITHUB_SHA: &str = "${{ github.event.pull_request.head.sha || github.sha }}"; + +pub fn mac_bundle_envs() -> Env { + Env::default() + .add("MACOS_CERTIFICATE", MACOS_CERTIFICATE) + .add("MACOS_CERTIFICATE_PASSWORD", MACOS_CERTIFICATE_PASSWORD) + .add("APPLE_NOTARIZATION_KEY", APPLE_NOTARIZATION_KEY) + .add("APPLE_NOTARIZATION_KEY_ID", APPLE_NOTARIZATION_KEY_ID) + .add("APPLE_NOTARIZATION_ISSUER_ID", APPLE_NOTARIZATION_ISSUER_ID) +} + +pub fn windows_bundle_envs() -> Env { + Env::default() + .add("AZURE_TENANT_ID", AZURE_SIGNING_TENANT_ID) + .add("AZURE_CLIENT_ID", AZURE_SIGNING_CLIENT_ID) + .add("AZURE_CLIENT_SECRET", AZURE_SIGNING_CLIENT_SECRET) + .add("ACCOUNT_NAME", AZURE_SIGNING_ACCOUNT_NAME) + .add("CERT_PROFILE_NAME", AZURE_SIGNING_CERT_PROFILE_NAME) + .add("ENDPOINT", AZURE_SIGNING_ENDPOINT) + .add("FILE_DIGEST", "SHA256") + .add("TIMESTAMP_DIGEST", "SHA256") + .add("TIMESTAMP_SERVER", "http://timestamp.acs.microsoft.com") +}