@meltemi/diagrams-capture 1.9.0 → 1.10.0

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.
package/dist/capture.mjs CHANGED
@@ -96,7 +96,7 @@ export async function capture(jobs, options = {}) {
96
96
  if (!executable) throw new Error(NO_BROWSER);
97
97
  const session = await PipeSession.launch(executable, { timeout: options.timeout ?? 30_000 });
98
98
  try {
99
- const { product } = await session.send("Browser.getVersion");
99
+ const { product } = await session.started();
100
100
  const results = [];
101
101
  for (const job of jobs) results.push(await captureOne(session, job));
102
102
  return { browser: product, results };
package/dist/cdp.d.mts CHANGED
@@ -1,14 +1,20 @@
1
1
  /** Arguments of the headless browser. */
2
2
  export function browserArgs(profile: string): string[];
3
3
 
4
+ /** How long a starting browser may take to answer its first call (see `started`). */
5
+ export const STARTUP_TIMEOUT: number;
6
+
4
7
  /** A DevTools protocol session with a browser over a pipe. */
5
8
  export class PipeSession {
6
9
  static launch(executable: string, options?: { timeout?: number }): Promise<PipeSession>;
10
+ /** The browser's version once it has started, with the longer startup timeout. */
11
+ started(): Promise<Record<string, unknown>>;
7
12
  // Replies and events are plain JSON objects shaped by the DevTools protocol.
8
13
  send(
9
14
  method: string,
10
15
  params?: Record<string, unknown>,
11
16
  sessionId?: string,
17
+ timeout?: number,
12
18
  ): Promise<Record<string, unknown>>;
13
19
  waitFor(method: string, sessionId?: string): Promise<Record<string, unknown>>;
14
20
  close(): Promise<void>;
package/dist/cdp.mjs CHANGED
@@ -53,6 +53,9 @@ export function browserArgs(profile) {
53
53
  ];
54
54
  }
55
55
 
56
+ /** How long a starting browser may take to answer its first call (see `started`). */
57
+ export const STARTUP_TIMEOUT = 120_000;
58
+
56
59
  export class PipeSession {
57
60
  /** Starts the browser. */
58
61
  static async launch(executable, { timeout = 30_000 } = {}) {
@@ -120,16 +123,25 @@ export class PipeSession {
120
123
  }
121
124
  }
122
125
 
123
- /** Sends a command and waits for its result. */
124
- send(method, params = {}, sessionId) {
126
+ /**
127
+ * Waits for the browser to have started: its version, once it answers. A first start builds the
128
+ * browser's caches (fonts, profile), which on a fresh or busy machine takes far longer than any
129
+ * later call, so it may take up to `STARTUP_TIMEOUT` (or the session's timeout, if longer).
130
+ */
131
+ started() {
132
+ return this.send("Browser.getVersion", {}, undefined, Math.max(this.timeout, STARTUP_TIMEOUT));
133
+ }
134
+
135
+ /** Sends a command and waits for its result, for `timeout` ms (the session's by default). */
136
+ send(method, params = {}, sessionId, timeout = this.timeout) {
125
137
  if (this.closed) return Promise.reject(new Error("The browser is closed."));
126
138
  const id = this.nextId++;
127
139
  const message = { id, method, params, ...(sessionId ? { sessionId } : {}) };
128
140
  return new Promise((resolve, reject) => {
129
141
  const timer = setTimeout(() => {
130
142
  this.pending.delete(id);
131
- reject(new Error(`The browser did not answer ${method} within ${this.timeout} ms.`));
132
- }, this.timeout);
143
+ reject(new Error(`The browser did not answer ${method} within ${timeout} ms.`));
144
+ }, timeout);
133
145
  this.pending.set(id, { resolve, reject, timer });
134
146
  this.child.stdio[3].write(`${JSON.stringify(message)}\0`);
135
147
  });
package/dist/video.mjs CHANGED
@@ -148,7 +148,7 @@ export async function captureVideo(job, options = {}) {
148
148
  });
149
149
  const session = await PipeSession.launch(browser, { timeout: options.timeout ?? 30_000 });
150
150
  try {
151
- const { product } = await session.send("Browser.getVersion");
151
+ const { product } = await session.started();
152
152
  const { targetId } = await session.send("Target.createTarget", { url: "about:blank" });
153
153
  const { sessionId } = await session.send("Target.attachToTarget", { targetId, flatten: true });
154
154
  await session.send("Page.enable", {}, sessionId);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@meltemi/diagrams-capture",
3
- "version": "1.9.0",
3
+ "version": "1.10.0",
4
4
  "description": "PNG, PDF and video captures of rendered SVG with the installed Edge, Chrome or Chromium over the DevTools protocol, and video encoding with the installed FFmpeg.",
5
5
  "license": "MIT",
6
6
  "repository": {