Skip to content

chore(repo): overhaul the CI and turbo configuration - #477

Merged
HugoRCD merged 14 commits into
mainfrom
chore/ci-overhaul
Aug 1, 2026
Merged

chore(repo): overhaul the CI and turbo configuration#477
HugoRCD merged 14 commits into
mainfrom
chore/ci-overhaul

Conversation

@HugoRCD

@HugoRCD HugoRCD commented Aug 1, 2026

Copy link
Copy Markdown
Owner

❓ Type of change

  • 🧹 Chore (updates to the build process or auxiliary tools and libraries)

📚 Description

Two things were silently broken

The remote cache had never been hit. Every run logged empty values:

TURBO_TOKEN:
TURBO_TEAM:

Neither secret ever existed. The token is now minted per run by exchanging the
GitHub OIDC token through vercel/setup-turborepo-remote-cache-action, so there
is no long-lived secret to rotate and only a TURBO_TEAM repository variable
to configure. Fork PRs get no OIDC token, so TURBO_CACHE falls back to
local:rw instead of failing.

--affected was a no-op. With fetch-depth: 1 turbo could not resolve a
base to diff against:

WARNING unable to detect git range, assuming all files have changed:
Unable to resolve base branch. Please set with `TURBO_SCM_BASE`.
   • Packages in scope: //, @evlog/cli, ... (all 34)

Fixed with a full-depth checkout plus TURBO_SCM_BASE.

The job graph came from measuring a run

Per-step timings over the last runs: pnpm install is 18s (the pnpm cache
already works), but each of the four test shards spent ~90s of runner time to
run 7s of tests, and coverage replayed the entire suite a fifth time.

Ten jobs become five: quality, test, examples, publish, and a ci gate
job so branch protection has one stable required check instead of a list of
matrix names. Preview publishing no longer waits on the test jobs — a preview
build is most useful while the PR is still red.

examples is new: nothing built the examples before.

Composite action

The checkout/pnpm/setup-node/install block was copied across eight jobs and
node-version: 22 was hardcoded in nine places. .github/actions/setup owns it
now, with .node-version as the single source of truth and one automatic
install retry for registry flakes.

Hardening

Every action pinned to a commit SHA, persist-credentials: false wherever the
job has no further git operations (release.yml keeps them: changesets/action
pushes the release branch), least-privilege permissions, timeout-minutes,
concurrency groups, and --frozen-lockfile in release.yml, which installed
unpinned before. Adds dependency-review on the PR diff and a cleanup of
per-branch caches on PR close.

ubuntu-slim and parallel

The three API-only jobs move to ubuntu-slim. parallel groups the remote
cache and Node setup steps, matching turborepo's lint.yml. Lint and
typecheck stay a single turbo run lint typecheck — turbo already parallelises
them and knows their dependency graph.

turbo.json

globalEnv carried thirteen app secrets, so rotating POSTHOG_HOST or
DATABASE_URL invalidated every cached task in the repo, including lint on
the core package. They only matter to build and dev. lint now hashes the
root eslint config through $TURBO_ROOT$ — editing it used to leave every lint
result cached and green.

Root scripts

Twenty-four near-identical scripts existed only to spell out a turbo filter:

pnpm example          # pick from a list
pnpm example hono     # run examples/hono
pnpm playground next  # run apps/next-playground

This also reaches examples/bun-script, which no root script could start. The
dead workspaces field is dropped: pnpm reads pnpm-workspace.yaml.

📝 Notes

  • actionlint is not added: v1.7.12 predates the parallel keyword and
    rejects it (rhysd/actionlint#693).
    Worth adding once that lands.
  • Node stays on 22 to keep this a behaviour-preserving refactor, but
    examples/eve wants >=24 and warns on every install.
  • A Renovate lockfile bump makes every example affected, so the examples job
    will build all of them. Can be moved behind a label like e2e if that is too
    heavy.

Summary by CodeRabbit

Summary by CodeRabbit

  • New Features

    • Added a unified command launcher for running examples and playgrounds by name or partial match.
    • Added structured client-side error logging that preserves standard and custom error details.
    • Standardized the development environment on Node.js 22.
  • Documentation

    • Updated framework integration guides with the new example-running commands.
  • Improvements

    • Improved automated checks, caching, dependency review, release validation, and pull-request cache cleanup.

Update: examples are fixed and gated

examples started out informational because it reported failures. One was real
and is fixed here; the earlier reading that several examples were broken was
wrong twice over.

First, turbo stops at the first failure by default, so most of what looked like
failures were cancelled tasks. The job now runs with --continue.

Second, the remaining failures came from a bad install state in my working
tree, not from the examples. On a clean checkout, all eleven example builds
pass with no exclusions
.

What is genuinely fixed:

  • examples/vite is a Hono server, so vite build looked for an
    index.html that does not exist. It now builds src/server.ts as an ssr
    entry, which is also what its start script always expected to run — that
    script had never worked either. Verified: reverting this config reproduces
    Could not resolve entry module "index.html".
  • turbo declared no outputs covering build/ or .svelte-kit/, so
    react-router and sveltekit warned on every run and were never cached.

The client log.error() fix

Independent of the examples. createLogMethod routes any object to emitLog,
which spreads it — but name, message and stack are non-enumerable on an
Error. So log.error(new Error('boom')) emitted an event containing no
error at all
, silently. The type did not accept an Error either, while the
Next.js docs teach exactly that pattern for client components.

Errors now land under error with the same shape the server logger stores.
Separate commit, patch changeset, three tests.

HugoRCD added 4 commits August 1, 2026 16:22
Every workflow repeated the same checkout/pnpm/setup-node/install block and
hardcoded node 22 in nine places. .github/actions/setup owns that now, with
.node-version as the single source of truth and one automatic install retry
for registry flakes.

Also pins every action to a commit SHA, sets persist-credentials: false
wherever the job has no further git operations, adds concurrency groups and
timeouts, and moves the two API-only jobs to the ubuntu-slim runner.

Adds a dependency-review job on the PR diff.
Two things were silently broken. TURBO_TOKEN and TURBO_TEAM were never set,
so the remote cache had never once been hit; and every run logged 'unable to
detect git range, assuming all files have changed', so --affected was a no-op
and all 34 packages were always in scope.

The token is now minted per run from the GitHub OIDC token, which removes the
secret entirely and degrades to the local cache on fork PRs. TURBO_SCM_BASE
and a full-depth checkout make --affected actually filter.

The job graph followed from measuring a run: each of the four test shards spent
~90s to run 7s of tests, and the coverage job replayed the whole suite a fifth
time. Ten jobs become four, plus a gate job so branch protection has one stable
required check. Preview publishing no longer waits on the test jobs.

Adds a build of the affected examples, which nothing covered before, and a
cleanup of per-branch caches on PR close.
globalEnv fed thirteen app secrets into the global hash, so rotating
POSTHOG_HOST or DATABASE_URL invalidated every cached task in the repo,
including lint on the core package. They only ever matter to build and dev, so
they move there.

lint now hashes the root eslint config through $TURBO_ROOT$: editing it used
to leave every lint result cached and green. test declares its coverage
output.
Twenty-four near-identical root scripts existed only to spell out a turbo
filter, and adding an example meant adding another. scripts/run-app.mjs
discovers them instead:

  pnpm example          pick from a list
  pnpm example hono     run examples/hono
  pnpm playground next  run apps/next-playground

This also reaches examples/bun-script, which no root script could start
because it has a start script rather than dev. Docs updated to match.

Drops the workspaces field: pnpm reads pnpm-workspace.yaml, so it was a second
declaration of the workspace layout that nothing consumed.
@vercel

vercel Bot commented Aug 1, 2026

Copy link
Copy Markdown
Contributor

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
evlog-docs Ready Ready Preview, v0 Aug 1, 2026 5:17pm
evlog-render-lab Ready Ready Preview Aug 1, 2026 5:17pm
evlog-telemetry Ready Ready Preview Aug 1, 2026 5:17pm
just-use-evlog Ready Ready Preview Aug 1, 2026 5:17pm

Request Review

@changeset-bot

changeset-bot Bot commented Aug 1, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: a44c904

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 2 packages
Name Type
evlog Patch
@evlog/cli Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@github-actions

github-actions Bot commented Aug 1, 2026

Copy link
Copy Markdown
Contributor

Thank you for following the naming conventions! 🙏

@coderabbitai

coderabbitai Bot commented Aug 1, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Warning

Review limit reached

@HugoRCD, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 4 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 0f0c7833-4f61-412d-8c3e-297c1c516806

📥 Commits

Reviewing files that changed from the base of the PR and between 6eb1217 and a44c904.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (12)
  • .github/actions/setup/action.yml
  • .github/workflows/autofix.yml
  • .github/workflows/ci.yml
  • .github/workflows/dependency-review.yml
  • .github/workflows/pr-clean-caches.yml
  • .github/workflows/release.yml
  • .github/workflows/semantic-pull-request.yml
  • examples/tanstack-start/package.json
  • packages/evlog/src/runtime/client/log.ts
  • packages/evlog/test/core/client-console.test.ts
  • pnpm-workspace.yaml
  • scripts/run-app.mjs
📝 Walkthrough

Walkthrough

The change adds a shared repository setup action, consolidates CI jobs, adds a local example runner, updates Turbo configuration, pins workflow actions, adds workflow permission and cache controls, and adds structured client Error logging.

Changes

Repository tooling and automation

Layer / File(s) Summary
Local runners and task configuration
.node-version, package.json, scripts/run-app.mjs, turbo.json, apps/docs/content/..., examples/...
Generic example and playground commands now use scripts/run-app.mjs. Documentation and example configuration use the updated commands and build settings.
Shared repository setup action
.github/actions/setup/action.yml
The composite action configures Node.js, pnpm, registry settings, caching, filtered installation, and one installation retry.
Consolidated CI jobs
.github/workflows/ci.yml
CI now runs affected quality, test, example, publishing, and aggregation jobs with shared setup and cache configuration.
Workflow adoption and controls
.github/workflows/*.yml
Selected workflows now use pinned actions, shared setup, explicit permissions, concurrency controls, bounded runtimes, dependency review, or pull-request cache cleanup.

Client Error logging

Layer / File(s) Summary
Error logging contract and serialization
packages/evlog/src/types.ts, packages/evlog/src/runtime/client/log.ts
Log.error accepts Error instances. Client logging serializes standard and selected custom error fields under error.
Error logging validation and release note
packages/evlog/test/core/client-console.test.ts, .changeset/client-log-error-instance.md
Tests validate serialized error metadata and unchanged plain-object handling. A patch changeset documents the API behavior.

Estimated code review effort: 4 (Complex) | ~60 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Caller
  participant Log
  participant ErrorSerializer
  participant Output
  Caller->>Log: call error with Error instance
  Log->>ErrorSerializer: serialize Error fields
  ErrorSerializer-->>Log: return structured error data
  Log->>Output: emit error under error
Loading
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 40.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly identifies the primary CI and Turborepo configuration overhaul and follows the repository's conventional commit format.
Description check ✅ Passed The description explains the changes, motivation, implementation details, testing, and known notes, with only optional template checklist sections omitted.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch chore/ci-overhaul

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@pkg-pr-new

pkg-pr-new Bot commented Aug 1, 2026

Copy link
Copy Markdown
npm i https://pkg.pr.new/@evlog/cli@477
npm i https://pkg.pr.new/evlog@477
npm i https://pkg.pr.new/@evlog/nuxthub@477
npm i https://pkg.pr.new/@evlog/telemetry@477

commit: a44c904

The new job surfaced pre-existing breakage: seven examples do not build from
a clean checkout. examples/vite is a server example whose `vite build` script
was never meaningful, and sveltekit, react-router, solidstart and
tanstack-start need framework codegen that no dev:prepare script runs.

None of that is caused by this branch and fixing it is its own piece of work,
so the job reports without blocking the gate.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.github/actions/setup/action.yml:
- Around line 27-35: Update the pinned references for pnpm/action-setup and
changesets/action to the commit SHAs that resolve to their intended tags,
preserving the corresponding version comments and all other workflow
configuration.

In @.github/workflows/ci.yml:
- Around line 45-53: Remove the unsupported “parallel” wrapper from the setup
steps in the quality, test, examples, and publish jobs. In each job’s steps
list, place “Set up Turborepo remote cache” and “Set up pnpm and Node” as
top-level sequential steps, preserving their existing conditions, actions, and
configuration.
- Around line 64-66: Update the permissions blocks for the test, examples, and
publish jobs in the CI workflow to document each sensitive grant with comments
matching the existing quality job style: explain id-token: write as remote cache
OIDC and document publish’s pull-requests: write purpose as well. Keep the
permission values unchanged.

In @.github/workflows/pr-clean-caches.yml:
- Around line 12-13: Set workflow-level permissions to an empty mapping in
.github/workflows/pr-clean-caches.yml, then move actions: write into
jobs.cleanup.permissions. In .github/workflows/semantic-pull-request.yml, also
set workflow-level permissions to an empty mapping and move contents: read and
pull-requests: write into jobs.validate-pr.permissions.
- Around line 8-10: Add a required pr_number workflow_dispatch input in the
workflow definition, then update the BRANCH construction to use
github.event.pull_request.number for pull_request events and the manual input
when that value is absent. Preserve the existing pull-request behavior while
ensuring manual runs target refs/pull/{pr_number}/merge.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: e8811a23-ea71-41ec-aa4f-099c25f7e4ca

📥 Commits

Reviewing files that changed from the base of the PR and between 1b97c2f and 0833eb1.

📒 Files selected for processing (23)
  • .github/actions/setup/action.yml
  • .github/workflows/autofix.yml
  • .github/workflows/ci.yml
  • .github/workflows/dependency-review.yml
  • .github/workflows/e2e.yml
  • .github/workflows/label-pr.yml
  • .github/workflows/mutation.yml
  • .github/workflows/pr-clean-caches.yml
  • .github/workflows/release.yml
  • .github/workflows/semantic-pull-request.yml
  • .node-version
  • apps/docs/content/4.integrate/frameworks/03.sveltekit.md
  • apps/docs/content/4.integrate/frameworks/06.nestjs.md
  • apps/docs/content/4.integrate/frameworks/07.express.md
  • apps/docs/content/4.integrate/frameworks/08.hono.md
  • apps/docs/content/4.integrate/frameworks/09.fastify.md
  • apps/docs/content/4.integrate/frameworks/10.elysia.md
  • apps/docs/content/4.integrate/frameworks/11.react-router.md
  • apps/docs/content/4.integrate/frameworks/15.orpc.md
  • apps/docs/content/5.use-cases/5.eve.md
  • package.json
  • scripts/run-app.mjs
  • turbo.json

Comment thread .github/actions/setup/action.yml
Comment thread .github/workflows/ci.yml
Comment thread .github/workflows/ci.yml Outdated
Comment thread .github/workflows/pr-clean-caches.yml
Comment thread .github/workflows/pr-clean-caches.yml Outdated
name, message and stack are non-enumerable, so spreading an Error into a wide
event contributed nothing: log.error(new Error('boom')) emitted an event with
no error in it at all. The type only accepted a tag pair or a plain object, so
the call did not type check either — while the Next.js docs teach exactly that
pattern for client components, and examples/nextjs uses it.

Errors now land under `error` with the same shape the server logger stores,
carrying code, status, cause and friends.
@github-actions

github-actions Bot commented Aug 1, 2026

Copy link
Copy Markdown
Contributor

Dependency Review

The following issues were found:
  • ❌ 1 vulnerable package(s)
  • ✅ 0 package(s) with incompatible licenses
  • ✅ 0 package(s) with invalid SPDX license definitions
  • ✅ 0 package(s) with unknown licenses.
See the Details below.

Vulnerabilities

pnpm-lock.yaml

NameVersionVulnerabilitySeverity
h32.0.1-rc.2h3 has a Server-Sent Events Injection via Unsanitized Newlines in Event Stream Fieldshigh
h3 has a middleware bypass with one gadgethigh
Only included vulnerabilities with severity high or higher.

OpenSSF Scorecard

Scorecard details
PackageVersionScoreDetails
actions/actions/checkout d23441a48e516b6c34aea4fa41551a30e30af803 🟢 6.9
Details
CheckScoreReason
Binary-Artifacts🟢 10no binaries found in the repo
Code-Review🟢 10all changesets reviewed
Maintained🟢 1025 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Fuzzing⚠️ 0project is not fuzzed
Pinned-Dependencies🟢 3dependency not pinned by hash detected -- score normalized to 3
License🟢 10license file detected
Packaging⚠️ -1packaging workflow not detected
Signed-Releases⚠️ -1no releases found
Security-Policy🟢 9security policy file detected
Branch-Protection🟢 5branch protection is not maximal on development and all release branches
SAST🟢 10SAST tool is run on all commits
actions/actions/checkout d23441a48e516b6c34aea4fa41551a30e30af803 🟢 6.9
Details
CheckScoreReason
Binary-Artifacts🟢 10no binaries found in the repo
Code-Review🟢 10all changesets reviewed
Maintained🟢 1025 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 10
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Fuzzing⚠️ 0project is not fuzzed
Pinned-Dependencies🟢 3dependency not pinned by hash detected -- score normalized to 3
License🟢 10license file detected
Packaging⚠️ -1packaging workflow not detected
Signed-Releases⚠️ -1no releases found
Security-Policy🟢 9security policy file detected
Branch-Protection🟢 5branch protection is not maximal on development and all release branches
SAST🟢 10SAST tool is run on all commits
npm/h3 2.0.1-rc.2 UnknownUnknown
npm/srvx 0.8.16 UnknownUnknown
npm/@emnapi/core 2.0.0-alpha.3 🟢 3.6
Details
CheckScoreReason
Maintained🟢 1021 commit(s) and 1 issue activity found in the last 90 days -- score normalized to 10
Code-Review⚠️ 2Found 6/30 approved changesets -- score normalized to 2
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Binary-Artifacts🟢 10no binaries found in the repo
Pinned-Dependencies⚠️ 0dependency not pinned by hash detected -- score normalized to 0
Security-Policy⚠️ 0security policy file not detected
License🟢 10license file detected
Fuzzing⚠️ 0project is not fuzzed
Branch-Protection⚠️ 0branch protection not enabled on development/release branches
Signed-Releases⚠️ 0Project has not signed or included provenance with any releases.
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
npm/@emnapi/runtime 2.0.0-alpha.3 🟢 3.6
Details
CheckScoreReason
Maintained🟢 1021 commit(s) and 1 issue activity found in the last 90 days -- score normalized to 10
Code-Review⚠️ 2Found 6/30 approved changesets -- score normalized to 2
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Binary-Artifacts🟢 10no binaries found in the repo
Pinned-Dependencies⚠️ 0dependency not pinned by hash detected -- score normalized to 0
Security-Policy⚠️ 0security policy file not detected
License🟢 10license file detected
Fuzzing⚠️ 0project is not fuzzed
Branch-Protection⚠️ 0branch protection not enabled on development/release branches
Signed-Releases⚠️ 0Project has not signed or included provenance with any releases.
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
npm/@emnapi/wasi-threads 2.0.1 🟢 3.6
Details
CheckScoreReason
Maintained🟢 1021 commit(s) and 1 issue activity found in the last 90 days -- score normalized to 10
Code-Review⚠️ 2Found 6/30 approved changesets -- score normalized to 2
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Binary-Artifacts🟢 10no binaries found in the repo
Pinned-Dependencies⚠️ 0dependency not pinned by hash detected -- score normalized to 0
Security-Policy⚠️ 0security policy file not detected
License🟢 10license file detected
Fuzzing⚠️ 0project is not fuzzed
Branch-Protection⚠️ 0branch protection not enabled on development/release branches
Signed-Releases⚠️ 0Project has not signed or included provenance with any releases.
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
npm/@napi-rs/wasm-runtime 1.2.1 🟢 5.1
Details
CheckScoreReason
Code-Review⚠️ 1Found 3/19 approved changesets -- score normalized to 1
Security-Policy🟢 10security policy file detected
Maintained🟢 1030 commit(s) and 5 issue activity found in the last 90 days -- score normalized to 10
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Binary-Artifacts🟢 10no binaries found in the repo
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
License🟢 9license file detected
Packaging⚠️ -1packaging workflow not detected
Fuzzing⚠️ 0project is not fuzzed
Signed-Releases⚠️ -1no releases found
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Pinned-Dependencies⚠️ 0dependency not pinned by hash detected -- score normalized to 0
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
npm/@oxc-project/types 0.142.0 UnknownUnknown
npm/@rolldown/binding-android-arm64 1.2.1 UnknownUnknown
npm/@rolldown/binding-darwin-arm64 1.2.1 UnknownUnknown
npm/@rolldown/binding-darwin-x64 1.2.1 UnknownUnknown
npm/@rolldown/binding-freebsd-x64 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-arm-gnueabihf 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-arm64-gnu 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-arm64-musl 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-ppc64-gnu 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-s390x-gnu 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-x64-gnu 1.2.1 UnknownUnknown
npm/@rolldown/binding-linux-x64-musl 1.2.1 UnknownUnknown
npm/@rolldown/binding-openharmony-arm64 1.2.1 UnknownUnknown
npm/@rolldown/binding-wasm32-wasi 1.2.1 UnknownUnknown
npm/@rolldown/binding-win32-arm64-msvc 1.2.1 UnknownUnknown
npm/@rolldown/binding-win32-x64-msvc 1.2.1 UnknownUnknown
npm/nf3 0.1.12 UnknownUnknown
npm/nitro-nightly 4.0.0-20251010-091516-7cafddba 🟢 6.9
Details
CheckScoreReason
Code-Review🟢 6Found 18/29 approved changesets -- score normalized to 6
Maintained🟢 1030 commit(s) and 7 issue activity found in the last 90 days -- score normalized to 10
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 10no binaries found in the repo
Pinned-Dependencies🟢 4dependency not pinned by hash detected -- score normalized to 4
License🟢 9license file detected
Fuzzing⚠️ 0project is not fuzzed
Signed-Releases⚠️ -1no releases found
Packaging🟢 10packaging workflow detected
Security-Policy🟢 10security policy file detected
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
Branch-Protection🟢 3branch protection is not maximal on development and all release branches
npm/rendu 0.0.6 UnknownUnknown
npm/rolldown 1.2.1 UnknownUnknown
npm/unenv 2.0.0-rc.21 UnknownUnknown
npm/unstorage 2.0.0-alpha.3 🟢 3.6
Details
CheckScoreReason
Code-Review⚠️ 2Found 6/29 approved changesets -- score normalized to 2
Maintained⚠️ 23 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 2
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Packaging⚠️ -1packaging workflow not detected
Binary-Artifacts🟢 10no binaries found in the repo
Token-Permissions⚠️ 0detected GitHub workflow tokens with excessive permissions
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
Pinned-Dependencies⚠️ 1dependency not pinned by hash detected -- score normalized to 1
Fuzzing⚠️ 0project is not fuzzed
License🟢 10license file detected
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0

Scanned Files

  • .github/workflows/e2e.yml
  • .github/workflows/release.yml
  • pnpm-lock.yaml

examples/vite is a Hono server, so `vite build` looked for an index.html that
does not exist. It now builds src/server.ts as an ssr entry, which is also what
its `start` script already expected to run — that script had never worked.

examples/nextjs is fixed by the client log.error() change in the previous
commit.

turbo declared no outputs covering build/ or .svelte-kit/, so react-router and
sveltekit warned on every run and their builds were never cached.

The job runs with --continue, so one broken example no longer cancels the rest
and hides whether they are healthy, and it is back in the required gate.

Two examples stay excluded. Both are dependency-resolution problems needing a
lockfile change that a workflow PR should not carry: tanstack-start aliases
nitro to nitro-nightly@latest while shamefullyHoist puts a different nitro at
the workspace root, and eve fails to type check because three copies of
@types/react resolve at once.
pr-clean-caches only ever read the PR number from the pull_request payload, so
a workflow_dispatch run expanded the ref to refs/pull//merge and matched
nothing. Manual runs now take the number as an input.

Workflow-level write permissions applied to every job in pr-clean-caches and
semantic-pull-request; they move onto the job that needs them, with the
workflow scope emptied. Every id-token and pull-requests grant now says what
it is for.
CI builds ten of the eleven examples. eve is the one that fails, and it is a
real failure I had wrongly dismissed: three copies of @types/react resolve at
once, so React.Key from one is not assignable to Key from another and every JSX
element fails to type check. It only passed on my machine because repeated
installs had left node_modules in a state CI never reproduces.

Pinning @types/react through a workspace override fixes it, but any change to
the resolution graph forces a full re-resolve, and that re-resolve breaks
apps/playground with 'Could not resolve @nuxt/icon (specified as a dependency
of @nuxt/ui)' and drags nitro-nightly@latest from a July 2026 build back to an
October 2025 one that pins a vulnerable h3. None of that belongs in a workflow
PR, so the lockfile stays untouched and eve is excluded until it is sorted.
Two overrides, both needed because a single duplicated version breaks a
consumer:

@types/react resolved to three versions at once, so React.Key from one copy
was not assignable to Key from another and every JSX element in examples/eve
failed to type check.

Pinning it forces a re-resolve that pulls a second rolldown, which splits
@nuxt/icon into two peer variants. shamefullyHoist then hoists neither, and
apps/playground dies on 'Could not resolve @nuxt/icon'. Scoping rolldown to
tsdown@0.22.8 keeps @nuxthub/core's older tsdown on its own copy.

examples/tanstack-start pinned off nitro-nightly@latest, which had drifted from
a July 2026 build to an October 2025 one carrying h3 2.0.1-rc.2 and its two
high-severity advisories.

All 11 examples build, 35 lint and typecheck tasks pass, 1647 tests green.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (3)
turbo.json (1)

97-98: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

Make test wait for the package-local build.

test depends only on dev:prepare, and dev:prepare is scoped to dependency build outputs via ^build. Run the current package build as well so tests that consume dist artifacts do not use stale output.

Proposed fix
     "test": {
-      "dependsOn": ["dev:prepare"],
+      "dependsOn": ["dev:prepare", "build"],
       "outputs": ["coverage/**"]
     },
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@turbo.json` around lines 97 - 98, Update the test task configuration to
depend on both dev:prepare and the current package’s build task, preserving the
existing coverage outputs and dependency build behavior.

Source: Learnings

.github/workflows/ci.yml (2)

73-81: 🎯 Functional Correctness | 🔴 Critical

Remove the unsupported parallel wrappers.

GitHub Actions does not support parallel: inside steps. Each setup action must be a top-level sequential step with uses:. The test, examples, and publish jobs remain invalid.

This is the same finding as the previous review comment, and it is still present in the current file.

#!/usr/bin/env bash
set -euo pipefail
actionlint .github/workflows/ci.yml

Also applies to: 104-112, 146-154

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ci.yml around lines 73 - 81, Remove the unsupported
parallel wrappers from the setup steps in the test, examples, and publish jobs.
Promote each nested setup action directly to the job’s steps list, preserving
its name, if condition, uses reference, and with configuration so every step
remains sequential and valid GitHub Actions syntax.

88-89: 🗄️ Data Integrity & Integration | 🟡 Minor | ⚡ Quick win

Use Turbo for the evlog coverage step.

.turbo/turbo.json defines test with dependsOn: ["dev:prepare"], but .github/workflows/ci.yml runs pnpm --filter evlog run test:coverage, which uses the direct vitest run --coverage script. Run pnpm exec turbo run test --filter=evlog or update test:coverage to preserve the required preparation dependency.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ci.yml around lines 88 - 89, Update the “Test evlog with
coverage” workflow step to invoke the Turbo `test` task for the `evlog` package,
using the existing `dev:prepare` dependency defined in `.turbo/turbo.json`,
instead of running `pnpm --filter evlog run test:coverage` directly.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.github/workflows/ci.yml:
- Around line 124-127: Update the “Build affected examples” workflow step so
evlog-eve-example is included in the required example build gate by removing its
exclusion filter. If its dependency issue prevents inclusion, resolve that
dependency or add a separate required build step for evlog-eve-example.

In @.github/workflows/pr-clean-caches.yml:
- Around line 34-35: Update the cache ID retrieval command in the PR cache
cleanup workflow to use gh api pagination, ensuring all pages of caches for the
pull request ref are fetched before deletion. Preserve the existing ref filter,
page size, and jq extraction.

In @.github/workflows/semantic-pull-request.yml:
- Around line 25-27: Split the workflow’s validate-pr flow so
amannn/action-semantic-pull-request runs in a separate job with only
pull-requests: read (and contents: read only if required by the pinned action),
then pass its lint failure result to the existing sticky-comment reporting job
configured with pull-requests: write. Preserve the current validation and
reporting behavior while ensuring write permissions are limited to
comment-posting steps.

In `@examples/eve/next-env.d.ts`:
- Line 3: Remove the manually added generated declaration import from
examples/eve/next-env.d.ts at lines 3-3 and examples/nextjs/next-env.d.ts at
lines 1-6, restoring both files to their original warning-only content so
Next.js regenerates them from .next/types/routes.d.ts.

In `@packages/evlog/src/runtime/client/log.ts`:
- Around line 123-126: Update serializeError() to preserve the full documented
payload by including internal and the EvlogError metadata fields why, fix, and
link alongside the existing fields. When serializing cause, recursively
serialize nested Error values while tracking visited objects to prevent cycles,
so their message and stack are retained rather than becoming {}. Add regression
coverage for internal, EvlogError metadata, and an Error-valued cause.

---

Outside diff comments:
In @.github/workflows/ci.yml:
- Around line 73-81: Remove the unsupported parallel wrappers from the setup
steps in the test, examples, and publish jobs. Promote each nested setup action
directly to the job’s steps list, preserving its name, if condition, uses
reference, and with configuration so every step remains sequential and valid
GitHub Actions syntax.
- Around line 88-89: Update the “Test evlog with coverage” workflow step to
invoke the Turbo `test` task for the `evlog` package, using the existing
`dev:prepare` dependency defined in `.turbo/turbo.json`, instead of running
`pnpm --filter evlog run test:coverage` directly.

In `@turbo.json`:
- Around line 97-98: Update the test task configuration to depend on both
dev:prepare and the current package’s build task, preserving the existing
coverage outputs and dependency build behavior.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: fcc149ee-f51d-4459-8b3f-d144d5a9a075

📥 Commits

Reviewing files that changed from the base of the PR and between 0833eb1 and 6eb1217.

📒 Files selected for processing (11)
  • .changeset/client-log-error-instance.md
  • .github/workflows/ci.yml
  • .github/workflows/pr-clean-caches.yml
  • .github/workflows/semantic-pull-request.yml
  • examples/eve/next-env.d.ts
  • examples/nextjs/next-env.d.ts
  • examples/vite/vite.config.ts
  • packages/evlog/src/runtime/client/log.ts
  • packages/evlog/src/types.ts
  • packages/evlog/test/core/client-console.test.ts
  • turbo.json

Comment thread .github/workflows/ci.yml Outdated
Comment thread .github/workflows/pr-clean-caches.yml Outdated
Comment thread .github/workflows/semantic-pull-request.yml Outdated
Comment thread examples/eve/next-env.d.ts Outdated
/// <reference types="next" />
/// <reference types="next/image-types/global" />
import "./.next/dev/types/routes.d.ts";
import "./.next/types/routes.d.ts";

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/usr/bin/env bash
set -euo pipefail

for file in examples/eve/next-env.d.ts examples/nextjs/next-env.d.ts; do
  rg -n 'NOTE: This file should not be edited|types/routes\.d\.ts' "$file"
done

git diff --check -- examples/eve/next-env.d.ts examples/nextjs/next-env.d.ts

Repository: HugoRCD/evlog

Length of output: 311


🏁 Script executed:

#!/usr/bin/env bash
set -euo pipefail

printf '--- tracked next-env.d.ts files ---\n'
git ls-files '*next-env.d.ts' || true

printf '\n--- file contents ---\n'
while IFS= read -r f; do
  echo "#### $f"
  cat -n "$f"
done < <(git ls-files '*next-env.d.ts')

printf '\n--- checked out diff/stat for target files ---\n'
git diff --ignore-submodules -- examples/eve/next-env.d.ts examples/nextjs/next-env.d.ts | sed -n '1,120p' || true

printf '\n--- lint/typecheck/test status without repo execution ---\n'
printf 'package scripts (if available)...\n'
python3 - <<'PY'
import json, pathlib
for path in ['package.json','pnpm-lock.yaml','yarn.lock','package-lock.json']:
    p=pathlib.Path(path)
    if p.exists():
        print(path)
        if p.name=='package.json':
            data=json.loads(p.read_text())
            print('scripts=',\njson.dumps(data.get('scripts',{}), indent=2, sort_keys=True))
PY

Repository: HugoRCD/evlog

Length of output: 242


🏁 Script executed:

#!/usr/bin/env bash
set -euo pipefail

printf '%s\n' '--- tracked next-env.d.ts files ---'
git ls-files '*next-env.d.ts' || true

printf '%s\n' ''
printf '%s\n' '--- file contents ---'
while IFS= read -r f; do
  echo "#### $f"
  cat -n "$f"
done < <(git ls-files '*next-env.d.ts')

printf '%s\n' ''
printf '%s\n' '--- checked out diff/stat for target files ---'
git diff --ignore-submodules -- examples/eve/next-env.d.ts examples/nextjs/next-env.d.ts | sed -n '1,120p' || true

printf '%s\n' ''
printf '%s\n' '--- package.json scripts if available ---'
python3 - <<'PY'
import json, pathlib
p=pathlib.Path('package.json')
if p.exists():
    data=json.loads(p.read_text())
    print(json.dumps(data.get('scripts', {}), indent=2, sort_keys=True))
else:
    print('no package.json')
PY

Repository: HugoRCD/evlog

Length of output: 355


🏁 Script executed:

#!/usr/bin/env bash
set -euo pipefail

printf '%s\n' '--- file contents ---'
git ls-files '*next-env.d.ts' | while IFS= read -r f; do
  echo "#### $f"
  cat -n "$f"
done

printf '%s\n' ''
printf '%s\n' '--- checked out diff/stat for target files ---'
git diff --ignore-submodules -- examples/eve/next-env.d.ts examples/nextjs/next-env.d.ts | sed -n '1,120p' || true

printf '%s\n' ''
printf '%s\n' '--- package.json scripts if available ---'
python3 - <<'PY'
import json, pathlib
p=pathlib.Path('package.json')
if p.exists():
    data=json.loads(p.read_text())
    print(json.dumps(data.get('scripts', {}), indent=2, sort_keys=True))
else:
    print('no package.json')
PY

Repository: HugoRCD/evlog

Length of output: 2777


Do not commit generated Next.js declaration changes.

next-env.d.ts is a generated declaration file, and both changed examples still include the unedited warning. Let Next.js regenerate next-env.d.ts from .next/types/routes.d.ts rather than committing these manual changes.

🧰 Tools
🪛 ESLint

[error] 3-3: Extra semicolon.

(semi)

📍 Affects 2 files
  • examples/eve/next-env.d.ts#L3-L3 (this comment)
  • examples/nextjs/next-env.d.ts#L1-L6
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@examples/eve/next-env.d.ts` at line 3, Remove the manually added generated
declaration import from examples/eve/next-env.d.ts at lines 3-3 and
examples/nextjs/next-env.d.ts at lines 1-6, restoring both files to their
original warning-only content so Next.js regenerates them from
.next/types/routes.d.ts.

Sources: Coding guidelines, Linters/SAST tools

Comment thread packages/evlog/src/runtime/client/log.ts
…Error

serializeError dropped internal and the EvlogError why/fix/link metadata that
the server logger stores, and it passed cause straight through: a nested Error
JSON.stringify's to {}, so the console output lost its message and stack.
Causes are now serialized recursively, with a seen set for cycles.

Also splits PR-title validation from comment posting so pull-requests: write is
scoped to the job that comments, paginates the cache listing in
pr-clean-caches, and drops two generated next-env.d.ts files that git add -A
had swept in.
Its drizzle query results resolve to any on a cold CI checkout, so vue-tsc
reports implicit-any on thirteen callbacks that type fine locally. The old
telemetry job only ran test and build, so this never ran in CI either and no
coverage is lost by leaving it out until the NuxtHub type generation is sorted.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant