diff --git a/CHANGELOG.md b/CHANGELOG.md
index 1853951..6a2aba2 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -4,12 +4,31 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
-## [1.1.1] - 2024-11-24
+
+## [1.2.0] - 2024-11-26
+
+### Added
+- **浏览器特征伪装**
+ - 在 Windows10 官方 Chrome 环境下已通过 [antibot](https://bot.sannysoft.com/) 和 [CreepJS](https://abrahamjuliot.github.io/creepjs/) 测试(无红色警示)(但在Linux下未完全通过,需要用户配合,详情和进一步伪装请查看文档常见问题部分)
+ - 引入 `ghost-cursor` 优化鼠标移动轨迹伪装,不再重复造轮子
+
+### Changed
+- **指定模型**
+ - 更改模型UUID的拦截器不再使用注入Fetch脚本和Puppeteer Interception,改用CDP拦截器,减少特征
+
+- **浏览器特征伪装**
+ - 优化浏览器启动参数,减少特征
+ - 优化窗口大小计算方式
+
+---
+
+## [1.1.1] - 2024-11-25
### Fixed
- **指定模型**
- 修复因错误的UUID映射导致的 gemini-3-pro-image-preview 模型触发HTTP500的 BUG
+---
## [1.1.0] - 2024-11-24
diff --git a/README.md b/README.md
index ec0cbd1..9ab929b 100644
--- a/README.md
+++ b/README.md
@@ -10,12 +10,13 @@ LMArenaImagenAutomator 是一个基于 Puppeteer 的自动化图像生成工具
### ✨ 主要特性
-- 🎭 **拟人化操作**:使用贝塞尔曲线模拟真实鼠标移动轨迹
+- 💁♂️ **拟人操作**:模拟真实鼠标移动轨迹和抖动
- 🤖 **智能输入**:模拟人类打字速度和错误纠正行为
- 🖼️ **多图支持**:最多支持同时上传 5 张参考图片
- 🔐 **安全认证**:基于 Bearer Token 的 API 鉴权
- 📊 **队列管理**:智能任务队列,防止请求过载
- 🌐 **代理支持**:支持 HTTP 和 SOCKS5 代理配置
+- 🎭 **特征伪装**:尽量伪装成真实浏览器的特征(详情参考文档结尾)
---
@@ -25,7 +26,7 @@ LMArenaImagenAutomator 是一个基于 Puppeteer 的自动化图像生成工具
- **Node.js**: 16.0 或更高版本
- **操作系统**: Windows、Linux 或 macOS
-- **浏览器**: Google Chrome 或 Chromium (可选,Puppeteer 会自动下载)
+- **浏览器**: Google Chrome 或 Chromium (Puppeteer 会自动下载,但是**更推荐**使用Google Chrome)
### 安装步骤
@@ -443,7 +444,7 @@ chrome:
-🐧 Linux 环境下非无头模式运行
+🐧 【Linux 环境下非无头模式运行】
**问题**: 需要在 Linux 服务器上显示浏览器界面(如手动过验证码)
@@ -475,6 +476,60 @@ chrome:
+
+🎭 【浏览器特征伪装】
+
+**问题**: 如何优化浏览器特征伪装,减少验证码弹出频率?
+
+**当前状态**:
+- ✅ **Windows 10 官方 Chrome**: 已通过 [antibot](https://bot.sannysoft.com/) 和 [CreepJS](https://abrahamjuliot.github.io/creepjs/) 测试(无红色警示)
+- ⚠️ **Linux 环境**: 未完全通过 CreepJS 测试,但基本不影响使用
+
+**进一步优化建议**:
+
+> [!TIP]
+> 完成后,可有效缓解验证码的弹出频率。
+
+**1. 使用官方 Chrome(推荐)**
+
+不推荐使用 Chromium,因为它缺少 MP4/H.264 解码器等插件,且被大量爬虫使用,会成为明显特征。
+
+**Linux 安装官方 Chrome**:
+```bash
+# 从 Google 官方下载 Chrome deb 安装包
+# 大陆服务器可手动下载deb安装包 https://www.google.com/chrome/?platform=linux
+wget https://dl.google.com/linux/direct/google-chrome-stable_current_amd64.deb
+sudo dpkg -i google-chrome-stable_current_amd64.deb
+sudo apt-get install -f # 修复可能的依赖问题
+```
+
+**配置方式**:
+
+修改 `config.yaml`,可使用`which google-chrome`指令查询路径
+```yaml
+chrome:
+ path: "/usr/bin/google-chrome"
+```
+
+使用环境变量可跳过 Puppeteer 自动下载 Chromium
+```bash
+export PUPPETEER_SKIP_CHROMIUM_DOWNLOAD="true"
+```
+
+**2. 优化字体指纹**
+
+Linux 服务器通常只安装了极少量字体(甚至没有中文),这会增加指纹特征。
+
+**安装常用字体**:
+```bash
+# 安装中文字体(必备,否则中文提示词将显示方框)
+sudo apt install fonts-wqy-zenhei fonts-wqy-microhei
+
+# 安装微软核心字体(减少字体指纹差异)
+sudo apt install ttf-mscorefonts-installer
+```
+
+
---
diff --git a/lib/lmarena.js b/lib/lmarena.js
index ca87ef8..1083f43 100644
--- a/lib/lmarena.js
+++ b/lib/lmarena.js
@@ -1,14 +1,17 @@
-import puppeteer from 'puppeteer';
+import puppeteer from 'puppeteer-extra';
+import StealthPlugin from 'puppeteer-extra-plugin-stealth';
+import { createCursor } from 'ghost-cursor';
import fs from 'fs';
import path from 'path';
-import { fileURLToPath } from 'url';
import { anonymizeProxy, closeAnonymizedProxy } from 'proxy-chain';
-const __filename = fileURLToPath(import.meta.url);
-const __dirname = path.dirname(__filename);
+
+const stealth = StealthPlugin();
+stealth.enabledEvasions.delete('user-agent-override');
+stealth.enabledEvasions.delete('iframe.contentWindow');
+puppeteer.use(stealth);
// --- 配置常量 ---
-const CHROME_PATH = 'C:\\Program Files\\Google\\Chrome\\Application\\chrome.exe';
const USER_DATA_DIR = path.join(process.cwd(), 'data', 'chromeUserData');
const TARGET_URL = 'https://lmarena.ai/c/new?mode=direct&chat-modality=image';
const TEMP_DIR = path.join(process.cwd(), 'data', 'temp');
@@ -46,48 +49,7 @@ function getMimeType(filePath) {
return map[ext] || 'application/octet-stream';
}
-// --- 核心拟人化算法 (贝塞尔曲线 + 物理模拟) ---
-/**
- * 三次贝塞尔曲线计算
- */
-function cubicBezier(t, p0, p1, p2, p3) {
- const k = 1 - t;
- return k * k * k * p0 + 3 * k * k * t * p1 + 3 * k * t * t * p2 + t * t * t * p3;
-}
-
-/**
- * 模拟人类鼠标移动轨迹
- * @param {object} page Puppeteer 页面对象
- * @param {number} startX 起始 X 坐标
- * @param {number} startY 起始 Y 坐标
- * @param {number} targetX 目标 X 坐标
- * @param {number} targetY 目标 Y 坐标
- */
-async function humanMove(page, startX, startY, targetX, targetY) {
- const distance = Math.sqrt(Math.pow(targetX - startX, 2) + Math.pow(targetY - startY, 2));
- const steps = Math.floor(Math.max(distance / 8, 15));
-
- const offset = distance * 0.4;
- // 生成两个随机控制点,使轨迹弯曲
- const cp1X = startX + (targetX - startX) / 3 + random(-offset, offset);
- const cp1Y = startY + (targetY - startY) / 3 + random(-offset, offset);
- const cp2X = startX + 2 * (targetX - startX) / 3 + random(-offset, offset);
- const cp2Y = startY + 2 * (targetY - startY) / 3 + random(-offset, offset);
-
- for (let i = 0; i <= steps; i++) {
- const t = i / steps;
- // 缓动函数:起步快,结尾慢,模拟人类肌肉运动
- const easeT = t < 0.5 ? 2 * t * t : -1 + (4 - 2 * t) * t;
-
- let x = cubicBezier(easeT, startX, cp1X, cp2X, targetX);
- let y = cubicBezier(easeT, startY, cp1Y, cp2Y, targetY);
-
- // 添加微小的随机抖动
- if (i % 3 === 0) { x += random(-1, 1); y += random(-1, 1); }
- await page.mouse.move(x, y);
- }
-}
/**
* 安全点击元素(包含拟人化移动和点击)
@@ -98,24 +60,15 @@ async function safeClick(page, selector) {
try {
const el = await page.$(selector);
if (!el) throw new Error(`未找到: ${selector}`);
- const box = await el.boundingBox();
- if (!box) throw new Error(`不可见: ${selector}`);
- // 先稍微移动一下当前位置 (增加真实感)
- await page.mouse.move(box.x - random(50, 100), box.y - random(50, 100), { steps: 2 });
+ // 使用 ghost-cursor 点击
+ if (page.cursor) {
+ await page.cursor.click(el);
+ return;
+ }
- // 目标点击位置在元素内部随机区域
- const targetX = box.x + box.width * random(0.3, 0.7);
- const targetY = box.y + box.height * random(0.3, 0.7);
-
- // 移动鼠标到目标位置
- await humanMove(page, box.x - 50, box.y - 50, targetX, targetY);
-
- // 模拟点击过程:按下 -> 停顿 -> 抬起
- await sleep(100, 300);
- await page.mouse.down();
- await sleep(60, 120);
- await page.mouse.up();
+ // 降级逻辑
+ await el.click();
} catch (err) {
throw err;
}
@@ -242,35 +195,32 @@ function extractImage(text) {
/**
* 初始化浏览器
* @param {object} config 配置对象 (包含 chrome 配置)
- * @returns {Promise<{browser: object, page: object, client: object, width: number, height: number}>}
+ * @returns {Promise<{browser: object, page: object, client: object}>}
*/
async function initBrowser(config) {
console.log('>>> [Browser] 开始初始化浏览器');
const chromeConfig = config?.chrome || {};
- const width = Math.floor(random(900, 1100));
- const height = Math.floor(random(500, 700));
// 1. 基础参数
const args = [
'--no-sandbox',
'--disable-setuid-sandbox',
- `--window-size=${width},${height}`,
'--disable-blink-features=AutomationControlled',
- '--disable-infobars',
- '--test-type',
- '--no-zygote',
- '--disable-dev-shm-usage'
+ '--disable-dev-shm-usage',
];
- // 2. Headless 模式配置
+ // 2. Headless 模式配置 & 窗口大小
let headlessMode = false;
if (chromeConfig.headless) {
headlessMode = 'new';
- args.push('--disable-gl-drawing-for-tests');
- console.log('>>> [Browser] Headless 模式: 启用');
+ // 无头模式锁死分辨率
+ args.push('--window-size=1280,690');
+ console.log('>>> [Browser] Headless 模式: 启用 (1280x690)');
} else {
- console.log('>>> [Browser] Headless 模式: 禁用');
+ // 有头模式:最大化窗口以适配屏幕
+ args.push('--start-maximized');
+ console.log('>>> [Browser] Headless 模式: 禁用 (最大化窗口)');
}
// 3. GPU 配置
@@ -323,9 +273,11 @@ async function initBrowser(config) {
args: args
});
- // 重用第一个标签页
- const pages = await browser.pages();
- const page = pages[0];
+ // 保留第一个标签页 (about:blank),在新标签页中打开
+ const page = await browser.newPage();
+
+ // 初始化 ghost-cursor
+ page.cursor = createCursor(page);
// 5. 代理认证 (仅当未使用 proxy-chain 桥接时)
if (chromeConfig.proxy && chromeConfig.proxy.enable && chromeConfig.proxy.user && !proxyUrlForChrome) {
@@ -336,11 +288,6 @@ async function initBrowser(config) {
console.log('>>> [Browser] 代理认证: 已设置 (HTTP Basic Auth)');
}
- // 隐藏 WebDriver 特征
- await page.evaluateOnNewDocument(() => {
- Object.defineProperty(navigator, 'webdriver', { get: () => undefined });
- });
-
// 创建 CDP 会话以监听网络请求
const client = await page.target().createCDPSession();
await client.send('Network.enable');
@@ -351,12 +298,19 @@ async function initBrowser(config) {
console.log('>>> [Warmup] 正在随机浏览页面以建立信任...');
- // 计算屏幕中心点
+ // 计算屏幕中心点 (动态获取视口大小)
+ let viewport = page.viewport();
+ // 如果是 null (有时候 headless 初始化慢),给个默认值
+ let width = viewport ? viewport.width : 1280;
+ let height = viewport ? viewport.height : 690;
+
const centerX = width / 2;
const centerY = height / 2;
// 第一次移动:从左上角移动到中心附近
- await humanMove(page, 0, 0, centerX + random(-200, 200), centerY + random(-200, 200));
+ if (page.cursor) {
+ await page.cursor.moveTo({ x: centerX + random(-200, 200), y: centerY + random(-200, 200) });
+ }
await sleep(500, 1000);
// 模拟滚动行为
@@ -373,11 +327,14 @@ async function initBrowser(config) {
// 移动鼠标到输入框
const box = await (await page.$(textareaSelector)).boundingBox();
if (box) {
- await humanMove(page, centerX, centerY, box.x + box.width / 2, box.y + box.height / 2);
+ if (page.cursor) {
+ await page.cursor.moveTo({ x: box.x + box.width / 2, y: box.y + box.height / 2 });
+ }
await sleep(500, 1000);
}
console.log('>>> [Browser] 浏览器初始化完成,系统就绪');
+ console.log('>>> [Browser] 当程序有任务运行时请勿随意调节窗口大小,以免鼠标轨迹错位!');
// 注册清理钩子:浏览器关闭时关闭代理服务器
if (proxyUrlForChrome) {
@@ -391,21 +348,21 @@ async function initBrowser(config) {
});
}
- return { browser, page, client, width, height };
+ return { browser, page, client };
}
/**
* 执行生图任务
- * @param {object} context 浏览器上下文 {page, client, width, height}
+ * @param {object} context 浏览器上下文 {page, client}
* @param {string} prompt 提示词
* @param {string[]} imgPaths 图片路径数组
* @param {string|null} modelId 模型 UUID (可选)
* @returns {Promise<{image?: string, text?: string, error?: string}>}
*/
async function generateImage(context, prompt, imgPaths, modelId) {
- const { page, client, width, height } = context;
+ const { page, client } = context;
const textareaSelector = 'textarea';
- let requestHandler = null;
+ let fetchPausedHandler = null;
try {
// 1. 强制开启新会话 (通过URL跳转)
@@ -428,34 +385,70 @@ async function generateImage(context, prompt, imgPaths, modelId) {
await humanType(page, textareaSelector, prompt);
await sleep(800, 1500);
- // --- 注入 Fetch 拦截器 (Puppeteer Request Interception) ---
+ // 注入 CDP Fetch 拦截器
if (modelId) {
- await page.setRequestInterception(true);
- requestHandler = async (request) => {
- const url = request.url();
- if (url.includes('/nextjs-api/stream/') && request.method() === 'POST') {
+ // 1. 启用 Fetch 域拦截,仅拦截特定 URL
+ await client.send('Fetch.enable', {
+ patterns: [{
+ urlPattern: '*nextjs-api/stream*',
+ requestStage: 'Request'
+ }]
+ });
+
+ // 2. 定义拦截处理函数
+ fetchPausedHandler = async (event) => {
+ const { requestId, request } = event;
+
+ if (request.method === 'POST' && request.postData) {
try {
- const postData = request.postData();
- if (postData) {
- const data = JSON.parse(postData);
- console.log(`[Browser] 正在拦截请求。原始 modelAId: ${data.modelAId}`);
+ // 尝试解码可能是 base64 编码的postData
+ let rawBody = request.postData;
+ // 尝试解析 JSON
+ let data;
+ try {
+ data = JSON.parse(rawBody);
+ } catch (e) {
+ // 尝试 Base64 解码
+ try {
+ rawBody = Buffer.from(rawBody, 'base64').toString('utf8');
+ data = JSON.parse(rawBody);
+ } catch (e2) {
+ // 无法解析,跳过
+ }
+ }
+
+ if (data && data.modelAId) {
+ console.log(`>>> [CDP] 正在拦截请求。原始 modelAId: ${data.modelAId}`);
// 修改 modelAId
data.modelAId = modelId;
- const newPostData = JSON.stringify(data);
- console.log(`[Browser] 请求已修改。新 modelAId: ${data.modelAId}`);
- await request.continue({ postData: newPostData });
+ // 重新序列化并转为 Base64 (Fetch.continueRequest 需要 base64)
+ const newBody = JSON.stringify(data);
+ const newBodyBase64 = Buffer.from(newBody).toString('base64');
+
+ console.log(`>>> [CDP] 请求已修改。新 modelAId: ${data.modelAId}`);
+
+ await client.send('Fetch.continueRequest', {
+ requestId,
+ postData: newBodyBase64
+ });
return;
}
} catch (e) {
- console.error('[Browser] 拦截修改失败:', e);
+ console.error('[CDP] 拦截处理出错:', e);
}
}
- await request.continue();
+
+ // 如果不匹配或出错,直接放行
+ try {
+ await client.send('Fetch.continueRequest', { requestId });
+ } catch (e) { }
};
- page.on('request', requestHandler);
- console.log(`>>> [Test] 已启用请求拦截,目标模型: ${modelId}`);
+
+ // 3. 监听拦截事件
+ client.on('Fetch.requestPaused', fetchPausedHandler);
+ console.log(`>>> [Test] 已启用 CDP Fetch 拦截,目标模型: ${modelId}`);
}
// 4. 发送
@@ -515,7 +508,12 @@ async function generateImage(context, prompt, imgPaths, modelId) {
});
// 任务结束,像人一样把鼠标移开,防止遮挡或误触
- await humanMove(page, width / 2, height / 2, width - 100, height / 2);
+ if (page.cursor) {
+ const vp = page.viewport();
+ const w = vp ? vp.width : 1280;
+ const h = vp ? vp.height : 690;
+ await page.cursor.moveTo({ x: w - 100, y: h / 2 });
+ }
return result;
@@ -523,10 +521,10 @@ async function generateImage(context, prompt, imgPaths, modelId) {
console.error('>>> [Error] 生成任务失败:', err.message);
return { error: err.message };
} finally {
- if (requestHandler) {
- page.off('request', requestHandler);
+ if (fetchPausedHandler) {
+ client.off('Fetch.requestPaused', fetchPausedHandler);
try {
- await page.setRequestInterception(false);
+ await client.send('Fetch.disable');
} catch (e) { }
}
}
diff --git a/package.json b/package.json
index 49ee76b..21c378e 100644
--- a/package.json
+++ b/package.json
@@ -11,10 +11,13 @@
"genkey": "node lib/genApiKey.js"
},
"dependencies": {
+ "ghost-cursor": "^1.4.1",
"got-scraping": "^4.1.2",
"js-yaml": "^4.1.1",
"proxy-chain": "^2.6.0",
"puppeteer": "^24.31.0",
+ "puppeteer-extra": "^3.3.6",
+ "puppeteer-extra-plugin-stealth": "^2.11.2",
"sharp": "^0.34.5"
}
}
\ No newline at end of file
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 0a84a0a..c5e90e2 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -8,6 +8,9 @@ importers:
.:
dependencies:
+ ghost-cursor:
+ specifier: ^1.4.1
+ version: 1.4.1
got-scraping:
specifier: ^4.1.2
version: 4.1.2
@@ -20,6 +23,12 @@ importers:
puppeteer:
specifier: ^24.31.0
version: 24.31.0
+ puppeteer-extra:
+ specifier: ^3.3.6
+ version: 3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)
+ puppeteer-extra-plugin-stealth:
+ specifier: ^2.11.2
+ version: 2.11.2(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0))
sharp:
specifier: ^0.34.5
version: 0.34.5
@@ -216,9 +225,18 @@ packages:
'@tootallnate/quickjs-emscripten@0.23.0':
resolution: {integrity: sha512-C5Mc6rdnsaJDjO3UpGW/CQTHtCKaYlScZTly4JIu97Jxo/odCiH0ITnDXSJPTOrEKk/ycSZ0AOgTmkDtkOsvIA==}
+ '@types/bezier-js@4.1.3':
+ resolution: {integrity: sha512-FNVVCu5mx/rJCWBxLTcL7oOajmGtWtBTDjq6DSUWUI12GeePivrZZXz+UgE0D6VYsLEjvExRO03z4hVtu3pTEQ==}
+
+ '@types/debug@4.1.12':
+ resolution: {integrity: sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==}
+
'@types/http-cache-semantics@4.0.4':
resolution: {integrity: sha512-1m0bIFVc7eJWyve9S0RnuRgcQqF/Xd5QsUZAZeQFr1Q3/p9JWoQQEqmVy+DPTNpGXwhgIetAoYF8JSc33q29QA==}
+ '@types/ms@2.1.0':
+ resolution: {integrity: sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==}
+
'@types/node@24.10.1':
resolution: {integrity: sha512-GNWcUTRBgIRJD5zj+Tq0fKOJ5XZajIiBroOF0yvj2bSU1WvNdYS/dn9UxwsujGW4JX06dnHyjV2y9rRaybH0iQ==}
@@ -244,6 +262,10 @@ packages:
argparse@2.0.1:
resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==}
+ arr-union@3.1.0:
+ resolution: {integrity: sha512-sKpyeERZ02v1FeCZT8lrfJq5u6goHCtpTAzPwJYe7c8SPFOboNjNg1vz2L4VTn9T4PQxEx13TbXLmYUcS6Ug7Q==}
+ engines: {node: '>=0.10.0'}
+
ast-types@0.13.4:
resolution: {integrity: sha512-x1FCFnFifvYDDzTaLII71vG5uvDwgtmDTEVWAxrgeiR8VjMONcCXJx7E+USjDtHlwFmt9MysbqgF9b9Vjr6w+w==}
engines: {node: '>=4'}
@@ -256,6 +278,9 @@ packages:
react-native-b4a:
optional: true
+ balanced-match@1.0.2:
+ resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==}
+
bare-events@2.8.2:
resolution: {integrity: sha512-riJjyv1/mHLIPX4RwiK+oW9/4c3TEUeORHKefKAKnZ5kyslbN+HXowtbaVEqt4IMUB7OXlfixcs6gsFeo/jhiQ==}
peerDependencies:
@@ -302,6 +327,12 @@ packages:
resolution: {integrity: sha512-4Bcg1P8xhUuqcii/S0Z9wiHIrQVPMermM1any+MX5GeGD7faD3/msQUDGLol9wOcz4/jbg/WJnGqoJF6LiBdtg==}
engines: {node: '>=10.0.0'}
+ bezier-js@6.1.4:
+ resolution: {integrity: sha512-PA0FW9ZpcHbojUCMu28z9Vg/fNkwTj5YhusSAjHHDfHDGLxJ6YUKrAN2vk1fP2MMOxVw4Oko16FMlRGVBGqLKg==}
+
+ brace-expansion@1.1.12:
+ resolution: {integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==}
+
browserslist@4.28.0:
resolution: {integrity: sha512-tbydkR/CxfMwelN0vwdP/pLkDwyAASZ+VfWm4EOwlB6SWhx1sYnWLqo8N5j0rAzPfzfRaxt0mM/4wPU/Su84RQ==}
engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7}
@@ -342,6 +373,10 @@ packages:
resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==}
engines: {node: '>=12'}
+ clone-deep@0.2.4:
+ resolution: {integrity: sha512-we+NuQo2DHhSl+DP6jlUiAhyAjBQrYnpOk15rN6c6JSPScjiCLh8IbSU+VTcph6YS3o7mASE8a0+gbZ7ChLpgg==}
+ engines: {node: '>=0.10.0'}
+
color-convert@2.0.1:
resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==}
engines: {node: '>=7.0.0'}
@@ -349,6 +384,9 @@ packages:
color-name@1.1.4:
resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==}
+ concat-map@0.0.1:
+ resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==}
+
cosmiconfig@9.0.0:
resolution: {integrity: sha512-itvL5h8RETACmOTFc4UfIyB2RfEHi71Ax6E/PivVxq9NseKbOWpeyHEOIbmAw1rs8Ak0VursQNww7lf7YtUwzg==}
engines: {node: '>=14'}
@@ -375,6 +413,10 @@ packages:
resolution: {integrity: sha512-oj7KWToJuuxlPr7VV0vabvxEIiqNMo+q0NueIiL3XhtwC6FVOX7Hr1c0C4eD0bmf7Zr+S/dSf2xvkH3Ad6sU3Q==}
engines: {node: '>=20'}
+ deepmerge@4.3.1:
+ resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==}
+ engines: {node: '>=0.10.0'}
+
degenerator@5.0.1:
resolution: {integrity: sha512-TllpMR/t0M5sqCXfj85i4XaAzxmS5tVA16dqvdkMwGmzI+dXLXnw3J+3Vdv7VKw+ThlTMboK6i9rnZ6Nntj5CQ==}
engines: {node: '>= 14'}
@@ -446,10 +488,29 @@ packages:
fd-slicer@1.1.0:
resolution: {integrity: sha512-cE1qsB/VwyQozZ+q1dGxR8LBYNZeofhEdUNGSMbQD3Gw2lAzX9Zb3uIU6Ebc/Fmyjo9AWWfnn0AUCHqtevs/8g==}
+ for-in@0.1.8:
+ resolution: {integrity: sha512-F0to7vbBSHP8E3l6dCjxNOLuSFAACIxFy3UehTUlG7svlXi37HHsDkyVcHo0Pq8QwrE+pXvWSVX3ZT1T9wAZ9g==}
+ engines: {node: '>=0.10.0'}
+
+ for-in@1.0.2:
+ resolution: {integrity: sha512-7EwmXrOjyL+ChxMhmG5lnW9MPt1aIeZEwKhQzoBUdTV0N3zuwWDZYVJatDvZ2OyzPUvdIAZDsCetk3coyMfcnQ==}
+ engines: {node: '>=0.10.0'}
+
+ for-own@0.1.5:
+ resolution: {integrity: sha512-SKmowqGTJoPzLO1T0BBJpkfp3EMacCMOuH40hOUbrbzElVktk4DioXVM99QkLCyKoiuOmyjgcWMpVz2xjE7LZw==}
+ engines: {node: '>=0.10.0'}
+
form-data-encoder@4.1.0:
resolution: {integrity: sha512-G6NsmEW15s0Uw9XnCg+33H3ViYRyiM0hMrMhhqQOR8NFc5GhYrI+6I3u7OTw7b91J2g8rtvMBZJDbcGb2YUniw==}
engines: {node: '>= 18'}
+ fs-extra@10.1.0:
+ resolution: {integrity: sha512-oRXApq54ETRj4eMiFzGnHWGy+zo5raudjuxN0b8H7s/RU2oW0Wvsx9O0ACRN/kRq9E8Vu/ReskGB5o3ji+FzHQ==}
+ engines: {node: '>=12'}
+
+ fs.realpath@1.0.0:
+ resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==}
+
generative-bayesian-network@2.1.77:
resolution: {integrity: sha512-viU4CRPsmgiklR94LhvdMndaY73BkCH1pGjmOjWbLR/ZwcUd06gKF3TCcsS3npRl74o33YSInSixxm16wIukcA==}
@@ -469,6 +530,13 @@ packages:
resolution: {integrity: sha512-b1O07XYq8eRuVzBNgJLstU6FYc1tS6wnMtF1I1D9lE8LxZSOGZ7LhxN54yPP6mGw5f2CkXY2BQUL9Fx41qvcIg==}
engines: {node: '>= 14'}
+ ghost-cursor@1.4.1:
+ resolution: {integrity: sha512-K8A8/Co/Jbdqee694qrNsGWBG51DVK5UF2gGKEoZBDx9F1WmoD2SzUoDHWoY7O+TY84s1VrWwwfkVKxI2FoV2Q==}
+
+ glob@7.2.3:
+ resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==}
+ deprecated: Glob versions prior to v9 are no longer supported
+
got-scraping@4.1.2:
resolution: {integrity: sha512-LtVwPM5YLnNY7HVT/AK/yDBUg/4yOZSlAjjug2ovrHQseS43QCmO1XosKKXcXrfc6OMX8OnDbAWIauFMcaJ5TQ==}
engines: {node: '>=16'}
@@ -477,6 +545,9 @@ packages:
resolution: {integrity: sha512-DjsLab39NUMf5iYlK9asVCkHMhaA2hEhrlmf+qXRhjEivuuBHWYbjmty9DA3OORUwZgENTB+6vSmY2ZW8gFHVw==}
engines: {node: '>=20'}
+ graceful-fs@4.2.11:
+ resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==}
+
header-generator@2.1.77:
resolution: {integrity: sha512-ggSG/mfkFMu8CO7xP591G8kp1IJCBvgXu7M8oxTjC9u914JsIzE6zIfoFsXzA+pf0utWJhUsdqU0oV/DtQ4DFQ==}
engines: {node: '>=16.0.0'}
@@ -500,6 +571,13 @@ packages:
resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==}
engines: {node: '>=6'}
+ inflight@1.0.6:
+ resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==}
+ deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.
+
+ inherits@2.0.4:
+ resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==}
+
ip-address@10.1.0:
resolution: {integrity: sha512-XXADHxXmvT9+CRxhXg56LJovE+bmWnEWB78LB83VZTprKTmaC5QfruXocxzTZ2Kl0DNwKuBdlIhjL8LeY8Sf8Q==}
engines: {node: '>= 12'}
@@ -507,6 +585,13 @@ packages:
is-arrayish@0.2.1:
resolution: {integrity: sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==}
+ is-buffer@1.1.6:
+ resolution: {integrity: sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==}
+
+ is-extendable@0.1.1:
+ resolution: {integrity: sha512-5BMULNob1vgFX6EjQw5izWDxrecWK9AM72rugNr0TFldMOi0fj6Jk+zeKIt0xGj4cEfQIJth4w3OKWOJ4f+AFw==}
+ engines: {node: '>=0.10.0'}
+
is-fullwidth-code-point@3.0.0:
resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==}
engines: {node: '>=8'}
@@ -515,10 +600,18 @@ packages:
resolution: {integrity: sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==}
engines: {node: '>=8'}
+ is-plain-object@2.0.4:
+ resolution: {integrity: sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==}
+ engines: {node: '>=0.10.0'}
+
is-stream@4.0.1:
resolution: {integrity: sha512-Dnz92NInDqYckGEUJv689RbRiTSEHCQ7wOVeALbkOz999YpqT46yMRIGtSNl2iCL1waAZSx40+h59NV/EwzV/A==}
engines: {node: '>=18'}
+ isobject@3.0.1:
+ resolution: {integrity: sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==}
+ engines: {node: '>=0.10.0'}
+
js-tokens@4.0.0:
resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==}
@@ -529,9 +622,28 @@ packages:
json-parse-even-better-errors@2.3.1:
resolution: {integrity: sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==}
+ jsonfile@6.2.0:
+ resolution: {integrity: sha512-FGuPw30AdOIUTRMC2OMRtQV+jkVj2cfPqSeWXv1NEAJ1qZ5zb1X6z1mFhbfOB/iy3ssJCD+3KuZ8r8C3uVFlAg==}
+
keyv@5.5.4:
resolution: {integrity: sha512-eohl3hKTiVyD1ilYdw9T0OiB4hnjef89e3dMYKz+mVKDzj+5IteTseASUsOB+EU9Tf6VNTCjDePcP6wkDGmLKQ==}
+ kind-of@2.0.1:
+ resolution: {integrity: sha512-0u8i1NZ/mg0b+W3MGGw5I7+6Eib2nx72S/QvXa0hYjEkjTknYmEYQJwGu3mLC0BrhtJjtQafTkyRUQ75Kx0LVg==}
+ engines: {node: '>=0.10.0'}
+
+ kind-of@3.2.2:
+ resolution: {integrity: sha512-NOW9QQXMoZGg/oqnVNoNTTIFEIid1627WCffUBJEdMxYApq7mNE7CpzucIPc+ZQg25Phej7IJSmX3hO+oblOtQ==}
+ engines: {node: '>=0.10.0'}
+
+ lazy-cache@0.2.7:
+ resolution: {integrity: sha512-gkX52wvU/R8DVMMt78ATVPFMJqfW8FPz1GZ1sVHBVQHmu/WvhIWE4cE1GBzhJNFicDeYhnwp6Rl35BcAIM3YOQ==}
+ engines: {node: '>=0.10.0'}
+
+ lazy-cache@1.0.4:
+ resolution: {integrity: sha512-RE2g0b5VGZsOCFOCgP7omTRYFqydmZkBwl5oNnQ1lDYC57uyO9KqNnNVxT7COSHTxrRCWVcAVOcbjk+tvh/rgQ==}
+ engines: {node: '>=0.10.0'}
+
lines-and-columns@1.2.4:
resolution: {integrity: sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==}
@@ -547,13 +659,24 @@ packages:
resolution: {integrity: sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA==}
engines: {node: '>=12'}
+ merge-deep@3.0.3:
+ resolution: {integrity: sha512-qtmzAS6t6grwEkNrunqTBdn0qKwFgNWvlxUbAV8es9M7Ot1EbyApytCnvE0jALPa46ZpKDUo527kKiaWplmlFA==}
+ engines: {node: '>=0.10.0'}
+
mimic-response@4.0.0:
resolution: {integrity: sha512-e5ISH9xMYU0DzrT+jl8q2ze9D6eWBto+I8CNpe+VI+K2J/F/k3PdkdTdz4wvGVH4NTpo+NRYTVIuMQEMMcsLqg==}
engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0}
+ minimatch@3.1.2:
+ resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==}
+
mitt@3.0.1:
resolution: {integrity: sha512-vKivATfr97l2/QBCYAkXYDbrIWPM2IIKEl7YPhjCvKlG3kE2gm+uBo6nEXK3M5/Ffh/FLpKExzOQ3JJoJGFKBw==}
+ mixin-object@2.0.1:
+ resolution: {integrity: sha512-ALGF1Jt9ouehcaXaHhn6t1yGWRqGaHkPFndtFVHfZXOvkIZ/yoGaSi0AHVTafb3ZBGg4dr/bDwnaEKqCXzchMA==}
+ engines: {node: '>=0.10.0'}
+
ms@2.1.3:
resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==}
@@ -599,6 +722,10 @@ packages:
resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==}
engines: {node: '>=8'}
+ path-is-absolute@1.0.1:
+ resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==}
+ engines: {node: '>=0.10.0'}
+
pend@1.2.0:
resolution: {integrity: sha512-F3asv42UuXchdzt+xXqfW1OGlVBe+mxa2mqI0pg5yAHZPvFmY3Y6drSf/GQ1A86WgWEN9Kzh/WrgKa6iGcHXLg==}
@@ -627,6 +754,69 @@ packages:
resolution: {integrity: sha512-pnAohhSZipWQoFpXuGV7xCZfaGhqcBR9C4pVrU0QSrcMi7tQMH9J9lDBqBvyMAHQqe8HCARuREqFuVKRQOgTvg==}
engines: {node: '>=18'}
+ puppeteer-extra-plugin-stealth@2.11.2:
+ resolution: {integrity: sha512-bUemM5XmTj9i2ZerBzsk2AN5is0wHMNE6K0hXBzBXOzP5m5G3Wl0RHhiqKeHToe/uIH8AoZiGhc1tCkLZQPKTQ==}
+ engines: {node: '>=8'}
+ peerDependencies:
+ playwright-extra: '*'
+ puppeteer-extra: '*'
+ peerDependenciesMeta:
+ playwright-extra:
+ optional: true
+ puppeteer-extra:
+ optional: true
+
+ puppeteer-extra-plugin-user-data-dir@2.4.1:
+ resolution: {integrity: sha512-kH1GnCcqEDoBXO7epAse4TBPJh9tEpVEK/vkedKfjOVOhZAvLkHGc9swMs5ChrJbRnf8Hdpug6TJlEuimXNQ+g==}
+ engines: {node: '>=8'}
+ peerDependencies:
+ playwright-extra: '*'
+ puppeteer-extra: '*'
+ peerDependenciesMeta:
+ playwright-extra:
+ optional: true
+ puppeteer-extra:
+ optional: true
+
+ puppeteer-extra-plugin-user-preferences@2.4.1:
+ resolution: {integrity: sha512-i1oAZxRbc1bk8MZufKCruCEC3CCafO9RKMkkodZltI4OqibLFXF3tj6HZ4LZ9C5vCXZjYcDWazgtY69mnmrQ9A==}
+ engines: {node: '>=8'}
+ peerDependencies:
+ playwright-extra: '*'
+ puppeteer-extra: '*'
+ peerDependenciesMeta:
+ playwright-extra:
+ optional: true
+ puppeteer-extra:
+ optional: true
+
+ puppeteer-extra-plugin@3.2.3:
+ resolution: {integrity: sha512-6RNy0e6pH8vaS3akPIKGg28xcryKscczt4wIl0ePciZENGE2yoaQJNd17UiEbdmh5/6WW6dPcfRWT9lxBwCi2Q==}
+ engines: {node: '>=9.11.2'}
+ peerDependencies:
+ playwright-extra: '*'
+ puppeteer-extra: '*'
+ peerDependenciesMeta:
+ playwright-extra:
+ optional: true
+ puppeteer-extra:
+ optional: true
+
+ puppeteer-extra@3.3.6:
+ resolution: {integrity: sha512-rsLBE/6mMxAjlLd06LuGacrukP2bqbzKCLzV1vrhHFavqQE/taQ2UXv3H5P0Ls7nsrASa+6x3bDbXHpqMwq+7A==}
+ engines: {node: '>=8'}
+ peerDependencies:
+ '@types/puppeteer': '*'
+ puppeteer: '*'
+ puppeteer-core: '*'
+ peerDependenciesMeta:
+ '@types/puppeteer':
+ optional: true
+ puppeteer:
+ optional: true
+ puppeteer-core:
+ optional: true
+
puppeteer@24.31.0:
resolution: {integrity: sha512-q8y5yLxLD8xdZdzNWqdOL43NbfvUOp60SYhaLZQwHC9CdKldxQKXOyJAciOr7oUJfyAH/KgB2wKvqT2sFKoVXA==}
engines: {node: '>=18'}
@@ -655,11 +845,20 @@ packages:
resolution: {integrity: sha512-cGk8IbWEAnaCpdAt1BHzJ3Ahz5ewDJa0KseTsE3qIRMJ3C698W8psM7byCeWVpd/Ha7FUYzuRVzXoKoM6nRUbA==}
engines: {node: '>=20'}
+ rimraf@3.0.2:
+ resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==}
+ deprecated: Rimraf versions prior to v4 are no longer supported
+ hasBin: true
+
semver@7.7.3:
resolution: {integrity: sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q==}
engines: {node: '>=10'}
hasBin: true
+ shallow-clone@0.1.2:
+ resolution: {integrity: sha512-J1zdXCky5GmNnuauESROVu31MQSnLoYvlyEn6j2Ztk6Q5EHFIhxkMhYcv6vuDzl2XEzoRr856QwzMgWM/TmZgw==}
+ engines: {node: '>=0.10.0'}
+
sharp@0.34.5:
resolution: {integrity: sha512-Ou9I5Ft9WNcCbXrU9cMgPBcCK8LiwLqcbywW3t4oDV37n1pzpuNLsYiAV8eODnjbtQlSDwZ2cUEeQz4E54Hltg==}
engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0}
@@ -717,6 +916,10 @@ packages:
undici-types@7.16.0:
resolution: {integrity: sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==}
+ universalify@2.0.1:
+ resolution: {integrity: sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==}
+ engines: {node: '>= 10.0.0'}
+
update-browserslist-db@1.1.4:
resolution: {integrity: sha512-q0SPT4xyU84saUX+tomz1WLkxUbuaJnR1xWt17M7fJtEJigJeWUNGUqrauFXsHnqev9y9JTRGwk13tFBuKby4A==}
hasBin: true
@@ -905,8 +1108,16 @@ snapshots:
'@tootallnate/quickjs-emscripten@0.23.0': {}
+ '@types/bezier-js@4.1.3': {}
+
+ '@types/debug@4.1.12':
+ dependencies:
+ '@types/ms': 2.1.0
+
'@types/http-cache-semantics@4.0.4': {}
+ '@types/ms@2.1.0': {}
+
'@types/node@24.10.1':
dependencies:
undici-types: 7.16.0
@@ -929,12 +1140,16 @@ snapshots:
argparse@2.0.1: {}
+ arr-union@3.1.0: {}
+
ast-types@0.13.4:
dependencies:
tslib: 2.8.1
b4a@1.7.3: {}
+ balanced-match@1.0.2: {}
+
bare-events@2.8.2: {}
bare-fs@4.5.1:
@@ -976,6 +1191,13 @@ snapshots:
basic-ftp@5.0.5: {}
+ bezier-js@6.1.4: {}
+
+ brace-expansion@1.1.12:
+ dependencies:
+ balanced-match: 1.0.2
+ concat-map: 0.0.1
+
browserslist@4.28.0:
dependencies:
baseline-browser-mapping: 2.8.30
@@ -1018,12 +1240,22 @@ snapshots:
strip-ansi: 6.0.1
wrap-ansi: 7.0.0
+ clone-deep@0.2.4:
+ dependencies:
+ for-own: 0.1.5
+ is-plain-object: 2.0.4
+ kind-of: 3.2.2
+ lazy-cache: 1.0.4
+ shallow-clone: 0.1.2
+
color-convert@2.0.1:
dependencies:
color-name: 1.1.4
color-name@1.1.4: {}
+ concat-map@0.0.1: {}
+
cosmiconfig@9.0.0:
dependencies:
env-paths: 2.2.1
@@ -1041,6 +1273,8 @@ snapshots:
dependencies:
mimic-response: 4.0.0
+ deepmerge@4.3.1: {}
+
degenerator@5.0.1:
dependencies:
ast-types: 0.13.4
@@ -1111,8 +1345,24 @@ snapshots:
dependencies:
pend: 1.2.0
+ for-in@0.1.8: {}
+
+ for-in@1.0.2: {}
+
+ for-own@0.1.5:
+ dependencies:
+ for-in: 1.0.2
+
form-data-encoder@4.1.0: {}
+ fs-extra@10.1.0:
+ dependencies:
+ graceful-fs: 4.2.11
+ jsonfile: 6.2.0
+ universalify: 2.0.1
+
+ fs.realpath@1.0.0: {}
+
generative-bayesian-network@2.1.77:
dependencies:
adm-zip: 0.5.16
@@ -1137,6 +1387,23 @@ snapshots:
transitivePeerDependencies:
- supports-color
+ ghost-cursor@1.4.1:
+ dependencies:
+ '@types/bezier-js': 4.1.3
+ bezier-js: 6.1.4
+ debug: 4.4.3
+ transitivePeerDependencies:
+ - supports-color
+
+ glob@7.2.3:
+ dependencies:
+ fs.realpath: 1.0.0
+ inflight: 1.0.6
+ inherits: 2.0.4
+ minimatch: 3.1.2
+ once: 1.4.0
+ path-is-absolute: 1.0.1
+
got-scraping@4.1.2:
dependencies:
got: 14.6.4
@@ -1162,6 +1429,8 @@ snapshots:
responselike: 4.0.2
type-fest: 4.41.0
+ graceful-fs@4.2.11: {}
+
header-generator@2.1.77:
dependencies:
browserslist: 4.28.0
@@ -1195,16 +1464,33 @@ snapshots:
parent-module: 1.0.1
resolve-from: 4.0.0
+ inflight@1.0.6:
+ dependencies:
+ once: 1.4.0
+ wrappy: 1.0.2
+
+ inherits@2.0.4: {}
+
ip-address@10.1.0: {}
is-arrayish@0.2.1: {}
+ is-buffer@1.1.6: {}
+
+ is-extendable@0.1.1: {}
+
is-fullwidth-code-point@3.0.0: {}
is-obj@2.0.0: {}
+ is-plain-object@2.0.4:
+ dependencies:
+ isobject: 3.0.1
+
is-stream@4.0.1: {}
+ isobject@3.0.1: {}
+
js-tokens@4.0.0: {}
js-yaml@4.1.1:
@@ -1213,10 +1499,28 @@ snapshots:
json-parse-even-better-errors@2.3.1: {}
+ jsonfile@6.2.0:
+ dependencies:
+ universalify: 2.0.1
+ optionalDependencies:
+ graceful-fs: 4.2.11
+
keyv@5.5.4:
dependencies:
'@keyv/serialize': 1.1.1
+ kind-of@2.0.1:
+ dependencies:
+ is-buffer: 1.1.6
+
+ kind-of@3.2.2:
+ dependencies:
+ is-buffer: 1.1.6
+
+ lazy-cache@0.2.7: {}
+
+ lazy-cache@1.0.4: {}
+
lines-and-columns@1.2.4: {}
lodash.isequal@4.5.0: {}
@@ -1225,10 +1529,25 @@ snapshots:
lru-cache@7.18.3: {}
+ merge-deep@3.0.3:
+ dependencies:
+ arr-union: 3.1.0
+ clone-deep: 0.2.4
+ kind-of: 3.2.2
+
mimic-response@4.0.0: {}
+ minimatch@3.1.2:
+ dependencies:
+ brace-expansion: 1.1.12
+
mitt@3.0.1: {}
+ mixin-object@2.0.1:
+ dependencies:
+ for-in: 0.1.8
+ is-extendable: 0.1.1
+
ms@2.1.3: {}
netmask@2.0.2: {}
@@ -1288,6 +1607,8 @@ snapshots:
json-parse-even-better-errors: 2.3.1
lines-and-columns: 1.2.4
+ path-is-absolute@1.0.1: {}
+
pend@1.2.0: {}
picocolors@1.1.1: {}
@@ -1339,6 +1660,59 @@ snapshots:
- supports-color
- utf-8-validate
+ puppeteer-extra-plugin-stealth@2.11.2(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)):
+ dependencies:
+ debug: 4.4.3
+ puppeteer-extra-plugin: 3.2.3(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0))
+ puppeteer-extra-plugin-user-preferences: 2.4.1(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0))
+ optionalDependencies:
+ puppeteer-extra: 3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)
+ transitivePeerDependencies:
+ - supports-color
+
+ puppeteer-extra-plugin-user-data-dir@2.4.1(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)):
+ dependencies:
+ debug: 4.4.3
+ fs-extra: 10.1.0
+ puppeteer-extra-plugin: 3.2.3(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0))
+ rimraf: 3.0.2
+ optionalDependencies:
+ puppeteer-extra: 3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)
+ transitivePeerDependencies:
+ - supports-color
+
+ puppeteer-extra-plugin-user-preferences@2.4.1(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)):
+ dependencies:
+ debug: 4.4.3
+ deepmerge: 4.3.1
+ puppeteer-extra-plugin: 3.2.3(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0))
+ puppeteer-extra-plugin-user-data-dir: 2.4.1(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0))
+ optionalDependencies:
+ puppeteer-extra: 3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)
+ transitivePeerDependencies:
+ - supports-color
+
+ puppeteer-extra-plugin@3.2.3(puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)):
+ dependencies:
+ '@types/debug': 4.1.12
+ debug: 4.4.3
+ merge-deep: 3.0.3
+ optionalDependencies:
+ puppeteer-extra: 3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0)
+ transitivePeerDependencies:
+ - supports-color
+
+ puppeteer-extra@3.3.6(puppeteer-core@24.31.0)(puppeteer@24.31.0):
+ dependencies:
+ '@types/debug': 4.1.12
+ debug: 4.4.3
+ deepmerge: 4.3.1
+ optionalDependencies:
+ puppeteer: 24.31.0
+ puppeteer-core: 24.31.0
+ transitivePeerDependencies:
+ - supports-color
+
puppeteer@24.31.0:
dependencies:
'@puppeteer/browsers': 2.10.13
@@ -1370,8 +1744,19 @@ snapshots:
dependencies:
lowercase-keys: 3.0.0
+ rimraf@3.0.2:
+ dependencies:
+ glob: 7.2.3
+
semver@7.7.3: {}
+ shallow-clone@0.1.2:
+ dependencies:
+ is-extendable: 0.1.1
+ kind-of: 2.0.1
+ lazy-cache: 0.2.7
+ mixin-object: 2.0.1
+
sharp@0.34.5:
dependencies:
'@img/colour': 1.0.0
@@ -1478,6 +1863,8 @@ snapshots:
undici-types@7.16.0:
optional: true
+ universalify@2.0.1: {}
+
update-browserslist-db@1.1.4(browserslist@4.28.0):
dependencies:
browserslist: 4.28.0