chore: prepare v0.2.1 release — paginate loop state #40
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: CI | |
| on: | |
| push: | |
| branches: [main, "feature/*", "fix/*"] | |
| tags: ["v*"] | |
| pull_request: | |
| branches: [main] | |
| workflow_dispatch: | |
| # Cancel in-progress runs for the same branch / PR | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.ref }} | |
| cancel-in-progress: true | |
| # Opt into Node.js 24 (default after June 16, 2026). | |
| # erlef/setup-beam@v1 uses Node.js for the action runtime. | |
| env: | |
| FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: true | |
| MIX_ENV: test | |
| OTP_VERSION: "29.0" | |
| ELIXIR_VERSION: "1.20.1" | |
| jobs: | |
| # ── Linux: full CI quality gate ───────────────────────────── | |
| linux: | |
| name: "Linux · Elixir 1.20.1 · OTP 29.0" | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 20 | |
| steps: | |
| - uses: actions/checkout@v7 | |
| - name: Set up Elixir | |
| uses: erlef/setup-beam@v1 | |
| with: | |
| otp-version: ${{ env.OTP_VERSION }} | |
| elixir-version: ${{ env.ELIXIR_VERSION }} | |
| - name: Cache build artifacts | |
| uses: actions/cache@v6 | |
| with: | |
| path: | | |
| _build | |
| deps | |
| priv/plts | |
| key: ${{ runner.os }}-mix-${{ hashFiles('**/mix.lock') }} | |
| restore-keys: | | |
| ${{ runner.os }}-mix- | |
| ${{ runner.os }}- | |
| - name: Install dependencies | |
| run: mix deps.get | |
| - name: Install protoc | |
| # `protox` shells out to the system `protoc` to compile the | |
| # vendored .proto files. erlef/setup-beam's Ubuntu image | |
| # doesn't include it, so install via apt. | |
| run: | | |
| sudo apt-get update | |
| sudo apt-get install -y --no-install-recommends protobuf-compiler | |
| protoc --version | |
| - name: Compile (warnings-as-errors) | |
| # We intentionally don't pass --all-warnings: that flag treats | |
| # third-party dep warnings (yamerl's deprecated catch, etc.) | |
| # as errors. We only want to enforce warnings-as-errors on | |
| # our own code, which `mix compile --warnings-as-errors` does. | |
| run: mix compile --warnings-as-errors | |
| - name: Check formatting | |
| run: mix format --check-formatted | |
| - name: Credo (strict) | |
| run: mix credo --strict | |
| - name: Audit dependencies for CVEs | |
| run: mix deps.audit | |
| - name: Check for unused dependencies | |
| run: mix deps.unlock --check-unused | |
| - name: xref (no orphan modules) | |
| run: mix xref graph --label compile-connected --fail-above 0 | |
| - name: ExDNA (duplication) | |
| run: mix ex_dna | |
| - name: Reach (dead code + smells) | |
| run: mix reach.check --dead-code --smells | |
| - name: Dialyzer | |
| run: mix dialyzer | |
| timeout-minutes: 15 | |
| - name: Run tests with coverage | |
| # `mix coveralls.json` runs the test suite under coverage and | |
| # writes the coveralls.io-format JSON to cover/excoveralls.json, | |
| # which the codecov uploader consumes. We use `mix coveralls.json` | |
| # (not `mix test --cover`) because only the former produces the | |
| # cover/excoveralls.json file. `mix test --cover` only writes the | |
| # per-module HTML to cover/. | |
| # | |
| # The generated protobuf module (lib/longbridge/_protos.ex) is | |
| # excluded from coverage by `skip_files` in coveralls.json — its | |
| # 5,900+ lines would otherwise drag total coverage into the 30s. | |
| # The 80% target is enforced by codecov.yml's status check, not | |
| # locally (excoveralls' `coveralls.json` task doesn't call | |
| # `ensure_minimum_coverage/1`; only the local `mix coveralls`, | |
| # `coveralls.html`, and `coveralls.cobertura` tasks do). | |
| run: mix coveralls.json | |
| - name: Post coverage to Codecov | |
| # Push the excoveralls JSON to codecov.io using the bash | |
| # uploader (v0.8.0). The bash uploader has better format | |
| # detection for the coveralls.io JSON format than the new | |
| # codecov-cli (which doesn't ship an Elixir/coveralls plugin | |
| # and returns 'Found 0 coverage files to report' for the | |
| # same file). | |
| # | |
| # Requires CODECOV_TOKEN in repo Settings -> Secrets -> | |
| # Actions. Get the token at | |
| # https://codecov.io/gh/gilbertwong96/longbridge -> Settings | |
| # -> Upload Token. | |
| # | |
| # Skip the step if the secret is not set. We don't fail | |
| # the build over missing coverage uploads — coverage is | |
| # still available as an action artifact download. | |
| env: | |
| CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} | |
| run: | | |
| if [ -z "$CODECOV_TOKEN" ]; then | |
| echo "::notice::CODECOV_TOKEN not set - skipping Codecov upload." | |
| echo "Add it at https://codecov.io/gh/gilbertwong96/longbridge" | |
| echo "to enable the coverage badge." | |
| exit 0 | |
| fi | |
| curl -Os https://uploader.codecov.io/latest/linux/codecov | |
| chmod +x codecov | |
| ./codecov --token "$CODECOV_TOKEN" --file ./cover/excoveralls.json | |
| continue-on-error: true | |
| - name: Upload coverage artifact | |
| if: always() | |
| uses: actions/upload-artifact@v7 | |
| with: | |
| name: coverage-linux | |
| path: | | |
| cover/excoveralls.json | |
| cover/*.html | |
| retention-days: 30 |