mirror of
https://github.com/affaan-m/ECC.git
synced 2026-08-17 21:15:40 +02:00
* fix(hooks): remove stray '?' that made every 'yarn <anything>' trigger tmux reminder
The tmux-reminder matcher uses one alternation per package manager. Each
branch requires a subcommand (install|test) — except yarn, whose subcommand
group carried a trailing `?`:
yarn (install|test)?
That made the subcommand optional, so the branch degraded to "yarn " plus
anything: `yarn add foo`, `yarn build`, `yarn dev`, even `yarn --version`
all matched and spammed the "Consider running in tmux" hint into the
additional-context channel.
Drop the `?` so yarn matches parity with npm/pnpm/bun. Verified locally
against 14 cases (yarn install/test still fire; yarn add/build/dev/… no
longer do; npm/pnpm/bun/pytest behavior unchanged).
Fixes #2514
* test(hooks): add pre-bash-tmux-reminder regression tests
Add coverage for the tmux-reminder matcher following the auto-tmux-dev.test.js
structure — the regex-first hook now has direct regression tests for the yarn
branch fix in this PR (and for the sibling package managers, other matched
tools, TMUX bypass, and malformed input).
16 assertions total:
- fires for: yarn install, yarn test, npm install, pnpm test, bun install,
pytest tests/, cargo build
- does NOT fire for: yarn add react, yarn build, yarn dev, yarn --version,
bare `yarn`, npm run dev
- respects TMUX env var
- tolerates invalid JSON and missing command field
Verified the tests actually catch the bug: reintroducing the buggy
`yarn (install|test)?` fails 4 of the 5 yarn non-match cases (the fifth,
bare `yarn`, stays passing because even the buggy branch requires a trailing
space after yarn).
Addresses CodeRabbit review on #2517.
* test(hooks): fail loudly on spawn errors, use destructuring, split runTests
Address three CodeRabbit review notes on tests/hooks/pre-bash-tmux-reminder.test.js:
- Fail loudly on spawnSync errors: raise instead of coercing
`result.status || 0`, which would mask spawn errors, timeouts, or signal
termination as a successful exit 0 (masks legitimate test failures).
- Use destructuring (`const { TMUX, ...env } = process.env`) instead of
copy-then-`delete` so the base env is built immutably.
- Split `runTests` (was 66 lines) into small per-group helpers
(runYarnTests, runSiblingPackageManagerTests, runOtherToolTests,
runTmuxBypassTests, runEdgeCaseTests). `runTests` is now 18 lines and
purely orchestrates.
16 assertions still pass; no coverage changes.
The 4th CodeRabbit note (avoid console.log in test files) is intentionally
not adopted here — every sibling hook test in this repo
(auto-tmux-dev.test.js, bash-hook-dispatcher.test.js, block-no-verify.test.js,
etc.) writes to console.log because the project's own test runner
(tests/run-all.js) is console-log based and there is no Jest/Mocha
dependency. Diverging from the established convention in a bugfix PR is
out of scope.
* test(hooks): trim tmux reminder regression coverage
---------
Co-authored-by: Haley Chen <2022hachen@gmail.com>
62 lines
1.8 KiB
JavaScript
Executable File
62 lines
1.8 KiB
JavaScript
Executable File
#!/usr/bin/env node
|
|
'use strict';
|
|
|
|
const MAX_STDIN = 1024 * 1024;
|
|
const { buildPreToolUseAdditionalContext } = require('./pretooluse-visible-output');
|
|
let raw = '';
|
|
|
|
function run(rawInput) {
|
|
try {
|
|
const input = typeof rawInput === 'string' ? JSON.parse(rawInput) : rawInput;
|
|
const cmd = String(input.tool_input?.command || '');
|
|
|
|
if (
|
|
process.platform !== 'win32' &&
|
|
!process.env.TMUX &&
|
|
/(npm (install|test)|pnpm (install|test)|yarn (install|test)|bun (install|test)|cargo build|make\b|docker\b|pytest|vitest|playwright)/.test(cmd)
|
|
) {
|
|
return {
|
|
additionalContext: [
|
|
'[Hook] Consider running in tmux for session persistence',
|
|
'[Hook] tmux new -s dev | tmux attach -t dev',
|
|
],
|
|
exitCode: 0,
|
|
};
|
|
}
|
|
} catch {
|
|
// ignore parse errors and pass through
|
|
}
|
|
|
|
return typeof rawInput === 'string' ? rawInput : JSON.stringify(rawInput);
|
|
}
|
|
|
|
if (require.main === module) {
|
|
process.stdin.setEncoding('utf8');
|
|
process.stdin.on('data', chunk => {
|
|
if (raw.length < MAX_STDIN) {
|
|
const remaining = MAX_STDIN - raw.length;
|
|
raw += chunk.substring(0, remaining);
|
|
}
|
|
});
|
|
|
|
process.stdin.on('end', () => {
|
|
const result = run(raw);
|
|
if (result && typeof result === 'object') {
|
|
if (result.stderr) {
|
|
process.stderr.write(`${result.stderr}\n`);
|
|
}
|
|
if (Object.prototype.hasOwnProperty.call(result, 'additionalContext')) {
|
|
process.stdout.write(buildPreToolUseAdditionalContext(result.additionalContext));
|
|
} else {
|
|
process.stdout.write(String(result.stdout || ''));
|
|
}
|
|
process.exitCode = Number.isInteger(result.exitCode) ? result.exitCode : 0;
|
|
return;
|
|
}
|
|
|
|
process.stdout.write(String(result));
|
|
});
|
|
}
|
|
|
|
module.exports = { run };
|