From 7f77726a27efac28cef3b1e7a517c6d5d7e28f02 Mon Sep 17 00:00:00 2001 From: "Nabheet S. Sandhu" Date: Sat, 31 Oct 2026 16:34:09 -0600 Subject: [PATCH] chore(lint): adopt node-lint (biome + markdownlint) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Closes galactic-config#6. The repo had a markdownlint-only `lint` script and no `biome.json`, so it did not meet the `node-lint` skill and the JS was never linted or formatted. - Copy `biome.json` and `.markdownlint-cli2.jsonc` from the skill's `references/` (MD013 drops 120 -> 100 to match biome's lineWidth). - `lint` / `lint:fix` run biome then markdownlint, matching the skill's scripts. `check` is unchanged (lint + test) — no typecheck step on a plain-JS repo. - Add `@biomejs/biome` as a devDependency and to the release guard's inert list: it is a linter, it is not in `files`, so neither it nor its bumps can change what a consumer installs. - Fixes biome reported: a trailing comma in index.js, organised imports in the test file, and a missing semicolon in the README hook sample (a code block, so biome does not reach it — changed for consistency with the formatter). No behaviour change; the 7 existing tests still pass. - `.nvmrc` pins 24 (CI's version) and README Requirements notes that the dev tooling needs Node >= 22 while the plugin itself runs on 18+. CI already ran `npm run lint`, so the workflow only needed the inert-list entry. This changes published files (index.js, README.md), so the guard publishes a patch on merge — correct, and not what the lint wiring alone would have done. --- .github/workflows/ci.yml | 2 +- .markdownlint-cli2.jsonc | 11 ++- .nvmrc | 1 + README.md | 4 +- biome.json | 32 +++++++ index.js | 2 +- package-lock.json | 200 +++++++++++++++++++++++++++++++++++++++ package.json | 4 +- test/rewrite.test.mjs | 4 +- 9 files changed, 252 insertions(+), 8 deletions(-) create mode 100644 .nvmrc create mode 100644 biome.json diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 0ef9378..85ac9fc 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -177,7 +177,7 @@ jobs: # bundler or compiler), which still cuts a release when bumped. # jq -S normalises key order; on any error (e.g. package.json absent # on one side) treat it as shipping. - INERT_DEVDEPS='["markdownlint-cli2"]' + INERT_DEVDEPS='["@biomejs/biome","markdownlint-cli2"]' pkg_shipping_changed() { local before after # Single quotes are deliberate: $inert/$k are jq variables, not diff --git a/.markdownlint-cli2.jsonc b/.markdownlint-cli2.jsonc index 18d2ffe..ab2a5a7 100644 --- a/.markdownlint-cli2.jsonc +++ b/.markdownlint-cli2.jsonc @@ -1,6 +1,13 @@ { + // markdownlint-cli2 config — full enforcement, no rule exclusions. + // Full rule list: https://github.com/DavidAnson/markdownlint/blob/main/doc/Rules.md "config": { - "MD013": { "line_length": 120 } + "default": true, + // MD013: line length — ENFORCED at 100 everywhere (matches biome lineWidth) + "MD013": { "line_length": 100 } + // MD024: duplicate headings — ENFORCED (changelogs/reference docs must vary) + // MD041: first line must be top-level heading — ENFORCED + // MD060: table column style — ENFORCED }, - "ignores": ["node_modules"] + "globs": ["**/*.md", "!node_modules/**", "!dist/**", "!.git/**"] } diff --git a/.nvmrc b/.nvmrc new file mode 100644 index 0000000..a45fd52 --- /dev/null +++ b/.nvmrc @@ -0,0 +1 @@ +24 diff --git a/README.md b/README.md index 8dcb771..6a16e6d 100644 --- a/README.md +++ b/README.md @@ -21,6 +21,8 @@ form before the model ever sees it. This plugin wires the two together. - OpenCode **v2** (`opencode --version` reports 2.x). - `rtk` >= 0.23.0 on `PATH` — see [rtk-ai/rtk](https://github.com/rtk-ai/rtk): `brew install rtk` +- Node >= 22 to run the dev tooling (`markdownlint-cli2` needs it); `.nvmrc` + pins 24, matching CI. The plugin itself runs on Node 18+. ## Install @@ -86,7 +88,7 @@ The plugin registers one OpenCode v2 shell hook: ```js ctx.shell.hook("create.before", (event) => { // event.command is the command about to run; mutate it to rewrite -}) +}); ``` For each shell command it runs `rtk rewrite ` and replaces the command diff --git a/biome.json b/biome.json new file mode 100644 index 0000000..164ca8f --- /dev/null +++ b/biome.json @@ -0,0 +1,32 @@ +{ + "$schema": "https://biomejs.dev/schemas/2.6.4/schema.json", + "formatter": { + "enabled": true, + "indentStyle": "space", + "indentWidth": 2, + "lineWidth": 100, + "lineEnding": "lf" + }, + "linter": { + "enabled": true, + "rules": { + "preset": "recommended" + } + }, + "assist": { + "actions": { + "source": { + "organizeImports": "on" + } + } + }, + "javascript": { + "formatter": { + "quoteStyle": "double", + "semicolons": "always" + } + }, + "files": { + "includes": ["**", "!node_modules", "!dist", "!.git", "!coverage"] + } +} diff --git a/index.js b/index.js index eedc5ed..e0e943c 100644 --- a/index.js +++ b/index.js @@ -44,7 +44,7 @@ function rewriteCommand(binary, command, timeoutMs) { (_err, stdout) => { const out = String(stdout ?? "").trim(); done(out && out !== command ? out : null); - } + }, ); } catch { return done(null); diff --git a/package-lock.json b/package-lock.json index 9e2f8e1..08e6e55 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,12 +9,212 @@ "version": "0.1.0", "license": "MIT", "devDependencies": { + "@biomejs/biome": "^2.6.4", "markdownlint-cli2": "^0.24.0" }, "engines": { "node": ">=18" } }, + "node_modules/@biomejs/biome": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/biome/-/biome-2.6.4.tgz", + "integrity": "sha512-8sKKwaNW4ot22awZ3lBjwWLHnUFXgXnrBPYS2gNlBAXRbDC++7kqjK2H7dR/FgCDtPvO1xfKpgEhJkGxAKYkxA==", + "dev": true, + "license": "MIT OR Apache-2.0", + "bin": { + "biome": "bin/biome" + }, + "engines": { + "node": ">=14.21.3" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/biome" + }, + "optionalDependencies": { + "@biomejs/cli-android-arm64": "2.6.4", + "@biomejs/cli-android-x64": "2.6.4", + "@biomejs/cli-darwin-arm64": "2.6.4", + "@biomejs/cli-darwin-x64": "2.6.4", + "@biomejs/cli-linux-arm64": "2.6.4", + "@biomejs/cli-linux-arm64-musl": "2.6.4", + "@biomejs/cli-linux-x64": "2.6.4", + "@biomejs/cli-linux-x64-musl": "2.6.4", + "@biomejs/cli-win32-arm64": "2.6.4", + "@biomejs/cli-win32-x64": "2.6.4" + } + }, + "node_modules/@biomejs/cli-android-arm64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-android-arm64/-/cli-android-arm64-2.6.4.tgz", + "integrity": "sha512-jwrwigP4tBcHxzuV8izioX/BOUhJL/4e2rNSOE5nCjBkVC018LQAQUGiH+CNkFYvLtQ1dcZo5/xXERmaAGc7JQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-android-x64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-android-x64/-/cli-android-x64-2.6.4.tgz", + "integrity": "sha512-HdGInPJ4nZFwHxzvEtcp2nmSBtUyJrurmtIK43upFckuS3+ZqVM05HtsxQWnqGsuy/pxckIAjyKWlEKRlBXUyA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-darwin-arm64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-arm64/-/cli-darwin-arm64-2.6.4.tgz", + "integrity": "sha512-0VvcUz46wbg59Q4TZ59KkIjDJrxEyu4Eoe79+F4SChxoWe+W7AEyIp6F5r72C9+p6MsB6dIovnZt1D30lGM3XA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-darwin-x64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-x64/-/cli-darwin-x64-2.6.4.tgz", + "integrity": "sha512-fxmvkF81srlS3DiMyfm+aG3J0eG+6/BjaxRyjy57KbLSafnq0PO+hHfVWmtH2ty0S7nm6yDXBRwySfFeaRJKRQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-linux-arm64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64/-/cli-linux-arm64-2.6.4.tgz", + "integrity": "sha512-6+bK1Y/evmIUiJr7auertuMbiaYVicJhqA1bZyL47lCMWugv8l0gFQCqvR/gN1vZMHYm+HwoTKgeMxdNFCoQTg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-linux-arm64-musl": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64-musl/-/cli-linux-arm64-musl-2.6.4.tgz", + "integrity": "sha512-31ZaH/MHqPX+O+evRwRrCHQ8W5/9adY+/eMytGGWZnRx1T41QsWIF09+/WujynLBhWZUxNGS5CtsWLwgOFTAyg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-linux-x64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64/-/cli-linux-x64-2.6.4.tgz", + "integrity": "sha512-tbFZMdL6dP/ws4edXxYG9WhvaVa1ZDzL4G5DzahnWW7Psib9H+VTdyU4XXVxpJk5j/nYZroSbvSNyYlpW3yCIw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-linux-x64-musl": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64-musl/-/cli-linux-x64-musl-2.6.4.tgz", + "integrity": "sha512-bomSa2XdQAGGj6Cwdm4M13qE+lN9+AOlW8KtI4hdyVyRRF/Z71qPAi95T4wtdZK0QpBbkTW8hgbZZCwPi4xzIw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-win32-arm64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-win32-arm64/-/cli-win32-arm64-2.6.4.tgz", + "integrity": "sha512-eCsqt8Ma3eVap+oyJCDnJZH60SIU464B66n3y38EUTJdM1T/HfZol1FJC9vb+sHToX0ix8XzqPcwJnOzyAJz0g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=14.21.3" + } + }, + "node_modules/@biomejs/cli-win32-x64": { + "version": "2.6.4", + "resolved": "https://registry.npmjs.org/@biomejs/cli-win32-x64/-/cli-win32-x64-2.6.4.tgz", + "integrity": "sha512-pYsMy5AThiHFOZAsngg8qN4PurM6nInKBhVX7sbj3eNpRQqo1Hb0MgCwPL7VqVMrmcEEMj9Ks3qbkallR65e8g==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT OR Apache-2.0", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=14.21.3" + } + }, "node_modules/@nodelib/fs.scandir": { "version": "2.1.5", "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", diff --git a/package.json b/package.json index 0691b2c..b93ffb2 100644 --- a/package.json +++ b/package.json @@ -41,11 +41,13 @@ "access": "public" }, "scripts": { - "lint": "markdownlint-cli2 \"**/*.md\"", + "lint": "biome check . && markdownlint-cli2 \"**/*.md\" \"#node_modules/**\" \"#dist/**\" \"#.git/**\"", + "lint:fix": "biome check --write . && markdownlint-cli2 --fix \"**/*.md\" \"#node_modules/**\" \"#dist/**\" \"#.git/**\"", "test": "node --check index.js && node --test test/*.test.mjs", "check": "npm run lint && npm test" }, "devDependencies": { + "@biomejs/biome": "^2.6.4", "markdownlint-cli2": "^0.24.0" }, "overrides": { diff --git a/test/rewrite.test.mjs b/test/rewrite.test.mjs index 3e5f559..67fd304 100644 --- a/test/rewrite.test.mjs +++ b/test/rewrite.test.mjs @@ -4,11 +4,11 @@ // without rtk installed. The critical regression: `rtk rewrite` exits 3 with // the rewrite on stdout — the plugin must key on stdout, not exit status. -import { test } from "node:test"; import assert from "node:assert/strict"; -import { mkdtemp, writeFile, chmod } from "node:fs/promises"; +import { chmod, mkdtemp, writeFile } from "node:fs/promises"; import { tmpdir } from "node:os"; import { join } from "node:path"; +import { test } from "node:test"; import plugin from "../index.js";