build(nix): repackage publint for nix-update and auto-merge update PRs#1317
build(nix): repackage publint for nix-update and auto-merge update PRs#1317ryoppippi wants to merge 6 commits into
Conversation
The previous derivation embedded a hand-written pnpm-lock.yaml inside a runCommand, so updating publint meant editing the inlined lockfile by hand and it was not consumable by nix-update. Repackage it with buildNpmPackage and a committed package-lock.json generated from a thin wrapper package that depends on the pinned release. The whole runtime closure now lives in one lockfile plus a single npmDepsHash, and `version` is the single source of truth that feeds the wrapper's dependency entry. Exclude the generated lockfile from oxfmt: npmDepsHash is computed against the lockfile bytes, and reformatting it to tabs breaks the buildNpmPackage consistency check. The CLI closure (publint plus its five runtime deps) is unchanged.
Add nix-update to the dev shell and a `just update-publint [<version>]` recipe that regenerates the committed lockfile, then bumps the version and npmDepsHash in nix/publint.nix via nix-update. nix-update alone cannot regenerate the npm lockfile through the runCommand indirection, so the recipe wraps both steps into one entry point shared by maintainers and CI.
Add an update-publint job to the update-pricing workflow, chained after the models.dev job and mirroring the existing litellm/models.dev jobs: run `just update-publint`, skip when unchanged, validate with `just check`, and open or update a PR on automation/publint.
Add a composite action that mints an installation token from the ccusage org updater GitHub App and configures the matching bot git identity. Ported from the dotfiles updater so automated jobs can act as the App rather than the default GITHUB_TOKEN.
Drive the litellm, models.dev and publint update jobs with the ccusage org App token (CCUSAGE_UPDATER_APP_ID / _PRIVATE_KEY) instead of the default GITHUB_TOKEN, and enable squash auto-merge on each PR. PRs opened with the default GITHUB_TOKEN do not trigger on:pull_request workflows, so the automation PRs never ran CI and could not be merged hands-off. Using an App token makes CI run on the PR; auto-merge then lands it once required checks pass (configure branch protection on main for the gate to take effect).
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: defaults Review profile: CHILL Plan: Pro Plus Run ID: 📒 Files selected for processing (1)
🚧 Files skipped from review as they are similar to previous changes (1)
📝 WalkthroughWalkthroughMigrates the Changespublint Nix derivation migration and local tooling
GitHub Actions bot token and update-publint CI job
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
Poem
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
Deploying with
|
| Status | Name | Latest Commit | Preview URL | Updated (UTC) |
|---|---|---|---|---|
| ✅ Deployment successful! View logs |
ccusage-guide | 1d06090 | Commit Preview URL Branch Preview URL |
Jun 14 2026, 07:02 PM |
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 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/update-pricing.yaml:
- Line 86: The `gh pr merge` command is using a blanket `|| echo
"::warning::..."` that suppresses all failures including authentication errors,
API errors, and branch protection mismatches, allowing the job to pass despite
broken automation. Replace the blanket error suppression with conditional logic
that only suppresses the warning when auto-merge is specifically not enabled as
a feature, while allowing other error conditions (auth failures, API errors,
etc.) to fail the job as they should. This fix needs to be applied at all three
locations where the `gh pr merge` command with auto-merge is called.
- Around line 27-31: The checkout action is persisting the bot token in
`.git/config` which unnecessarily expands the token exposure surface. Remove the
token parameter from the checkout action that uses the bot token output, which
will prevent storing credentials in git config. Instead, authenticate the push
operations only where needed by passing the token directly to the git push
commands in each "Create pull request" step, limiting token exposure to only the
operations that actually require authentication.
🪄 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: defaults
Review profile: CHILL
Plan: Pro Plus
Run ID: a31b293b-dd3d-4a93-a257-dac2fb847a46
📒 Files selected for processing (7)
.github/actions/setup-git-bot/action.yml.github/workflows/update-pricing.yamljustfilenix/dev-shell.nixnix/publint-package-lock.jsonnix/publint.nixnix/treefmt.nix
ccusage
@ccusage/ccusage-darwin-arm64
@ccusage/ccusage-darwin-x64
@ccusage/ccusage-linux-arm64
@ccusage/ccusage-linux-x64
@ccusage/ccusage-win32-x64
commit: |
ccusage performance comparisonPR SHA: This compares the Rust PR release binary against the configured base package on the same CI runner. Package runtime diagnosticsCompares the PR package wrapper, the installed native optional dependency binary, and the workspace release binary on the same large fixture. This identifies whether slow package results come from JavaScript wrapper overhead, the published native binary build, or the Rust core itself. Fixtures: Claude
Committed fixture performanceCommitted small fixtures for stable PR-to-PR feedback and explicit Claude/Codex command coverage. Fixtures: Claude
Large real-world-shaped fixture performanceGenerated fixtures shaped from aggregate local log statistics: thousands of JSONL files, many small sessions, and a long tail of larger sessions. No real prompts, paths, or outputs are stored in the fixtures. Fixtures: Claude
Artifact size
Lower medians and smaller artifacts are better. CI runner noise still applies; use same-run ratios as directional PR feedback, not release guarantees. |
ccusage performance comparisonPR SHA: This compares the PR package against the configured base package on the same CI runner. Package runtime diagnosticsCompares the PR package wrapper, the installed native optional dependency binary, and the workspace release binary on the same large fixture. This identifies whether slow package results come from JavaScript wrapper overhead, the published native binary build, or the Rust core itself. Fixtures: Claude
Committed fixture performanceCommitted small fixtures for stable PR-to-PR feedback and explicit Claude/Codex command coverage. Fixtures: Claude
Large real-world-shaped fixture performanceGenerated fixtures shaped from aggregate local log statistics: thousands of JSONL files, many small sessions, and a long tail of larger sessions. No real prompts, paths, or outputs are stored in the fixtures. Fixtures: Claude
Artifact size
Lower medians and smaller artifacts are better. CI runner noise still applies; use same-run ratios as directional PR feedback, not release guarantees. |
There was a problem hiding this comment.
2 issues found across 7 files
Reply with feedback, questions, or to request a fix.
Fix all with cubic | Re-trigger cubic
Add persist-credentials: false to the bot-token checkouts so the token is not left in .git/config across later steps, and set the authenticated push URL explicitly inside each 'Create pull request' step where it is actually needed. Replace the blanket 'gh pr merge ... || echo' with a check that only emits the auto-merge warning when the failure message mentions auto-merge; auth, API, and branch-protection errors now fail the job instead of being silently dropped. Co-authored-by: Codesmith <codesmith-bot@users.noreply.github.com>
ccusage performance comparisonPR SHA: This compares the Rust PR release binary against the configured base package on the same CI runner. Package runtime diagnosticsCompares the PR package wrapper, the installed native optional dependency binary, and the workspace release binary on the same large fixture. This identifies whether slow package results come from JavaScript wrapper overhead, the published native binary build, or the Rust core itself. Fixtures: Claude
Committed fixture performanceCommitted small fixtures for stable PR-to-PR feedback and explicit Claude/Codex command coverage. Fixtures: Claude
Large real-world-shaped fixture performanceGenerated fixtures shaped from aggregate local log statistics: thousands of JSONL files, many small sessions, and a long tail of larger sessions. No real prompts, paths, or outputs are stored in the fixtures. Fixtures: Claude
Artifact size
Lower medians and smaller artifacts are better. CI runner noise still applies; use same-run ratios as directional PR feedback, not release guarantees. |
ccusage performance comparisonPR SHA: This compares the PR package against the configured base package on the same CI runner. Package runtime diagnosticsCompares the PR package wrapper, the installed native optional dependency binary, and the workspace release binary on the same large fixture. This identifies whether slow package results come from JavaScript wrapper overhead, the published native binary build, or the Rust core itself. Fixtures: Claude
Committed fixture performanceCommitted small fixtures for stable PR-to-PR feedback and explicit Claude/Codex command coverage. Fixtures: Claude
Large real-world-shaped fixture performanceGenerated fixtures shaped from aggregate local log statistics: thousands of JSONL files, many small sessions, and a long tail of larger sessions. No real prompts, paths, or outputs are stored in the fixtures. Fixtures: Claude
Artifact sizeLower medians and smaller artifacts are better. CI runner noise still applies; use same-run ratios as directional PR feedback, not release guarantees. |


Summary
Repackages the pinned
publintCLI so it can be updated bynix-update,adds a one-command update path, and rewires the scheduled update workflow
so its PRs actually run CI and auto-merge.
What changed
publint packaging
pnpm-lock.yamlinnix/publint.nixwith
buildNpmPackage+ a committednix/publint-package-lock.jsongenerated from a thin wrapper package. The runtime closure (publint +
its 5 deps) is unchanged;
versionis now the single source of truth.oxfmtinnix/treefmt.nix:npmDepsHashis computed against the lockfile bytes, so reformatting itbreaks the
buildNpmPackageconsistency check.nix-updateto the dev shell and ajust update-publint [<version>]recipe that regenerates the lockfile and bumps
version+npmDepsHash.update automation
setup-git-botcomposite action that mints a token from theccusage org updater GitHub App.
update-publintjob to theupdate pricingworkflow.(
CCUSAGE_UPDATER_APP_ID/_PRIVATE_KEY) instead of the defaultGITHUB_TOKEN, and enable squash auto-merge.Why
nix-updatealone cannot regenerate the npm lockfile through therunCommandindirection, so the recipe wraps both steps into one entrypoint shared by maintainers and CI. PRs opened with the default
GITHUB_TOKENdo not triggeron: pull_requestworkflows, so theautomation PRs never ran CI and could not merge hands-off; an App token
fixes that.
Follow-up required before the App jobs work
ccusageorg updater GitHub App (Contents + Pull requests:read & write) and install it on
ccusage/ccusage.CCUSAGE_UPDATER_APP_IDandCCUSAGE_UPDATER_APP_PRIVATE_KEY.mainsoauto-merge waits for green.
Testing
nix build .#publint→publint, 0.3.12just update-publint 0.3.21→ builds; reverted to 0.3.12nix flake check(treefmt / publint check),actionlint,typosNeed help on this PR? Tag
/codesmithwith what you need. Autofix is enabled.Summary by cubic
Repackages the pinned
publintCLI withbuildNpmPackageso it can be updated vianix-update, and hardens the scheduled updaters to use an App token, run CI, and auto-merge with proper error handling.Refactors
publinttobuildNpmPackagewith a committednix/publint-package-lock.json;versionis the single source of truth and the runtime closure is unchanged.just update-publint [<version>]and includednix-updatein the dev shell to regenerate the lockfile and bumpversion+npmDepsHash.nix/publint-package-lock.jsonfromoxfmtto keepnpmDepsHashstable.Migration
CCUSAGE_UPDATER_APP_IDandCCUSAGE_UPDATER_APP_PRIVATE_KEY.mainso squash auto-merge can trigger.Written for commit 1d06090. Summary will update on new commits.
Summary by CodeRabbit
update-publinttask to bump publint and regenerate the pinned lockfile/flake inputs.nix-update).