Skip to content

Pull Request for 1201/merge by dfrankland #3801

Pull Request for 1201/merge by dfrankland

Pull Request for 1201/merge by dfrankland #3801

Workflow file for this run

name: Pull Request
run-name: Pull Request for ${{ github.ref_name }} by ${{ github.actor }}
concurrency:
group: ${{ github.head_ref || github.run_id }}
cancel-in-progress: true
permissions: write-all
on:
pull_request: {}
workflow_dispatch: {}
push:
branches:
- main
env:
CARGO_TERM_COLOR: always
jobs:
# Trunk decides which jobs this PR needs. Fails open: no verdict means no
# output, so every gate below tests `!= 'false'`. Gating is scoped to
# pull_request -- push (main), tags and dispatch run everything outright.
dynamic-ci-filter:
name: Dynamic CI Filter
runs-on: ubuntu-latest
timeout-minutes: 5
if: github.event_name == 'pull_request'
# Per-job outputs are set at runtime, so they are re-exported here by name.
outputs:
build_release: ${{ steps.ci-filter.outputs.build_release }}
test: ${{ steps.ci-filter.outputs.test }}
trunk_check_runner: ${{ steps.ci-filter.outputs.trunk_check_runner }}
build_pyo3: ${{ steps.ci-filter.outputs.build_pyo3 }}
build_wasm: ${{ steps.ci-filter.outputs.build_wasm }}
steps:
- name: Run Dynamic CI Filter
id: ci-filter
uses: trunk-io/dynamic-ci@v1
with:
# Prod, not staging: this repo's merge queue lives in prod.
token: ${{ secrets.TRUNK_PROD_ORG_API_TOKEN }}
build_release:
name: Build CLI for ${{ matrix.platform.target }}
needs: [dynamic-ci-filter]
# Also runs when `test` is wanted: it consumes this job's binary artifact.
if: >-
!cancelled() &&
(github.event_name != 'pull_request' ||
needs.dynamic-ci-filter.outputs.build_release != 'false' ||
needs.dynamic-ci-filter.outputs.test != 'false')
strategy:
matrix:
platform:
- os-name: linux-x86_64
runs-on: ubuntu-latest
target: x86_64-unknown-linux-musl
- os-name: linux-aarch64
runs-on: ubuntu-24.04-arm
target: aarch64-unknown-linux-musl
- os-name: x86_64-darwin
runs-on: macos-latest
target: x86_64-apple-darwin
- os-name: aarch64-darwin
runs-on: macos-latest
target: aarch64-apple-darwin
- os-name: windows-x86_64
runs-on: public-amd64-4xlarge-dind-germany
target: x86_64-pc-windows-gnu
runs-on: ${{ matrix.platform.runs-on }}
steps:
# we've been hitting out of free space issues
- name: Delete unnecessary tools folder
run: rm -rf /opt/hostedtoolcache
- name: Install build tools (Windows and Linux build)
shell: bash
if: ${{ !contains(matrix.platform.os-name, 'darwin') }}
run: |
sudo bash -c 'cat << EOF > /etc/apt/sources.list
deb http://mirror.hetzner.com/ubuntu/packages jammy main restricted universe multiverse
deb http://mirror.hetzner.com/ubuntu/packages jammy-updates main restricted universe multiverse
deb http://mirror.hetzner.com/ubuntu/packages jammy-backports main restricted universe multiverse
deb http://mirror.hetzner.com/ubuntu/packages jammy-security main restricted universe multiverse
EOF'
sudo apt-get update
sudo apt-get install -y git-lfs build-essential
git lfs install
- name: Checkout
uses: actions/checkout@v4
with:
lfs: "true"
- name: Setup Rust & Cargo
uses: ./.github/actions/setup_rust_cargo
- name: Build darwin target
uses: ./.github/actions/build_cli_macos_target
if: contains(matrix.platform.os-name, 'darwin')
with:
target: ${{ matrix.platform.target }}
profile: release
force-sentry-dev: true
- name: Build unix/Windows target
uses: ./.github/actions/build_cli_linux_windows_target
if: ${{ !contains(matrix.platform.os-name, 'darwin') }}
with:
target: ${{ matrix.platform.target }}
profile: release
force-sentry-dev: true
- name: Upload built binary
uses: actions/upload-artifact@v4
if: always()
with:
name: binary-${{ matrix.platform.target }}
path: target/${{ matrix.platform.target }}/release/trunk-analytics-cli*
retention-days: 1
test:
name: Test for ${{ matrix.platform.target }}
needs: [build_release, dynamic-ci-filter]
if: >-
!cancelled() &&
needs.build_release.result == 'success' &&
(github.event_name != 'pull_request' ||
needs.dynamic-ci-filter.outputs.test != 'false')
strategy:
matrix:
platform:
- os-name: linux-x86_64
runs-on: ubuntu-latest
target: x86_64-unknown-linux-musl
- os-name: linux-aarch64
runs-on: ubuntu-24.04-arm
target: aarch64-unknown-linux-musl
- os-name: x86_64-darwin
runs-on: macos-latest
target: x86_64-apple-darwin
- os-name: aarch64-darwin
runs-on: macos-latest
target: aarch64-apple-darwin
- os-name: windows-x86_64
runs-on: public-amd64-4xlarge-dind-germany
target: x86_64-pc-windows-gnu
runs-on: ${{ matrix.platform.runs-on }}
steps:
# we've been hitting out of free space issues
- name: Delete unnecessary tools folder
run: rm -rf /opt/hostedtoolcache
- name: Install build tools (Windows and Linux build)
shell: bash
if: ${{ !contains(matrix.platform.os-name, 'darwin') }}
run: |
sudo bash -c 'cat << EOF > /etc/apt/sources.list
deb http://mirror.hetzner.com/ubuntu/packages jammy main restricted universe multiverse
deb http://mirror.hetzner.com/ubuntu/packages jammy-updates main restricted universe multiverse
deb http://mirror.hetzner.com/ubuntu/packages jammy-backports main restricted universe multiverse
deb http://mirror.hetzner.com/ubuntu/packages jammy-security main restricted universe multiverse
EOF'
sudo apt-get update
sudo apt-get install -y git-lfs build-essential
git lfs install
- name: Checkout
uses: actions/checkout@v4
with:
lfs: "true"
- name: Setup Rust & Cargo
uses: ./.github/actions/setup_rust_cargo
# This is a canary test to ensure that the github actions crate is working
# as expected in a real environment. If this fails, we should investigate
# why the github actions crate is not working as expected. This test relies
# on the github actions crate to be able to extract the job ID from the logs,
# which is an undocumented feature that can break at any moment.
- name: canary - Test github actions crate
shell: bash
run: |
cargo run --bin github-actions -- -v
if [[ "$?" -ne 0 ]]; then
echo "Failed to run github-actions crate"
exit 1
fi
# The declaration path finds `sourcekit-lsp` on `PATH`, which is where every documented
# Linux install puts it. The Ubuntu runner image is the exception: it symlinks only
# `swift` and `swiftc` into /usr/local/bin and leaves the rest of the toolchain reachable
# only through $SWIFT_PATH. Without this the swift-test-xunit tests find no server.
- name: Put the Swift toolchain on PATH
if: ${{ startsWith(matrix.platform.os-name, 'linux-') }}
shell: bash
run: |
if [[ -z "${SWIFT_PATH:-}" ]]; then
echo "SWIFT_PATH is unset - the runner image no longer ships Swift where expected" >&2
exit 1
fi
echo "$SWIFT_PATH" >> "$GITHUB_PATH"
- name: Run tests
uses: ./.github/actions/run_tests
id: tests
continue-on-error: true
env:
# macOS finds the server through `xcrun`, and the step above puts it on `PATH` for
# Linux -- so anywhere but the self-hosted Windows runner, which has no Swift at all,
# a missing server means the environment broke rather than that these should skip.
REQUIRE_LANGUAGE_SERVER: ${{ matrix.platform.os-name != 'windows-x86_64' && '1' || '' }}
with:
target: ${{ matrix.platform.target }}
codecov-token: ${{ secrets.CODECOV_TOKEN }}
- name: Download built binary
uses: actions/download-artifact@v4
with:
name: binary-${{ matrix.platform.target }}
path: target/${{ matrix.platform.target }}/release/
- name: Make binary executable
shell: bash
if: ${{ !contains(matrix.platform.os-name, 'windows') }}
run: chmod +x target/${{ matrix.platform.target }}/release/trunk-analytics-cli
- name: Extract step outcome
shell: bash
id: extract
run: |
if [[ "${{steps.tests.outcome}}" == "failure" ]]; then
echo "test-step-outcome=1" >> $GITHUB_OUTPUT
else
echo "test-step-outcome=0" >> $GITHUB_OUTPUT
fi
# Repo monitors: https://app.trunk-staging.io/trunk-staging-org/flaky-tests/repo/a84c7f42-9400-4bc4-a469-6dab0c859ac5/monitor
- name: Upload results to staging using built CLI
env:
TRUNK_PUBLIC_API_ADDRESS: https://api.trunk-staging.io
shell: bash
# Skip Windows builds - can't run Windows binaries on Linux runners
# Windows binaries are tested in the release workflow on actual Windows runners
if: ${{ !contains(matrix.platform.target, 'illumos') && !contains(matrix.platform.os-name, 'windows') }}
run: |
target/${{ matrix.platform.target }}/release/trunk-analytics-cli upload \
--junit-paths ${{ github.workspace }}/target/**/*junit.xml \
--org-url-slug trunk-staging-org \
--token ${{ secrets.TRUNK_STAGING_ORG_API_TOKEN }} \
--test-process-exit-code ${{ steps.extract.outputs.test-step-outcome }} \
--test-collection-id 2tYJWMu7 \
--variant ${{ matrix.platform.target }}
# analytics-cli-pr: https://app.trunk-staging.io/trunk-staging-org/flaky-tests/collections/2tYJWMu7/monitors
- name: Upload results to staging using built CLI (repo-wide collection)
env:
TRUNK_PUBLIC_API_ADDRESS: https://api.trunk-staging.io
shell: bash
# Skip Windows builds - can't run Windows binaries on Linux runners
# Windows binaries are tested in the release workflow on actual Windows runners
if: ${{ !contains(matrix.platform.target, 'illumos') && !contains(matrix.platform.os-name, 'windows') }}
run: |
target/${{ matrix.platform.target }}/release/trunk-analytics-cli upload \
--junit-paths ${{ github.workspace }}/target/**/*junit.xml \
--org-url-slug trunk-staging-org \
--token ${{ secrets.TRUNK_STAGING_ORG_API_TOKEN }} \
--test-process-exit-code ${{ steps.extract.outputs.test-step-outcome }} \
--test-collection-id Gtnr7BWl \
--variant ${{ matrix.platform.target }}
# analytics-cli-repo-wide: https://app.trunk-staging.io/trunk-staging-org/flaky-tests/collections/Gtnr7BWl/monitors
# Repo monitors: https://app.trunk.io/trunk/flaky-tests/repo/d442f488-c374-4913-af40-d0eae875b5cb/monitor
- name: Upload results to prod using built CLI
shell: bash
# Skip Windows builds - can't run Windows binaries on Linux runners
# Windows binaries are tested in the release workflow on actual Windows runners
if: ${{ !contains(matrix.platform.target, 'illumos') && !contains(matrix.platform.os-name, 'windows') }}
run: |
target/${{ matrix.platform.target }}/release/trunk-analytics-cli upload \
--junit-paths ${{ github.workspace }}/target/**/*junit.xml \
--org-url-slug trunk \
--token ${{ secrets.TRUNK_PROD_ORG_API_TOKEN }} \
--test-collection-id EWhNPVic \
--variant ${{ matrix.platform.target }}
# analytics-cli-pr: https://app.trunk.io/trunk/flaky-tests/collections/EWhNPVic/monitors
trunk_check_runner:
name: Trunk Check runner [linux]
runs-on: ubuntu-latest
needs: [dynamic-ci-filter]
if: >-
!cancelled() &&
(github.event_name != 'pull_request' ||
needs.dynamic-ci-filter.outputs.trunk_check_runner != 'false')
steps:
- uses: actions/checkout@v4
- name: Delete huge unnecessary tools folder
run: rm -rf /opt/hostedtoolcache
- name: Setup Rust & Cargo
uses: ./.github/actions/setup_rust_cargo
- name: Setup Ruby
uses: ./.github/actions/setup_ruby
- name: Build workspace
run: cargo build --all
- name: Setup and build wasm
uses: ./.github/actions/setup_build_wasm
# pyright type-checks context-py against context_py.pyi, which is generated rather than
# committed. Without this, every symbol imported from context_py is `Unknown` and each new
# import is a fresh pyright finding. The wasm step above exists for the same reason on the
# JS side -- eslint needs the generated pkg/ to resolve.
- name: Generate Python stubs
run: cargo run --bin stub_gen --manifest-path context-py/Cargo.toml --no-default-features
- name: Trunk Check
uses: trunk-io/trunk-action@v1
with:
cache: false
build_pyo3:
name: Build context-py
runs-on: ubuntu-latest
needs: [dynamic-ci-filter]
if: >-
!cancelled() &&
(github.event_name != 'pull_request' ||
needs.dynamic-ci-filter.outputs.build_pyo3 != 'false')
steps:
- uses: actions/checkout@v4
- name: Delete huge unnecessary tools folder
run: rm -rf /opt/hostedtoolcache
- name: Setup and build pyo3
uses: ./.github/actions/setup_build_pyo3
build_wasm:
name: Build context-js (WASM)
runs-on: ubuntu-latest
needs: [dynamic-ci-filter]
if: >-
!cancelled() &&
(github.event_name != 'pull_request' ||
needs.dynamic-ci-filter.outputs.build_wasm != 'false')
steps:
- uses: actions/checkout@v4
- name: Delete huge unnecessary tools folder
run: rm -rf /opt/hostedtoolcache
- name: Setup and build wasm
uses: ./.github/actions/setup_build_wasm
gate:
name: PR Gate
runs-on: ubuntu-latest
timeout-minutes: 5
# Branch-protection fan-in: one stable required context for this whole workflow.
# A matrix job skipped by its job-level `if:` reports a single check run under the
# *unexpanded* name (`Test for ${{ matrix.platform.target }}`) because the matrix is
# never evaluated -- so per-leg contexts never report and required checks hang on
# "Expected". This job always runs, so its name always reports.
if: always()
needs: [build_release, test, trunk_check_runner, build_pyo3, build_wasm]
steps:
- name: Check fan-in results
env:
RESULTS: ${{ join(needs.*.result, ' ') }}
shell: bash
run: |
read -ra results <<<"${RESULTS}"
for result in "${results[@]}"; do
case "${result}" in
# A skipped job is a pass: it was deliberately not run for this change.
success | skipped) ;;
*)
echo "::error::a needed job reported '${result}'"
exit 1
;;
esac
done
echo "needed jobs all passed or were skipped: ${RESULTS}"