Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 13 additions & 3 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,27 +21,37 @@ jobs:
- name: Install dependencies
run: bun install --frozen-lockfile

- name: Build Chrome extension
run: |
VERSION="${GITHUB_REF_NAME#v}"
bun run build:ext
# ZIP the extension dist (platform-independent)
cd packages/extension/dist
zip -r "../../../browseruse-extension-${VERSION}.zip" .
cd ../../..

- name: Compile cli.ts (arm64 native + x64 cross-compile)
run: |
VERSION="${GITHUB_REF_NAME#v}"

# arm64 (native)
bun build --compile src/cli.ts --outfile browseruse
bun build --compile packages/cli/src/cli.ts --outfile browseruse
tar czf "browseruse-${VERSION}-darwin-arm64.tar.gz" browseruse
rm browseruse

# x64 (cross-compile)
bun build --compile --target=bun-darwin-x64 src/cli.ts --outfile browseruse
bun build --compile --target=bun-darwin-x64 packages/cli/src/cli.ts --outfile browseruse
tar czf "browseruse-${VERSION}-darwin-x64.tar.gz" browseruse
rm browseruse

- name: Generate checksums
run: shasum -a 256 browseruse-*.tar.gz > checksums.txt
run: shasum -a 256 browseruse-*.tar.gz browseruse-extension-*.zip > checksums.txt

- name: Create GitHub Release
uses: softprops/action-gh-release@v2
with:
generate_release_notes: true
files: |
browseruse-*.tar.gz
browseruse-extension-*.zip
checksums.txt
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,4 @@ node_modules/
bun.lock
/tmp/browseruse.log
.DS_Store
packages/extension/dist/
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ src/
generated.ts Auto-generated CDP types (56 domains, 652 methods)
browser_protocol.json
js_protocol.json
interaction-skills/ CDP pattern recipes (screenshots, cookies, tabs, etc.)
interaction-skills/ CDP pattern recipes (screenshots, cookies, tabs, etc.)
SKILL.md Agent-facing documentation
```

Expand Down
22 changes: 16 additions & 6 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,19 +1,29 @@
{
"name": "browseruse",
"version": "0.3.0",
"version": "0.4.0",
"type": "module",
"private": true,
"workspaces": ["packages/*"],
"bin": {
"browseruse": "./src/cli.ts"
"browseruse": "./packages/cli/src/cli.ts"
},
"scripts": {
"gen": "bun src/gen.ts",
"repl": "bun src/repl.ts",
"start": "bun src/cli.ts --start",
"test": "bun test"
"gen": "bun packages/cli/src/gen.ts",
"repl": "bun packages/cli/src/repl.ts",
"start": "bun packages/cli/src/cli.ts --start",
"test": "bun test",
"build:ext": "bun packages/extension/build.ts",
"install:ext": "bun packages/extension/install.ts"
},
"dependencies": {
"@browseruse/cli": "workspace:*",
"@browseruse/protocol": "workspace:*",
"puppeteer-core": "^24.43.1"
},
"devDependencies": {
"@types/bun": "latest",
"@types/chrome": "^0.0.287",
"esbuild": "^0.24.0",
"typescript": "^5.5.0"
}
}
File renamed without changes.
12 changes: 12 additions & 0 deletions packages/cli/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"name": "@browseruse/cli",
"version": "0.4.0",
"type": "module",
"private": true,
"bin": {
"browseruse": "./src/cli.ts"
},
"dependencies": {
"@browseruse/protocol": "workspace:*"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ beforeAll(async () => {
port = randomPort();
baseUrl = `http://127.0.0.1:${port}`;

proc = Bun.spawn(['bun', 'src/repl.ts'], {
proc = Bun.spawn(['bun', 'packages/cli/src/repl.ts'], {
env: { ...process.env, BROWSERUSE_PORT: String(port) },
stdout: 'pipe',
stderr: 'pipe',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ beforeAll(async () => {
port = randomPort();
baseUrl = `http://127.0.0.1:${port}`;

proc = Bun.spawn(['bun', 'src/repl.ts'], {
proc = Bun.spawn(['bun', 'packages/cli/src/repl.ts'], {
env: { ...process.env, BROWSERUSE_PORT: String(port) },
stdout: 'pipe',
stderr: 'pipe',
Expand Down
File renamed without changes.
36 changes: 34 additions & 2 deletions src/browser.ts → packages/cli/src/browser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
*/

import { readFileSync, writeFileSync, unlinkSync, existsSync, mkdirSync } from 'fs';
import { join } from 'path';
import { join, dirname } from 'path';
import { homedir } from 'os';

// ---------------------------------------------------------------------------
Expand Down Expand Up @@ -49,6 +49,27 @@ const PROFILES_DIR = join(BROWSERUSE_DIR, 'profiles');
const PORT_FILE = join(BROWSERUSE_DIR, 'cdp-port');
const PID_FILE = join(BROWSERUSE_DIR, 'cdp-pid');

/**
* Resolve the Chrome extension directory. Checks in order:
* 1. Sarea app bundle: .app/Contents/Resources/browseruse-extension/
* 2. Development: packages/extension/dist/ (relative to source)
*/
function extensionDistDir(): string {
const execDir = dirname(process.execPath);

// Bundled in Sarea.app: .app/Contents/Resources/bin/browseruse
// Extension at: .app/Contents/Resources/browseruse-extension/
if (execDir.includes('.app/Contents/')) {
const resourcesDir = join(execDir, '..');
const bundled = join(resourcesDir, 'browseruse-extension');
if (existsSync(join(bundled, 'manifest.json'))) return bundled;
}

// Development: packages/cli/src/browser.ts → packages/extension/dist
const cliSrc = dirname(new URL(import.meta.url).pathname);
return join(cliSrc, '..', '..', 'extension', 'dist');
}

function profileDir(name: string): string {
return join(PROFILES_DIR, name);
}
Expand Down Expand Up @@ -152,7 +173,6 @@ const DEFAULT_FLAGS = [
'--disable-background-networking',
'--disable-client-side-phishing-detection',
'--disable-default-apps',
'--disable-extensions-except=',
'--disable-hang-monitor',
'--disable-popup-blocking',
'--disable-prompt-on-repost',
Expand Down Expand Up @@ -183,10 +203,22 @@ export async function launchBrowser(opts: LaunchOptions = {}): Promise<ManagedBr

const chromePath = findChromePath();

// Auto-load the browseruse extension as a fallback for profiles that don't
// have the Chrome Web Store version installed. For 'system' profiles the user's
// real Chrome likely has the store extension already, so we skip --load-extension
// to avoid loading a duplicate.
const extDir = extensionDistDir();
const hasExt = existsSync(join(extDir, 'manifest.json'));
const isSystem = profile === 'system' || opts.userDataDir === systemChromeProfileDir();
const extFlags = (hasExt && !isSystem)
? [`--load-extension=${extDir}`]
: [];

const args = [
`--remote-debugging-port=${port}`,
`--user-data-dir=${userDataDir}`,
...DEFAULT_FLAGS,
...extFlags,
];

if (opts.headless) {
Expand Down
File renamed without changes.
2 changes: 1 addition & 1 deletion src/cli.ts → packages/cli/src/cli.ts
Original file line number Diff line number Diff line change
Expand Up @@ -493,7 +493,7 @@ async function main(): Promise<void> {

// Fast-path: help / version (no server needed, no dynamic imports)
if (cmd === '--help' || cmd === '-h') { printUsage(); return; }
if (cmd === '--version' || cmd === '-v') { console.log('browseruse 0.3.0'); return; }
if (cmd === '--version' || cmd === '-v') { console.log('browseruse 0.4.0'); return; }

// Command registry lookup
const command = commandMap.get(cmd);
Expand Down
Loading