From fe5495482faed57e095e82d2533bf3c69c5f5d6b Mon Sep 17 00:00:00 2001 From: Justin Beckwith Date: Mon, 3 Aug 2026 11:19:52 -0700 Subject: [PATCH 1/3] ci: speed up lint checks --- .github/workflows/ci-checks.yml | 57 ++++++++++++++++++++++++++------- Rakefile | 22 +++++++------ 2 files changed, 58 insertions(+), 21 deletions(-) diff --git a/.github/workflows/ci-checks.yml b/.github/workflows/ci-checks.yml index f1e0ef47b..1dd364e1a 100644 --- a/.github/workflows/ci-checks.yml +++ b/.github/workflows/ci-checks.yml @@ -30,8 +30,7 @@ jobs: - name: Set up Ruby uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1 with: - bundler-cache: false - - run: bundle install + bundler-cache: true - name: Get GitHub OIDC token id: github-oidc @@ -49,10 +48,12 @@ jobs: lint: timeout-minutes: 10 - name: lint + name: lint (rubocop) permissions: contents: read runs-on: ${{ inputs.runner }} + env: + RUBOCOP_CACHE_ROOT: ${{ github.workspace }}/.cache/rubocop steps: - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6 with: @@ -61,10 +62,43 @@ jobs: uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1 with: ruby-version: '4.0' - bundler-cache: false - - run: bundle install - - name: Run lints - run: ./scripts/lint + bundler-cache: true + - name: Restore RuboCop cache + uses: actions/cache@55cc8345863c7cc4c66a329aec7e433d2d1c52a9 # v6.1.0 + with: + path: ${{ env.RUBOCOP_CACHE_ROOT }} + key: >- + rubocop-${{ runner.os }}-ruby-4.0-${{ hashFiles('Gemfile.lock', '.rubocop.yml') }}-${{ github.sha }} + restore-keys: | + rubocop-${{ runner.os }}-ruby-4.0-${{ hashFiles('Gemfile.lock', '.rubocop.yml') }}- + - name: Run RuboCop + run: bundle exec rake lint:rubocop + + typecheck: + timeout-minutes: 10 + name: typecheck (${{ matrix.format }}) + permissions: + contents: read + runs-on: ${{ inputs.runner }} + strategy: + fail-fast: false + matrix: + include: + - format: rbi + task: typecheck:sorbet + - format: rbs + task: typecheck:steep + steps: + - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6 + with: + persist-credentials: false + - name: Set up Ruby + uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1 + with: + ruby-version: '4.0' + bundler-cache: true + - name: Typecheck ${{ matrix.format }} files + run: bundle exec rake ${{ matrix.task }} package: timeout-minutes: 10 @@ -80,8 +114,7 @@ jobs: uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1 with: ruby-version: '4.0' - bundler-cache: false - - run: bundle install + bundler-cache: true - name: Build gem run: bundle exec rake build:gem @@ -103,8 +136,7 @@ jobs: uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1 with: ruby-version: ${{ matrix.ruby-version }} - bundler-cache: false - - run: bundle install + bundler-cache: true - name: Run tests run: ./scripts/test @@ -115,6 +147,7 @@ jobs: needs: - stainless-artifact - lint + - typecheck - package - test-ruby if: ${{ always() }} @@ -125,10 +158,12 @@ jobs: env: ARTIFACT_RESULT: ${{ needs.stainless-artifact.result }} LINT_RESULT: ${{ needs.lint.result }} + TYPECHECK_RESULT: ${{ needs.typecheck.result }} PACKAGE_RESULT: ${{ needs.package.result }} TEST_RESULT: ${{ needs.test-ruby.result }} run: | test "$ARTIFACT_RESULT" = "success" || test "$ARTIFACT_RESULT" = "skipped" test "$LINT_RESULT" = "success" + test "$TYPECHECK_RESULT" = "success" test "$PACKAGE_RESULT" = "success" test "$TEST_RESULT" = "success" diff --git a/Rakefile b/Rakefile index 6f47d64ca..e0f94c844 100644 --- a/Rakefile +++ b/Rakefile @@ -55,17 +55,17 @@ filtered = ->(ext, dirs) do end desc("Lint `*.rb(i)`") -multitask(:"lint:rubocop") do - find = %w[find ./lib ./test ./rbi ./examples -type f -and ( -name *.rb -or -name *.rbi ) -print0] - - rubocop = %w[rubocop] - rubocop += %w[--format github] if ENV.key?("CI") +RuboCop::RakeTask.new(:"lint:rubocop") do |task| + task.patterns = FileList[ + "./lib/**/*.rb", + "./test/**/*.rb", + "./rbi/**/*.rbi", + "./examples/**/*.rb", + ] + task.formatters = %w[github] if ENV.key?("CI") # some lines cannot be shortened - rubocop += %w[--except Lint/RedundantCopDisableDirective,Layout/LineLength] - - lint = xargs + rubocop - sh("#{find.shelljoin} | #{lint.shelljoin}") + task.options = %w[--parallel --except Lint/RedundantCopDisableDirective,Layout/LineLength] end norm_lines = %w[tr -- \n \0].shelljoin @@ -133,7 +133,9 @@ multitask(format: [:"format:rb", :"format:rbi", :"format:rbs"]) desc("Typecheck `*.rbs`") multitask(:"typecheck:steep") do - sh(*%w[steep check]) + steep = %w[steep check] + steep += ["--jobs=#{Etc.nprocessors}", "--format=github"] if ENV.key?("CI") + sh(*steep) end directory(examples) From 7469348e642d7d26986ea126d15795fd031119a9 Mon Sep 17 00:00:00 2001 From: Justin Beckwith Date: Mon, 3 Aug 2026 11:31:32 -0700 Subject: [PATCH 2/3] ci: tune Steep worker count --- Rakefile | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Rakefile b/Rakefile index e0f94c844..98ba69d56 100644 --- a/Rakefile +++ b/Rakefile @@ -134,7 +134,8 @@ multitask(format: [:"format:rb", :"format:rbi", :"format:rbs"]) desc("Typecheck `*.rbs`") multitask(:"typecheck:steep") do steep = %w[steep check] - steep += ["--jobs=#{Etc.nprocessors}", "--format=github"] if ENV.key?("CI") + # Steep defaults to two workers in CI; eight is the tested balance for this project's runner. + steep += %w[--jobs=8 --format=github] if ENV.key?("CI") sh(*steep) end From fb11844191a9637768e3a158ba92e7efefac8b68 Mon Sep 17 00:00:00 2001 From: Justin Beckwith Date: Mon, 3 Aug 2026 11:50:18 -0700 Subject: [PATCH 3/3] ci: simplify lint configuration --- .github/workflows/ci-checks.yml | 3 +++ Rakefile | 10 ++++------ scripts/detect-breaking-changes | 2 +- scripts/lint | 9 --------- 4 files changed, 8 insertions(+), 16 deletions(-) delete mode 100755 scripts/lint diff --git a/.github/workflows/ci-checks.yml b/.github/workflows/ci-checks.yml index 1dd364e1a..e1f90283a 100644 --- a/.github/workflows/ci-checks.yml +++ b/.github/workflows/ci-checks.yml @@ -80,6 +80,9 @@ jobs: permissions: contents: read runs-on: ${{ inputs.runner }} + env: + # Steep defaults to two workers in CI; eight is the measured balance for this runner. + STEEP_JOBS: 8 strategy: fail-fast: false matrix: diff --git a/Rakefile b/Rakefile index 98ba69d56..48461f77d 100644 --- a/Rakefile +++ b/Rakefile @@ -57,10 +57,8 @@ end desc("Lint `*.rb(i)`") RuboCop::RakeTask.new(:"lint:rubocop") do |task| task.patterns = FileList[ - "./lib/**/*.rb", - "./test/**/*.rb", - "./rbi/**/*.rbi", - "./examples/**/*.rb", + "./{lib,test,rbi,examples}/**/*.rb", + "./{lib,test,rbi,examples}/**/*.rbi", ] task.formatters = %w[github] if ENV.key?("CI") @@ -134,8 +132,8 @@ multitask(format: [:"format:rb", :"format:rbi", :"format:rbs"]) desc("Typecheck `*.rbs`") multitask(:"typecheck:steep") do steep = %w[steep check] - # Steep defaults to two workers in CI; eight is the tested balance for this project's runner. - steep += %w[--jobs=8 --format=github] if ENV.key?("CI") + steep += ["--jobs", ENV.fetch("STEEP_JOBS")] if ENV.key?("STEEP_JOBS") + steep += %w[--format=github] if ENV.key?("CI") sh(*steep) end diff --git a/scripts/detect-breaking-changes b/scripts/detect-breaking-changes index f7b9b3afa..d52cdff77 100755 --- a/scripts/detect-breaking-changes +++ b/scripts/detect-breaking-changes @@ -113,4 +113,4 @@ done # Instead of running the tests, use the linter to check if an # older test is no longer compatible with the latest SDK. -./scripts/lint +bundle exec rake lint diff --git a/scripts/lint b/scripts/lint deleted file mode 100755 index 08b0dbeb6..000000000 --- a/scripts/lint +++ /dev/null @@ -1,9 +0,0 @@ -#!/usr/bin/env bash - -set -e - -cd -- "$(dirname -- "$0")/.." - -echo "==> Running linters" - -exec -- bundle exec rake lint "$@"