mirror of
https://github.com/microsoft/playwright-mcp.git
synced 2025-07-27 09:02:26 +08:00
chore: merge browser and channel settings (#100)
This commit is contained in:
parent
9042c03faa
commit
4f16786432
18
README.md
18
README.md
@ -59,9 +59,25 @@ code-insiders --add-mcp '{"name":"playwright","command":"npx","args":["@playwrig
|
|||||||
|
|
||||||
After installation, the Playwright MCP server will be available for use with your GitHub Copilot agent in VS Code.
|
After installation, the Playwright MCP server will be available for use with your GitHub Copilot agent in VS Code.
|
||||||
|
|
||||||
|
### CLI Options
|
||||||
|
|
||||||
|
The Playwright MCP server supports the following command-line options:
|
||||||
|
|
||||||
|
- `--browser <browser>`: Browser or chrome channel to use. Possible values:
|
||||||
|
- `chrome`, `firefox`, `webkit`, `msedge`
|
||||||
|
- Chrome channels: `chrome-beta`, `chrome-canary`, `chrome-dev`
|
||||||
|
- Edge channels: `msedge-beta`, `msedge-canary`, `msedge-dev`
|
||||||
|
- Default: `chrome`
|
||||||
|
- `--cdp-endpoint <endpoint>`: CDP endpoint to connect to
|
||||||
|
- `--executable-path <path>`: Path to the browser executable
|
||||||
|
- `--headless`: Run browser in headless mode (headed by default)
|
||||||
|
- `--port <port>`: Port to listen on for SSE transport
|
||||||
|
- `--user-data-dir <path>`: Path to the user data directory
|
||||||
|
- `--vision`: Run server that uses screenshots (Aria snapshots are used by default)
|
||||||
|
|
||||||
### User data directory
|
### User data directory
|
||||||
|
|
||||||
Playwright MCP will launch Chrome browser with the new profile, located at
|
Playwright MCP will launch the browser with the new profile, located at
|
||||||
|
|
||||||
```
|
```
|
||||||
- `%USERPROFILE%\AppData\Local\ms-playwright\mcp-chrome-profile` on Windows
|
- `%USERPROFILE%\AppData\Local\ms-playwright\mcp-chrome-profile` on Windows
|
||||||
|
@ -20,6 +20,7 @@ import path from 'path';
|
|||||||
import * as playwright from 'playwright';
|
import * as playwright from 'playwright';
|
||||||
|
|
||||||
export type ContextOptions = {
|
export type ContextOptions = {
|
||||||
|
browserName?: 'chromium' | 'firefox' | 'webkit';
|
||||||
userDataDir: string;
|
userDataDir: string;
|
||||||
launchOptions?: playwright.LaunchOptions;
|
launchOptions?: playwright.LaunchOptions;
|
||||||
cdpEndpoint?: string;
|
cdpEndpoint?: string;
|
||||||
@ -73,7 +74,7 @@ export class Context {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async install(): Promise<string> {
|
async install(): Promise<string> {
|
||||||
const channel = this._options.launchOptions?.channel || 'chrome';
|
const channel = this._options.launchOptions?.channel ?? this._options.browserName ?? 'chrome';
|
||||||
const cli = path.join(require.resolve('playwright/package.json'), '..', 'cli.js');
|
const cli = path.join(require.resolve('playwright/package.json'), '..', 'cli.js');
|
||||||
const child = fork(cli, ['install', channel], {
|
const child = fork(cli, ['install', channel], {
|
||||||
stdio: 'pipe',
|
stdio: 'pipe',
|
||||||
@ -125,9 +126,11 @@ export class Context {
|
|||||||
private async _createPage(): Promise<{ browser?: playwright.Browser, page: playwright.Page }> {
|
private async _createPage(): Promise<{ browser?: playwright.Browser, page: playwright.Page }> {
|
||||||
if (this._options.remoteEndpoint) {
|
if (this._options.remoteEndpoint) {
|
||||||
const url = new URL(this._options.remoteEndpoint);
|
const url = new URL(this._options.remoteEndpoint);
|
||||||
|
if (this._options.browserName)
|
||||||
|
url.searchParams.set('browser', this._options.browserName);
|
||||||
if (this._options.launchOptions)
|
if (this._options.launchOptions)
|
||||||
url.searchParams.set('launch-options', JSON.stringify(this._options.launchOptions));
|
url.searchParams.set('launch-options', JSON.stringify(this._options.launchOptions));
|
||||||
const browser = await playwright.chromium.connect(String(url));
|
const browser = await playwright[this._options.browserName ?? 'chromium'].connect(String(url));
|
||||||
const page = await browser.newPage();
|
const page = await browser.newPage();
|
||||||
return { browser, page };
|
return { browser, page };
|
||||||
}
|
}
|
||||||
@ -148,7 +151,8 @@ export class Context {
|
|||||||
|
|
||||||
private async _launchPersistentContext(): Promise<playwright.BrowserContext> {
|
private async _launchPersistentContext(): Promise<playwright.BrowserContext> {
|
||||||
try {
|
try {
|
||||||
return await playwright.chromium.launchPersistentContext(this._options.userDataDir, this._options.launchOptions);
|
const browserType = this._options.browserName ? playwright[this._options.browserName] : playwright.chromium;
|
||||||
|
return await browserType.launchPersistentContext(this._options.userDataDir, this._options.launchOptions);
|
||||||
} catch (error: any) {
|
} catch (error: any) {
|
||||||
if (error.message.includes('Executable doesn\'t exist'))
|
if (error.message.includes('Executable doesn\'t exist'))
|
||||||
throw new Error(`Browser specified in your config is not installed. Either install it (likely) or change the config.`);
|
throw new Error(`Browser specified in your config is not installed. Either install it (likely) or change the config.`);
|
||||||
|
@ -65,6 +65,7 @@ const resources: Resource[] = [
|
|||||||
];
|
];
|
||||||
|
|
||||||
type Options = {
|
type Options = {
|
||||||
|
browserName?: 'chromium' | 'firefox' | 'webkit';
|
||||||
userDataDir?: string;
|
userDataDir?: string;
|
||||||
launchOptions?: LaunchOptions;
|
launchOptions?: LaunchOptions;
|
||||||
cdpEndpoint?: string;
|
cdpEndpoint?: string;
|
||||||
@ -80,6 +81,7 @@ export function createServer(options?: Options): Server {
|
|||||||
version: packageJSON.version,
|
version: packageJSON.version,
|
||||||
tools,
|
tools,
|
||||||
resources,
|
resources,
|
||||||
|
browserName: options?.browserName,
|
||||||
userDataDir: options?.userDataDir ?? '',
|
userDataDir: options?.userDataDir ?? '',
|
||||||
launchOptions: options?.launchOptions,
|
launchOptions: options?.launchOptions,
|
||||||
cdpEndpoint: options?.cdpEndpoint,
|
cdpEndpoint: options?.cdpEndpoint,
|
||||||
|
@ -35,21 +35,52 @@ const packageJSON = require('../package.json');
|
|||||||
program
|
program
|
||||||
.version('Version ' + packageJSON.version)
|
.version('Version ' + packageJSON.version)
|
||||||
.name(packageJSON.name)
|
.name(packageJSON.name)
|
||||||
|
.option('--browser <browser>', 'Browser or chrome channel to use, possible values: chrome, firefox, webkit, msedge.')
|
||||||
|
.option('--cdp-endpoint <endpoint>', 'CDP endpoint to connect to.')
|
||||||
|
.option('--executable-path <path>', 'Path to the browser executable.')
|
||||||
.option('--headless', 'Run browser in headless mode, headed by default')
|
.option('--headless', 'Run browser in headless mode, headed by default')
|
||||||
|
.option('--port <port>', 'Port to listen on for SSE transport.')
|
||||||
.option('--user-data-dir <path>', 'Path to the user data directory')
|
.option('--user-data-dir <path>', 'Path to the user data directory')
|
||||||
.option('--vision', 'Run server that uses screenshots (Aria snapshots are used by default)')
|
.option('--vision', 'Run server that uses screenshots (Aria snapshots are used by default)')
|
||||||
.option('--port <port>', 'Port to listen on for SSE transport.')
|
|
||||||
.option('--cdp-endpoint <endpoint>', 'CDP endpoint to connect to.')
|
|
||||||
.option('--channel <channel>', 'Channel to use for browser, possible values: chrome, msedge, chromium. Default: chrome')
|
|
||||||
.option('--executable-path <path>', 'Path to the browser executable.')
|
|
||||||
.action(async options => {
|
.action(async options => {
|
||||||
|
let browserName: 'chromium' | 'firefox' | 'webkit';
|
||||||
|
let channel: string | undefined;
|
||||||
|
switch (options.browser) {
|
||||||
|
case 'chrome':
|
||||||
|
case 'chrome-beta':
|
||||||
|
case 'chrome-canary':
|
||||||
|
case 'chrome-dev':
|
||||||
|
case 'msedge':
|
||||||
|
case 'msedge-beta':
|
||||||
|
case 'msedge-canary':
|
||||||
|
case 'msedge-dev':
|
||||||
|
browserName = 'chromium';
|
||||||
|
channel = options.browser;
|
||||||
|
break;
|
||||||
|
case 'chromium':
|
||||||
|
browserName = 'chromium';
|
||||||
|
break;
|
||||||
|
case 'firefox':
|
||||||
|
browserName = 'firefox';
|
||||||
|
break;
|
||||||
|
case 'webkit':
|
||||||
|
browserName = 'webkit';
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
browserName = 'chromium';
|
||||||
|
channel = 'chrome';
|
||||||
|
}
|
||||||
|
|
||||||
const launchOptions: LaunchOptions = {
|
const launchOptions: LaunchOptions = {
|
||||||
headless: !!options.headless,
|
headless: !!options.headless,
|
||||||
channel: options.channel ?? 'chrome',
|
channel,
|
||||||
executablePath: options.executablePath,
|
executablePath: options.executablePath,
|
||||||
};
|
};
|
||||||
const userDataDir = options.userDataDir ?? await createUserDataDir();
|
|
||||||
|
const userDataDir = options.userDataDir ?? await createUserDataDir(browserName);
|
||||||
|
|
||||||
const serverList = new ServerList(() => createServer({
|
const serverList = new ServerList(() => createServer({
|
||||||
|
browserName,
|
||||||
userDataDir,
|
userDataDir,
|
||||||
launchOptions,
|
launchOptions,
|
||||||
vision: !!options.vision,
|
vision: !!options.vision,
|
||||||
@ -75,7 +106,7 @@ function setupExitWatchdog(serverList: ServerList) {
|
|||||||
|
|
||||||
program.parse(process.argv);
|
program.parse(process.argv);
|
||||||
|
|
||||||
async function createUserDataDir() {
|
async function createUserDataDir(browserName: 'chromium' | 'firefox' | 'webkit') {
|
||||||
let cacheDirectory: string;
|
let cacheDirectory: string;
|
||||||
if (process.platform === 'linux')
|
if (process.platform === 'linux')
|
||||||
cacheDirectory = process.env.XDG_CACHE_HOME || path.join(os.homedir(), '.cache');
|
cacheDirectory = process.env.XDG_CACHE_HOME || path.join(os.homedir(), '.cache');
|
||||||
@ -85,7 +116,7 @@ async function createUserDataDir() {
|
|||||||
cacheDirectory = process.env.LOCALAPPDATA || path.join(os.homedir(), 'AppData', 'Local');
|
cacheDirectory = process.env.LOCALAPPDATA || path.join(os.homedir(), 'AppData', 'Local');
|
||||||
else
|
else
|
||||||
throw new Error('Unsupported platform: ' + process.platform);
|
throw new Error('Unsupported platform: ' + process.platform);
|
||||||
const result = path.join(cacheDirectory, 'ms-playwright', 'mcp-chrome-profile');
|
const result = path.join(cacheDirectory, 'ms-playwright', `mcp-${browserName}-profile`);
|
||||||
await fs.promises.mkdir(result, { recursive: true });
|
await fs.promises.mkdir(result, { recursive: true });
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user