puppeteer-core
Version:
A high-level API to control headless Chrome over the DevTools Protocol
254 lines • 11.9 kB
JavaScript
"use strict";
/**
* @license
* Copyright 2022 Google Inc.
* SPDX-License-Identifier: Apache-2.0
*/
var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
var _, done = false;
for (var i = decorators.length - 1; i >= 0; i--) {
var context = {};
for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
for (var p in contextIn.access) context.access[p] = contextIn.access[p];
context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
if (kind === "accessor") {
if (result === void 0) continue;
if (result === null || typeof result !== "object") throw new TypeError("Object expected");
if (_ = accept(result.get)) descriptor.get = _;
if (_ = accept(result.set)) descriptor.set = _;
if (_ = accept(result.init)) initializers.unshift(_);
}
else if (_ = accept(result)) {
if (kind === "field") initializers.unshift(_);
else descriptor[key] = _;
}
}
if (target) Object.defineProperty(target, contextIn.name, descriptor);
done = true;
};
var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
var useValue = arguments.length > 2;
for (var i = 0; i < initializers.length; i++) {
value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
}
return useValue ? value : void 0;
};
var __setFunctionName = (this && this.__setFunctionName) || function (f, name, prefix) {
if (typeof name === "symbol") name = name.description ? "[".concat(name.description, "]") : "";
return Object.defineProperty(f, "name", { configurable: true, value: prefix ? "".concat(prefix, " ", name) : name });
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.BidiBrowser = void 0;
const Browser_js_1 = require("../api/Browser.js");
const EventEmitter_js_1 = require("../common/EventEmitter.js");
const util_js_1 = require("../common/util.js");
const decorators_js_1 = require("../util/decorators.js");
const BrowserContext_js_1 = require("./BrowserContext.js");
const Session_js_1 = require("./core/Session.js");
const Target_js_1 = require("./Target.js");
/**
* @internal
*/
let BidiBrowser = (() => {
let _classSuper = Browser_js_1.Browser;
let _private_trustedEmitter_decorators;
let _private_trustedEmitter_initializers = [];
let _private_trustedEmitter_extraInitializers = [];
let _private_trustedEmitter_descriptor;
return class BidiBrowser extends _classSuper {
static {
const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
_private_trustedEmitter_decorators = [(0, decorators_js_1.bubble)()];
__esDecorate(this, _private_trustedEmitter_descriptor = { get: __setFunctionName(function () { return this.#trustedEmitter_accessor_storage; }, "#trustedEmitter", "get"), set: __setFunctionName(function (value) { this.#trustedEmitter_accessor_storage = value; }, "#trustedEmitter", "set") }, _private_trustedEmitter_decorators, { kind: "accessor", name: "#trustedEmitter", static: false, private: true, access: { has: obj => #trustedEmitter in obj, get: obj => obj.#trustedEmitter, set: (obj, value) => { obj.#trustedEmitter = value; } }, metadata: _metadata }, _private_trustedEmitter_initializers, _private_trustedEmitter_extraInitializers);
if (_metadata) Object.defineProperty(this, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
}
protocol = 'webDriverBiDi';
static subscribeModules = [
'browsingContext',
'network',
'log',
'script',
];
static subscribeCdpEvents = [
// Coverage
'goog:cdp.Debugger.scriptParsed',
'goog:cdp.CSS.styleSheetAdded',
'goog:cdp.Runtime.executionContextsCleared',
// Tracing
'goog:cdp.Tracing.tracingComplete',
// TODO: subscribe to all CDP events in the future.
'goog:cdp.Network.requestWillBeSent',
'goog:cdp.Debugger.scriptParsed',
'goog:cdp.Page.screencastFrame',
];
static async create(opts) {
const session = await Session_js_1.Session.from(opts.connection, {
firstMatch: opts.capabilities?.firstMatch,
alwaysMatch: {
...opts.capabilities?.alwaysMatch,
// Capabilities that come from Puppeteer's API take precedence.
acceptInsecureCerts: opts.acceptInsecureCerts,
unhandledPromptBehavior: {
default: "ignore" /* Bidi.Session.UserPromptHandlerType.Ignore */,
},
webSocketUrl: true,
// Puppeteer with WebDriver BiDi does not support prerendering
// yet because WebDriver BiDi behavior is not specified. See
// https://github.com/w3c/webdriver-bidi/issues/321.
'goog:prerenderingDisabled': true,
},
});
await session.subscribe(session.capabilities.browserName.toLocaleLowerCase().includes('firefox')
? BidiBrowser.subscribeModules
: [...BidiBrowser.subscribeModules, ...BidiBrowser.subscribeCdpEvents]);
const browser = new BidiBrowser(session.browser, opts);
browser.#initialize();
return browser;
}
#trustedEmitter_accessor_storage = __runInitializers(this, _private_trustedEmitter_initializers, new EventEmitter_js_1.EventEmitter());
get #trustedEmitter() { return _private_trustedEmitter_descriptor.get.call(this); }
set #trustedEmitter(value) { return _private_trustedEmitter_descriptor.set.call(this, value); }
#process = __runInitializers(this, _private_trustedEmitter_extraInitializers);
#closeCallback;
#browserCore;
#defaultViewport;
#browserContexts = new WeakMap();
#target = new Target_js_1.BidiBrowserTarget(this);
#cdpConnection;
constructor(browserCore, opts) {
super();
this.#process = opts.process;
this.#closeCallback = opts.closeCallback;
this.#browserCore = browserCore;
this.#defaultViewport = opts.defaultViewport;
this.#cdpConnection = opts.cdpConnection;
}
#initialize() {
// Initializing existing contexts.
for (const userContext of this.#browserCore.userContexts) {
this.#createBrowserContext(userContext);
}
this.#browserCore.once('disconnected', () => {
this.#trustedEmitter.emit("disconnected" /* BrowserEvent.Disconnected */, undefined);
this.#trustedEmitter.removeAllListeners();
});
this.#process?.once('close', () => {
this.#browserCore.dispose('Browser process exited.', true);
this.connection.dispose();
});
}
get #browserName() {
return this.#browserCore.session.capabilities.browserName;
}
get #browserVersion() {
return this.#browserCore.session.capabilities.browserVersion;
}
get cdpSupported() {
return this.#cdpConnection !== undefined;
}
get cdpConnection() {
return this.#cdpConnection;
}
async userAgent() {
return this.#browserCore.session.capabilities.userAgent;
}
#createBrowserContext(userContext) {
const browserContext = BrowserContext_js_1.BidiBrowserContext.from(this, userContext, {
defaultViewport: this.#defaultViewport,
});
this.#browserContexts.set(userContext, browserContext);
browserContext.trustedEmitter.on("targetcreated" /* BrowserContextEvent.TargetCreated */, target => {
this.#trustedEmitter.emit("targetcreated" /* BrowserEvent.TargetCreated */, target);
});
browserContext.trustedEmitter.on("targetchanged" /* BrowserContextEvent.TargetChanged */, target => {
this.#trustedEmitter.emit("targetchanged" /* BrowserEvent.TargetChanged */, target);
});
browserContext.trustedEmitter.on("targetdestroyed" /* BrowserContextEvent.TargetDestroyed */, target => {
this.#trustedEmitter.emit("targetdestroyed" /* BrowserEvent.TargetDestroyed */, target);
});
return browserContext;
}
get connection() {
// SAFETY: We only have one implementation.
return this.#browserCore.session.connection;
}
wsEndpoint() {
return this.connection.url;
}
async close() {
if (this.connection.closed) {
return;
}
try {
await this.#browserCore.close();
await this.#closeCallback?.call(null);
}
catch (error) {
// Fail silently.
(0, util_js_1.debugError)(error);
}
finally {
this.connection.dispose();
}
}
get connected() {
return !this.#browserCore.disconnected;
}
process() {
return this.#process ?? null;
}
async createBrowserContext(_options) {
const userContext = await this.#browserCore.createUserContext();
return this.#createBrowserContext(userContext);
}
async version() {
return `${this.#browserName}/${this.#browserVersion}`;
}
browserContexts() {
return [...this.#browserCore.userContexts].map(context => {
return this.#browserContexts.get(context);
});
}
defaultBrowserContext() {
return this.#browserContexts.get(this.#browserCore.defaultUserContext);
}
newPage() {
return this.defaultBrowserContext().newPage();
}
targets() {
return [
this.#target,
...this.browserContexts().flatMap(context => {
return context.targets();
}),
];
}
target() {
return this.#target;
}
async disconnect() {
try {
await this.#browserCore.session.end();
}
catch (error) {
// Fail silently.
(0, util_js_1.debugError)(error);
}
finally {
this.connection.dispose();
}
}
get debugInfo() {
return {
pendingProtocolErrors: this.connection.getPendingProtocolErrors(),
};
}
};
})();
exports.BidiBrowser = BidiBrowser;
//# sourceMappingURL=Browser.js.map