@rettangoli/vt 0.0.3 → 0.0.4
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/package.json +1 -1
- package/src/common.js +52 -79
package/package.json
CHANGED
package/src/common.js
CHANGED
|
@@ -16,12 +16,14 @@ import { codeToHtml } from "shiki";
|
|
|
16
16
|
import sharp from "sharp";
|
|
17
17
|
import path from "path";
|
|
18
18
|
|
|
19
|
+
const removeExtension = (filePath) => filePath.replace(/\.[^/.]+$/, "");
|
|
20
|
+
|
|
19
21
|
const convertToHtmlExtension = (filePath) => {
|
|
20
22
|
if (filePath.endsWith(".html")) {
|
|
21
23
|
return filePath;
|
|
22
24
|
}
|
|
23
25
|
// Remove existing extension and add .html
|
|
24
|
-
const baseName = filePath
|
|
26
|
+
const baseName = removeExtension(filePath);
|
|
25
27
|
return baseName + ".html";
|
|
26
28
|
};
|
|
27
29
|
|
|
@@ -50,7 +52,7 @@ engine.registerFilter("slug", (value) => {
|
|
|
50
52
|
// Add custom filter to remove file extension
|
|
51
53
|
engine.registerFilter("remove_ext", (value) => {
|
|
52
54
|
if (typeof value !== "string") return "";
|
|
53
|
-
return value
|
|
55
|
+
return removeExtension(value);
|
|
54
56
|
});
|
|
55
57
|
|
|
56
58
|
/**
|
|
@@ -136,10 +138,10 @@ async function generateHtml(specsDir, templatePath, outputDir, templateConfig) {
|
|
|
136
138
|
const relativePath = path.relative(specsDir, filePath);
|
|
137
139
|
|
|
138
140
|
let templateToUse = defaultTemplateContent;
|
|
139
|
-
const resolvedTemplatePath = frontMatterObj
|
|
141
|
+
const resolvedTemplatePath = frontMatterObj?.template ?
|
|
140
142
|
join(templateConfig.vtPath, "templates", frontMatterObj.template) :
|
|
141
143
|
templateConfig.defaultTemplate;
|
|
142
|
-
templateToUse = readFileSync(resolvedTemplatePath, "utf8");
|
|
144
|
+
templateToUse = readFileSync(resolvedTemplatePath, "utf8");
|
|
143
145
|
|
|
144
146
|
// Render template
|
|
145
147
|
const renderedContent = engine.parseAndRenderSync(templateToUse, {
|
|
@@ -214,7 +216,7 @@ function startWebServer(artifactsDir, staticDir, port) {
|
|
|
214
216
|
server.listen(port, () => {
|
|
215
217
|
console.log(`Server started at http://localhost:${port}`);
|
|
216
218
|
});
|
|
217
|
-
|
|
219
|
+
|
|
218
220
|
return server;
|
|
219
221
|
}
|
|
220
222
|
|
|
@@ -255,9 +257,23 @@ async function takeScreenshots(
|
|
|
255
257
|
console.log("Launching browser to take screenshots...");
|
|
256
258
|
const browser = await chromium.launch();
|
|
257
259
|
|
|
260
|
+
const takeAndSaveScreenshot = async (page, basePath, suffix = '') => {
|
|
261
|
+
const finalPath = suffix ? `${basePath}-${suffix}` : basePath;
|
|
262
|
+
const tempPngPath = join(screenshotsDir, `${finalPath}.png`);
|
|
263
|
+
const screenshotPath = join(screenshotsDir, `${finalPath}.webp`);
|
|
264
|
+
ensureDirectoryExists(dirname(screenshotPath));
|
|
265
|
+
|
|
266
|
+
await page.screenshot({ path: tempPngPath, fullPage: true, animations: "disabled" });
|
|
267
|
+
await sharp(tempPngPath).webp({ quality: 85 }).toFile(screenshotPath);
|
|
268
|
+
|
|
269
|
+
if (existsSync(tempPngPath)) {
|
|
270
|
+
unlinkSync(tempPngPath);
|
|
271
|
+
}
|
|
272
|
+
return screenshotPath;
|
|
273
|
+
};
|
|
274
|
+
|
|
258
275
|
try {
|
|
259
|
-
|
|
260
|
-
const files = [...generatedFiles]; // Create a copy to work with
|
|
276
|
+
const files = [...generatedFiles];
|
|
261
277
|
const total = files.length;
|
|
262
278
|
let completed = 0;
|
|
263
279
|
|
|
@@ -268,95 +284,52 @@ async function takeScreenshots(
|
|
|
268
284
|
// Create a new context and page for each file (for parallelism)
|
|
269
285
|
const context = await browser.newContext();
|
|
270
286
|
const page = await context.newPage();
|
|
287
|
+
let screenshotIndex = 0;
|
|
271
288
|
|
|
272
289
|
try {
|
|
273
290
|
// Construct URL from file path (add /candidate prefix since server serves from parent)
|
|
274
291
|
const fileUrl = convertToHtmlExtension(
|
|
275
292
|
`${serverUrl}/candidate/${file.path.replace(/\\/g, '/')}`
|
|
276
293
|
);
|
|
277
|
-
console.log(`
|
|
278
|
-
|
|
279
|
-
// Navigate to the page
|
|
294
|
+
console.log(`Navigating to ${fileUrl}`);
|
|
280
295
|
await page.goto(fileUrl, { waitUntil: "networkidle" });
|
|
281
|
-
|
|
282
|
-
// Create screenshot output path (remove extension and add .webp)
|
|
283
|
-
const baseName = file.path.replace(/\.[^/.]+$/, "");
|
|
284
|
-
const tempPngPath = join(screenshotsDir, `${baseName}.png`);
|
|
285
|
-
const screenshotPath = join(screenshotsDir, `${baseName}.webp`);
|
|
286
|
-
ensureDirectoryExists(dirname(screenshotPath));
|
|
287
|
-
|
|
288
296
|
if (waitTime > 0) {
|
|
289
|
-
await
|
|
297
|
+
await page.waitForTimeout(waitTime);
|
|
290
298
|
}
|
|
299
|
+
const baseName = removeExtension(file.path);
|
|
291
300
|
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
path: tempPngPath,
|
|
295
|
-
fullPage: true
|
|
296
|
-
});
|
|
301
|
+
const initialScreenshotPath = await takeAndSaveScreenshot(page, baseName);
|
|
302
|
+
console.log(`Initial screenshot saved: ${initialScreenshotPath}`);
|
|
297
303
|
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
.webp({ quality: 85 })
|
|
301
|
-
.toFile(screenshotPath);
|
|
302
|
-
|
|
303
|
-
// Remove temporary PNG file
|
|
304
|
-
if (existsSync(tempPngPath)) {
|
|
305
|
-
unlinkSync(tempPngPath);
|
|
306
|
-
}
|
|
307
|
-
|
|
308
|
-
// example instructions:
|
|
309
|
-
for (const instruction of file.frontMatter?.instructions || []) {
|
|
310
|
-
const [command, ...args] = instruction.split(" ");
|
|
304
|
+
for (const step of file.frontMatter?.steps || []) {
|
|
305
|
+
const [command, ...args] = step.split(" ");
|
|
311
306
|
switch (command) {
|
|
312
|
-
case "
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
307
|
+
case "move":
|
|
308
|
+
await page.mouse.move(Number(args[0]), Number(args[1]));
|
|
309
|
+
break;
|
|
310
|
+
case "click":
|
|
311
|
+
await page.mouse.click(Number(args[0]), Number(args[1]), { button: "left" });
|
|
312
|
+
break;
|
|
313
|
+
case "rclick":
|
|
314
|
+
await page.mouse.click(Number(args[0]), Number(args[1]), { button: "right" });
|
|
318
315
|
break;
|
|
319
|
-
case "
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
);
|
|
329
|
-
console.log(`Taking additional screenshot at ${additonalScreenshotPath}`);
|
|
330
|
-
|
|
331
|
-
// Take screenshot as PNG first
|
|
332
|
-
await page.screenshot({
|
|
333
|
-
path: tempAdditionalPngPath,
|
|
334
|
-
fullPage: true
|
|
335
|
-
});
|
|
336
|
-
|
|
337
|
-
// Convert PNG to WebP using Sharp
|
|
338
|
-
await sharp(tempAdditionalPngPath)
|
|
339
|
-
.webp({ quality: 85 })
|
|
340
|
-
.toFile(additonalScreenshotPath);
|
|
341
|
-
|
|
342
|
-
// Remove temporary PNG file
|
|
343
|
-
if (existsSync(tempAdditionalPngPath)) {
|
|
344
|
-
unlinkSync(tempAdditionalPngPath);
|
|
345
|
-
}
|
|
346
|
-
|
|
347
|
-
console.log(
|
|
348
|
-
`Additional screenshot taken at ${additonalScreenshotPath}`
|
|
349
|
-
);
|
|
316
|
+
case "keypress":
|
|
317
|
+
await page.keyboard.press(args[0]);
|
|
318
|
+
break;
|
|
319
|
+
case "wait":
|
|
320
|
+
await page.waitForTimeout(Number(args[0]));
|
|
321
|
+
break;
|
|
322
|
+
case "screenshot":
|
|
323
|
+
screenshotIndex++;
|
|
324
|
+
const screenshotPath = await takeAndSaveScreenshot(page, `${baseName}-${screenshotIndex}`);
|
|
325
|
+
console.log(`Screenshot saved: ${screenshotPath}`);
|
|
350
326
|
break;
|
|
351
327
|
}
|
|
352
328
|
}
|
|
353
|
-
|
|
354
329
|
completed++;
|
|
355
|
-
console.log(
|
|
356
|
-
`Screenshot saved: ${screenshotPath} (${completed}/${total})`
|
|
357
|
-
);
|
|
330
|
+
console.log(`Finished processing ${file.path} (${completed}/${total})`);
|
|
358
331
|
} catch (error) {
|
|
359
|
-
console.error(`Error
|
|
332
|
+
console.error(`Error processing instructions for ${file.path}:`, error);
|
|
360
333
|
} finally {
|
|
361
334
|
// Close the context when done
|
|
362
335
|
await context.close();
|
|
@@ -467,4 +440,4 @@ export {
|
|
|
467
440
|
takeScreenshots,
|
|
468
441
|
generateOverview,
|
|
469
442
|
readYaml,
|
|
470
|
-
};
|
|
443
|
+
};
|