brick-break 1.0.0 → 1.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +44 -5
- package/dist/cli.js +13 -2
- package/dist/index.js +37 -2
- package/dist/next.d.ts +4 -0
- package/dist/next.js +37 -0
- package/package.json +24 -3
package/README.md
CHANGED
|
@@ -27,24 +27,63 @@ or just run it directly:
|
|
|
27
27
|
npx brick-break next build
|
|
28
28
|
```
|
|
29
29
|
|
|
30
|
+
## global install (recommended for non-js projects)
|
|
31
|
+
|
|
32
|
+
```bash
|
|
33
|
+
npm i -g brick-break
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
now you can use `bb` anywhere:
|
|
37
|
+
|
|
38
|
+
```bash
|
|
39
|
+
bb cargo build
|
|
40
|
+
bb go build
|
|
41
|
+
bb pytest
|
|
42
|
+
bb make
|
|
43
|
+
```
|
|
44
|
+
|
|
30
45
|
## works with everything
|
|
31
46
|
|
|
32
47
|
```bash
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
48
|
+
bb next build
|
|
49
|
+
bb npm run build
|
|
50
|
+
bb tsc
|
|
51
|
+
bb cargo build
|
|
52
|
+
bb go build
|
|
38
53
|
```
|
|
39
54
|
|
|
40
55
|
if it can fail, brick-break can make it funnier.
|
|
41
56
|
|
|
57
|
+
## next.js hmr support
|
|
58
|
+
|
|
59
|
+
for errors that happen while the dev server is running (hot reload), add the component to your layout:
|
|
60
|
+
|
|
61
|
+
```tsx
|
|
62
|
+
// app/layout.tsx
|
|
63
|
+
import { BrickBreak } from 'brick-break/next'
|
|
64
|
+
|
|
65
|
+
export default function RootLayout({ children }) {
|
|
66
|
+
return (
|
|
67
|
+
<html>
|
|
68
|
+
<body>
|
|
69
|
+
<BrickBreak />
|
|
70
|
+
{children}
|
|
71
|
+
</body>
|
|
72
|
+
</html>
|
|
73
|
+
)
|
|
74
|
+
}
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
now errors play the sound even during hot reload.
|
|
78
|
+
|
|
42
79
|
## how it works
|
|
43
80
|
|
|
44
81
|
1. runs your command
|
|
45
82
|
2. build fails? plays the sound
|
|
46
83
|
3. thats it
|
|
47
84
|
|
|
85
|
+
(for next.js hmr: watches for the error overlay in the browser)
|
|
86
|
+
|
|
48
87
|
## requirements
|
|
49
88
|
|
|
50
89
|
uses your system audio player (already installed):
|
package/dist/cli.js
CHANGED
|
@@ -4,8 +4,19 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
4
4
|
const index_1 = require("./index");
|
|
5
5
|
const args = process.argv.slice(2);
|
|
6
6
|
if (!args.length) {
|
|
7
|
-
console.log('usage:
|
|
8
|
-
console.log('example:
|
|
7
|
+
console.log('usage: bb <command>');
|
|
8
|
+
console.log('example: bb npm run build');
|
|
9
9
|
process.exit(1);
|
|
10
10
|
}
|
|
11
|
+
// detect next.js dev mode
|
|
12
|
+
const isNextDev = args.some(a => a.includes('next')) && args.some(a => a === 'dev');
|
|
13
|
+
if (isNextDev) {
|
|
14
|
+
console.log('\x1b[36m');
|
|
15
|
+
console.log('brick-break: for hmr error sounds, add to your layout.tsx:');
|
|
16
|
+
console.log('');
|
|
17
|
+
console.log(" import { BrickBreak } from 'brick-break/next'");
|
|
18
|
+
console.log('');
|
|
19
|
+
console.log(' // then add <BrickBreak /> inside <body>');
|
|
20
|
+
console.log('\x1b[0m');
|
|
21
|
+
}
|
|
11
22
|
(0, index_1.runCommand)(args);
|
package/dist/index.js
CHANGED
|
@@ -8,7 +8,13 @@ exports.runCommand = runCommand;
|
|
|
8
8
|
const child_process_1 = require("child_process");
|
|
9
9
|
const path_1 = __importDefault(require("path"));
|
|
10
10
|
const sound = path_1.default.join(__dirname, '..', 'sound.mp3');
|
|
11
|
+
let lastPlayed = 0;
|
|
12
|
+
const cooldown = 3000; // don't spam the sound
|
|
11
13
|
function playSound() {
|
|
14
|
+
const now = Date.now();
|
|
15
|
+
if (now - lastPlayed < cooldown)
|
|
16
|
+
return;
|
|
17
|
+
lastPlayed = now;
|
|
12
18
|
const p = process.platform;
|
|
13
19
|
if (p === 'darwin') {
|
|
14
20
|
(0, child_process_1.spawn)('afplay', [sound]);
|
|
@@ -17,15 +23,44 @@ function playSound() {
|
|
|
17
23
|
(0, child_process_1.spawn)('powershell', ['-c', `(New-Object Media.SoundPlayer '${sound}').PlaySync()`]);
|
|
18
24
|
}
|
|
19
25
|
else {
|
|
20
|
-
// linux - try pulseaudio first, fallback to alsa
|
|
21
26
|
const player = (0, child_process_1.spawn)('paplay', [sound]);
|
|
22
27
|
player.on('error', () => (0, child_process_1.spawn)('aplay', [sound]));
|
|
23
28
|
}
|
|
24
29
|
}
|
|
30
|
+
// patterns that indicate an error
|
|
31
|
+
const errorPatterns = [
|
|
32
|
+
/\u{2A2F}/u, // ⨯ (nextjs error)
|
|
33
|
+
/error(\[|:|\s)/i, // error: or error[ or error
|
|
34
|
+
/failed/i,
|
|
35
|
+
/exception/i,
|
|
36
|
+
/panic/i, // rust/go
|
|
37
|
+
/cannot find/i,
|
|
38
|
+
/not found/i,
|
|
39
|
+
/undefined/i,
|
|
40
|
+
/compilation failed/i,
|
|
41
|
+
];
|
|
42
|
+
function hasError(text) {
|
|
43
|
+
return errorPatterns.some(p => p.test(text));
|
|
44
|
+
}
|
|
25
45
|
function runCommand(args) {
|
|
26
46
|
const cmd = args[0];
|
|
27
47
|
const rest = args.slice(1);
|
|
28
|
-
const proc = (0, child_process_1.spawn)(cmd, rest, {
|
|
48
|
+
const proc = (0, child_process_1.spawn)(cmd, rest, {
|
|
49
|
+
stdio: ['inherit', 'pipe', 'pipe'],
|
|
50
|
+
shell: true
|
|
51
|
+
});
|
|
52
|
+
proc.stdout?.on('data', (data) => {
|
|
53
|
+
const text = data.toString();
|
|
54
|
+
process.stdout.write(text);
|
|
55
|
+
if (hasError(text))
|
|
56
|
+
playSound();
|
|
57
|
+
});
|
|
58
|
+
proc.stderr?.on('data', (data) => {
|
|
59
|
+
const text = data.toString();
|
|
60
|
+
process.stderr.write(text);
|
|
61
|
+
if (hasError(text))
|
|
62
|
+
playSound();
|
|
63
|
+
});
|
|
29
64
|
proc.on('close', code => {
|
|
30
65
|
if (code !== 0)
|
|
31
66
|
playSound();
|
package/dist/next.d.ts
ADDED
package/dist/next.js
ADDED
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
'use client';
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.BrickBreak = BrickBreak;
|
|
5
|
+
const jsx_runtime_1 = require("react/jsx-runtime");
|
|
6
|
+
const react_1 = require("react");
|
|
7
|
+
let lastPlayed = 0;
|
|
8
|
+
const cooldown = 3000;
|
|
9
|
+
function playSound() {
|
|
10
|
+
const now = Date.now();
|
|
11
|
+
if (now - lastPlayed < cooldown)
|
|
12
|
+
return;
|
|
13
|
+
lastPlayed = now;
|
|
14
|
+
const audio = new Audio('https://unpkg.com/brick-break/sound.mp3');
|
|
15
|
+
audio.play().catch(() => { });
|
|
16
|
+
}
|
|
17
|
+
function BrickBreak({ children }) {
|
|
18
|
+
const seenErrors = (0, react_1.useRef)(new Set());
|
|
19
|
+
(0, react_1.useEffect)(() => {
|
|
20
|
+
if (process.env.NODE_ENV !== 'development')
|
|
21
|
+
return;
|
|
22
|
+
const observer = new MutationObserver(() => {
|
|
23
|
+
// nextjs error overlay
|
|
24
|
+
const dialog = document.querySelector('[data-nextjs-dialog]');
|
|
25
|
+
if (dialog) {
|
|
26
|
+
const errorText = dialog.textContent || '';
|
|
27
|
+
if (!seenErrors.current.has(errorText)) {
|
|
28
|
+
seenErrors.current.add(errorText);
|
|
29
|
+
playSound();
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
});
|
|
33
|
+
observer.observe(document.body, { childList: true, subtree: true });
|
|
34
|
+
return () => observer.disconnect();
|
|
35
|
+
}, []);
|
|
36
|
+
return (0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, { children: children });
|
|
37
|
+
}
|
package/package.json
CHANGED
|
@@ -1,11 +1,22 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "brick-break",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.2.1",
|
|
4
4
|
"description": "Play a Lego break sound when your build fails",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"types": "./dist/index.d.ts",
|
|
10
|
+
"default": "./dist/index.js"
|
|
11
|
+
},
|
|
12
|
+
"./next": {
|
|
13
|
+
"types": "./dist/next.d.ts",
|
|
14
|
+
"default": "./dist/next.js"
|
|
15
|
+
}
|
|
16
|
+
},
|
|
7
17
|
"bin": {
|
|
8
|
-
"brick-break": "dist/cli.js"
|
|
18
|
+
"brick-break": "dist/cli.js",
|
|
19
|
+
"bb": "dist/cli.js"
|
|
9
20
|
},
|
|
10
21
|
"files": [
|
|
11
22
|
"dist",
|
|
@@ -22,7 +33,8 @@
|
|
|
22
33
|
"error",
|
|
23
34
|
"fun",
|
|
24
35
|
"developer-experience",
|
|
25
|
-
"nextjs"
|
|
36
|
+
"nextjs",
|
|
37
|
+
"react"
|
|
26
38
|
],
|
|
27
39
|
"author": "ShinniUwU",
|
|
28
40
|
"license": "MIT",
|
|
@@ -34,8 +46,17 @@
|
|
|
34
46
|
"bugs": {
|
|
35
47
|
"url": "https://github.com/ShinniUwU/brick-break/issues"
|
|
36
48
|
},
|
|
49
|
+
"peerDependencies": {
|
|
50
|
+
"react": ">=18.0.0"
|
|
51
|
+
},
|
|
52
|
+
"peerDependenciesMeta": {
|
|
53
|
+
"react": {
|
|
54
|
+
"optional": true
|
|
55
|
+
}
|
|
56
|
+
},
|
|
37
57
|
"devDependencies": {
|
|
38
58
|
"@types/node": "^20.0.0",
|
|
59
|
+
"@types/react": "^18.0.0",
|
|
39
60
|
"typescript": "^5.0.0"
|
|
40
61
|
}
|
|
41
62
|
}
|