put pim on the example's launcher icon and give it a real name #12
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 | |
| # Four Dart packages live here — the SDK, the two companions and the example — | |
| # and each has its own pubspec. A change to the core breaks the companions | |
| # without touching a file in them, so all four are checked on every push. | |
| on: | |
| push: | |
| branches: [main] | |
| tags: ["v*"] | |
| pull_request: | |
| workflow_dispatch: | |
| # A second push supersedes the first. Nothing here deploys, so cancelling a run | |
| # in flight costs nothing. | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.ref }} | |
| cancel-in-progress: true | |
| jobs: | |
| test: | |
| runs-on: ubuntu-latest | |
| strategy: | |
| # Every package is reported, rather than stopping at the first red one. | |
| fail-fast: false | |
| matrix: | |
| package: | |
| - . | |
| - packages/code_scout_dio | |
| - packages/code_scout_http | |
| - packages/code_scout_talker | |
| - example | |
| steps: | |
| - uses: actions/checkout@v5 | |
| - uses: subosito/flutter-action@v2 | |
| with: | |
| channel: stable | |
| cache: true | |
| # Every package, not just this one. `flutter analyze` at the root reaches | |
| # down into packages/, and without their own resolution it reports every | |
| # companion symbol as undefined — 39 errors about code that is fine. | |
| - name: Resolve every package | |
| run: | | |
| flutter pub get | |
| (cd packages/code_scout_dio && flutter pub get) | |
| (cd packages/code_scout_http && flutter pub get) | |
| (cd packages/code_scout_talker && flutter pub get) | |
| (cd example && flutter pub get) | |
| # analyze before test: a type error reads better as an analyzer message | |
| # than as a compile failure inside a test runner. | |
| - run: flutter analyze | |
| working-directory: ${{ matrix.package }} | |
| - run: flutter test | |
| working-directory: ${{ matrix.package }} | |
| # What ends up in the archive is not what is in the repository, and the gap | |
| # is easy to miss: `example/` was gitignored for months, which meant pub | |
| # silently shipped a package with no example and nobody noticed until someone | |
| # looked at the pub.dev page. | |
| package: | |
| runs-on: ubuntu-latest | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| package: | |
| - . | |
| - packages/code_scout_dio | |
| - packages/code_scout_http | |
| - packages/code_scout_talker | |
| steps: | |
| - uses: actions/checkout@v5 | |
| - uses: subosito/flutter-action@v2 | |
| with: | |
| channel: stable | |
| cache: true | |
| - run: flutter pub get | |
| working-directory: ${{ matrix.package }} | |
| # pub refuses to package a dirty tree, and `pub get` itself rewrites the | |
| # example's generated_plugins.cmake — so anything generated has to be | |
| # untracked or this fails for a reason that has nothing to do with the | |
| # package. | |
| - run: flutter pub publish --dry-run | |
| working-directory: ${{ matrix.package }} | |
| # The SDK against a real dashboard. | |
| # | |
| # This is the one job worth the setup. Everything above proves each side | |
| # against its own idea of the contract; this proves the two still agree. It | |
| # needs the server repository, so it is also the only job that can break | |
| # because somebody else's repository changed — which is the point. | |
| sdk-e2e: | |
| runs-on: ubuntu-latest | |
| services: | |
| postgres: | |
| image: postgres:16-alpine | |
| env: | |
| POSTGRES_USER: code_scout | |
| POSTGRES_PASSWORD: code_scout | |
| POSTGRES_DB: code_scout_e2e | |
| ports: | |
| - 5432:5432 | |
| options: >- | |
| --health-cmd "pg_isready -U code_scout" | |
| --health-interval 5s | |
| --health-timeout 5s | |
| --health-retries 10 | |
| steps: | |
| - uses: actions/checkout@v5 | |
| # Into a dot directory: pub and the Flutter tool walk the tree looking | |
| # for pubspecs, and ignore anything starting with a dot. | |
| - uses: actions/checkout@v5 | |
| with: | |
| repository: getcodescout/code_scout | |
| path: .server | |
| - uses: actions/setup-go@v5 | |
| with: | |
| go-version-file: .server/go.mod | |
| cache-dependency-path: .server/go.sum | |
| - uses: subosito/flutter-action@v2 | |
| with: | |
| channel: stable | |
| cache: true | |
| # sqflite_common_ffi opens SQLite through dart:ffi, so the runner needs | |
| # the library itself. Without it every test that touches the database | |
| # fails at load with a missing symbol. | |
| - name: Install SQLite | |
| run: sudo apt-get update && sudo apt-get install -y libsqlite3-dev | |
| # No /etc/code-scout.conf here, which is fine: the loader treats the file | |
| # as optional and every setting has a CS_* environment override. | |
| - name: Start the dashboard | |
| working-directory: .server | |
| env: | |
| CS_DB_HOST: 127.0.0.1 | |
| CS_DB_PORT: "5432" | |
| CS_DB_USER: code_scout | |
| CS_DB_PASSWORD: code_scout | |
| CS_DB_NAME: code_scout_e2e | |
| CS_PORT: "24284" | |
| run: | | |
| go build -o /tmp/code_scout . | |
| # nohup and disown: the server has to outlive the step that starts it, | |
| # and a shell exiting can take an ordinary background child with it. | |
| nohup /tmp/code_scout > /tmp/code_scout.log 2>&1 & | |
| disown | |
| for i in $(seq 1 60); do | |
| curl -sf http://127.0.0.1:24284/healthz >/dev/null && exit 0 | |
| sleep 0.5 | |
| done | |
| echo "::error::The dashboard never came up." | |
| cat /tmp/code_scout.log | |
| exit 1 | |
| - run: flutter pub get | |
| # Checked again here so a server that died between steps fails with that | |
| # sentence, rather than as a confusing "sign in failed" inside the test. | |
| - name: Check the dashboard is still up | |
| run: | | |
| curl -sf http://127.0.0.1:24284/healthz || { | |
| echo "::error::The dashboard stopped before the tests ran." | |
| cat /tmp/code_scout.log | |
| exit 1 | |
| } | |
| - name: Run the SDK against it | |
| env: | |
| CS_E2E_BASE: http://127.0.0.1:24284 | |
| run: flutter test test/e2e/ | |
| # The server's own log is the only place an ingest rejection explains | |
| # itself, and a failed run is exactly when you want it. | |
| # Session upserts are deliberately not fatal to an upload — the logs are | |
| # the payload and the session is context — so a failure there is only ever | |
| # a line in this log. Promoted to an annotation so it shows in the run | |
| # summary rather than needing the step expanded. | |
| - name: Dashboard log | |
| if: failure() | |
| run: | | |
| grep -iE "session|error" /tmp/code_scout.log | tail -20 | | |
| while IFS= read -r line; do echo "::error::$line"; done | |
| cat /tmp/code_scout.log |