name: CI on: push: branches: [main] pull_request: branches: [main] jobs: build: runs-on: ubuntu-latest steps: - name: Checkout uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 - name: Setup Node.js uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0 with: node-version: '20' - name: Enable Corepack run: corepack enable - name: Install dependencies run: yarn install --immutable - name: Generate types run: ./node_modules/.bin/subql codegen pezkuwi.yaml - name: Build run: ./node_modules/.bin/subql build pezkuwi.yaml # Dependency Review allows the @subql packages because the mapping imports # only their types; this is the check that keeps it true. A type-only # import is erased on emit, a value import survives as a require. - name: The mapping imports no @subql code run: | out=$(mktemp -d) ./node_modules/.bin/tsc -p tsconfig.json --outDir "$out" --declaration false ! grep -rn 'require("@subql/' "$out" || { echo "the mapping imports @subql code; import its types with 'import type' or drop it"; exit 1; } # The noter and payout bots ship as their own images (docker-compose.prod.yml) # and nothing else here builds or runs them. Build each image as production # does, then run inside it: the crypto stack must be the locked one and sign # with every key type, and the bot must load its whole module graph and stop # only where it reads the mnemonic that CI does not have. bots: name: bots (${{ matrix.bot }}) runs-on: ubuntu-latest strategy: fail-fast: false matrix: include: - bot: noter mode: esm expect: 'No noter mnemonic found' - bot: payout-bot mode: cjs expect: "ENOENT: no such file or directory, open '/run/secrets/payout_mnemonic'" steps: - name: Checkout uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 - name: Build the image run: docker build -t bot ${{ matrix.bot }} # Dependency Review allows these GPL-3.0 packages in the lockfiles only # because no image installs them; this is the check that keeps it true. - name: No light client in the image run: | docker run --rm bot sh -c '! [ -e node_modules/@bizinikiwi ] && ! [ -e node_modules/smoldot ]' || { echo "the image installs the light client; it must be built with --omit=optional"; exit 1; } - name: Crypto stack run: docker run --rm -v "$PWD/scripts/bot-smoke.mjs:/app/bot-smoke.mjs:ro" bot node bot-smoke.mjs ${{ matrix.mode }} # Run inside the image, so the modules under test are the ones the image ships. - name: Unit tests if: matrix.bot == 'noter' run: docker run --rm -v "$PWD/noter/test:/app/test:ro" bot node --test test/submit.test.mjs test/confirm.test.mjs - name: The bot loads and stops at its missing mnemonic env: EXPECT: ${{ matrix.expect }} run: | set +e out=$(timeout 60 docker run --rm bot 2>&1) code=$? set -e echo "$out" [ "$code" -ne 0 ] && [ "$code" -ne 124 ] || { echo "expected the bot to exit with an error, got $code"; exit 1; } grep -qF "$EXPECT" <<<"$out" || { echo "expected: $EXPECT"; exit 1; } # The indexers run docker/Dockerfile.node (docker-compose.prod.yml). Build it # as production does: the patch step fails the build if a pattern no longer # matches. Then the aliased crypto stack must be the locked one and sign with # every key type, and subql-node must load. indexer: name: Indexer image runs-on: ubuntu-latest steps: - name: Checkout uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 - name: Build the image run: docker build -f docker/Dockerfile.node -t indexer . - name: Crypto stack run: docker run --rm --entrypoint node -v "$PWD/scripts/bot-smoke.mjs:/app/bot-smoke.mjs:ro" indexer /app/bot-smoke.mjs indexer - name: subql-node loads run: docker run --rm indexer --help >/dev/null # The scripts the deploy key is pinned to are the whole of what CI can do on # the host, so they are checked with every change. host-scripts: name: Host deploy scripts runs-on: ubuntu-latest steps: - uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0 - run: | shellcheck -S warning ops/host/subquery-deploy ops/host/subquery-deploy-ssh ops/host/test-deploy.sh bash ops/host/test-deploy.sh