brosh 0.2.2 → 0.2.3

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.
Files changed (42) hide show
  1. package/README.github.md +169 -0
  2. package/README.md +18 -141
  3. package/README.npm.md +58 -0
  4. package/dist/lib.d.ts +1 -1
  5. package/dist/lib.d.ts.map +1 -1
  6. package/dist/lib.js +1 -1
  7. package/dist/lib.js.map +1 -1
  8. package/dist/terminal/index.d.ts +1 -1
  9. package/dist/terminal/index.d.ts.map +1 -1
  10. package/dist/terminal/index.js +1 -1
  11. package/dist/terminal/index.js.map +1 -1
  12. package/dist/terminal/session.d.ts +14 -1
  13. package/dist/terminal/session.d.ts.map +1 -1
  14. package/dist/terminal/session.js +263 -78
  15. package/dist/terminal/session.js.map +1 -1
  16. package/package.json +7 -4
  17. package/packages/desktop-electron/build/afterInstall-linux.sh +4 -0
  18. package/packages/desktop-electron/build/afterPack.cjs +29 -19
  19. package/packages/desktop-electron/build/entitlements.mac.inherit.plist +14 -0
  20. package/packages/desktop-electron/build/entitlements.mac.plist +16 -0
  21. package/packages/desktop-electron/package-lock.json +666 -165
  22. package/packages/desktop-electron/package.json +53 -14
  23. package/packages/desktop-electron/scripts/bundle-main.mjs +97 -0
  24. package/packages/desktop-electron/scripts/bytecode-compiler.cjs +3 -0
  25. package/packages/desktop-electron/scripts/fix-dev-entitlements.js +56 -0
  26. package/packages/desktop-electron/vite.config.ts +13 -0
  27. package/packaging/aur/.SRCINFO +20 -0
  28. package/packaging/aur/PKGBUILD +26 -0
  29. package/vendor/xterm-headless-5.5.0.tgz +0 -0
  30. package/vendor/xterm-xterm-5.5.0.tgz +0 -0
  31. package/website/CNAME +1 -0
  32. package/website/assets/images/.gitkeep +0 -0
  33. package/website/assets/videos/.gitkeep +0 -0
  34. package/website/css/styles.css +735 -0
  35. package/website/gpg.key +37 -0
  36. package/website/index.html +314 -0
  37. package/website/install.sh.asc +16 -0
  38. package/website/js/main.js +293 -0
  39. package/website/rpm/brosh.repo +6 -0
  40. package/website/uninstall.sh +10 -0
  41. package/packages/desktop-electron/tests/main/error-triage/buildTriagePrompt.test.ts +0 -133
  42. package/packages/desktop-electron/tests/main/error-triage/parseTriageResponse.test.ts +0 -123
@@ -1,30 +1,37 @@
1
1
  {
2
2
  "name": "brosh-desktop",
3
3
  "productName": "brosh",
4
- "version": "0.2.2",
4
+ "version": "0.1.9",
5
5
  "description": "Desktop GUI for brosh - A terminal emulator with MCP support",
6
- "author": "Ellery Familia",
6
+ "author": {
7
+ "name": "Ellery Familia",
8
+ "email": "ellery@elleryfamilia.com"
9
+ },
10
+ "homepage": "https://github.com/elleryfamilia/brosh",
7
11
  "license": "MIT",
8
12
  "main": "dist/main/index.js",
9
13
  "type": "module",
10
14
  "scripts": {
11
- "dev": "ELECTRON_DEV=true npm run build:main && concurrently \"npm run watch:main\" \"npm run watch:renderer\" \"ELECTRON_DEV=true npm run electron\"",
15
+ "dev": "ELECTRON_DEV=true npm run build:main:dev && concurrently \"npm run watch:main\" \"npm run watch:renderer\" \"ELECTRON_DEV=true npm run electron\"",
12
16
  "build": "npm run build:main && npm run build:renderer",
13
- "build:main": "tsc -p tsconfig.main.json && cp src/main/preload.cjs dist/main/",
17
+ "build:main": "tsc -p tsconfig.main.json --noEmit && node scripts/bundle-main.mjs",
18
+ "build:main:bytecode": "tsc -p tsconfig.main.json --noEmit && node scripts/bundle-main.mjs --bytecode",
19
+ "build:bytecode": "npm run build:main:bytecode && npm run build:renderer",
20
+ "build:main:dev": "tsc -p tsconfig.main.json && cp src/main/preload.cjs dist/main/",
14
21
  "build:renderer": "vite build",
15
22
  "watch:main": "tsc -p tsconfig.main.json --watch",
16
23
  "watch:renderer": "vite build --watch",
17
24
  "electron": "electron .",
18
25
  "start": "npm run build && electron .",
19
26
  "prepackage": "node scripts/prepare-sandbox-bins.js && rm -rf node_modules/brosh && mkdir -p node_modules/brosh && cp -r ../../dist ../../package.json node_modules/brosh/",
20
- "package": "npm run prepackage && npm run build && electron-builder",
21
- "package:mac": "npm run prepackage && npm run build && electron-builder --mac",
22
- "package:win": "npm run prepackage && npm run build && electron-builder --win",
23
- "package:linux": "npm run prepackage && npm run build && electron-builder --linux",
27
+ "package": "npm run prepackage && npm run build:bytecode && electron-builder",
28
+ "package:mac": "npm run prepackage && npm run build:bytecode && electron-builder --mac -c.extraMetadata.localBuild=true",
29
+ "package:win": "npm run prepackage && npm run build:bytecode && electron-builder --win -c.extraMetadata.localBuild=true",
30
+ "package:linux": "npm run prepackage && npm run build:bytecode && electron-builder --linux -c.extraMetadata.localBuild=true",
24
31
  "postpackage": "rm -rf node_modules/brosh && npm install",
25
32
  "download-models": "node scripts/download-models.js",
26
33
  "prepare-sandbox-bins": "node scripts/prepare-sandbox-bins.js",
27
- "postinstall": "node scripts/download-models.js",
34
+ "postinstall": "node scripts/download-models.js && node scripts/fix-dev-entitlements.js",
28
35
  "test": "vitest run",
29
36
  "test:watch": "vitest",
30
37
  "test:coverage": "vitest run --coverage"
@@ -51,13 +58,15 @@
51
58
  "@xterm/addon-search": "^0.16.0",
52
59
  "@xterm/addon-web-links": "^0.11.0",
53
60
  "@xterm/addon-webgl": "^0.18.0",
54
- "@xterm/xterm": "^5.5.0",
61
+ "@xterm/xterm": "file:../../vendor/xterm-xterm-5.5.0.tgz",
55
62
  "brosh": "file:../..",
63
+ "bytenode": "^1.5.7",
56
64
  "chokidar": "^5.0.0",
57
65
  "cli-highlight": "^2.1.11",
58
66
  "electron-store": "^10.0.0",
59
67
  "electron-updater": "^6.7.3",
60
68
  "fastest-levenshtein": "^1.0.16",
69
+ "material-file-icons": "^2.4.0",
61
70
  "monaco-editor": "^0.55.1",
62
71
  "monaco-vim": "^0.4.4",
63
72
  "posthog-node": "^5.24.7",
@@ -72,8 +81,9 @@
72
81
  "@vitejs/plugin-react": "^4.2.0",
73
82
  "@vitest/coverage-v8": "^2.0.0",
74
83
  "concurrently": "^8.2.0",
75
- "electron": "^33.0.0",
84
+ "electron": "^33.4.11",
76
85
  "electron-builder": "^25.0.0",
86
+ "esbuild": "^0.25.12",
77
87
  "react": "^18.2.0",
78
88
  "react-dom": "^18.2.0",
79
89
  "typescript": "^5.0.0",
@@ -83,6 +93,7 @@
83
93
  "build": {
84
94
  "appId": "com.ellery.brosh",
85
95
  "productName": "brosh",
96
+ "asar": false,
86
97
  "afterPack": "./build/afterPack.cjs",
87
98
  "directories": {
88
99
  "output": "release"
@@ -139,7 +150,8 @@
139
150
  {
140
151
  "provider": "github",
141
152
  "owner": "elleryfamilia",
142
- "repo": "brosh"
153
+ "repo": "brosh",
154
+ "releaseType": "release"
143
155
  }
144
156
  ],
145
157
  "mac": {
@@ -153,9 +165,15 @@
153
165
  "target": "zip"
154
166
  }
155
167
  ],
168
+ "hardenedRuntime": true,
169
+ "gatekeeperAssess": false,
170
+ "entitlements": "build/entitlements.mac.plist",
171
+ "entitlementsInherit": "build/entitlements.mac.inherit.plist",
172
+ "notarize": true,
156
173
  "extendInfo": {
157
174
  "NSSupportsAutomaticTermination": false,
158
- "NSSupportsSuddenTermination": false
175
+ "NSSupportsSuddenTermination": false,
176
+ "NSMicrophoneUsageDescription": "brosh needs microphone access for voice input features."
159
177
  }
160
178
  },
161
179
  "win": {
@@ -164,7 +182,28 @@
164
182
  },
165
183
  "linux": {
166
184
  "icon": "resources/icons/png",
167
- "category": "Development"
185
+ "category": "Development",
186
+ "target": [
187
+ "deb",
188
+ "rpm"
189
+ ],
190
+ "executableName": "brosh"
191
+ },
192
+ "deb": {
193
+ "afterInstall": "build/afterInstall-linux.sh",
194
+ "recommends": [
195
+ "bubblewrap",
196
+ "socat",
197
+ "ripgrep"
198
+ ]
199
+ },
200
+ "rpm": {
201
+ "afterInstall": "build/afterInstall-linux.sh",
202
+ "fpm": [
203
+ "--rpm-tag", "Suggests: bubblewrap",
204
+ "--rpm-tag", "Suggests: socat",
205
+ "--rpm-tag", "Suggests: ripgrep"
206
+ ]
168
207
  }
169
208
  }
170
209
  }
@@ -0,0 +1,97 @@
1
+ import { build } from "esbuild";
2
+ import { cpSync, existsSync, writeFileSync, unlinkSync } from "fs";
3
+ import { execFileSync } from "child_process";
4
+ import { createRequire } from "module";
5
+
6
+ const bytecode = process.argv.includes("--bytecode");
7
+
8
+ if (bytecode) {
9
+ // Bytecode path: bundle as CJS → compile with Electron's V8 → ESM loader stub
10
+ await build({
11
+ entryPoints: ["src/main/index.ts"],
12
+ bundle: true,
13
+ outfile: "dist/main/bundle.cjs",
14
+ platform: "node",
15
+ format: "cjs",
16
+ target: "node20",
17
+ sourcemap: false,
18
+ // Bytecode externals differ from ESM: CJS can't require() ESM-only packages,
19
+ // so we inline them (electron-store, chokidar, brosh) and let esbuild convert
20
+ // to CJS. node-pty stays external (native addon).
21
+ external: [
22
+ "electron",
23
+ "electron-updater",
24
+ "node-pty",
25
+ "ws",
26
+ "posthog-node",
27
+ "@huggingface/transformers",
28
+ "cli-highlight",
29
+ "bytenode",
30
+ ],
31
+ // Convert import() → require() so no dynamic imports in bytecode (vm.Script
32
+ // doesn't support import() without --experimental-vm-modules).
33
+ supported: { "dynamic-import": false },
34
+ });
35
+
36
+ // Compile CJS bundle to V8 bytecode using Electron's V8
37
+ const require = createRequire(import.meta.url);
38
+ const electronPath = require("electron");
39
+ execFileSync(electronPath, ["scripts/bytecode-compiler.cjs", "dist/main/bundle.cjs"], {
40
+ env: { ...process.env, ELECTRON_RUN_AS_NODE: "1" },
41
+ stdio: "inherit",
42
+ });
43
+
44
+ // Write ESM loader stub
45
+ writeFileSync(
46
+ "dist/main/index.js",
47
+ [
48
+ `import { createRequire } from 'module';`,
49
+ `import v8 from 'v8';`,
50
+ `v8.setFlagsFromString('--no-lazy');`,
51
+ `v8.setFlagsFromString('--no-flush-bytecode');`,
52
+ `const require = createRequire(import.meta.url);`,
53
+ `require('bytenode');`,
54
+ `require('./bundle.jsc');`,
55
+ ``,
56
+ ].join("\n"),
57
+ );
58
+
59
+ // Clean up intermediate CJS bundle and stale sourcemap from previous ESM builds
60
+ unlinkSync("dist/main/bundle.cjs");
61
+ if (existsSync("dist/main/index.js.map")) {
62
+ unlinkSync("dist/main/index.js.map");
63
+ }
64
+ } else {
65
+ // Standard ESM bundle path
66
+ await build({
67
+ entryPoints: ["src/main/index.ts"],
68
+ bundle: true,
69
+ outfile: "dist/main/index.js",
70
+ platform: "node",
71
+ format: "esm",
72
+ target: "node20",
73
+ sourcemap: true,
74
+ external: [
75
+ "electron",
76
+ "electron-store",
77
+ "electron-updater",
78
+ "brosh",
79
+ "ws",
80
+ "posthog-node",
81
+ "@huggingface/transformers",
82
+ "chokidar",
83
+ "cli-highlight",
84
+ ],
85
+ banner: {
86
+ js: [
87
+ `import { fileURLToPath as _bundled_fileURLToPath } from 'url';`,
88
+ `import { dirname as _bundled_dirname } from 'path';`,
89
+ `const __filename = _bundled_fileURLToPath(import.meta.url);`,
90
+ `const __dirname = _bundled_dirname(__filename);`,
91
+ ].join("\n"),
92
+ },
93
+ });
94
+ }
95
+
96
+ // Preload script is CJS, loaded separately by Electron — just copy it
97
+ cpSync("src/main/preload.cjs", "dist/main/preload.cjs");
@@ -0,0 +1,3 @@
1
+ require("bytenode");
2
+ const bytenode = require("bytenode");
3
+ bytenode.compileFile(process.argv[2]);
@@ -0,0 +1,56 @@
1
+ /**
2
+ * Re-sign the dev Electron binary with microphone entitlement.
3
+ *
4
+ * The stock Electron.app ships with a broken signature on macOS, so
5
+ * systemPreferences.askForMediaAccess("microphone") silently returns
6
+ * "denied" instead of showing the TCC prompt. Re-signing with ad-hoc
7
+ * identity + the audio-input entitlement fixes this.
8
+ *
9
+ * Runs automatically via postinstall; safe to re-run at any time.
10
+ */
11
+
12
+ import { execFileSync } from "child_process";
13
+ import { writeFileSync, unlinkSync, existsSync } from "fs";
14
+ import { join, dirname } from "path";
15
+ import { fileURLToPath } from "url";
16
+
17
+ const __dirname = dirname(fileURLToPath(import.meta.url));
18
+
19
+ if (process.platform !== "darwin") {
20
+ process.exit(0);
21
+ }
22
+
23
+ const electronApp = join(
24
+ __dirname,
25
+ "../node_modules/electron/dist/Electron.app"
26
+ );
27
+
28
+ if (!existsSync(electronApp)) {
29
+ // electron not installed yet (possible during CI)
30
+ process.exit(0);
31
+ }
32
+
33
+ const entitlements = `<?xml version="1.0" encoding="UTF-8"?>
34
+ <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
35
+ <plist version="1.0">
36
+ <dict>
37
+ <key>com.apple.security.device.audio-input</key>
38
+ <true/>
39
+ </dict>
40
+ </plist>`;
41
+
42
+ const tmpPlist = join(__dirname, "_dev-entitlements.plist");
43
+
44
+ try {
45
+ writeFileSync(tmpPlist, entitlements);
46
+ execFileSync("codesign", [
47
+ "--force", "--deep", "--sign", "-",
48
+ "--entitlements", tmpPlist,
49
+ electronApp,
50
+ ], { stdio: "inherit" });
51
+ console.log("[fix-dev-entitlements] Electron.app re-signed with microphone entitlement");
52
+ } catch (err) {
53
+ console.warn("[fix-dev-entitlements] Failed to re-sign Electron.app:", err.message);
54
+ } finally {
55
+ try { unlinkSync(tmpPlist); } catch {}
56
+ }
@@ -6,11 +6,24 @@ export default defineConfig({
6
6
  plugins: [react()],
7
7
  base: './',
8
8
  root: 'src/renderer',
9
+ resolve: {
10
+ preserveSymlinks: true,
11
+ },
9
12
  build: {
10
13
  outDir: '../../dist/renderer',
11
14
  emptyOutDir: true,
12
15
  rollupOptions: {
13
16
  input: resolve(__dirname, 'src/renderer/index.html'),
17
+ output: {
18
+ manualChunks: {
19
+ 'vendor-react': ['react', 'react-dom', 'react/jsx-runtime'],
20
+ 'vendor-xterm': [
21
+ '@xterm/xterm', '@xterm/addon-fit', '@xterm/addon-webgl',
22
+ '@xterm/addon-canvas', '@xterm/addon-web-links', '@xterm/addon-image',
23
+ '@xterm/addon-clipboard', '@xterm/addon-search',
24
+ ],
25
+ },
26
+ },
14
27
  },
15
28
  },
16
29
  server: {
@@ -0,0 +1,20 @@
1
+ pkgbase = brosh-bin
2
+ pkgdesc = AI-native terminal built for Claude coders
3
+ pkgver = 0.1.0
4
+ pkgrel = 1
5
+ url = https://github.com/elleryfamilia/brosh
6
+ arch = x86_64
7
+ arch = aarch64
8
+ license = MIT
9
+ depends = gtk3
10
+ depends = nss
11
+ depends = libxss
12
+ depends = alsa-lib
13
+ provides = brosh
14
+ conflicts = brosh
15
+ source_x86_64 = https://github.com/elleryfamilia/brosh/releases/download/v0.1.0/brosh_0.1.0_amd64.deb
16
+ source_aarch64 = https://github.com/elleryfamilia/brosh/releases/download/v0.1.0/brosh_0.1.0_arm64.deb
17
+ sha256sums_x86_64 = SKIP
18
+ sha256sums_aarch64 = SKIP
19
+
20
+ pkgname = brosh-bin
@@ -0,0 +1,26 @@
1
+ # Maintainer: Ellery Familia <ellery@elleryfamilia.com>
2
+ pkgname=brosh-bin
3
+ pkgver=0.1.0
4
+ pkgrel=1
5
+ pkgdesc="AI-native terminal built for Claude coders"
6
+ arch=('x86_64' 'aarch64')
7
+ url="https://github.com/elleryfamilia/brosh"
8
+ license=('MIT')
9
+ depends=('gtk3' 'nss' 'libxss' 'alsa-lib')
10
+ provides=('brosh')
11
+ conflicts=('brosh')
12
+ source_x86_64=("${url}/releases/download/v${pkgver}/brosh_${pkgver}_amd64.deb")
13
+ source_aarch64=("${url}/releases/download/v${pkgver}/brosh_${pkgver}_arm64.deb")
14
+ sha256sums_x86_64=('SKIP')
15
+ sha256sums_aarch64=('SKIP')
16
+
17
+ package() {
18
+ bsdtar -xf data.tar.* -C "$pkgdir/"
19
+
20
+ # Fix permissions
21
+ find "$pkgdir" -type d -exec chmod 755 {} +
22
+
23
+ # Install license
24
+ install -Dm644 "$pkgdir/usr/share/doc/brosh/copyright" \
25
+ "$pkgdir/usr/share/licenses/$pkgname/LICENSE" 2>/dev/null || true
26
+ }
Binary file
Binary file
package/website/CNAME ADDED
@@ -0,0 +1 @@
1
+ bro.sh
File without changes
File without changes