fix(stealth): 修复 headed 模式下 stealth 失效并统一策略
- 修复 launch 协议未透传 stealth 导致 --headed 下补丁失效的问题\n- 在 BrowserManager 引入 StealthPolicy,统一 local/CDP/provider 能力决策\n- 增加 launch 返回 stealth 状态并在 --debug 输出连接类型与能力\n- 补充 local/CDP 回归测试与 bot.sannysoft.com 自动检查脚本\n- 同步 README、CLI help、技能文档与 CDP 文档中的 stealth 能力矩阵
This commit is contained in:
@@ -0,0 +1,54 @@
|
||||
import { afterEach, describe, expect, it } from 'vitest';
|
||||
import { BrowserManager } from './browser.js';
|
||||
|
||||
async function readWebdriverSignals(browser: BrowserManager): Promise<{
|
||||
value: boolean | undefined;
|
||||
inNavigator: boolean;
|
||||
ownNavigator: boolean;
|
||||
ownPrototype: boolean;
|
||||
}> {
|
||||
const page = browser.getPage();
|
||||
await page.goto('about:blank');
|
||||
return page.evaluate(() => {
|
||||
const prototype = Object.getPrototypeOf(navigator);
|
||||
return {
|
||||
value: navigator.webdriver,
|
||||
inNavigator: 'webdriver' in navigator,
|
||||
ownNavigator: Object.prototype.hasOwnProperty.call(navigator, 'webdriver'),
|
||||
ownPrototype: Object.prototype.hasOwnProperty.call(prototype, 'webdriver'),
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
describe('Stealth mode', () => {
|
||||
let browser: BrowserManager;
|
||||
|
||||
afterEach(async () => {
|
||||
if (browser?.isLaunched()) {
|
||||
await browser.close();
|
||||
}
|
||||
});
|
||||
|
||||
it('removes navigator.webdriver when stealth is enabled', async () => {
|
||||
browser = new BrowserManager();
|
||||
await browser.launch({ headless: true, stealth: true });
|
||||
|
||||
const signals = await readWebdriverSignals(browser);
|
||||
expect(signals.value).toBeUndefined();
|
||||
expect(signals.inNavigator).toBe(false);
|
||||
expect(signals.ownNavigator).toBe(false);
|
||||
expect(signals.ownPrototype).toBe(false);
|
||||
});
|
||||
|
||||
it('applies stealth patches to contexts created by newWindow', async () => {
|
||||
browser = new BrowserManager();
|
||||
await browser.launch({ headless: true, stealth: true });
|
||||
await browser.newWindow();
|
||||
|
||||
const signals = await readWebdriverSignals(browser);
|
||||
expect(signals.value).toBeUndefined();
|
||||
expect(signals.inNavigator).toBe(false);
|
||||
expect(signals.ownNavigator).toBe(false);
|
||||
expect(signals.ownPrototype).toBe(false);
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user