Reduce Subtensor compilation time and run E2E tests a few times faster #4
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Bittensor Bittensor E2E Test | |
| permissions: | |
| pull-requests: write | |
| contents: read | |
| concurrency: | |
| group: e2e-cli-${{ github.ref }} | |
| cancel-in-progress: true | |
| on: | |
| pull_request: | |
| branches: ["*"] | |
| types: [opened, synchronize, reopened, labeled, unlabeled] | |
| workflow_dispatch: | |
| inputs: | |
| verbose: | |
| description: "Output more information when triggered manually" | |
| required: false | |
| default: "" | |
| env: | |
| CARGO_TERM_COLOR: always | |
| VERBOSE: ${{ github.event.inputs.verbose }} | |
| jobs: | |
| check-label: | |
| runs-on: ubuntu-latest | |
| outputs: | |
| skip-bittensor-e2e-tests: ${{ steps.get-labels.outputs.skip-bittensor-e2e-tests || steps.set-default.outputs.skip-bittensor-e2e-tests }} | |
| steps: | |
| - name: Install dependencies | |
| run: | | |
| sudo DEBIAN_FRONTEND=noninteractive NEEDRESTART_MODE=a apt-get update | |
| sudo DEBIAN_FRONTEND=noninteractive NEEDRESTART_MODE=a apt-get install -y --no-install-recommends -o Dpkg::Options::="--force-confdef" -o Dpkg::Options::="--force-confold" gh jq | |
| - name: Check out repository | |
| uses: actions/checkout@v4 | |
| with: | |
| repository: ${{ github.event.pull_request.head.repo.full_name || github.repository }} | |
| ref: ${{ github.event.pull_request.head.ref || github.ref_name }} | |
| - name: Get labels from PR | |
| id: get-labels | |
| if: github.event_name == 'pull_request' | |
| run: | | |
| LABELS=$(gh pr -R ${{ github.repository }} view ${{ github.event.pull_request.number }} --json labels --jq '.labels[].name') | |
| echo "Current labels: $LABELS" | |
| if echo "$LABELS" | grep -q "skip-bittensor-e2e-tests"; then | |
| echo "skip-bittensor-e2e-tests=true" >> $GITHUB_OUTPUT | |
| else | |
| echo "skip-bittensor-e2e-tests=false" >> $GITHUB_OUTPUT | |
| fi | |
| env: | |
| GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Set default skip value for workflow_dispatch | |
| id: set-default | |
| if: github.event_name == 'workflow_dispatch' | |
| run: | | |
| echo "skip-bittensor-e2e-tests=false" >> $GITHUB_OUTPUT | |
| find-btcli-e2e-tests: | |
| needs: check-label | |
| if: needs.check-label.outputs.skip-bittensor-e2e-tests == 'false' | |
| runs-on: ubuntu-latest | |
| outputs: | |
| test-files: ${{ steps.get-btcli-tests.outputs.test-files }} | |
| steps: | |
| - name: Install dependencies | |
| run: | | |
| sudo DEBIAN_FRONTEND=noninteractive NEEDRESTART_MODE=a apt-get update | |
| sudo DEBIAN_FRONTEND=noninteractive NEEDRESTART_MODE=a apt-get install -y --no-install-recommends -o Dpkg::Options::="--force-confdef" -o Dpkg::Options::="--force-confold" jq | |
| - name: Research preparation | |
| working-directory: ${{ github.workspace }} | |
| run: git clone https://github.com/opentensor/btcli.git | |
| - name: Checkout | |
| working-directory: ${{ github.workspace }}/btcli | |
| run: git checkout staging | |
| - name: Find e2e test files | |
| id: get-btcli-tests | |
| run: | | |
| test_files=$(find ${{ github.workspace }}/btcli/tests/e2e_tests -name "test*.py" | jq -R -s -c 'split("\n") | map(select(. != ""))') | |
| echo "test-files=$test_files" >> $GITHUB_OUTPUT | |
| shell: bash | |
| find-sdk-e2e-tests: | |
| needs: check-label | |
| if: needs.check-label.outputs.skip-bittensor-e2e-tests == 'false' | |
| runs-on: ubuntu-latest | |
| outputs: | |
| test-files: ${{ steps.get-sdk-tests.outputs.test-files }} | |
| steps: | |
| - name: Install dependencies | |
| run: | | |
| sudo DEBIAN_FRONTEND=noninteractive NEEDRESTART_MODE=a apt-get update | |
| sudo DEBIAN_FRONTEND=noninteractive NEEDRESTART_MODE=a apt-get install -y --no-install-recommends -o Dpkg::Options::="--force-confdef" -o Dpkg::Options::="--force-confold" jq | |
| - name: Research preparation | |
| working-directory: ${{ github.workspace }} | |
| run: git clone https://github.com/opentensor/bittensor.git | |
| - name: Checkout | |
| working-directory: ${{ github.workspace }}/bittensor | |
| run: git checkout staging | |
| - name: Find e2e test files | |
| id: get-sdk-tests | |
| run: | | |
| test_files=$(find ${{ github.workspace }}/bittensor/tests/e2e_tests -name "test*.py" | jq -R -s -c 'split("\n") | map(select(. != ""))') | |
| echo "test-files=$test_files" >> $GITHUB_OUTPUT | |
| shell: bash | |
| # build artifacts for non-fast-runtime (e2e tests only need this) | |
| artifacts: | |
| name: Node β’ ${{ matrix.runtime }} β’ ${{ matrix.platform.arch }} | |
| needs: check-label | |
| if: needs.check-label.outputs.skip-bittensor-e2e-tests == 'false' | |
| strategy: | |
| matrix: | |
| platform: | |
| - triple: x86_64-unknown-linux-gnu | |
| arch: amd64 | |
| runtime: ["non-fast-runtime"] | |
| runs-on: ubuntu-latest | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| with: | |
| repository: ${{ github.event.pull_request.head.repo.full_name || github.repository }} | |
| ref: ${{ github.event.pull_request.head.ref || github.ref_name }} | |
| - name: Install Rust + dependencies | |
| run: | | |
| chmod +x ./scripts/install_build_env.sh | |
| ./scripts/install_build_env.sh | |
| - name: Add Rust target triple | |
| run: | | |
| source "$HOME/.cargo/env" | |
| rustup target add ${{ matrix.platform.triple }} | |
| - name: Patch limits for local run | |
| run: | | |
| chmod +x ./scripts/localnet_patch.sh | |
| ./scripts/localnet_patch.sh | |
| - name: Build binaries | |
| run: | | |
| export PATH="$HOME/.cargo/bin:$PATH" | |
| export CARGO_BUILD_TARGET="${{ matrix.platform.triple }}" | |
| ./scripts/localnet.sh False --build-only | |
| # use `ci_target` name bc .dockerignore excludes `target` | |
| - name: Prepare artifacts for upload | |
| run: | | |
| RUNTIME="${{ matrix.runtime }}" | |
| TRIPLE="${{ matrix.platform.triple }}" | |
| # Verify binaries exist before copying | |
| BINARY_PATH="target/${RUNTIME}/${TRIPLE}/release/node-subtensor" | |
| WASM_PATH="target/${RUNTIME}/${TRIPLE}/release/wbuild/node-subtensor-runtime/node_subtensor_runtime.compact.compressed.wasm" | |
| if [[ ! -f "$BINARY_PATH" ]]; then | |
| echo "β Error: Binary not found at $BINARY_PATH" | |
| exit 1 | |
| fi | |
| if [[ ! -f "$WASM_PATH" ]]; then | |
| echo "β Error: WASM file not found at $WASM_PATH" | |
| exit 1 | |
| fi | |
| mkdir -p build/ci_target/${RUNTIME}/${TRIPLE}/release/ | |
| cp -v "$BINARY_PATH" \ | |
| build/ci_target/${RUNTIME}/${TRIPLE}/release/ | |
| mkdir -p build/ci_target/${RUNTIME}/${TRIPLE}/release/wbuild/node-subtensor-runtime/ | |
| cp -v "$WASM_PATH" \ | |
| build/ci_target/${RUNTIME}/${TRIPLE}/release/wbuild/node-subtensor-runtime/ | |
| - name: Upload artifact | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: binaries-${{ matrix.platform.triple }}-${{ matrix.runtime }} | |
| path: build/ | |
| if-no-files-found: error | |
| # Collect all artifacts and build a Docker image | |
| build-image-with-current-branch: | |
| needs: [check-label, artifacts] | |
| if: needs.check-label.outputs.skip-bittensor-e2e-tests == 'false' | |
| runs-on: ubuntu-latest | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| with: | |
| repository: ${{ github.event.pull_request.head.repo.full_name || github.repository }} | |
| ref: ${{ github.event.pull_request.head.ref || github.ref_name }} | |
| - name: Download all binary artifacts | |
| uses: actions/download-artifact@v5 | |
| with: | |
| pattern: binaries-* | |
| path: build/ | |
| merge-multiple: true | |
| - name: Move Docker data-root to /mnt/data | |
| run: | | |
| sudo systemctl stop docker | |
| sudo mkdir -p /mnt/data/docker | |
| sudo chown -R runner:runner /mnt/data | |
| sudo chmod -R 777 /mnt/data | |
| echo '{"data-root": "/mnt/data/docker"}' | sudo tee /etc/docker/daemon.json | |
| sudo systemctl start docker | |
| docker info | grep "Docker Root Dir" | |
| - name: Build Docker Image | |
| run: docker build -f Dockerfile-localnet -t localnet . | |
| - name: Save Docker Image as Tar | |
| run: docker save -o /mnt/data/subtensor-localnet.tar localnet | |
| - name: Upload Docker Image as Artifact | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: subtensor-localnet | |
| path: /mnt/data/subtensor-localnet.tar | |
| # main btcli job | |
| run-btcli-e2e-tests: | |
| needs: | |
| - check-label | |
| - find-btcli-e2e-tests | |
| - build-image-with-current-branch | |
| if: needs.check-label.outputs.skip-bittensor-e2e-tests == 'false' | |
| runs-on: ubuntu-latest | |
| strategy: | |
| fail-fast: false | |
| max-parallel: 16 | |
| matrix: | |
| rust-branch: | |
| - stable | |
| rust-target: | |
| - x86_64-unknown-linux-gnu | |
| os: | |
| - ubuntu-latest | |
| test-file: ${{ fromJson(needs.find-btcli-e2e-tests.outputs.test-files) }} | |
| env: | |
| RELEASE_NAME: development | |
| RUSTV: ${{ matrix.rust-branch }} | |
| RUST_BACKTRACE: full | |
| RUST_BIN_DIR: target/${{ matrix.rust-target }} | |
| TARGET: ${{ matrix.rust-target }} | |
| timeout-minutes: 60 | |
| name: "cli: ${{ matrix.test-file }}" | |
| steps: | |
| - name: Check-out repository | |
| uses: actions/checkout@v4 | |
| with: | |
| repository: ${{ github.event.pull_request.head.repo.full_name || github.repository }} | |
| ref: ${{ github.event.pull_request.head.ref || github.ref_name }} | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v5 | |
| with: | |
| enable-cache: "false" | |
| - name: Create Python virtual environment | |
| working-directory: ${{ github.workspace }} | |
| run: uv venv --seed ${{ github.workspace }}/venv | |
| - name: Clone Bittensor CLI repo | |
| working-directory: ${{ github.workspace }} | |
| run: git clone https://github.com/opentensor/btcli.git | |
| - name: Setup Bittensor-cli from cloned repo | |
| working-directory: ${{ github.workspace }}/btcli | |
| run: | | |
| source ${{ github.workspace }}/venv/bin/activate | |
| git checkout staging | |
| git fetch origin staging | |
| uv run --active pip install --upgrade pip | |
| uv run --active pip install '.[dev]' | |
| uv run --active pip install pytest | |
| - name: Download Cached Docker Image | |
| uses: actions/download-artifact@v4 | |
| with: | |
| name: subtensor-localnet | |
| - name: Load Docker Image | |
| run: docker load -i subtensor-localnet.tar | |
| - name: Retag Docker Image | |
| run: docker tag localnet ghcr.io/opentensor/subtensor-localnet:devnet-ready | |
| - name: Run with retry | |
| working-directory: ${{ github.workspace }}/btcli | |
| run: | | |
| source ${{ github.workspace }}/venv/bin/activate | |
| export SKIP_PULL=1 | |
| set +e | |
| for i in 1 2; do | |
| echo "π Attempt $i: Running tests" | |
| uv run pytest ${{ matrix.test-file }} -s | |
| status=$? | |
| if [ $status -eq 0 ]; then | |
| echo "β Tests passed on attempt $i" | |
| break | |
| else | |
| echo "β Tests failed on attempt $i" | |
| if [ $i -eq 2 ]; then | |
| echo "π₯ Tests failed after 2 attempts" | |
| exit 1 | |
| fi | |
| echo "π Retrying..." | |
| sleep 5 | |
| fi | |
| done | |
| # main sdk job | |
| run-sdk-e2e-tests: | |
| needs: | |
| - check-label | |
| - find-sdk-e2e-tests | |
| - build-image-with-current-branch | |
| if: needs.check-label.outputs.skip-bittensor-e2e-tests == 'false' | |
| runs-on: ubuntu-latest | |
| strategy: | |
| fail-fast: false | |
| max-parallel: 16 | |
| matrix: | |
| rust-branch: | |
| - stable | |
| rust-target: | |
| - x86_64-unknown-linux-gnu | |
| os: | |
| - ubuntu-latest | |
| test-file: ${{ fromJson(needs.find-sdk-e2e-tests.outputs.test-files) }} | |
| env: | |
| RELEASE_NAME: development | |
| RUSTV: ${{ matrix.rust-branch }} | |
| RUST_BACKTRACE: full | |
| RUST_BIN_DIR: target/${{ matrix.rust-target }} | |
| TARGET: ${{ matrix.rust-target }} | |
| timeout-minutes: 60 | |
| name: "sdk: ${{ matrix.test-file }}" | |
| steps: | |
| - name: Check-out repository | |
| uses: actions/checkout@v4 | |
| with: | |
| repository: ${{ github.event.pull_request.head.repo.full_name || github.repository }} | |
| ref: ${{ github.event.pull_request.head.ref || github.ref_name }} | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v5 | |
| with: | |
| enable-cache: "false" | |
| - name: Create Python virtual environment | |
| working-directory: ${{ github.workspace }} | |
| run: uv venv --seed ${{ github.workspace }}/venv | |
| - name: Clone Bittensor SDK repo | |
| working-directory: ${{ github.workspace }} | |
| run: git clone https://github.com/opentensor/bittensor.git | |
| - name: Setup Bittensor SDK from cloned repo | |
| working-directory: ${{ github.workspace }}/bittensor | |
| run: | | |
| source ${{ github.workspace }}/venv/bin/activate | |
| git checkout staging | |
| git fetch origin staging | |
| uv run --active pip install --upgrade pip | |
| uv run --active pip install '.[dev]' | |
| uv run --active pip install pytest | |
| - name: Download Cached Docker Image | |
| uses: actions/download-artifact@v4 | |
| with: | |
| name: subtensor-localnet | |
| - name: Load Docker Image | |
| run: docker load -i subtensor-localnet.tar | |
| - name: Retag Docker Image | |
| run: docker tag localnet ghcr.io/opentensor/subtensor-localnet:devnet-ready | |
| - name: Run with retry | |
| working-directory: ${{ github.workspace }}/bittensor | |
| run: | | |
| source ${{ github.workspace }}/venv/bin/activate | |
| export SKIP_PULL=1 | |
| set +e | |
| for i in 1 2; do | |
| echo "π Attempt $i: Running tests" | |
| uv run pytest ${{ matrix.test-file }} -s | |
| status=$? | |
| if [ $status -eq 0 ]; then | |
| echo "β Tests passed on attempt $i" | |
| break | |
| else | |
| echo "β Tests failed on attempt $i" | |
| if [ $i -eq 2 ]; then | |
| echo "π₯ Tests failed after 2 attempts" | |
| exit 1 | |
| fi | |
| echo "π Retrying..." | |
| sleep 5 | |
| fi | |
| done |