registry  /  @linsoai/browser-relay  /  1.2.0

@linsoai/browser-relay@1.2.0

Universal browser relay — control your Chrome from any AI agent via HTTP API or MCP. No auth, no cloud.

AI Security Review

scanned 2h ago · by lpm-firewall-ai

LPM treats this as warn-only first-party agent extension lifecycle risk. The package intentionally provides a browser automation relay. Risk is from a global-install autostart service plus unauthenticated localhost browser-control API, but this is package-aligned and not a confirmed malicious chain.

Static reason
High-risk behavior combination matched malicious policy.
Trigger
Global npm install starts postinstall; runtime use starts relay and installed Chrome extension connects.
Impact
Local processes, and remote callers with the explicit Device ID when enabled, can control attached browser tabs and evaluate JavaScript.
Mechanism
package-owned browser automation relay with user-service persistence
Rationale
Source inspection confirms high-risk browser-control and persistence capabilities, but they are explicit package functionality and no unconsented broad AI-agent control mutation, exfiltration, destructive action, or remote payload execution was found. Because global install autostarts a powerful no-auth relay, warn rather than block.
Evidence
package.jsonserver/install.jsserver/uninstall.jsserver/relay-server.jsserver/mcp-server.jsserver/remote-protocol.jsextension/manifest.jsonextension/background.jsextension/options.js~/Library/LaunchAgents/org.browser-relay.service.plist~/.config/systemd/user/browser-relay.service~/.browser-relay/remotes.json
Network endpoints4
127.0.0.1:18795ws://127.0.0.1:18795/extensionrelay.linso.aiwss://relay.linso.ai/v1/device/connect

Decision evidence

public snapshot
AI called this Suspicious at 86.0% confidence as Dangerous Capability with medium false-positive risk.
Evidence for warning
  • package.json runs postinstall server/install.js and postuninstall server/uninstall.js
  • server/install.js registers launchd/systemd user service on global install and starts relay
  • server/relay-server.js exposes unauthenticated localhost HTTP/WebSocket browser-control API including /api/eval
  • extension/manifest.json requests debugger/tabs/downloads permissions
  • extension/background.js supports opt-in remote control via https://relay.linso.ai with capability secret
Evidence against
  • server/install.js skips service registration for local installs
  • No install-time writes to foreign AI-agent config; it only checks stale skills and prints update advice
  • Remote relay requires extension option toggle and generated secret in extension/options.js
  • Network header capture redacts authorization/cookie/set-cookie in server/relay-server.js
  • No credential file harvesting, destructive actions, or remote payload download/execute found
Behavioral surface
Source
ChildProcessCryptoEnvironmentVarsFilesystemNetworkShellWebSocket
Supply chain
HighEntropyStringsUrlStrings
ManifestNo manifest risk signals triggered.
scanned 14 file(s), 230 KB of source, external domains: 127.0.0.1, deploy.workers.cloudflare.com, device.local, example.com, github.com, relay.linso.ai, relay.local, www.apple.com, www.npmjs.com

Source & flagged code

4 flagged · loading source
package.jsonView file
scripts.postinstall = node server/install.js
High
Install Time Lifecycle Scripts

Package defines install-time lifecycle scripts.

package.jsonView on unpkg
scripts.postinstall = node server/install.js
Medium
Ambiguous Install Lifecycle Script

Install-time lifecycle script is not statically allowlisted and needs review.

package.jsonView on unpkg
server/install.jsView file
1Install-time AI-agent control hijack evidence: L1: #!/usr/bin/env node L2: import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs"; L3: import { dirname, join } from "node:path"; ... L64: L65: mkdirSync(dirname(plistDst), { recursive: true }); L66: writeFileSync(plistDst, plistContent); L67: ... L100: L101: mkdirSync(dirname(serviceDst), { recursive: true }); L102: writeFileSync(serviceDst, serviceContent); L103: ... L123: const AGENT_SKILL_ROOTS = [ Payload evidence from skill/SKILL.md: L32: ``` L33: Relay URL: http://127.0.0.1:18795 L34: WebSocket: ws://127.0.0.1:18795/extension ... L118: Header: Content-Type: application/json L119: Body: { "url": "https://example.com", "tabId?": "optional-target-id" } L120: ``` ... L187: ### 8. browser_screenshot L188: Capture a PNG screenshot (base64). L189: ```
Critical
Ai Agent Control Hijack

Install-time source drops package-supplied AI-agent/MCP control files or instructions.

server/install.jsView on unpkg · L1
5import { homedir, platform } from "node:os"; L6: import { execSync } from "node:child_process"; L7: L8: const __dirname = dirname(fileURLToPath(import.meta.url)); L9: const RELAY_DIR = dirname(__dirname); ... L67: L68: // Use bootstrap/bootout — `launchctl load/unload` is the legacy API and L69: // often silently fails or returns EBADEXEC on macOS 13+. bootout first for ... L153: // a daemon hijacking their machine. L154: const isGlobal = process.env.npm[redacted] === "true"; L155: if (!isGlobal) { ... L182: try {
Medium
Install Persistence

Source writes installer persistence such as shell profile or service configuration.

server/install.jsView on unpkg · L5

Findings

1 Critical1 High5 Medium5 Low
CriticalAi Agent Control Hijackserver/install.js
HighInstall Time Lifecycle Scriptspackage.json
MediumAmbiguous Install Lifecycle Scriptpackage.json
MediumNetwork
MediumEnvironment Vars
MediumInstall Persistenceserver/install.js
MediumStructural Risk Force Deep Review
LowNon Install Lifecycle Scripts
LowScripts Present
LowFilesystem
LowHigh Entropy Strings
LowUrl Strings