@skrillex1224/playwright-toolkit 3.0.14 → 3.0.15
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/browser.js +161 -409
- package/dist/browser.js.map +4 -4
- package/dist/index.cjs +479 -992
- package/dist/index.cjs.map +4 -4
- package/dist/index.js +479 -992
- package/dist/index.js.map +4 -4
- package/index.d.ts +9 -40
- package/package.json +1 -7
package/dist/index.js
CHANGED
|
@@ -13,11 +13,9 @@ __export(constants_exports, {
|
|
|
13
13
|
ActorInfo: () => ActorInfo,
|
|
14
14
|
Code: () => Code,
|
|
15
15
|
Device: () => Device,
|
|
16
|
-
Mode: () => Mode,
|
|
17
16
|
PresetOfLiveViewKey: () => PresetOfLiveViewKey,
|
|
18
17
|
Status: () => Status,
|
|
19
|
-
normalizeDevice: () => normalizeDevice
|
|
20
|
-
normalizeMode: () => normalizeMode
|
|
18
|
+
normalizeDevice: () => normalizeDevice
|
|
21
19
|
});
|
|
22
20
|
var Code = {
|
|
23
21
|
Success: 0,
|
|
@@ -37,10 +35,6 @@ var Device = Object.freeze({
|
|
|
37
35
|
Desktop: "desktop",
|
|
38
36
|
Mobile: "mobile"
|
|
39
37
|
});
|
|
40
|
-
var Mode = Object.freeze({
|
|
41
|
-
Default: "default",
|
|
42
|
-
Cloak: "cloak"
|
|
43
|
-
});
|
|
44
38
|
var normalizeDevice = (value, fallback = Device.Desktop) => {
|
|
45
39
|
const normalizedFallback = String(fallback || "").trim().toLowerCase() === Device.Mobile ? Device.Mobile : Device.Desktop;
|
|
46
40
|
const raw = String(value || "").trim().toLowerCase();
|
|
@@ -48,13 +42,6 @@ var normalizeDevice = (value, fallback = Device.Desktop) => {
|
|
|
48
42
|
if (raw === Device.Desktop) return Device.Desktop;
|
|
49
43
|
return normalizedFallback;
|
|
50
44
|
};
|
|
51
|
-
var normalizeMode = (value, fallback = Mode.Default) => {
|
|
52
|
-
const normalizedFallback = String(fallback || "").trim().toLowerCase() === Mode.Cloak ? Mode.Cloak : Mode.Default;
|
|
53
|
-
const raw = String(value || "").trim().toLowerCase();
|
|
54
|
-
if (raw === Mode.Cloak) return Mode.Cloak;
|
|
55
|
-
if (raw === Mode.Default) return Mode.Default;
|
|
56
|
-
return normalizedFallback;
|
|
57
|
-
};
|
|
58
45
|
var createActorInfo = (info) => {
|
|
59
46
|
const normalizeDomain = (value) => {
|
|
60
47
|
if (!value) return "";
|
|
@@ -122,6 +109,7 @@ var createActorInfo = (info) => {
|
|
|
122
109
|
const buildLandingUrl = ({ protocol: protocol2, domain: domain2, path: path4 }) => {
|
|
123
110
|
const safeProtocol = String(protocol2).trim();
|
|
124
111
|
const safeDomain = normalizeDomain(domain2);
|
|
112
|
+
if (!safeDomain) return "";
|
|
125
113
|
const safePath = normalizePath(path4);
|
|
126
114
|
return `${safeProtocol}://${safeDomain}${safePath}`;
|
|
127
115
|
};
|
|
@@ -329,6 +317,18 @@ var ActorInfo = {
|
|
|
329
317
|
prefix: "",
|
|
330
318
|
xurl: []
|
|
331
319
|
}
|
|
320
|
+
}),
|
|
321
|
+
// 通用网页抓取 Actor:入口 URL 来自 query,因此这里只声明统一的 Actor 元信息。
|
|
322
|
+
webpage: createActorInfo({
|
|
323
|
+
key: "webpage",
|
|
324
|
+
name: "\u901A\u7528\u7F51\u9875",
|
|
325
|
+
domain: "",
|
|
326
|
+
path: "/",
|
|
327
|
+
share: {
|
|
328
|
+
mode: "dom",
|
|
329
|
+
prefix: "",
|
|
330
|
+
xurl: []
|
|
331
|
+
}
|
|
332
332
|
})
|
|
333
333
|
};
|
|
334
334
|
|
|
@@ -360,18 +360,18 @@ var fallbackLog = {
|
|
|
360
360
|
error: (...args) => console.error(...args),
|
|
361
361
|
debug: (...args) => console.debug ? console.debug(...args) : console.log(...args)
|
|
362
362
|
};
|
|
363
|
-
var resolveLogMethod = (
|
|
364
|
-
if (
|
|
365
|
-
return
|
|
363
|
+
var resolveLogMethod = (logger16, name) => {
|
|
364
|
+
if (logger16 && typeof logger16[name] === "function") {
|
|
365
|
+
return logger16[name].bind(logger16);
|
|
366
366
|
}
|
|
367
|
-
if (name === "warning" &&
|
|
368
|
-
return
|
|
367
|
+
if (name === "warning" && logger16 && typeof logger16.warn === "function") {
|
|
368
|
+
return logger16.warn.bind(logger16);
|
|
369
369
|
}
|
|
370
370
|
return fallbackLog[name];
|
|
371
371
|
};
|
|
372
372
|
var defaultLogger = null;
|
|
373
|
-
var setDefaultLogger = (
|
|
374
|
-
defaultLogger =
|
|
373
|
+
var setDefaultLogger = (logger16) => {
|
|
374
|
+
defaultLogger = logger16;
|
|
375
375
|
};
|
|
376
376
|
var resolveLogger = (explicitLogger) => {
|
|
377
377
|
if (explicitLogger && typeof explicitLogger.info === "function") {
|
|
@@ -398,8 +398,8 @@ var colorize = (text, color) => {
|
|
|
398
398
|
var createBaseLogger = (prefix = "", explicitLogger) => {
|
|
399
399
|
const name = prefix ? String(prefix) : "";
|
|
400
400
|
const dispatch = (methodName, icon, message, color) => {
|
|
401
|
-
const
|
|
402
|
-
const logFn = resolveLogMethod(
|
|
401
|
+
const logger16 = resolveLogger(explicitLogger);
|
|
402
|
+
const logFn = resolveLogMethod(logger16, methodName);
|
|
403
403
|
const timestamp = colorize(`[${formatTimestamp()}]`, ANSI.gray);
|
|
404
404
|
const line = formatLine(name, icon, message);
|
|
405
405
|
const coloredLine = colorize(line, color);
|
|
@@ -753,7 +753,7 @@ var adjustAffixedElementsForExpandedScreenshot = async (page, options = {}) => {
|
|
|
753
753
|
if (safeTargetHeight <= viewportHeight + 1) {
|
|
754
754
|
return 0;
|
|
755
755
|
}
|
|
756
|
-
const
|
|
756
|
+
const hasOwn = (source, key) => Object.prototype.hasOwnProperty.call(source, key);
|
|
757
757
|
const isVisible = (el, style, rect) => {
|
|
758
758
|
if (!el || !style || !rect) return false;
|
|
759
759
|
if (style.display === "none" || style.visibility === "hidden" || style.visibility === "collapse") {
|
|
@@ -793,7 +793,7 @@ var adjustAffixedElementsForExpandedScreenshot = async (page, options = {}) => {
|
|
|
793
793
|
return true;
|
|
794
794
|
});
|
|
795
795
|
topLevelCandidates.forEach(({ el, position, edge }) => {
|
|
796
|
-
if (!
|
|
796
|
+
if (!hasOwn(el.dataset, "pkAffixedAdjusted")) {
|
|
797
797
|
el.dataset.pkAffixedAdjusted = "1";
|
|
798
798
|
el.dataset.pkOrigPosition = el.style.getPropertyValue("position") || "";
|
|
799
799
|
el.dataset.pkOrigPositionPriority = el.style.getPropertyPriority("position") || "";
|
|
@@ -824,7 +824,7 @@ var adjustAffixedElementsForExpandedScreenshot = async (page, options = {}) => {
|
|
|
824
824
|
};
|
|
825
825
|
var restoreAffixedElementsForExpandedScreenshot = async (page) => {
|
|
826
826
|
await page.evaluate((className) => {
|
|
827
|
-
const
|
|
827
|
+
const hasOwn = (source, key) => Object.prototype.hasOwnProperty.call(source, key);
|
|
828
828
|
const expansionKeys = [
|
|
829
829
|
"pkOrigOverflow",
|
|
830
830
|
"pkOrigHeight",
|
|
@@ -832,28 +832,28 @@ var restoreAffixedElementsForExpandedScreenshot = async (page) => {
|
|
|
832
832
|
"pkOrigMaxHeight"
|
|
833
833
|
];
|
|
834
834
|
document.querySelectorAll('[data-pk-affixed-adjusted="1"]').forEach((el) => {
|
|
835
|
-
if (
|
|
835
|
+
if (hasOwn(el.dataset, "pkOrigPosition")) {
|
|
836
836
|
el.style.setProperty("position", el.dataset.pkOrigPosition || "", el.dataset.pkOrigPositionPriority || "");
|
|
837
837
|
delete el.dataset.pkOrigPosition;
|
|
838
838
|
delete el.dataset.pkOrigPositionPriority;
|
|
839
839
|
}
|
|
840
|
-
if (
|
|
840
|
+
if (hasOwn(el.dataset, "pkOrigTop")) {
|
|
841
841
|
el.style.setProperty("top", el.dataset.pkOrigTop || "", el.dataset.pkOrigTopPriority || "");
|
|
842
842
|
delete el.dataset.pkOrigTop;
|
|
843
843
|
delete el.dataset.pkOrigTopPriority;
|
|
844
844
|
}
|
|
845
|
-
if (
|
|
845
|
+
if (hasOwn(el.dataset, "pkOrigBottom")) {
|
|
846
846
|
el.style.setProperty("bottom", el.dataset.pkOrigBottom || "", el.dataset.pkOrigBottomPriority || "");
|
|
847
847
|
delete el.dataset.pkOrigBottom;
|
|
848
848
|
delete el.dataset.pkOrigBottomPriority;
|
|
849
849
|
}
|
|
850
|
-
if (
|
|
850
|
+
if (hasOwn(el.dataset, "pkOrigTranslate")) {
|
|
851
851
|
el.style.setProperty("translate", el.dataset.pkOrigTranslate || "", el.dataset.pkOrigTranslatePriority || "");
|
|
852
852
|
delete el.dataset.pkOrigTranslate;
|
|
853
853
|
delete el.dataset.pkOrigTranslatePriority;
|
|
854
854
|
}
|
|
855
855
|
delete el.dataset.pkAffixedAdjusted;
|
|
856
|
-
const stillExpanded = expansionKeys.some((key) =>
|
|
856
|
+
const stillExpanded = expansionKeys.some((key) => hasOwn(el.dataset, key));
|
|
857
857
|
if (!stillExpanded) {
|
|
858
858
|
el.classList.remove(className);
|
|
859
859
|
}
|
|
@@ -896,7 +896,7 @@ var prepareExpandedFullPageScreenshot = async (page, options = {}) => {
|
|
|
896
896
|
viewportResized
|
|
897
897
|
};
|
|
898
898
|
};
|
|
899
|
-
var restoreExpandedFullPageScreenshot = async (page,
|
|
899
|
+
var restoreExpandedFullPageScreenshot = async (page, state = {}) => {
|
|
900
900
|
await page.evaluate((className) => {
|
|
901
901
|
const targets = new Set([
|
|
902
902
|
...document.querySelectorAll(`.${className}`),
|
|
@@ -920,8 +920,8 @@ var restoreExpandedFullPageScreenshot = async (page, state2 = {}) => {
|
|
|
920
920
|
el.classList.remove(className);
|
|
921
921
|
});
|
|
922
922
|
}, EXPANDED_SCROLLABLE_CLASS);
|
|
923
|
-
if (
|
|
924
|
-
await page.setViewportSize(
|
|
923
|
+
if (state?.originalViewport && state?.viewportResized) {
|
|
924
|
+
await page.setViewportSize(state.originalViewport);
|
|
925
925
|
}
|
|
926
926
|
};
|
|
927
927
|
var capturePageScreenshot = async (page, options = {}) => {
|
|
@@ -978,21 +978,21 @@ var capturePageScreenshot = async (page, options = {}) => {
|
|
|
978
978
|
}
|
|
979
979
|
};
|
|
980
980
|
var captureExpandedFullPageScreenshot = async (page, options = {}) => {
|
|
981
|
-
const
|
|
981
|
+
const state = await prepareExpandedFullPageScreenshot(page, options);
|
|
982
982
|
try {
|
|
983
983
|
return await capturePageScreenshot(page, {
|
|
984
984
|
fullPage: true,
|
|
985
985
|
type: options.type || "png",
|
|
986
986
|
quality: options.quality,
|
|
987
987
|
timeout: options.timeout,
|
|
988
|
-
maxClipHeight:
|
|
988
|
+
maxClipHeight: state.targetHeight
|
|
989
989
|
});
|
|
990
990
|
} finally {
|
|
991
991
|
await restoreAffixedElementsForExpandedScreenshot(page).catch((error) => {
|
|
992
992
|
logger.warning(`\u79FB\u52A8\u7AEF\u5438\u9644\u5143\u7D20\u6062\u590D\u5931\u8D25: ${error?.message || error}`);
|
|
993
993
|
});
|
|
994
994
|
if (options.restore) {
|
|
995
|
-
await restoreExpandedFullPageScreenshot(page,
|
|
995
|
+
await restoreExpandedFullPageScreenshot(page, state);
|
|
996
996
|
}
|
|
997
997
|
}
|
|
998
998
|
};
|
|
@@ -1910,8 +1910,8 @@ var normalizeBrowserProfile = (value) => {
|
|
|
1910
1910
|
payload: buildBrowserProfilePayload(core, observed)
|
|
1911
1911
|
};
|
|
1912
1912
|
};
|
|
1913
|
-
var rememberRuntimeState = (
|
|
1914
|
-
rememberedRuntimeState = deepClone(
|
|
1913
|
+
var rememberRuntimeState = (state) => {
|
|
1914
|
+
rememberedRuntimeState = deepClone(state);
|
|
1915
1915
|
return rememberedRuntimeState;
|
|
1916
1916
|
};
|
|
1917
1917
|
var normalizeRuntimeState = (source = {}, actor = "") => {
|
|
@@ -1970,7 +1970,7 @@ var RuntimeEnv = {
|
|
|
1970
1970
|
} else {
|
|
1971
1971
|
delete normalizedRuntime.browser_profile;
|
|
1972
1972
|
}
|
|
1973
|
-
const
|
|
1973
|
+
const state = {
|
|
1974
1974
|
actor: resolvedActor,
|
|
1975
1975
|
device,
|
|
1976
1976
|
runtime: normalizedRuntime,
|
|
@@ -1984,73 +1984,73 @@ var RuntimeEnv = {
|
|
|
1984
1984
|
browserProfileCore: browserProfile.core,
|
|
1985
1985
|
browserProfileObserved: browserProfile.observed
|
|
1986
1986
|
};
|
|
1987
|
-
rememberRuntimeState(
|
|
1988
|
-
return
|
|
1987
|
+
rememberRuntimeState(state);
|
|
1988
|
+
return state;
|
|
1989
1989
|
},
|
|
1990
1990
|
// buildEnvPatch 只构造允许回写到后端 env 的字段集合。
|
|
1991
1991
|
buildEnvPatch(source = {}, actor = "") {
|
|
1992
|
-
const
|
|
1993
|
-
const browserProfile = buildBrowserProfilePayload(
|
|
1992
|
+
const state = normalizeRuntimeState(source, actor);
|
|
1993
|
+
const browserProfile = buildBrowserProfilePayload(state.browserProfileCore, state.browserProfileObserved);
|
|
1994
1994
|
const envPatch = {
|
|
1995
|
-
...Array.isArray(
|
|
1996
|
-
...Object.keys(
|
|
1997
|
-
...Object.keys(
|
|
1995
|
+
...Array.isArray(state.cookies) && state.cookies.length > 0 ? { cookies: state.cookies } : {},
|
|
1996
|
+
...Object.keys(state.localStorage || {}).length > 0 ? { local_storage: state.localStorage } : {},
|
|
1997
|
+
...Object.keys(state.sessionStorage || {}).length > 0 ? { session_storage: state.sessionStorage } : {},
|
|
1998
1998
|
...Object.keys(browserProfile).length > 0 ? { browser_profile: browserProfile } : {}
|
|
1999
1999
|
};
|
|
2000
2000
|
return Object.keys(envPatch).length > 0 ? envPatch : null;
|
|
2001
2001
|
},
|
|
2002
2002
|
// hasLoginState 只判断 runtime 是否存在有效载荷,不再区分具体字段来源。
|
|
2003
2003
|
hasLoginState(source = {}, actor = "") {
|
|
2004
|
-
const
|
|
2005
|
-
return isPlainObject(
|
|
2004
|
+
const state = normalizeRuntimeState(source, actor);
|
|
2005
|
+
return isPlainObject(state.runtime) && Object.keys(state.runtime || {}).length > 0;
|
|
2006
2006
|
},
|
|
2007
2007
|
rememberState(source = {}) {
|
|
2008
|
-
const
|
|
2009
|
-
rememberRuntimeState(
|
|
2008
|
+
const state = normalizeRuntimeState(source);
|
|
2009
|
+
rememberRuntimeState(state);
|
|
2010
2010
|
return RuntimeEnv.peekRememberedState();
|
|
2011
2011
|
},
|
|
2012
2012
|
peekRememberedState() {
|
|
2013
2013
|
return rememberedRuntimeState ? deepClone(rememberedRuntimeState) : null;
|
|
2014
2014
|
},
|
|
2015
2015
|
getBrowserProfileCore(source = {}, actor = "") {
|
|
2016
|
-
const
|
|
2017
|
-
return deepClone(
|
|
2016
|
+
const state = normalizeRuntimeState(source, actor);
|
|
2017
|
+
return deepClone(state.browserProfileCore || {});
|
|
2018
2018
|
},
|
|
2019
2019
|
setBrowserProfileCore(source = {}, core = {}, actor = "") {
|
|
2020
|
-
const
|
|
2020
|
+
const state = normalizeRuntimeState(source, actor);
|
|
2021
2021
|
const normalizedCore = normalizeBrowserProfileCore({
|
|
2022
2022
|
...core,
|
|
2023
|
-
device: normalizeKnownDevice(core?.device) ||
|
|
2023
|
+
device: normalizeKnownDevice(core?.device) || state.device
|
|
2024
2024
|
});
|
|
2025
|
-
|
|
2026
|
-
|
|
2027
|
-
if (Object.keys(
|
|
2028
|
-
|
|
2025
|
+
state.browserProfileCore = normalizedCore;
|
|
2026
|
+
state.browserProfile = buildBrowserProfilePayload(normalizedCore, state.browserProfileObserved);
|
|
2027
|
+
if (Object.keys(state.browserProfile).length > 0) {
|
|
2028
|
+
state.runtime.browser_profile = state.browserProfile;
|
|
2029
2029
|
} else {
|
|
2030
|
-
delete
|
|
2030
|
+
delete state.runtime.browser_profile;
|
|
2031
2031
|
}
|
|
2032
|
-
rememberRuntimeState(
|
|
2033
|
-
return
|
|
2032
|
+
rememberRuntimeState(state);
|
|
2033
|
+
return state;
|
|
2034
2034
|
},
|
|
2035
2035
|
// applyToPage 只负责把登录态相关字段注入页面:
|
|
2036
2036
|
// cookies / localStorage / sessionStorage。
|
|
2037
2037
|
// 指纹、时区、UA、viewport 的回放发生在 launch.js 启动阶段,不在这里做。
|
|
2038
2038
|
async applyToPage(page, source = {}, options = {}) {
|
|
2039
2039
|
if (!page) return;
|
|
2040
|
-
let
|
|
2040
|
+
let state = normalizeRuntimeState(source, options?.actor || "");
|
|
2041
2041
|
if (typeof options?.preapply === "function") {
|
|
2042
|
-
|
|
2043
|
-
rememberRuntimeState(
|
|
2042
|
+
state = await options.preapply(state) || state;
|
|
2043
|
+
rememberRuntimeState(state);
|
|
2044
2044
|
}
|
|
2045
2045
|
Object.defineProperty(page, PageRuntimeStateKey, {
|
|
2046
2046
|
configurable: true,
|
|
2047
2047
|
enumerable: false,
|
|
2048
2048
|
writable: true,
|
|
2049
|
-
value:
|
|
2049
|
+
value: state
|
|
2050
2050
|
});
|
|
2051
|
-
const localStorage =
|
|
2052
|
-
const sessionStorage =
|
|
2053
|
-
const cookies = (
|
|
2051
|
+
const localStorage = state.localStorage || {};
|
|
2052
|
+
const sessionStorage = state.sessionStorage || {};
|
|
2053
|
+
const cookies = (state.cookies || []).map((cookie) => {
|
|
2054
2054
|
const normalized = { ...cookie };
|
|
2055
2055
|
if (!normalized.path) {
|
|
2056
2056
|
normalized.path = "/";
|
|
@@ -2088,8 +2088,8 @@ var RuntimeEnv = {
|
|
|
2088
2088
|
},
|
|
2089
2089
|
// captureEnvPatch 在任务结束时采集最新环境快照,用于 pushSuccess / pushFailed 自动回写。
|
|
2090
2090
|
async captureEnvPatch(page, source = {}, options = {}) {
|
|
2091
|
-
const
|
|
2092
|
-
const baseline = RuntimeEnv.buildEnvPatch(
|
|
2091
|
+
const state = normalizeRuntimeState(source, options?.actor || "");
|
|
2092
|
+
const baseline = RuntimeEnv.buildEnvPatch(state) || {};
|
|
2093
2093
|
if (!page || typeof page.evaluate !== "function" || typeof page.context !== "function") {
|
|
2094
2094
|
return Object.keys(baseline).length > 0 ? baseline : null;
|
|
2095
2095
|
}
|
|
@@ -2108,7 +2108,7 @@ var RuntimeEnv = {
|
|
|
2108
2108
|
cookies
|
|
2109
2109
|
},
|
|
2110
2110
|
{
|
|
2111
|
-
browserProfileCore:
|
|
2111
|
+
browserProfileCore: state.browserProfileCore
|
|
2112
2112
|
}
|
|
2113
2113
|
);
|
|
2114
2114
|
return RuntimeEnv.mergeEnvPatches(baseline, capturedPatch);
|
|
@@ -2122,11 +2122,11 @@ var RuntimeEnv = {
|
|
|
2122
2122
|
var logger3 = createInternalLogger("ApifyKit");
|
|
2123
2123
|
var resolveRuntimeContext = (input) => {
|
|
2124
2124
|
const rememberedState = RuntimeEnv.peekRememberedState();
|
|
2125
|
-
const
|
|
2126
|
-
const envPatch = RuntimeEnv.buildEnvPatch(
|
|
2125
|
+
const state = rememberedState || RuntimeEnv.parseInput(input || {});
|
|
2126
|
+
const envPatch = RuntimeEnv.buildEnvPatch(state) || null;
|
|
2127
2127
|
return {
|
|
2128
|
-
actor:
|
|
2129
|
-
runtime:
|
|
2128
|
+
actor: state.actor,
|
|
2129
|
+
runtime: state.runtime,
|
|
2130
2130
|
envPatch
|
|
2131
2131
|
};
|
|
2132
2132
|
};
|
|
@@ -2485,82 +2485,8 @@ var Utils = {
|
|
|
2485
2485
|
}
|
|
2486
2486
|
};
|
|
2487
2487
|
|
|
2488
|
-
// src/
|
|
2489
|
-
var
|
|
2490
|
-
mode: Mode.Default
|
|
2491
|
-
};
|
|
2492
|
-
var normalizeStrategies = (strategies) => strategies && typeof strategies === "object" ? strategies : {};
|
|
2493
|
-
var ToolkitContext = {
|
|
2494
|
-
get mode() {
|
|
2495
|
-
return state.mode;
|
|
2496
|
-
},
|
|
2497
|
-
setMode(mode = Mode.Default) {
|
|
2498
|
-
state.mode = normalizeMode(mode, Mode.Default);
|
|
2499
|
-
return state.mode;
|
|
2500
|
-
}
|
|
2501
|
-
};
|
|
2502
|
-
var getToolkitMode = () => state.mode;
|
|
2503
|
-
var setToolkitMode = (mode = Mode.Default) => ToolkitContext.setMode(mode);
|
|
2504
|
-
var resolveModeStrategy = (strategies = {}, mode = getToolkitMode(), fallbackMode = Mode.Default) => {
|
|
2505
|
-
const normalizedStrategies = normalizeStrategies(strategies);
|
|
2506
|
-
const normalizedMode = normalizeMode(mode, fallbackMode);
|
|
2507
|
-
const strategy = normalizedStrategies[normalizedMode] ?? normalizedStrategies[fallbackMode] ?? Object.values(normalizedStrategies).find(Boolean) ?? null;
|
|
2508
|
-
return {
|
|
2509
|
-
mode: normalizedMode,
|
|
2510
|
-
strategy
|
|
2511
|
-
};
|
|
2512
|
-
};
|
|
2513
|
-
|
|
2514
|
-
// src/internals/reflect.js
|
|
2515
|
-
var normalizeStrategies2 = (strategies) => strategies && typeof strategies === "object" ? strategies : {};
|
|
2516
|
-
var collectFunctionNames = (strategies = []) => {
|
|
2517
|
-
const names = /* @__PURE__ */ new Set();
|
|
2518
|
-
for (const strategy of strategies) {
|
|
2519
|
-
if (!strategy || typeof strategy !== "object") continue;
|
|
2520
|
-
for (const name of Reflect.ownKeys(strategy)) {
|
|
2521
|
-
if (typeof name === "string" && typeof strategy[name] === "function") {
|
|
2522
|
-
names.add(name);
|
|
2523
|
-
}
|
|
2524
|
-
}
|
|
2525
|
-
}
|
|
2526
|
-
return names;
|
|
2527
|
-
};
|
|
2528
|
-
var methodDescriptor = (namespace, name, resolveTarget) => ({
|
|
2529
|
-
enumerable: true,
|
|
2530
|
-
configurable: true,
|
|
2531
|
-
writable: true,
|
|
2532
|
-
value: (...args) => {
|
|
2533
|
-
const { mode, strategy } = resolveTarget(args);
|
|
2534
|
-
const method = strategy?.[name];
|
|
2535
|
-
if (typeof method !== "function") {
|
|
2536
|
-
throw new Error(`${namespace}.${name} is not available in ${mode} mode`);
|
|
2537
|
-
}
|
|
2538
|
-
return method.apply(strategy, args);
|
|
2539
|
-
}
|
|
2540
|
-
});
|
|
2541
|
-
var withModeReflect = (namespace, strategies = {}) => {
|
|
2542
|
-
const normalizedStrategies = normalizeStrategies2(strategies);
|
|
2543
|
-
const baseStrategy = normalizedStrategies.default ?? Object.values(normalizedStrategies).find(Boolean);
|
|
2544
|
-
const names = collectFunctionNames([baseStrategy]);
|
|
2545
|
-
const descriptors = {};
|
|
2546
|
-
for (const name of names) {
|
|
2547
|
-
descriptors[name] = methodDescriptor(namespace, name, () => resolveModeStrategy(normalizedStrategies));
|
|
2548
|
-
}
|
|
2549
|
-
return Object.defineProperties({}, descriptors);
|
|
2550
|
-
};
|
|
2551
|
-
var withPageReflect = (namespace, resolveStrategy, strategies = []) => {
|
|
2552
|
-
const names = collectFunctionNames(strategies);
|
|
2553
|
-
const descriptors = {};
|
|
2554
|
-
for (const name of names) {
|
|
2555
|
-
descriptors[name] = methodDescriptor(namespace, name, ([page]) => ({
|
|
2556
|
-
mode: "page",
|
|
2557
|
-
strategy: resolveStrategy(page)
|
|
2558
|
-
}));
|
|
2559
|
-
}
|
|
2560
|
-
return Object.defineProperties({}, descriptors);
|
|
2561
|
-
};
|
|
2562
|
-
|
|
2563
|
-
// src/internals/anti-cheat/default.js
|
|
2488
|
+
// src/anti-cheat.js
|
|
2489
|
+
var logger5 = createInternalLogger("AntiCheat");
|
|
2564
2490
|
var BASE_CONFIG = Object.freeze({
|
|
2565
2491
|
locale: "zh-CN",
|
|
2566
2492
|
acceptLanguage: "zh-CN,zh;q=0.9",
|
|
@@ -2595,7 +2521,7 @@ function buildFingerprintOptions({ locale = BASE_CONFIG.locale, browserMajorVers
|
|
|
2595
2521
|
}
|
|
2596
2522
|
return options;
|
|
2597
2523
|
}
|
|
2598
|
-
var
|
|
2524
|
+
var AntiCheat = {
|
|
2599
2525
|
/**
|
|
2600
2526
|
* 获取统一的基础配置
|
|
2601
2527
|
*/
|
|
@@ -2632,47 +2558,6 @@ var DefaultAntiCheat = {
|
|
|
2632
2558
|
}
|
|
2633
2559
|
};
|
|
2634
2560
|
|
|
2635
|
-
// src/internals/anti-cheat/cloak.js
|
|
2636
|
-
var CLOAK_BASE_CONFIG = Object.freeze({
|
|
2637
|
-
locale: "",
|
|
2638
|
-
acceptLanguage: "",
|
|
2639
|
-
timezoneId: "",
|
|
2640
|
-
timezoneOffset: null,
|
|
2641
|
-
geolocation: null
|
|
2642
|
-
});
|
|
2643
|
-
var normalizeHeaders = (headers) => headers && typeof headers === "object" ? headers : {};
|
|
2644
|
-
var CloakAntiCheat = {
|
|
2645
|
-
/**
|
|
2646
|
-
* Cloak 自身会负责浏览器指纹,toolkit 在该模式下尽量不再注入额外反检测配置。
|
|
2647
|
-
*/
|
|
2648
|
-
getBaseConfig() {
|
|
2649
|
-
return { ...CLOAK_BASE_CONFIG };
|
|
2650
|
-
},
|
|
2651
|
-
getFingerprintGeneratorOptions() {
|
|
2652
|
-
return {};
|
|
2653
|
-
},
|
|
2654
|
-
getLaunchArgs() {
|
|
2655
|
-
return [];
|
|
2656
|
-
},
|
|
2657
|
-
getTlsFingerprintOptions() {
|
|
2658
|
-
return {};
|
|
2659
|
-
},
|
|
2660
|
-
applyLocaleHeaders(headers, acceptLanguage = "") {
|
|
2661
|
-
const normalizedHeaders = normalizeHeaders(headers);
|
|
2662
|
-
if (acceptLanguage && !normalizedHeaders["accept-language"]) {
|
|
2663
|
-
normalizedHeaders["accept-language"] = acceptLanguage;
|
|
2664
|
-
}
|
|
2665
|
-
return normalizedHeaders;
|
|
2666
|
-
}
|
|
2667
|
-
};
|
|
2668
|
-
|
|
2669
|
-
// src/anti-cheat.js
|
|
2670
|
-
var antiCheatStrategies = {
|
|
2671
|
-
[Mode.Default]: DefaultAntiCheat,
|
|
2672
|
-
[Mode.Cloak]: CloakAntiCheat
|
|
2673
|
-
};
|
|
2674
|
-
var AntiCheat = withModeReflect("AntiCheat", antiCheatStrategies);
|
|
2675
|
-
|
|
2676
2561
|
// src/device-input.js
|
|
2677
2562
|
var resolveDeviceFromPage = (page) => normalizeDevice(page?.[PageRuntimeStateKey]?.device);
|
|
2678
2563
|
var assertPage = (page, method) => {
|
|
@@ -3072,12 +2957,12 @@ var resolveDescriptor = (descriptor, device) => {
|
|
|
3072
2957
|
}
|
|
3073
2958
|
return resolved;
|
|
3074
2959
|
};
|
|
3075
|
-
var attachRuntimeState = (page,
|
|
2960
|
+
var attachRuntimeState = (page, state) => {
|
|
3076
2961
|
Object.defineProperty(page, PageRuntimeStateKey, {
|
|
3077
2962
|
configurable: true,
|
|
3078
2963
|
enumerable: false,
|
|
3079
2964
|
writable: true,
|
|
3080
|
-
value:
|
|
2965
|
+
value: state
|
|
3081
2966
|
});
|
|
3082
2967
|
};
|
|
3083
2968
|
var restoreRuntimeState = (page, snapshot) => {
|
|
@@ -3223,13 +3108,10 @@ var DeviceView = {
|
|
|
3223
3108
|
}
|
|
3224
3109
|
};
|
|
3225
3110
|
|
|
3226
|
-
// src/internals/humanize/index.js
|
|
3227
|
-
import delay4 from "delay";
|
|
3228
|
-
|
|
3229
3111
|
// src/internals/humanize/desktop.js
|
|
3230
3112
|
import delay2 from "delay";
|
|
3231
3113
|
import { createCursor } from "ghost-cursor-playwright";
|
|
3232
|
-
var
|
|
3114
|
+
var logger6 = createInternalLogger("Humanize");
|
|
3233
3115
|
var $CursorWeakMap = /* @__PURE__ */ new WeakMap();
|
|
3234
3116
|
function $GetCursor(page) {
|
|
3235
3117
|
const cursor = $CursorWeakMap.get(page);
|
|
@@ -3257,13 +3139,13 @@ var Humanize = {
|
|
|
3257
3139
|
*/
|
|
3258
3140
|
async initializeCursor(page) {
|
|
3259
3141
|
if ($CursorWeakMap.has(page)) {
|
|
3260
|
-
|
|
3142
|
+
logger6.debug("initializeCursor: cursor already exists, skipping");
|
|
3261
3143
|
return;
|
|
3262
3144
|
}
|
|
3263
|
-
|
|
3145
|
+
logger6.start("initializeCursor", "creating cursor");
|
|
3264
3146
|
const cursor = await createCursor(page);
|
|
3265
3147
|
$CursorWeakMap.set(page, cursor);
|
|
3266
|
-
|
|
3148
|
+
logger6.success("initializeCursor", "cursor initialized");
|
|
3267
3149
|
},
|
|
3268
3150
|
/**
|
|
3269
3151
|
* 人类化鼠标移动 - 使用 ghost-cursor 移动到指定位置或元素
|
|
@@ -3273,17 +3155,17 @@ var Humanize = {
|
|
|
3273
3155
|
*/
|
|
3274
3156
|
async humanMove(page, target) {
|
|
3275
3157
|
const cursor = $GetCursor(page);
|
|
3276
|
-
|
|
3158
|
+
logger6.start("humanMove", `target=${typeof target === "string" ? target : "element/coords"}`);
|
|
3277
3159
|
try {
|
|
3278
3160
|
if (typeof target === "string") {
|
|
3279
3161
|
const element = await page.$(target);
|
|
3280
3162
|
if (!element) {
|
|
3281
|
-
|
|
3163
|
+
logger6.warn(`humanMove: \u5143\u7D20\u4E0D\u5B58\u5728 ${target}`);
|
|
3282
3164
|
return false;
|
|
3283
3165
|
}
|
|
3284
3166
|
const box = await element.boundingBox();
|
|
3285
3167
|
if (!box) {
|
|
3286
|
-
|
|
3168
|
+
logger6.warn(`humanMove: \u65E0\u6CD5\u83B7\u53D6\u4F4D\u7F6E ${target}`);
|
|
3287
3169
|
return false;
|
|
3288
3170
|
}
|
|
3289
3171
|
const x = box.x + box.width / 2 + (Math.random() - 0.5) * box.width * 0.2;
|
|
@@ -3299,10 +3181,10 @@ var Humanize = {
|
|
|
3299
3181
|
await cursor.actions.move({ x, y });
|
|
3300
3182
|
}
|
|
3301
3183
|
}
|
|
3302
|
-
|
|
3184
|
+
logger6.success("humanMove");
|
|
3303
3185
|
return true;
|
|
3304
3186
|
} catch (error) {
|
|
3305
|
-
|
|
3187
|
+
logger6.fail("humanMove", error);
|
|
3306
3188
|
throw error;
|
|
3307
3189
|
}
|
|
3308
3190
|
},
|
|
@@ -3326,12 +3208,12 @@ var Humanize = {
|
|
|
3326
3208
|
maxDurationMs = maxSteps * 220 + 800
|
|
3327
3209
|
} = options;
|
|
3328
3210
|
const targetDesc = typeof target === "string" ? target : "ElementHandle";
|
|
3329
|
-
|
|
3211
|
+
logger6.start("humanScroll", `target=${targetDesc}`);
|
|
3330
3212
|
let element;
|
|
3331
3213
|
if (typeof target === "string") {
|
|
3332
3214
|
element = await page.$(target);
|
|
3333
3215
|
if (!element) {
|
|
3334
|
-
|
|
3216
|
+
logger6.warn(`humanScroll | \u5143\u7D20\u672A\u627E\u5230: ${target}`);
|
|
3335
3217
|
return { element: null, didScroll: false };
|
|
3336
3218
|
}
|
|
3337
3219
|
} else {
|
|
@@ -3406,26 +3288,26 @@ var Humanize = {
|
|
|
3406
3288
|
try {
|
|
3407
3289
|
for (let i = 0; i < maxSteps; i++) {
|
|
3408
3290
|
if (Date.now() - startTime > maxDurationMs) {
|
|
3409
|
-
|
|
3291
|
+
logger6.warn(`humanScroll | \u8D85\u65F6\u4FDD\u62A4\u89E6\u53D1 (${maxDurationMs}ms)`);
|
|
3410
3292
|
return { element, didScroll };
|
|
3411
3293
|
}
|
|
3412
3294
|
const status = await checkVisibility();
|
|
3413
3295
|
if (status.code === "VISIBLE") {
|
|
3414
3296
|
if (status.isFixed) {
|
|
3415
|
-
|
|
3297
|
+
logger6.info("humanScroll | fixed \u5BB9\u5668\u5185\uFF0C\u8DF3\u8FC7\u6EDA\u52A8");
|
|
3416
3298
|
} else {
|
|
3417
|
-
|
|
3299
|
+
logger6.debug("humanScroll | \u5143\u7D20\u53EF\u89C1\u4E14\u65E0\u906E\u6321");
|
|
3418
3300
|
}
|
|
3419
|
-
|
|
3301
|
+
logger6.success("humanScroll", didScroll ? "\u5DF2\u6EDA\u52A8" : "\u65E0\u9700\u6EDA\u52A8");
|
|
3420
3302
|
return { element, didScroll };
|
|
3421
3303
|
}
|
|
3422
|
-
|
|
3304
|
+
logger6.debug(`humanScroll | \u6B65\u9AA4 ${i + 1}/${maxSteps}: ${status.reason} ${status.direction ? `(${status.direction})` : ""}`);
|
|
3423
3305
|
if (status.code === "OBSTRUCTED" && status.obstruction) {
|
|
3424
|
-
|
|
3306
|
+
logger6.debug(`humanScroll | \u88AB\u4EE5\u4E0B\u5143\u7D20\u906E\u6321 <${status.obstruction.tag} id="${status.obstruction.id}">`);
|
|
3425
3307
|
}
|
|
3426
3308
|
const scrollRect = await getScrollableRect2();
|
|
3427
3309
|
if (!scrollRect && status.isFixed) {
|
|
3428
|
-
|
|
3310
|
+
logger6.warn("humanScroll | fixed \u5BB9\u5668\u5185\u4E14\u65E0\u53EF\u6EDA\u52A8\u7956\u5148\uFF0C\u8DF3\u8FC7\u6EDA\u52A8");
|
|
3429
3311
|
return { element, didScroll };
|
|
3430
3312
|
}
|
|
3431
3313
|
const stepMin = scrollRect ? Math.min(minStep, Math.max(60, scrollRect.height * 0.4)) : minStep;
|
|
@@ -3461,10 +3343,10 @@ var Humanize = {
|
|
|
3461
3343
|
didScroll = true;
|
|
3462
3344
|
await delay2(this.jitterMs(20 + Math.random() * 40, 0.2));
|
|
3463
3345
|
}
|
|
3464
|
-
|
|
3346
|
+
logger6.warn(`humanScroll | \u5728 ${maxSteps} \u6B65\u540E\u65E0\u6CD5\u786E\u4FDD\u53EF\u89C1\u6027`);
|
|
3465
3347
|
return { element, didScroll };
|
|
3466
3348
|
} catch (error) {
|
|
3467
|
-
|
|
3349
|
+
logger6.fail("humanScroll", error);
|
|
3468
3350
|
throw error;
|
|
3469
3351
|
}
|
|
3470
3352
|
},
|
|
@@ -3482,7 +3364,7 @@ var Humanize = {
|
|
|
3482
3364
|
const cursor = $GetCursor(page);
|
|
3483
3365
|
const { reactionDelay = 250, throwOnMissing = true, scrollIfNeeded = true, restore = false } = options;
|
|
3484
3366
|
const targetDesc = target == null ? "Current Position" : typeof target === "string" ? target : "ElementHandle";
|
|
3485
|
-
|
|
3367
|
+
logger6.start("humanClick", `target=${targetDesc}`);
|
|
3486
3368
|
const restoreOnce = async () => {
|
|
3487
3369
|
if (restoreOnce.restored) return;
|
|
3488
3370
|
restoreOnce.restored = true;
|
|
@@ -3491,14 +3373,14 @@ var Humanize = {
|
|
|
3491
3373
|
await delay2(this.jitterMs(1e3));
|
|
3492
3374
|
await restoreOnce.do();
|
|
3493
3375
|
} catch (restoreError) {
|
|
3494
|
-
|
|
3376
|
+
logger6.warn(`humanClick: \u6062\u590D\u6EDA\u52A8\u4F4D\u7F6E\u5931\u8D25: ${restoreError.message}`);
|
|
3495
3377
|
}
|
|
3496
3378
|
};
|
|
3497
3379
|
try {
|
|
3498
3380
|
if (target == null) {
|
|
3499
3381
|
await delay2(this.jitterMs(reactionDelay, 0.4));
|
|
3500
3382
|
await cursor.actions.click();
|
|
3501
|
-
|
|
3383
|
+
logger6.success("humanClick", "Clicked current position");
|
|
3502
3384
|
return true;
|
|
3503
3385
|
}
|
|
3504
3386
|
let element;
|
|
@@ -3508,7 +3390,7 @@ var Humanize = {
|
|
|
3508
3390
|
if (throwOnMissing) {
|
|
3509
3391
|
throw new Error(`\u627E\u4E0D\u5230\u5143\u7D20 ${target}`);
|
|
3510
3392
|
}
|
|
3511
|
-
|
|
3393
|
+
logger6.warn(`humanClick: \u5143\u7D20\u4E0D\u5B58\u5728\uFF0C\u8DF3\u8FC7\u70B9\u51FB ${target}`);
|
|
3512
3394
|
return false;
|
|
3513
3395
|
}
|
|
3514
3396
|
} else {
|
|
@@ -3524,7 +3406,7 @@ var Humanize = {
|
|
|
3524
3406
|
if (throwOnMissing) {
|
|
3525
3407
|
throw new Error("\u65E0\u6CD5\u83B7\u53D6\u5143\u7D20\u4F4D\u7F6E");
|
|
3526
3408
|
}
|
|
3527
|
-
|
|
3409
|
+
logger6.warn("humanClick: \u65E0\u6CD5\u83B7\u53D6\u4F4D\u7F6E\uFF0C\u8DF3\u8FC7\u70B9\u51FB");
|
|
3528
3410
|
return false;
|
|
3529
3411
|
}
|
|
3530
3412
|
const x = box.x + box.width / 2 + (Math.random() - 0.5) * box.width * 0.3;
|
|
@@ -3533,11 +3415,11 @@ var Humanize = {
|
|
|
3533
3415
|
await delay2(this.jitterMs(reactionDelay, 0.4));
|
|
3534
3416
|
await cursor.actions.click();
|
|
3535
3417
|
await restoreOnce();
|
|
3536
|
-
|
|
3418
|
+
logger6.success("humanClick");
|
|
3537
3419
|
return true;
|
|
3538
3420
|
} catch (error) {
|
|
3539
3421
|
await restoreOnce();
|
|
3540
|
-
|
|
3422
|
+
logger6.fail("humanClick", error);
|
|
3541
3423
|
throw error;
|
|
3542
3424
|
}
|
|
3543
3425
|
},
|
|
@@ -3548,9 +3430,9 @@ var Humanize = {
|
|
|
3548
3430
|
*/
|
|
3549
3431
|
async randomSleep(baseMs, jitterPercent = 0.3) {
|
|
3550
3432
|
const ms = this.jitterMs(baseMs, jitterPercent);
|
|
3551
|
-
|
|
3433
|
+
logger6.start("randomSleep", `base=${baseMs}, actual=${ms}ms`);
|
|
3552
3434
|
await delay2(ms);
|
|
3553
|
-
|
|
3435
|
+
logger6.success("randomSleep");
|
|
3554
3436
|
},
|
|
3555
3437
|
/**
|
|
3556
3438
|
* 模拟人类"注视"或"阅读"行为:鼠标在页面上随机微动
|
|
@@ -3560,7 +3442,7 @@ var Humanize = {
|
|
|
3560
3442
|
async simulateGaze(page, baseDurationMs = 2500) {
|
|
3561
3443
|
const cursor = $GetCursor(page);
|
|
3562
3444
|
const durationMs = this.jitterMs(baseDurationMs, 0.4);
|
|
3563
|
-
|
|
3445
|
+
logger6.start("simulateGaze", `duration=${durationMs}ms`);
|
|
3564
3446
|
const startTime = Date.now();
|
|
3565
3447
|
const viewportSize = page.viewportSize() || { width: 1920, height: 1080 };
|
|
3566
3448
|
while (Date.now() - startTime < durationMs) {
|
|
@@ -3569,7 +3451,7 @@ var Humanize = {
|
|
|
3569
3451
|
await cursor.actions.move({ x, y });
|
|
3570
3452
|
await delay2(this.jitterMs(600, 0.5));
|
|
3571
3453
|
}
|
|
3572
|
-
|
|
3454
|
+
logger6.success("simulateGaze");
|
|
3573
3455
|
},
|
|
3574
3456
|
/**
|
|
3575
3457
|
* 人类化输入 - 带节奏变化(快-慢-停顿-偶尔加速)
|
|
@@ -3582,7 +3464,7 @@ var Humanize = {
|
|
|
3582
3464
|
* @param {number} [options.pauseBase=800] - 停顿时长基础值 (ms),实际 ±50% 抖动
|
|
3583
3465
|
*/
|
|
3584
3466
|
async humanType(page, selector, text, options = {}) {
|
|
3585
|
-
|
|
3467
|
+
logger6.start("humanType", `selector=${selector}, textLen=${text.length}`);
|
|
3586
3468
|
const {
|
|
3587
3469
|
baseDelay = 180,
|
|
3588
3470
|
pauseProbability = 0.08,
|
|
@@ -3606,13 +3488,13 @@ var Humanize = {
|
|
|
3606
3488
|
await delay2(charDelay);
|
|
3607
3489
|
if (Math.random() < pauseProbability && i < text.length - 1) {
|
|
3608
3490
|
const pauseTime = this.jitterMs(pauseBase, 0.5);
|
|
3609
|
-
|
|
3491
|
+
logger6.debug(`\u505C\u987F ${pauseTime}ms...`);
|
|
3610
3492
|
await delay2(pauseTime);
|
|
3611
3493
|
}
|
|
3612
3494
|
}
|
|
3613
|
-
|
|
3495
|
+
logger6.success("humanType");
|
|
3614
3496
|
} catch (error) {
|
|
3615
|
-
|
|
3497
|
+
logger6.fail("humanType", error);
|
|
3616
3498
|
throw error;
|
|
3617
3499
|
}
|
|
3618
3500
|
},
|
|
@@ -3636,7 +3518,7 @@ var Humanize = {
|
|
|
3636
3518
|
keyboardOptions = {}
|
|
3637
3519
|
} = pressOptions || {};
|
|
3638
3520
|
const targetDesc = hasTarget ? typeof targetOrKey === "string" ? targetOrKey : "ElementHandle" : "current focus";
|
|
3639
|
-
|
|
3521
|
+
logger6.start("humanPress", `key=${key}, target=${targetDesc}`);
|
|
3640
3522
|
try {
|
|
3641
3523
|
if (hasTarget) {
|
|
3642
3524
|
await this.humanClick(page, targetOrKey, { reactionDelay: focusDelay, scrollIfNeeded, throwOnMissing });
|
|
@@ -3646,10 +3528,10 @@ var Humanize = {
|
|
|
3646
3528
|
...keyboardOptions,
|
|
3647
3529
|
delay: this.jitterMs(holdDelay, 0.5)
|
|
3648
3530
|
});
|
|
3649
|
-
|
|
3531
|
+
logger6.success("humanPress");
|
|
3650
3532
|
return true;
|
|
3651
3533
|
} catch (error) {
|
|
3652
|
-
|
|
3534
|
+
logger6.fail("humanPress", error);
|
|
3653
3535
|
throw error;
|
|
3654
3536
|
}
|
|
3655
3537
|
},
|
|
@@ -3659,22 +3541,22 @@ var Humanize = {
|
|
|
3659
3541
|
* @param {string} selector - 输入框选择器
|
|
3660
3542
|
*/
|
|
3661
3543
|
async humanClear(page, selector) {
|
|
3662
|
-
|
|
3544
|
+
logger6.start("humanClear", `selector=${selector}`);
|
|
3663
3545
|
try {
|
|
3664
3546
|
const locator = page.locator(selector);
|
|
3665
3547
|
await locator.click();
|
|
3666
3548
|
await delay2(this.jitterMs(200, 0.4));
|
|
3667
3549
|
const currentValue = await locator.inputValue();
|
|
3668
3550
|
if (!currentValue || currentValue.length === 0) {
|
|
3669
|
-
|
|
3551
|
+
logger6.success("humanClear", "already empty");
|
|
3670
3552
|
return;
|
|
3671
3553
|
}
|
|
3672
3554
|
await page.keyboard.press("Meta+A");
|
|
3673
3555
|
await delay2(this.jitterMs(100, 0.4));
|
|
3674
3556
|
await page.keyboard.press("Backspace");
|
|
3675
|
-
|
|
3557
|
+
logger6.success("humanClear");
|
|
3676
3558
|
} catch (error) {
|
|
3677
|
-
|
|
3559
|
+
logger6.fail("humanClear", error);
|
|
3678
3560
|
throw error;
|
|
3679
3561
|
}
|
|
3680
3562
|
},
|
|
@@ -3686,7 +3568,7 @@ var Humanize = {
|
|
|
3686
3568
|
async warmUpBrowsing(page, baseDuration = 3500) {
|
|
3687
3569
|
const cursor = $GetCursor(page);
|
|
3688
3570
|
const durationMs = this.jitterMs(baseDuration, 0.4);
|
|
3689
|
-
|
|
3571
|
+
logger6.start("warmUpBrowsing", `duration=${durationMs}ms`);
|
|
3690
3572
|
const startTime = Date.now();
|
|
3691
3573
|
const viewportSize = page.viewportSize() || { width: 1920, height: 1080 };
|
|
3692
3574
|
try {
|
|
@@ -3705,9 +3587,9 @@ var Humanize = {
|
|
|
3705
3587
|
await delay2(this.jitterMs(800, 0.5));
|
|
3706
3588
|
}
|
|
3707
3589
|
}
|
|
3708
|
-
|
|
3590
|
+
logger6.success("warmUpBrowsing");
|
|
3709
3591
|
} catch (error) {
|
|
3710
|
-
|
|
3592
|
+
logger6.fail("warmUpBrowsing", error);
|
|
3711
3593
|
throw error;
|
|
3712
3594
|
}
|
|
3713
3595
|
},
|
|
@@ -3721,7 +3603,7 @@ var Humanize = {
|
|
|
3721
3603
|
async naturalScroll(page, direction = "down", distance = 300, baseSteps = 5) {
|
|
3722
3604
|
const steps = Math.max(3, baseSteps + Math.floor(Math.random() * 3) - 1);
|
|
3723
3605
|
const actualDistance = this.jitterMs(distance, 0.15);
|
|
3724
|
-
|
|
3606
|
+
logger6.start("naturalScroll", `dir=${direction}, dist=${actualDistance}, steps=${steps}`);
|
|
3725
3607
|
const sign = direction === "down" ? 1 : -1;
|
|
3726
3608
|
const stepDistance = actualDistance / steps;
|
|
3727
3609
|
try {
|
|
@@ -3733,9 +3615,9 @@ var Humanize = {
|
|
|
3733
3615
|
const baseDelay = 60 + i * 25;
|
|
3734
3616
|
await delay2(this.jitterMs(baseDelay, 0.3));
|
|
3735
3617
|
}
|
|
3736
|
-
|
|
3618
|
+
logger6.success("naturalScroll");
|
|
3737
3619
|
} catch (error) {
|
|
3738
|
-
|
|
3620
|
+
logger6.fail("naturalScroll", error);
|
|
3739
3621
|
throw error;
|
|
3740
3622
|
}
|
|
3741
3623
|
}
|
|
@@ -3764,7 +3646,7 @@ var resolveElement = async (page, target, { throwOnMissing = true } = {}) => {
|
|
|
3764
3646
|
var waitJitter = (base, jitterPercent = 0.3) => delay3(jitterMs(base, jitterPercent));
|
|
3765
3647
|
|
|
3766
3648
|
// src/internals/humanize/mobile.js
|
|
3767
|
-
var
|
|
3649
|
+
var logger7 = createInternalLogger("Humanize.Mobile");
|
|
3768
3650
|
var initializedPages = /* @__PURE__ */ new WeakSet();
|
|
3769
3651
|
var DEFAULT_TAP_TIMEOUT_MS = 2500;
|
|
3770
3652
|
var DEFAULT_MOUSE_TAP_FALLBACK_TIMEOUT_MS = 1200;
|
|
@@ -4134,7 +4016,7 @@ var restoreWindowFromSnapshot = async (page, before, after) => {
|
|
|
4134
4016
|
return;
|
|
4135
4017
|
}
|
|
4136
4018
|
await page.evaluate(
|
|
4137
|
-
(
|
|
4019
|
+
(state) => window.scrollTo(state.x, state.y),
|
|
4138
4020
|
{ x: Number(before.scrollX || 0), y: Number(before.scrollY || 0) }
|
|
4139
4021
|
).catch(() => {
|
|
4140
4022
|
});
|
|
@@ -4221,7 +4103,7 @@ var dispatchTouchSwipe = async (page, deltaY, options = {}) => {
|
|
|
4221
4103
|
}
|
|
4222
4104
|
return true;
|
|
4223
4105
|
} catch (error) {
|
|
4224
|
-
|
|
4106
|
+
logger7.debug(`touch swipe fallback: ${error?.message || error}`);
|
|
4225
4107
|
try {
|
|
4226
4108
|
await page.evaluate((amount) => window.scrollBy(0, amount), deltaY);
|
|
4227
4109
|
await waitJitter(120, 0.35);
|
|
@@ -4255,7 +4137,7 @@ var tapPoint = async (page, point, options = {}) => {
|
|
|
4255
4137
|
);
|
|
4256
4138
|
return { method: "touchscreen" };
|
|
4257
4139
|
} catch (error) {
|
|
4258
|
-
|
|
4140
|
+
logger7.warn(`tapPoint | touchscreen.tap \u5931\u8D25\u6216\u8D85\u65F6\uFF0C\u5C1D\u8BD5\u9F20\u6807\u515C\u5E95: ${error?.message || error}`);
|
|
4259
4141
|
if (!allowMouseFallback) throw error;
|
|
4260
4142
|
}
|
|
4261
4143
|
}
|
|
@@ -4271,10 +4153,10 @@ var MobileHumanize = {
|
|
|
4271
4153
|
async initializeCursor(page) {
|
|
4272
4154
|
if (initializedPages.has(page)) return;
|
|
4273
4155
|
initializedPages.add(page);
|
|
4274
|
-
|
|
4156
|
+
logger7.debug("initializeCursor: mobile mode uses touch gestures, cursor init skipped");
|
|
4275
4157
|
},
|
|
4276
4158
|
async humanMove(page, target) {
|
|
4277
|
-
|
|
4159
|
+
logger7.debug(`humanMove: mobile no-op target=${typeof target === "string" ? target : "element/coords"}`);
|
|
4278
4160
|
if (typeof target === "string" || target && typeof target.boundingBox === "function") {
|
|
4279
4161
|
const element = await resolveElement(page, target, { throwOnMissing: false });
|
|
4280
4162
|
if (!element) {
|
|
@@ -4293,10 +4175,10 @@ var MobileHumanize = {
|
|
|
4293
4175
|
throwOnMissing = false
|
|
4294
4176
|
} = options;
|
|
4295
4177
|
const targetDesc = describeTarget(target);
|
|
4296
|
-
|
|
4178
|
+
logger7.start("humanScroll", `target=${targetDesc}`);
|
|
4297
4179
|
const element = await resolveElement(page, target, { throwOnMissing });
|
|
4298
4180
|
if (!element) {
|
|
4299
|
-
|
|
4181
|
+
logger7.warn(`humanScroll | \u5143\u7D20\u672A\u627E\u5230: ${targetDesc}`);
|
|
4300
4182
|
return { element: null, didScroll: false, restore: null };
|
|
4301
4183
|
}
|
|
4302
4184
|
const startTime = Date.now();
|
|
@@ -4305,42 +4187,42 @@ var MobileHumanize = {
|
|
|
4305
4187
|
const status = await checkElementVisibility(element);
|
|
4306
4188
|
if (status.code === "VISIBLE") {
|
|
4307
4189
|
if (status.isFixed) {
|
|
4308
|
-
|
|
4190
|
+
logger7.info("humanScroll | fixed/sticky \u5BB9\u5668\u5185\uFF0C\u8DF3\u8FC7\u6EDA\u52A8");
|
|
4309
4191
|
} else {
|
|
4310
|
-
|
|
4192
|
+
logger7.debug("humanScroll | \u5143\u7D20\u53EF\u89C1\u4E14\u65E0\u906E\u6321");
|
|
4311
4193
|
}
|
|
4312
|
-
|
|
4194
|
+
logger7.success("humanScroll", didScroll ? "\u5DF2\u6EDA\u52A8" : "\u65E0\u9700\u6EDA\u52A8");
|
|
4313
4195
|
return { element, didScroll, restore: null };
|
|
4314
4196
|
}
|
|
4315
4197
|
if (status.code === "ZERO_DIMENSIONS" || status.code === "NOT_INTERACTABLE") {
|
|
4316
|
-
|
|
4198
|
+
logger7.warn(`humanScroll | \u5143\u7D20\u4E0D\u53EF\u6EDA\u52A8\u81F3\u53EF\u70B9\u51FB\u72B6\u6001: ${status.reason || status.code}`);
|
|
4317
4199
|
return { element, didScroll, restore: null };
|
|
4318
4200
|
}
|
|
4319
4201
|
const scrollRect = await getScrollableRect(element);
|
|
4320
4202
|
if (!scrollRect && status.isFixed && status.code === "OUT_OF_VIEWPORT") {
|
|
4321
|
-
|
|
4203
|
+
logger7.warn(`humanScroll | fixed/sticky \u76EE\u6807\u4E0D\u5728\u89C6\u53E3\u5185\uFF0C\u9875\u9762\u6EDA\u52A8\u65E0\u6CD5\u6539\u53D8\u5176\u4F4D\u7F6E (direction=${status.direction || "unknown"})`);
|
|
4322
4204
|
return { element, didScroll, restore: null, unscrollable: true };
|
|
4323
4205
|
}
|
|
4324
4206
|
if (!scrollRect && status.isFixed && status.code === "OBSTRUCTED") {
|
|
4325
|
-
|
|
4207
|
+
logger7.warn(`humanScroll | fixed/sticky \u76EE\u6807\u88AB\u906E\u6321\uFF0C\u6EDA\u52A8\u65E0\u6CD5\u89E3\u9664 (${status.obstruction?.tag || "unknown"})`);
|
|
4326
4208
|
return { element, didScroll, restore: null, unscrollable: true };
|
|
4327
4209
|
}
|
|
4328
4210
|
if (scrollRect && status.code === "OBSTRUCTED" && status.obstruction?.isFixed) {
|
|
4329
4211
|
const moved = await scrollAwayFromObstruction(element, status);
|
|
4330
4212
|
if (moved.moved) {
|
|
4331
|
-
|
|
4213
|
+
logger7.debug(`humanScroll | sticky/fixed \u906E\u6321\u8865\u507F\u6EDA\u52A8 top=${Math.round(moved.scrollTop || 0)}`);
|
|
4332
4214
|
await waitJitter(90, 0.3);
|
|
4333
4215
|
didScroll = true;
|
|
4334
4216
|
continue;
|
|
4335
4217
|
}
|
|
4336
4218
|
}
|
|
4337
4219
|
if (Date.now() - startTime > maxDurationMs) {
|
|
4338
|
-
|
|
4220
|
+
logger7.warn(`humanScroll | mobile timeout (${maxDurationMs}ms, status=${status.code}, direction=${status.direction || "unknown"}, fixed=${Boolean(status.isFixed)})`);
|
|
4339
4221
|
return { element, didScroll, restore: null };
|
|
4340
4222
|
}
|
|
4341
4223
|
const stepMin = scrollRect ? Math.min(minStep, Math.max(60, scrollRect.height * 0.4)) : minStep;
|
|
4342
4224
|
const stepMax = scrollRect ? Math.min(maxStep, Math.max(stepMin + 40, scrollRect.height * 0.8)) : maxStep;
|
|
4343
|
-
|
|
4225
|
+
logger7.debug(`humanScroll | \u6B65\u9AA4 ${i + 1}/${maxSteps}: ${status.reason || status.code} ${status.direction ? `(${status.direction})` : ""}`);
|
|
4344
4226
|
const distance = stepMin + Math.random() * Math.max(1, stepMax - stepMin);
|
|
4345
4227
|
let deltaY = status.direction === "up" ? -distance : distance;
|
|
4346
4228
|
if (status.code === "OBSTRUCTED") {
|
|
@@ -4380,8 +4262,8 @@ var MobileHumanize = {
|
|
|
4380
4262
|
if (scrollRect && beforeWindowState) {
|
|
4381
4263
|
const afterWindowState = await page.evaluate(() => ({ x: window.scrollX, y: window.scrollY }));
|
|
4382
4264
|
if (Math.abs(afterWindowState.x - beforeWindowState.x) > 2 || Math.abs(afterWindowState.y - beforeWindowState.y) > 2) {
|
|
4383
|
-
await page.evaluate((
|
|
4384
|
-
|
|
4265
|
+
await page.evaluate((state) => window.scrollTo(state.x, state.y), beforeWindowState);
|
|
4266
|
+
logger7.debug(`humanScroll | \u7A97\u53E3\u6EDA\u52A8\u56DE\u6536 from=${Math.round(afterWindowState.y)} to=${Math.round(beforeWindowState.y)}`);
|
|
4385
4267
|
}
|
|
4386
4268
|
}
|
|
4387
4269
|
let afterElementSnapshot = null;
|
|
@@ -4395,7 +4277,7 @@ var MobileHumanize = {
|
|
|
4395
4277
|
const afterSnapshot = await readAfterElementSnapshot();
|
|
4396
4278
|
if (isTargetImmobileAfterScroll(beforeElementSnapshot, afterSnapshot)) {
|
|
4397
4279
|
await restoreWindowFromSnapshot(page, beforeElementSnapshot, afterSnapshot);
|
|
4398
|
-
|
|
4280
|
+
logger7.warn(`humanScroll | \u76EE\u6807\u4E0D\u968F\u9875\u9762\u6EDA\u52A8\u79FB\u52A8\uFF0C\u9875\u9762\u6EDA\u52A8\u65E0\u6CD5\u6539\u53D8\u5176\u4F4D\u7F6E (status=${status.code}, direction=${status.direction || "unknown"})`);
|
|
4399
4281
|
return { element, didScroll, restore: null, unscrollable: true };
|
|
4400
4282
|
}
|
|
4401
4283
|
}
|
|
@@ -4427,12 +4309,12 @@ var MobileHumanize = {
|
|
|
4427
4309
|
const moved = beforeState.kind !== afterState.kind || Math.abs(topDelta) > 2 || Math.abs(leftDelta) > 2;
|
|
4428
4310
|
if (!moved) {
|
|
4429
4311
|
const fallback = await scrollScrollableAncestor(element, deltaY);
|
|
4430
|
-
|
|
4312
|
+
logger7.debug(`humanScroll | \u5BB9\u5668\u89E6\u6478\u65E0\u6548\uFF0C\u76F4\u63A5\u6EDA\u52A8 fallback=${fallback.scroller ? "ancestor" : "window"} top=${Math.round(fallback.scrollTop || 0)}`);
|
|
4431
4313
|
} else if (beforeState.kind === afterState.kind && Math.abs(expectedDelta) > 24 && Math.sign(topDelta || expectedDelta) === Math.sign(expectedDelta) && Math.abs(topDelta) < Math.min(Math.abs(expectedDelta) * 0.45, 96)) {
|
|
4432
4314
|
const residualDelta = expectedDelta - topDelta;
|
|
4433
4315
|
if (Math.sign(residualDelta) === Math.sign(expectedDelta) && Math.abs(residualDelta) > 24) {
|
|
4434
4316
|
const fallback = await scrollScrollableAncestor(element, residualDelta);
|
|
4435
|
-
|
|
4317
|
+
logger7.debug(`humanScroll | \u5BB9\u5668\u89E6\u6478\u8DDD\u79BB\u4E0D\u8DB3\uFF0C\u8865\u507F\u6EDA\u52A8 fallback=${fallback.scroller ? "ancestor" : "window"} top=${Math.round(fallback.scrollTop || 0)}`);
|
|
4436
4318
|
}
|
|
4437
4319
|
}
|
|
4438
4320
|
}
|
|
@@ -4440,7 +4322,7 @@ var MobileHumanize = {
|
|
|
4440
4322
|
const afterSnapshot = await getElementViewportSnapshot(element).catch(() => null);
|
|
4441
4323
|
if (isTargetImmobileAfterScroll(beforeElementSnapshot, afterSnapshot)) {
|
|
4442
4324
|
await restoreWindowFromSnapshot(page, beforeElementSnapshot, afterSnapshot);
|
|
4443
|
-
|
|
4325
|
+
logger7.warn(`humanScroll | \u76EE\u6807\u4E0D\u968F\u6EDA\u52A8\u5BB9\u5668\u79FB\u52A8\uFF0C\u6EDA\u52A8\u65E0\u6CD5\u6539\u53D8\u5176\u4F4D\u7F6E (status=${status.code}, direction=${status.direction || "unknown"})`);
|
|
4444
4326
|
return { element, didScroll, restore: null, unscrollable: true };
|
|
4445
4327
|
}
|
|
4446
4328
|
}
|
|
@@ -4451,14 +4333,14 @@ var MobileHumanize = {
|
|
|
4451
4333
|
await waitJitter(80, 0.3);
|
|
4452
4334
|
const finalStatus = await checkElementVisibility(element);
|
|
4453
4335
|
if (finalStatus.code === "VISIBLE") {
|
|
4454
|
-
|
|
4455
|
-
|
|
4336
|
+
logger7.info("humanScroll | \u539F\u751F scrollIntoViewIfNeeded \u515C\u5E95\u6210\u529F");
|
|
4337
|
+
logger7.success("humanScroll", didScroll ? "\u5DF2\u6EDA\u52A8" : "\u65E0\u9700\u6EDA\u52A8");
|
|
4456
4338
|
return { element, didScroll: true, restore: null };
|
|
4457
4339
|
}
|
|
4458
4340
|
} catch (fallbackError) {
|
|
4459
|
-
|
|
4341
|
+
logger7.debug(`humanScroll | native fallback failed: ${fallbackError?.message || fallbackError}`);
|
|
4460
4342
|
}
|
|
4461
|
-
|
|
4343
|
+
logger7.warn(`humanScroll | \u5728 ${maxSteps} \u6B65\u540E\u65E0\u6CD5\u786E\u4FDD\u53EF\u89C1\u6027`);
|
|
4462
4344
|
return { element, didScroll, restore: null };
|
|
4463
4345
|
},
|
|
4464
4346
|
async humanClick(page, target, options = {}) {
|
|
@@ -4473,7 +4355,7 @@ var MobileHumanize = {
|
|
|
4473
4355
|
fallbackDomClickOnTapError = true
|
|
4474
4356
|
} = options;
|
|
4475
4357
|
const targetDesc = describeTarget(target);
|
|
4476
|
-
|
|
4358
|
+
logger7.start("humanClick", `target=${targetDesc}`);
|
|
4477
4359
|
try {
|
|
4478
4360
|
if (target == null) {
|
|
4479
4361
|
const viewport = resolveViewport(page);
|
|
@@ -4485,12 +4367,12 @@ var MobileHumanize = {
|
|
|
4485
4367
|
timeoutMs: tapTimeoutMs,
|
|
4486
4368
|
mouseFallbackTimeoutMs
|
|
4487
4369
|
});
|
|
4488
|
-
|
|
4370
|
+
logger7.success("humanClick", "Tapped current position");
|
|
4489
4371
|
return true;
|
|
4490
4372
|
}
|
|
4491
4373
|
const element = await resolveElement(page, target, { throwOnMissing });
|
|
4492
4374
|
if (!element) {
|
|
4493
|
-
|
|
4375
|
+
logger7.warn(`humanClick: \u5143\u7D20\u4E0D\u5B58\u5728\uFF0C\u8DF3\u8FC7\u70B9\u51FB ${targetDesc}`);
|
|
4494
4376
|
return false;
|
|
4495
4377
|
}
|
|
4496
4378
|
const scrollResult = scrollIfNeeded ? await MobileHumanize.humanScroll(page, element, { throwOnMissing }) : null;
|
|
@@ -4514,19 +4396,19 @@ var MobileHumanize = {
|
|
|
4514
4396
|
).catch(() => null);
|
|
4515
4397
|
}
|
|
4516
4398
|
if (fallback?.activated) {
|
|
4517
|
-
|
|
4399
|
+
logger7.warn(`humanClick: \u4E0D\u53EF\u6EDA\u52A8\u76EE\u6807\u4E0D\u53EF\u7269\u7406\u70B9\u51FB\uFF0C\u5DF2\u7528 ${fallback.method} \u6FC0\u6D3B`);
|
|
4518
4400
|
return true;
|
|
4519
4401
|
}
|
|
4520
4402
|
}
|
|
4521
4403
|
const message = `\u5143\u7D20\u4E0D\u53EF\u70B9\u51FB: ${status.reason || status.code}`;
|
|
4522
4404
|
if (throwOnMissing) throw new Error(message);
|
|
4523
|
-
|
|
4405
|
+
logger7.warn(`humanClick: ${message}\uFF0C\u8DF3\u8FC7\u70B9\u51FB`);
|
|
4524
4406
|
return false;
|
|
4525
4407
|
}
|
|
4526
4408
|
const box = await element.boundingBox();
|
|
4527
4409
|
if (!box) {
|
|
4528
4410
|
if (throwOnMissing) throw new Error("\u65E0\u6CD5\u83B7\u53D6\u5143\u7D20\u4F4D\u7F6E");
|
|
4529
|
-
|
|
4411
|
+
logger7.warn("humanClick: \u65E0\u6CD5\u83B7\u53D6\u4F4D\u7F6E\uFF0C\u8DF3\u8FC7\u70B9\u51FB");
|
|
4530
4412
|
return false;
|
|
4531
4413
|
}
|
|
4532
4414
|
await waitJitter(reactionDelay, 0.45);
|
|
@@ -4547,13 +4429,13 @@ var MobileHumanize = {
|
|
|
4547
4429
|
"activation fallback"
|
|
4548
4430
|
).catch(() => null);
|
|
4549
4431
|
if (!fallback?.activated) throw tapError;
|
|
4550
|
-
|
|
4432
|
+
logger7.warn(`humanClick: tap \u5931\u8D25\u540E\u5DF2\u7528 ${fallback.method} \u515C\u5E95: ${tapError?.message || tapError}`);
|
|
4551
4433
|
}
|
|
4552
4434
|
await waitJitter(120, 0.35);
|
|
4553
|
-
|
|
4435
|
+
logger7.success("humanClick");
|
|
4554
4436
|
return true;
|
|
4555
4437
|
} catch (error) {
|
|
4556
|
-
|
|
4438
|
+
logger7.fail("humanClick", error);
|
|
4557
4439
|
throw error;
|
|
4558
4440
|
}
|
|
4559
4441
|
},
|
|
@@ -4606,7 +4488,7 @@ var MobileHumanize = {
|
|
|
4606
4488
|
keyboardOptions = {}
|
|
4607
4489
|
} = pressOptions || {};
|
|
4608
4490
|
const targetDesc = hasTarget ? describeTarget(targetOrKey) : "current focus";
|
|
4609
|
-
|
|
4491
|
+
logger7.start("humanPress", `key=${key}, target=${targetDesc}`);
|
|
4610
4492
|
try {
|
|
4611
4493
|
if (hasTarget) {
|
|
4612
4494
|
await MobileHumanize.humanClick(page, targetOrKey, {
|
|
@@ -4620,10 +4502,10 @@ var MobileHumanize = {
|
|
|
4620
4502
|
...keyboardOptions,
|
|
4621
4503
|
delay: jitterMs(holdDelay, 0.5)
|
|
4622
4504
|
});
|
|
4623
|
-
|
|
4505
|
+
logger7.success("humanPress");
|
|
4624
4506
|
return true;
|
|
4625
4507
|
} catch (error) {
|
|
4626
|
-
|
|
4508
|
+
logger7.fail("humanPress", error);
|
|
4627
4509
|
throw error;
|
|
4628
4510
|
}
|
|
4629
4511
|
},
|
|
@@ -4690,92 +4572,62 @@ var MobileHumanize = {
|
|
|
4690
4572
|
}
|
|
4691
4573
|
};
|
|
4692
4574
|
|
|
4693
|
-
// src/
|
|
4575
|
+
// src/humanize.js
|
|
4694
4576
|
var resolveDeviceFromPage2 = (page) => normalizeDevice(page?.[PageRuntimeStateKey]?.device);
|
|
4695
4577
|
var resolveDelegate = (page) => {
|
|
4696
4578
|
return resolveDeviceFromPage2(page) === Device.Mobile ? MobileHumanize : Humanize;
|
|
4697
4579
|
};
|
|
4698
|
-
var
|
|
4699
|
-
|
|
4700
|
-
|
|
4701
|
-
[Humanize, MobileHumanize]
|
|
4702
|
-
);
|
|
4703
|
-
|
|
4704
|
-
// src/internals/humanize/cloak.js
|
|
4705
|
-
var FORCE_CLICK = Object.freeze({
|
|
4706
|
-
forceClick: true,
|
|
4707
|
-
clickOptions: { force: true }
|
|
4708
|
-
});
|
|
4709
|
-
var pointOrNull = async (target) => {
|
|
4710
|
-
if (!target || typeof target.boundingBox !== "function") return null;
|
|
4711
|
-
const box = await target.boundingBox().catch(() => null);
|
|
4712
|
-
return box ? { x: box.x + box.width / 2, y: box.y + box.height / 2 } : null;
|
|
4580
|
+
var callDelegate = (method, page, args) => {
|
|
4581
|
+
const delegate = resolveDelegate(page);
|
|
4582
|
+
return delegate[method](page, ...args);
|
|
4713
4583
|
};
|
|
4714
|
-
var
|
|
4715
|
-
|
|
4716
|
-
return
|
|
4584
|
+
var Humanize2 = {
|
|
4585
|
+
jitterMs(base, jitterPercent = 0.3) {
|
|
4586
|
+
return Humanize.jitterMs(base, jitterPercent);
|
|
4717
4587
|
},
|
|
4718
|
-
|
|
4719
|
-
|
|
4720
|
-
return point ? await DeviceInput.move(page, point, { forceMouse: true }) : false;
|
|
4588
|
+
initializeCursor(page) {
|
|
4589
|
+
return callDelegate("initializeCursor", page, []);
|
|
4721
4590
|
},
|
|
4722
|
-
|
|
4723
|
-
|
|
4724
|
-
if (!element) return { element: null, didScroll: false, restore: null };
|
|
4725
|
-
await element.scrollIntoViewIfNeeded?.();
|
|
4726
|
-
return { element, didScroll: true, restore: null };
|
|
4591
|
+
humanMove(page, target) {
|
|
4592
|
+
return callDelegate("humanMove", page, [target]);
|
|
4727
4593
|
},
|
|
4728
|
-
|
|
4729
|
-
return
|
|
4594
|
+
humanScroll(page, target, options = {}) {
|
|
4595
|
+
return callDelegate("humanScroll", page, [target, options]);
|
|
4730
4596
|
},
|
|
4731
|
-
|
|
4732
|
-
|
|
4733
|
-
return await DeviceInput.keyboardType(page, text);
|
|
4597
|
+
humanClick(page, target, options = {}) {
|
|
4598
|
+
return callDelegate("humanClick", page, [target, options]);
|
|
4734
4599
|
},
|
|
4735
|
-
|
|
4736
|
-
|
|
4737
|
-
|
|
4738
|
-
|
|
4739
|
-
}
|
|
4600
|
+
randomSleep(pageOrBaseMs, maybeBaseMs, maybeJitterPercent) {
|
|
4601
|
+
if (pageOrBaseMs && typeof pageOrBaseMs === "object" && typeof pageOrBaseMs.evaluate === "function") {
|
|
4602
|
+
const delegate = resolveDelegate(pageOrBaseMs);
|
|
4603
|
+
return delegate.randomSleep(maybeBaseMs, maybeJitterPercent);
|
|
4604
|
+
}
|
|
4605
|
+
return Humanize.randomSleep(pageOrBaseMs, maybeBaseMs);
|
|
4740
4606
|
},
|
|
4741
|
-
|
|
4742
|
-
return
|
|
4607
|
+
simulateGaze(page, baseDurationMs = 2500) {
|
|
4608
|
+
return callDelegate("simulateGaze", page, [baseDurationMs]);
|
|
4743
4609
|
},
|
|
4744
|
-
|
|
4745
|
-
return
|
|
4610
|
+
humanType(page, selector, text, options = {}) {
|
|
4611
|
+
return callDelegate("humanType", page, [selector, text, options]);
|
|
4746
4612
|
},
|
|
4747
|
-
|
|
4748
|
-
|
|
4613
|
+
humanPress(page, targetOrKey, maybeKey, options = {}) {
|
|
4614
|
+
if (typeof maybeKey === "string") {
|
|
4615
|
+
return callDelegate("humanPress", page, [targetOrKey, maybeKey, options]);
|
|
4616
|
+
}
|
|
4617
|
+
return callDelegate("humanPress", page, [targetOrKey, maybeKey || options]);
|
|
4749
4618
|
},
|
|
4750
|
-
|
|
4751
|
-
|
|
4752
|
-
await page.mouse.wheel(0, Number(distance || 0) * sign);
|
|
4753
|
-
}
|
|
4754
|
-
};
|
|
4755
|
-
|
|
4756
|
-
// src/internals/humanize/index.js
|
|
4757
|
-
var HumanizeCommon = {
|
|
4758
|
-
jitterMs(base, jitterPercent = 0.3) {
|
|
4759
|
-
return jitterMs(base, jitterPercent);
|
|
4619
|
+
humanClear(page, selector) {
|
|
4620
|
+
return callDelegate("humanClear", page, [selector]);
|
|
4760
4621
|
},
|
|
4761
|
-
|
|
4762
|
-
|
|
4763
|
-
|
|
4764
|
-
|
|
4765
|
-
|
|
4622
|
+
warmUpBrowsing(page, baseDuration = 3500) {
|
|
4623
|
+
return callDelegate("warmUpBrowsing", page, [baseDuration]);
|
|
4624
|
+
},
|
|
4625
|
+
naturalScroll(page, direction = "down", distance = 300, baseSteps = 5) {
|
|
4626
|
+
return callDelegate("naturalScroll", page, [direction, distance, baseSteps]);
|
|
4766
4627
|
}
|
|
4767
4628
|
};
|
|
4768
|
-
var DefaultHumanize = Object.assign({}, DefaultHumanizeDevice, HumanizeCommon);
|
|
4769
|
-
var CloakHumanize = Object.assign({}, CloakHumanizeInput, HumanizeCommon);
|
|
4770
4629
|
|
|
4771
|
-
// src/
|
|
4772
|
-
var humanizeStrategies = {
|
|
4773
|
-
[Mode.Default]: DefaultHumanize,
|
|
4774
|
-
[Mode.Cloak]: CloakHumanize
|
|
4775
|
-
};
|
|
4776
|
-
var Humanize2 = withModeReflect("Humanize", humanizeStrategies);
|
|
4777
|
-
|
|
4778
|
-
// src/internals/launch/default.js
|
|
4630
|
+
// src/launch.js
|
|
4779
4631
|
import { execFileSync } from "node:child_process";
|
|
4780
4632
|
import { FingerprintGenerator } from "fingerprint-generator";
|
|
4781
4633
|
import { FingerprintInjector } from "fingerprint-injector";
|
|
@@ -4860,107 +4712,9 @@ var ByPass = {
|
|
|
4860
4712
|
resolveRouteByProxy
|
|
4861
4713
|
};
|
|
4862
4714
|
|
|
4863
|
-
// src/
|
|
4864
|
-
var logger7 = createInternalLogger("Launch");
|
|
4865
|
-
var normalizeObject = (value) => {
|
|
4866
|
-
if (!value || typeof value !== "object" || Array.isArray(value)) {
|
|
4867
|
-
return {};
|
|
4868
|
-
}
|
|
4869
|
-
return value;
|
|
4870
|
-
};
|
|
4871
|
-
var parseProxyConfiguration = (proxyConfiguration = {}) => {
|
|
4872
|
-
const config = normalizeObject(proxyConfiguration);
|
|
4873
|
-
const proxyUrl = String(config.proxy_url || "").trim();
|
|
4874
|
-
const enableProxy = typeof config.enable_proxy === "boolean" ? config.enable_proxy : proxyUrl !== "";
|
|
4875
|
-
const byPassDomains = enableProxy && proxyUrl ? ByPass.normalizeByPassDomains(config.by_pass_domains) : [];
|
|
4876
|
-
return {
|
|
4877
|
-
byPassDomains,
|
|
4878
|
-
enableProxy,
|
|
4879
|
-
proxyUrl
|
|
4880
|
-
};
|
|
4881
|
-
};
|
|
4882
|
-
var resolveLaunchTraffic = ({
|
|
4883
|
-
proxyConfiguration = {},
|
|
4884
|
-
debugMode = false,
|
|
4885
|
-
useMeter = true
|
|
4886
|
-
} = {}) => {
|
|
4887
|
-
const { byPassDomains, enableProxy, proxyUrl } = parseProxyConfiguration(proxyConfiguration);
|
|
4888
|
-
const byPassRules = ByPass.buildByPassDomainRules(byPassDomains);
|
|
4889
|
-
const proxyMeter = useMeter && enableProxy && proxyUrl ? ProxyMeterRuntime.startProxyMeter({ proxyUrl, debugMode }) : null;
|
|
4890
|
-
const launchProxy = proxyMeter ? { server: proxyMeter.server } : null;
|
|
4891
|
-
if (launchProxy && byPassDomains.length > 0) {
|
|
4892
|
-
launchProxy.bypass = byPassDomains.join(",");
|
|
4893
|
-
}
|
|
4894
|
-
return {
|
|
4895
|
-
byPassDomains,
|
|
4896
|
-
byPassRules,
|
|
4897
|
-
enableProxy,
|
|
4898
|
-
proxyUrl,
|
|
4899
|
-
launchProxy
|
|
4900
|
-
};
|
|
4901
|
-
};
|
|
4902
|
-
var logLaunchTraffic = ({
|
|
4903
|
-
byPassDomains = [],
|
|
4904
|
-
debugMode = false,
|
|
4905
|
-
enabled = false,
|
|
4906
|
-
enableProxy = false,
|
|
4907
|
-
explicitProxy = false,
|
|
4908
|
-
launchProxy = null,
|
|
4909
|
-
proxyUrl = ""
|
|
4910
|
-
} = {}) => {
|
|
4911
|
-
if (!enabled) return;
|
|
4912
|
-
if (explicitProxy) {
|
|
4913
|
-
logger7.info("[\u4EE3\u7406\u5DF2\u542F\u7528] \u4F7F\u7528\u663E\u5F0F proxy \u914D\u7F6E\uFF0C\u8DF3\u8FC7 toolkit \u672C\u5730\u6D41\u91CF\u89C2\u6D4B");
|
|
4914
|
-
return;
|
|
4915
|
-
}
|
|
4916
|
-
if (launchProxy) {
|
|
4917
|
-
let upstreamLabel = "";
|
|
4918
|
-
try {
|
|
4919
|
-
const parsedProxyUrl = new URL(proxyUrl.includes("://") ? proxyUrl : `http://${proxyUrl}`);
|
|
4920
|
-
upstreamLabel = `${parsedProxyUrl.protocol}//${parsedProxyUrl.host}`;
|
|
4921
|
-
} catch {
|
|
4922
|
-
}
|
|
4923
|
-
logger7.info(
|
|
4924
|
-
`[\u4EE3\u7406\u5DF2\u542F\u7528] \u672C\u5730=${launchProxy.server} \u4E0A\u6E38=${upstreamLabel || "-"} \u76F4\u8FDE\u57DF\u540D=${byPassDomains.join(",")}`
|
|
4925
|
-
);
|
|
4926
|
-
logger7.info(`[\u6D41\u91CF\u89C2\u6D4B] \u9010\u8BF7\u6C42\u8C03\u8BD5=${Boolean(debugMode) ? "\u5F00\u542F" : "\u5173\u95ED"}\uFF08\u6C47\u603B\u59CB\u7EC8\u5F00\u542F\uFF09`);
|
|
4927
|
-
return;
|
|
4928
|
-
}
|
|
4929
|
-
if (enableProxy) {
|
|
4930
|
-
logger7.info("[\u4EE3\u7406\u672A\u542F\u7528] enable_proxy=true \u4F46 proxy_url \u4E3A\u7A7A");
|
|
4931
|
-
} else if (proxyUrl) {
|
|
4932
|
-
logger7.info("[\u4EE3\u7406\u672A\u542F\u7528] enable_proxy=false \u4E14 proxy_url \u5DF2\u914D\u7F6E");
|
|
4933
|
-
}
|
|
4934
|
-
logger7.info(`[\u6D41\u91CF\u89C2\u6D4B] \u9010\u8BF7\u6C42\u8C03\u8BD5=${Boolean(debugMode) ? "\u5F00\u542F" : "\u5173\u95ED"}\uFF08\u6C47\u603B\u59CB\u7EC8\u5F00\u542F\uFF09`);
|
|
4935
|
-
};
|
|
4936
|
-
var createLaunchTrafficHook = ({
|
|
4937
|
-
byPassDomains = [],
|
|
4938
|
-
byPassRules = [],
|
|
4939
|
-
enabled = false,
|
|
4940
|
-
launchProxy = null
|
|
4941
|
-
} = {}) => {
|
|
4942
|
-
const patchedPages = /* @__PURE__ */ new WeakSet();
|
|
4943
|
-
return (page) => {
|
|
4944
|
-
if (!page || typeof page.on !== "function" || patchedPages.has(page)) {
|
|
4945
|
-
return;
|
|
4946
|
-
}
|
|
4947
|
-
patchedPages.add(page);
|
|
4948
|
-
page.on("request", (req) => {
|
|
4949
|
-
const requestUrl = req.url();
|
|
4950
|
-
const resourceType = req.resourceType();
|
|
4951
|
-
const matched = byPassDomains.length > 0 ? ByPass.findMatchedByPassRule(byPassRules, requestUrl) : null;
|
|
4952
|
-
if (launchProxy) {
|
|
4953
|
-
ProxyMeterRuntime.recordProxyMeterResourceType(requestUrl, resourceType);
|
|
4954
|
-
}
|
|
4955
|
-
if (!enabled || byPassDomains.length === 0) return;
|
|
4956
|
-
if (!matched || !matched.rule) return;
|
|
4957
|
-
logger7.info(`[\u76F4\u8FDE\u547D\u4E2D] \u89C4\u5219=${matched.rule.pattern} \u57DF\u540D=${matched.hostname} \u8D44\u6E90\u7C7B\u578B=${resourceType} \u65B9\u6CD5=${req.method()} \u5730\u5740=${requestUrl}`);
|
|
4958
|
-
});
|
|
4959
|
-
};
|
|
4960
|
-
};
|
|
4961
|
-
|
|
4962
|
-
// src/internals/launch/default.js
|
|
4715
|
+
// src/launch.js
|
|
4963
4716
|
var logger8 = createInternalLogger("Launch");
|
|
4717
|
+
var REQUEST_HOOK_FLAG = Symbol("playwright-toolkit-request-hook");
|
|
4964
4718
|
var injectedContexts = /* @__PURE__ */ new WeakSet();
|
|
4965
4719
|
var browserMajorVersionCache = /* @__PURE__ */ new Map();
|
|
4966
4720
|
var DEFAULT_BROWSER_PROFILE_SCHEMA_VERSION = 1;
|
|
@@ -4972,6 +4726,16 @@ var DEFAULT_CRAWLER_BASE_OPTIONS = Object.freeze({
|
|
|
4972
4726
|
navigationTimeoutSecs: 120
|
|
4973
4727
|
});
|
|
4974
4728
|
var fingerprintInjector = new FingerprintInjector();
|
|
4729
|
+
var resolveProxyLaunchOptions = (proxyConfiguration = {}) => {
|
|
4730
|
+
const config = proxyConfiguration && typeof proxyConfiguration === "object" && !Array.isArray(proxyConfiguration) ? proxyConfiguration : {};
|
|
4731
|
+
const proxyUrl = String(config.proxy_url || "").trim();
|
|
4732
|
+
const enableProxy = typeof config.enable_proxy === "boolean" ? config.enable_proxy : proxyUrl !== "";
|
|
4733
|
+
if (!enableProxy || !proxyUrl) {
|
|
4734
|
+
return { byPassDomains: [], enableProxy, proxyUrl };
|
|
4735
|
+
}
|
|
4736
|
+
const byPassDomains = ByPass.normalizeByPassDomains(config.by_pass_domains);
|
|
4737
|
+
return { byPassDomains, enableProxy, proxyUrl };
|
|
4738
|
+
};
|
|
4975
4739
|
var parseChromeMajorVersion = (rawValue = "") => {
|
|
4976
4740
|
const match = String(rawValue || "").match(/(?:Chrome|Chromium)(?:\/|\s+(?:for Testing\s+)?)(\d+)/i);
|
|
4977
4741
|
return match ? Number(match[1] || 0) : 0;
|
|
@@ -5015,7 +4779,7 @@ var resolveCoreDevice = (core = {}) => {
|
|
|
5015
4779
|
};
|
|
5016
4780
|
var buildFingerprintGenerator = ({ locale, browserMajorVersion, device }) => {
|
|
5017
4781
|
return new FingerprintGenerator(
|
|
5018
|
-
|
|
4782
|
+
AntiCheat.getFingerprintGeneratorOptions({
|
|
5019
4783
|
locale,
|
|
5020
4784
|
browserMajorVersion,
|
|
5021
4785
|
device
|
|
@@ -5059,7 +4823,7 @@ var buildReplayableBrowserProfile = (runtimeState, launcher) => {
|
|
|
5059
4823
|
}
|
|
5060
4824
|
let nextState = RuntimeEnv.rememberState(runtimeState);
|
|
5061
4825
|
let browserProfileCore = RuntimeEnv.getBrowserProfileCore(nextState);
|
|
5062
|
-
const timezoneId = String(browserProfileCore?.timezone_id || "").trim() ||
|
|
4826
|
+
const timezoneId = String(browserProfileCore?.timezone_id || "").trim() || AntiCheat.getBaseConfig().timezoneId;
|
|
5063
4827
|
const locale = DEFAULT_LOCALE;
|
|
5064
4828
|
const currentBrowserMajorVersion = detectBrowserMajorVersion(launcher);
|
|
5065
4829
|
const storedBrowserMajorVersion = Number(browserProfileCore?.browser_major_version || 0);
|
|
@@ -5138,7 +4902,7 @@ var applyFingerprintPageOptions = (pageOptions = {}, { fingerprintWithHeaders =
|
|
|
5138
4902
|
pageOptions.timezoneId = timezoneId;
|
|
5139
4903
|
}
|
|
5140
4904
|
};
|
|
5141
|
-
var buildReplayBrowserPoolOptions = (browserProfileCore) => {
|
|
4905
|
+
var buildReplayBrowserPoolOptions = (browserProfileCore, modifyPageOptions = null) => {
|
|
5142
4906
|
const fingerprintWithHeaders = browserProfileCore?.fingerprint;
|
|
5143
4907
|
const fingerprint = fingerprintWithHeaders?.fingerprint;
|
|
5144
4908
|
if (!fingerprintWithHeaders || !fingerprint) {
|
|
@@ -5147,13 +4911,16 @@ var buildReplayBrowserPoolOptions = (browserProfileCore) => {
|
|
|
5147
4911
|
return {
|
|
5148
4912
|
useFingerprints: false,
|
|
5149
4913
|
prePageCreateHooks: [
|
|
5150
|
-
(
|
|
4914
|
+
async (pageId, browserController, pageOptions = {}) => {
|
|
5151
4915
|
if (!pageOptions || typeof pageOptions !== "object") return;
|
|
5152
4916
|
applyFingerprintPageOptions(pageOptions, {
|
|
5153
4917
|
fingerprintWithHeaders,
|
|
5154
4918
|
locale: browserProfileCore.locale,
|
|
5155
4919
|
timezoneId: browserProfileCore.timezone_id
|
|
5156
4920
|
});
|
|
4921
|
+
if (modifyPageOptions) {
|
|
4922
|
+
await modifyPageOptions(pageOptions, { pageId, browserController });
|
|
4923
|
+
}
|
|
5157
4924
|
}
|
|
5158
4925
|
],
|
|
5159
4926
|
postPageCreateHooks: [
|
|
@@ -5168,7 +4935,7 @@ var buildReplayBrowserPoolOptions = (browserProfileCore) => {
|
|
|
5168
4935
|
]
|
|
5169
4936
|
};
|
|
5170
4937
|
};
|
|
5171
|
-
var
|
|
4938
|
+
var Launch = {
|
|
5172
4939
|
getPlaywrightCrawlerOptions(options = {}) {
|
|
5173
4940
|
const normalizedOptions = Array.isArray(options) ? { customArgs: options } : options || {};
|
|
5174
4941
|
const {
|
|
@@ -5179,35 +4946,54 @@ var DefaultLaunch = {
|
|
|
5179
4946
|
debugMode = false,
|
|
5180
4947
|
isRunningOnApify = false,
|
|
5181
4948
|
launcher = null,
|
|
4949
|
+
hooks = {},
|
|
5182
4950
|
preNavigationHooks = [],
|
|
5183
4951
|
postNavigationHooks = [],
|
|
5184
4952
|
runtimeState = null
|
|
5185
4953
|
} = normalizedOptions;
|
|
5186
4954
|
const device = resolveRuntimeDevice(runtimeState);
|
|
5187
|
-
const
|
|
5188
|
-
const
|
|
5189
|
-
const
|
|
5190
|
-
|
|
5191
|
-
|
|
5192
|
-
|
|
4955
|
+
const modifyPageOptions = typeof hooks?.modifyPageOptions === "function" ? hooks.modifyPageOptions : null;
|
|
4956
|
+
const { byPassDomains, enableProxy, proxyUrl } = resolveProxyLaunchOptions(proxyConfiguration);
|
|
4957
|
+
const byPassRules = ByPass.buildByPassDomainRules(byPassDomains);
|
|
4958
|
+
const proxyMeter = enableProxy && proxyUrl ? ProxyMeterRuntime.startProxyMeter({ proxyUrl, debugMode }) : null;
|
|
4959
|
+
const launchProxy = proxyMeter ? { server: proxyMeter.server } : null;
|
|
4960
|
+
if (launchProxy && byPassDomains.length > 0) {
|
|
4961
|
+
launchProxy.bypass = byPassDomains.join(",");
|
|
4962
|
+
}
|
|
5193
4963
|
const replayContext = buildReplayableBrowserProfile(runtimeState, launcher);
|
|
5194
|
-
const replayBrowserPoolOptions = buildReplayBrowserPoolOptions(replayContext.browserProfileCore);
|
|
4964
|
+
const replayBrowserPoolOptions = buildReplayBrowserPoolOptions(replayContext.browserProfileCore, modifyPageOptions);
|
|
5195
4965
|
const launchLocale = String(replayContext.browserProfileCore?.locale || DEFAULT_LOCALE).trim() || DEFAULT_LOCALE;
|
|
5196
4966
|
const launchOptions = {
|
|
5197
4967
|
args: [
|
|
5198
|
-
...
|
|
4968
|
+
...AntiCheat.getLaunchArgs({ locale: launchLocale }),
|
|
5199
4969
|
...customArgs
|
|
5200
4970
|
],
|
|
5201
4971
|
ignoreDefaultArgs: ["--enable-automation"]
|
|
5202
4972
|
};
|
|
5203
|
-
if (
|
|
5204
|
-
launchOptions.proxy =
|
|
4973
|
+
if (launchProxy) {
|
|
4974
|
+
launchOptions.proxy = launchProxy;
|
|
4975
|
+
}
|
|
4976
|
+
const enableByPassLogger = Boolean(logOptions && logOptions.enable);
|
|
4977
|
+
if (enableByPassLogger && launchProxy) {
|
|
4978
|
+
let upstreamLabel = "";
|
|
4979
|
+
try {
|
|
4980
|
+
const parsedProxyUrl = new URL(proxyUrl.includes("://") ? proxyUrl : `http://${proxyUrl}`);
|
|
4981
|
+
upstreamLabel = `${parsedProxyUrl.protocol}//${parsedProxyUrl.host}`;
|
|
4982
|
+
} catch {
|
|
4983
|
+
}
|
|
4984
|
+
logger8.info(
|
|
4985
|
+
`[\u4EE3\u7406\u5DF2\u542F\u7528] \u672C\u5730=${launchProxy.server} \u4E0A\u6E38=${upstreamLabel || "-"} \u76F4\u8FDE\u57DF\u540D=${(byPassDomains || []).join(",")}`
|
|
4986
|
+
);
|
|
4987
|
+
logger8.info(`[\u6D41\u91CF\u89C2\u6D4B] \u9010\u8BF7\u6C42\u8C03\u8BD5=${Boolean(debugMode) ? "\u5F00\u542F" : "\u5173\u95ED"}\uFF08\u6C47\u603B\u59CB\u7EC8\u5F00\u542F\uFF09`);
|
|
4988
|
+
} else if (enableByPassLogger && enableProxy && !launchProxy) {
|
|
4989
|
+
logger8.info("[\u4EE3\u7406\u672A\u542F\u7528] enable_proxy=true \u4F46 proxy_url \u4E3A\u7A7A");
|
|
4990
|
+
logger8.info(`[\u6D41\u91CF\u89C2\u6D4B] \u9010\u8BF7\u6C42\u8C03\u8BD5=${Boolean(debugMode) ? "\u5F00\u542F" : "\u5173\u95ED"}\uFF08\u6C47\u603B\u59CB\u7EC8\u5F00\u542F\uFF09`);
|
|
4991
|
+
} else if (enableByPassLogger && !enableProxy && proxyUrl) {
|
|
4992
|
+
logger8.info("[\u4EE3\u7406\u672A\u542F\u7528] enable_proxy=false \u4E14 proxy_url \u5DF2\u914D\u7F6E");
|
|
4993
|
+
logger8.info(`[\u6D41\u91CF\u89C2\u6D4B] \u9010\u8BF7\u6C42\u8C03\u8BD5=${Boolean(debugMode) ? "\u5F00\u542F" : "\u5173\u95ED"}\uFF08\u6C47\u603B\u59CB\u7EC8\u5F00\u542F\uFF09`);
|
|
4994
|
+
} else if (enableByPassLogger) {
|
|
4995
|
+
logger8.info(`[\u6D41\u91CF\u89C2\u6D4B] \u9010\u8BF7\u6C42\u8C03\u8BD5=${Boolean(debugMode) ? "\u5F00\u542F" : "\u5173\u95ED"}\uFF08\u6C47\u603B\u59CB\u7EC8\u5F00\u542F\uFF09`);
|
|
5205
4996
|
}
|
|
5206
|
-
logLaunchTraffic({
|
|
5207
|
-
...traffic,
|
|
5208
|
-
debugMode,
|
|
5209
|
-
enabled: enableByPassLogger
|
|
5210
|
-
});
|
|
5211
4997
|
const onPageCreated = (page) => {
|
|
5212
4998
|
const recommendedGotoOptions = {
|
|
5213
4999
|
waitUntil: "commit"
|
|
@@ -5215,7 +5001,22 @@ var DefaultLaunch = {
|
|
|
5215
5001
|
if (!page || typeof page.on !== "function") {
|
|
5216
5002
|
return recommendedGotoOptions;
|
|
5217
5003
|
}
|
|
5218
|
-
|
|
5004
|
+
if (page[REQUEST_HOOK_FLAG]) {
|
|
5005
|
+
return recommendedGotoOptions;
|
|
5006
|
+
}
|
|
5007
|
+
page[REQUEST_HOOK_FLAG] = true;
|
|
5008
|
+
const requestHandler = (req) => {
|
|
5009
|
+
const requestUrl = req.url();
|
|
5010
|
+
const resourceType = req.resourceType();
|
|
5011
|
+
const matched = byPassDomains.length > 0 ? ByPass.findMatchedByPassRule(byPassRules, requestUrl) : null;
|
|
5012
|
+
if (launchProxy) {
|
|
5013
|
+
ProxyMeterRuntime.recordProxyMeterResourceType(requestUrl, resourceType);
|
|
5014
|
+
}
|
|
5015
|
+
if (!enableByPassLogger || byPassDomains.length === 0) return;
|
|
5016
|
+
if (!matched || !matched.rule) return;
|
|
5017
|
+
logger8.info(`[\u76F4\u8FDE\u547D\u4E2D] \u89C4\u5219=${matched.rule.pattern} \u57DF\u540D=${matched.hostname} \u8D44\u6E90\u7C7B\u578B=${resourceType} \u65B9\u6CD5=${req.method()} \u5730\u5740=${requestUrl}`);
|
|
5018
|
+
};
|
|
5019
|
+
page.on("request", requestHandler);
|
|
5219
5020
|
return recommendedGotoOptions;
|
|
5220
5021
|
};
|
|
5221
5022
|
const launchContext = {
|
|
@@ -5232,20 +5033,23 @@ var DefaultLaunch = {
|
|
|
5232
5033
|
browserPoolOptions: replayBrowserPoolOptions || {
|
|
5233
5034
|
useFingerprints: true,
|
|
5234
5035
|
fingerprintOptions: {
|
|
5235
|
-
fingerprintGeneratorOptions:
|
|
5036
|
+
fingerprintGeneratorOptions: AntiCheat.getFingerprintGeneratorOptions({
|
|
5236
5037
|
locale: launchLocale,
|
|
5237
5038
|
device
|
|
5238
5039
|
})
|
|
5239
5040
|
},
|
|
5240
5041
|
prePageCreateHooks: [
|
|
5241
|
-
(
|
|
5042
|
+
async (pageId, browserController, pageOptions = {}) => {
|
|
5242
5043
|
const fingerprintWithHeaders = browserController?.launchContext?.fingerprint;
|
|
5243
|
-
const timezoneId =
|
|
5044
|
+
const timezoneId = AntiCheat.getBaseConfig().timezoneId;
|
|
5244
5045
|
applyFingerprintPageOptions(pageOptions, {
|
|
5245
5046
|
fingerprintWithHeaders,
|
|
5246
5047
|
locale: launchLocale,
|
|
5247
5048
|
timezoneId
|
|
5248
5049
|
});
|
|
5050
|
+
if (modifyPageOptions) {
|
|
5051
|
+
await modifyPageOptions(pageOptions, { pageId, browserController });
|
|
5052
|
+
}
|
|
5249
5053
|
}
|
|
5250
5054
|
]
|
|
5251
5055
|
},
|
|
@@ -5267,303 +5071,10 @@ var DefaultLaunch = {
|
|
|
5267
5071
|
}
|
|
5268
5072
|
};
|
|
5269
5073
|
|
|
5270
|
-
// src/internals/launch/cloak.js
|
|
5271
|
-
import { execFile } from "node:child_process";
|
|
5272
|
-
import { promisify } from "node:util";
|
|
5273
|
-
var logger9 = createInternalLogger("Launch");
|
|
5274
|
-
var execFileAsync = promisify(execFile);
|
|
5275
|
-
var DEFAULT_CLOAK_CRAWLER_BASE_OPTIONS = Object.freeze({
|
|
5276
|
-
maxConcurrency: 1,
|
|
5277
|
-
maxRequestRetries: 0,
|
|
5278
|
-
requestHandlerTimeoutSecs: 240,
|
|
5279
|
-
navigationTimeoutSecs: 120
|
|
5280
|
-
});
|
|
5281
|
-
var DEFAULT_CLOAK_HUMANIZE_OPTIONS = Object.freeze({
|
|
5282
|
-
humanize: true
|
|
5283
|
-
});
|
|
5284
|
-
var DEFAULT_CLOAK_GOTO_OPTIONS = Object.freeze({
|
|
5285
|
-
waitUntil: "commit"
|
|
5286
|
-
});
|
|
5287
|
-
var DEFAULT_CLOAK_FINGERPRINT_PLATFORM = "linux";
|
|
5288
|
-
var CLOAK_FINGERPRINT_PLATFORM_ARG_PREFIX = "--fingerprint-platform=";
|
|
5289
|
-
var SUPPORTED_CLOAK_FINGERPRINT_PLATFORMS = /* @__PURE__ */ new Set(["linux", "macos", "windows"]);
|
|
5290
|
-
var cachedCloakModulePromise = null;
|
|
5291
|
-
var hasOwn = (target, key) => Object.prototype.hasOwnProperty.call(target, key);
|
|
5292
|
-
var loadCloakModule = async () => {
|
|
5293
|
-
if (!cachedCloakModulePromise) {
|
|
5294
|
-
cachedCloakModulePromise = import("cloakbrowser").catch((error) => {
|
|
5295
|
-
cachedCloakModulePromise = null;
|
|
5296
|
-
throw new Error("Cloak \u6A21\u5757\u52A0\u8F7D\u5931\u8D25\uFF0C\u8BF7\u786E\u8BA4\u5F53\u524D\u8FD0\u884C\u73AF\u5883\u5DF2\u5B89\u88C5 cloakbrowser\u3002", {
|
|
5297
|
-
cause: error
|
|
5298
|
-
});
|
|
5299
|
-
});
|
|
5300
|
-
}
|
|
5301
|
-
return cachedCloakModulePromise;
|
|
5302
|
-
};
|
|
5303
|
-
var buildCloakLaunchOptions = async (options = {}) => {
|
|
5304
|
-
const { buildLaunchOptions } = await loadCloakModule();
|
|
5305
|
-
return await buildLaunchOptions(normalizeObject2(options));
|
|
5306
|
-
};
|
|
5307
|
-
var normalizeObject2 = (value) => {
|
|
5308
|
-
if (!value || typeof value !== "object" || Array.isArray(value)) {
|
|
5309
|
-
return {};
|
|
5310
|
-
}
|
|
5311
|
-
return value;
|
|
5312
|
-
};
|
|
5313
|
-
var normalizeStringArray = (value) => {
|
|
5314
|
-
if (!Array.isArray(value)) {
|
|
5315
|
-
return [];
|
|
5316
|
-
}
|
|
5317
|
-
return value.map((item) => String(item || "").trim()).filter(Boolean);
|
|
5318
|
-
};
|
|
5319
|
-
var resolveCloakFingerprintPlatformArg = (fingerprintPlatform = "", args = []) => {
|
|
5320
|
-
const normalizedFingerprintPlatform = String(fingerprintPlatform || "").trim().toLowerCase();
|
|
5321
|
-
if (SUPPORTED_CLOAK_FINGERPRINT_PLATFORMS.has(normalizedFingerprintPlatform)) {
|
|
5322
|
-
return `${CLOAK_FINGERPRINT_PLATFORM_ARG_PREFIX}${normalizedFingerprintPlatform}`;
|
|
5323
|
-
}
|
|
5324
|
-
const existingArg = normalizeStringArray(args).find((value) => value.startsWith(CLOAK_FINGERPRINT_PLATFORM_ARG_PREFIX));
|
|
5325
|
-
if (existingArg) {
|
|
5326
|
-
return existingArg;
|
|
5327
|
-
}
|
|
5328
|
-
return `${CLOAK_FINGERPRINT_PLATFORM_ARG_PREFIX}${DEFAULT_CLOAK_FINGERPRINT_PLATFORM}`;
|
|
5329
|
-
};
|
|
5330
|
-
var resolveCloakProxy = (proxyConfiguration = {}) => {
|
|
5331
|
-
const config = normalizeObject2(proxyConfiguration);
|
|
5332
|
-
const proxyUrl = String(config.proxy_url || "").trim();
|
|
5333
|
-
const enableProxy = typeof config.enable_proxy === "boolean" ? config.enable_proxy : proxyUrl !== "";
|
|
5334
|
-
if (!enableProxy || !proxyUrl) {
|
|
5335
|
-
return null;
|
|
5336
|
-
}
|
|
5337
|
-
const byPassDomains = ByPass.normalizeByPassDomains(config.by_pass_domains);
|
|
5338
|
-
if (byPassDomains.length === 0) {
|
|
5339
|
-
return proxyUrl;
|
|
5340
|
-
}
|
|
5341
|
-
const parsedProxyUrl = new URL(proxyUrl.includes("://") ? proxyUrl : `http://${proxyUrl}`);
|
|
5342
|
-
return {
|
|
5343
|
-
server: `${parsedProxyUrl.protocol}//${parsedProxyUrl.host}`,
|
|
5344
|
-
username: decodeURIComponent(parsedProxyUrl.username || ""),
|
|
5345
|
-
password: decodeURIComponent(parsedProxyUrl.password || ""),
|
|
5346
|
-
bypass: byPassDomains.join(",")
|
|
5347
|
-
};
|
|
5348
|
-
};
|
|
5349
|
-
var extractFingerprintArg = (launchOptions = {}) => {
|
|
5350
|
-
const args = Array.isArray(launchOptions?.args) ? launchOptions.args : [];
|
|
5351
|
-
return args.find((value) => String(value || "").startsWith("--fingerprint=")) || "";
|
|
5352
|
-
};
|
|
5353
|
-
var createStableGotoHook = (recommendedGotoOptions = DEFAULT_CLOAK_GOTO_OPTIONS) => {
|
|
5354
|
-
const normalizedRecommendedGotoOptions = normalizeObject2(recommendedGotoOptions);
|
|
5355
|
-
const fallbackGotoOptions = Object.keys(normalizedRecommendedGotoOptions).length > 0 ? normalizedRecommendedGotoOptions : DEFAULT_CLOAK_GOTO_OPTIONS;
|
|
5356
|
-
return async (_crawlingContext, gotoOptions = {}) => {
|
|
5357
|
-
for (const [key, value] of Object.entries(fallbackGotoOptions)) {
|
|
5358
|
-
if (gotoOptions[key] == null) {
|
|
5359
|
-
gotoOptions[key] = value;
|
|
5360
|
-
}
|
|
5361
|
-
}
|
|
5362
|
-
};
|
|
5363
|
-
};
|
|
5364
|
-
var attachCloakHumanizeHook = ({
|
|
5365
|
-
browserPoolOptions = {},
|
|
5366
|
-
activeBrowsers,
|
|
5367
|
-
patchedBrowsers,
|
|
5368
|
-
humanizeOptions = DEFAULT_CLOAK_HUMANIZE_OPTIONS
|
|
5369
|
-
} = {}) => {
|
|
5370
|
-
const normalizedBrowserPoolOptions = normalizeObject2(browserPoolOptions);
|
|
5371
|
-
const shouldHumanize = humanizeOptions !== false;
|
|
5372
|
-
const normalizedHumanizeOptions = shouldHumanize ? {
|
|
5373
|
-
...DEFAULT_CLOAK_HUMANIZE_OPTIONS,
|
|
5374
|
-
...normalizeObject2(humanizeOptions)
|
|
5375
|
-
} : null;
|
|
5376
|
-
return {
|
|
5377
|
-
...normalizedBrowserPoolOptions,
|
|
5378
|
-
useFingerprints: false,
|
|
5379
|
-
postLaunchHooks: [
|
|
5380
|
-
...Array.isArray(normalizedBrowserPoolOptions.postLaunchHooks) ? normalizedBrowserPoolOptions.postLaunchHooks : [],
|
|
5381
|
-
async (_pageId, browserController) => {
|
|
5382
|
-
const browser = browserController?.browser;
|
|
5383
|
-
if (!browser || typeof browser.contexts !== "function") {
|
|
5384
|
-
return;
|
|
5385
|
-
}
|
|
5386
|
-
activeBrowsers.add(browser);
|
|
5387
|
-
if (typeof browser.once === "function") {
|
|
5388
|
-
browser.once("disconnected", () => {
|
|
5389
|
-
activeBrowsers.delete(browser);
|
|
5390
|
-
});
|
|
5391
|
-
}
|
|
5392
|
-
if (!shouldHumanize || patchedBrowsers.has(browser)) {
|
|
5393
|
-
return;
|
|
5394
|
-
}
|
|
5395
|
-
const { humanizeBrowser } = await loadCloakModule();
|
|
5396
|
-
await humanizeBrowser(browser, normalizedHumanizeOptions);
|
|
5397
|
-
patchedBrowsers.add(browser);
|
|
5398
|
-
}
|
|
5399
|
-
]
|
|
5400
|
-
};
|
|
5401
|
-
};
|
|
5402
|
-
var closeTrackedBrowsers = async (activeBrowsers) => {
|
|
5403
|
-
const browsers = Array.from(activeBrowsers || []);
|
|
5404
|
-
activeBrowsers?.clear?.();
|
|
5405
|
-
await Promise.allSettled(
|
|
5406
|
-
browsers.map(async (browser) => {
|
|
5407
|
-
if (!browser || typeof browser.isConnected !== "function" || !browser.isConnected()) {
|
|
5408
|
-
return;
|
|
5409
|
-
}
|
|
5410
|
-
await browser.close().catch(() => {
|
|
5411
|
-
});
|
|
5412
|
-
})
|
|
5413
|
-
);
|
|
5414
|
-
};
|
|
5415
|
-
var forceTerminateBrowsersByFingerprintArg = async (fingerprintArg) => {
|
|
5416
|
-
if (!fingerprintArg) {
|
|
5417
|
-
return;
|
|
5418
|
-
}
|
|
5419
|
-
await execFileAsync("pkill", ["-f", "--", fingerprintArg]).catch((error) => {
|
|
5420
|
-
if (error?.code === 1 || error?.code === "ENOENT") {
|
|
5421
|
-
return;
|
|
5422
|
-
}
|
|
5423
|
-
logger9.info(`\u5F3A\u5236\u5173\u95ED Cloak \u8FDB\u7A0B\u5931\u8D25\uFF08\u5FFD\u7565\uFF09: ${error?.message || String(error)}`);
|
|
5424
|
-
});
|
|
5425
|
-
};
|
|
5426
|
-
var CloakLaunch = {
|
|
5427
|
-
resolveProxyConfiguration(proxyConfiguration = {}) {
|
|
5428
|
-
return resolveCloakProxy(proxyConfiguration);
|
|
5429
|
-
},
|
|
5430
|
-
extractFingerprintArg(launchOptions = {}) {
|
|
5431
|
-
return extractFingerprintArg(launchOptions);
|
|
5432
|
-
},
|
|
5433
|
-
createStableGotoHook(recommendedGotoOptions = DEFAULT_CLOAK_GOTO_OPTIONS) {
|
|
5434
|
-
return createStableGotoHook(recommendedGotoOptions);
|
|
5435
|
-
},
|
|
5436
|
-
async getPlaywrightCrawlerOptions(options = {}) {
|
|
5437
|
-
const runtime2 = await CloakLaunch.createPlaywrightCrawlerRuntime(options);
|
|
5438
|
-
return Object.defineProperties(runtime2.crawlerOptions, {
|
|
5439
|
-
cleanup: {
|
|
5440
|
-
enumerable: false,
|
|
5441
|
-
value: runtime2.cleanup
|
|
5442
|
-
},
|
|
5443
|
-
closeActiveBrowsers: {
|
|
5444
|
-
enumerable: false,
|
|
5445
|
-
value: runtime2.closeActiveBrowsers
|
|
5446
|
-
},
|
|
5447
|
-
forceTerminateActiveProcesses: {
|
|
5448
|
-
enumerable: false,
|
|
5449
|
-
value: runtime2.forceTerminateActiveProcesses
|
|
5450
|
-
}
|
|
5451
|
-
});
|
|
5452
|
-
},
|
|
5453
|
-
async buildLaunchOptions(options = {}) {
|
|
5454
|
-
return await buildCloakLaunchOptions(options);
|
|
5455
|
-
},
|
|
5456
|
-
async createPlaywrightCrawlerRuntime(options = {}) {
|
|
5457
|
-
const normalizedOptions = normalizeObject2(options);
|
|
5458
|
-
const {
|
|
5459
|
-
proxyConfiguration = {},
|
|
5460
|
-
log: logOptions = null,
|
|
5461
|
-
debugMode = false,
|
|
5462
|
-
runInHeadfulMode = false,
|
|
5463
|
-
isRunningOnApify = false,
|
|
5464
|
-
launcher = null,
|
|
5465
|
-
fingerprintPlatform = "",
|
|
5466
|
-
cloakOptions = {},
|
|
5467
|
-
humanizeOptions = DEFAULT_CLOAK_HUMANIZE_OPTIONS,
|
|
5468
|
-
crawlerBaseOptions = {},
|
|
5469
|
-
browserPoolOptions = {},
|
|
5470
|
-
launchContext = {},
|
|
5471
|
-
preNavigationHooks = [],
|
|
5472
|
-
postNavigationHooks = [],
|
|
5473
|
-
recommendedGotoOptions = DEFAULT_CLOAK_GOTO_OPTIONS
|
|
5474
|
-
} = normalizedOptions;
|
|
5475
|
-
const normalizedCloakOptions = normalizeObject2(cloakOptions);
|
|
5476
|
-
const activeBrowsers = /* @__PURE__ */ new Set();
|
|
5477
|
-
const patchedBrowsers = /* @__PURE__ */ new WeakSet();
|
|
5478
|
-
const defaultArgs = isRunningOnApify ? ["--no-sandbox", "--disable-setuid-sandbox"] : [];
|
|
5479
|
-
const fingerprintPlatformArg = resolveCloakFingerprintPlatformArg(fingerprintPlatform, normalizedCloakOptions.args);
|
|
5480
|
-
const extraArgs = normalizeStringArray(normalizedCloakOptions.args).filter((value) => !value.startsWith(CLOAK_FINGERPRINT_PLATFORM_ARG_PREFIX));
|
|
5481
|
-
const hasExplicitProxy = hasOwn(normalizedCloakOptions, "proxy");
|
|
5482
|
-
const proxyLaunchState = hasExplicitProxy ? resolveLaunchTraffic({ proxyConfiguration, debugMode, useMeter: false }) : resolveLaunchTraffic({ proxyConfiguration, debugMode });
|
|
5483
|
-
const proxy = hasExplicitProxy ? normalizedCloakOptions.proxy : proxyLaunchState.launchProxy;
|
|
5484
|
-
const headless = hasOwn(normalizedCloakOptions, "headless") ? normalizedCloakOptions.headless : !runInHeadfulMode || isRunningOnApify;
|
|
5485
|
-
const enableByPassLogger = Boolean(logOptions && logOptions.enable);
|
|
5486
|
-
const mergedCloakOptions = {
|
|
5487
|
-
...normalizedCloakOptions,
|
|
5488
|
-
headless,
|
|
5489
|
-
proxy,
|
|
5490
|
-
args: [...defaultArgs, ...extraArgs, fingerprintPlatformArg]
|
|
5491
|
-
};
|
|
5492
|
-
const launchOptions = await buildCloakLaunchOptions(mergedCloakOptions);
|
|
5493
|
-
const fingerprintArg = extractFingerprintArg(launchOptions);
|
|
5494
|
-
const internalPreNavigationHook = createStableGotoHook(recommendedGotoOptions);
|
|
5495
|
-
const trafficHook = createLaunchTrafficHook({
|
|
5496
|
-
byPassDomains: proxyLaunchState.byPassDomains,
|
|
5497
|
-
byPassRules: proxyLaunchState.byPassRules,
|
|
5498
|
-
enabled: enableByPassLogger,
|
|
5499
|
-
launchProxy: proxyLaunchState.launchProxy
|
|
5500
|
-
});
|
|
5501
|
-
const normalizedPreNavigationHooks = Array.isArray(preNavigationHooks) ? preNavigationHooks : [];
|
|
5502
|
-
const normalizedPostNavigationHooks = Array.isArray(postNavigationHooks) ? postNavigationHooks : [];
|
|
5503
|
-
logLaunchTraffic({
|
|
5504
|
-
...proxyLaunchState,
|
|
5505
|
-
debugMode,
|
|
5506
|
-
enabled: enableByPassLogger,
|
|
5507
|
-
explicitProxy: hasExplicitProxy
|
|
5508
|
-
});
|
|
5509
|
-
const crawlerOptions = {
|
|
5510
|
-
...DEFAULT_CLOAK_CRAWLER_BASE_OPTIONS,
|
|
5511
|
-
...normalizeObject2(crawlerBaseOptions),
|
|
5512
|
-
headless,
|
|
5513
|
-
launchContext: {
|
|
5514
|
-
useIncognitoPages: true,
|
|
5515
|
-
...normalizeObject2(launchContext),
|
|
5516
|
-
...launcher ? { launcher } : {},
|
|
5517
|
-
launchOptions
|
|
5518
|
-
},
|
|
5519
|
-
browserPoolOptions: attachCloakHumanizeHook({
|
|
5520
|
-
browserPoolOptions,
|
|
5521
|
-
activeBrowsers,
|
|
5522
|
-
patchedBrowsers,
|
|
5523
|
-
humanizeOptions
|
|
5524
|
-
}),
|
|
5525
|
-
preNavigationHooks: [
|
|
5526
|
-
async (crawlingContext, gotoOptions = {}) => {
|
|
5527
|
-
trafficHook(crawlingContext?.page);
|
|
5528
|
-
await internalPreNavigationHook(crawlingContext, gotoOptions);
|
|
5529
|
-
},
|
|
5530
|
-
...normalizedPreNavigationHooks
|
|
5531
|
-
],
|
|
5532
|
-
...normalizedPostNavigationHooks.length > 0 ? { postNavigationHooks: normalizedPostNavigationHooks } : {}
|
|
5533
|
-
};
|
|
5534
|
-
const closeActiveBrowsers = async () => {
|
|
5535
|
-
await closeTrackedBrowsers(activeBrowsers);
|
|
5536
|
-
};
|
|
5537
|
-
const forceTerminateActiveProcesses = async () => {
|
|
5538
|
-
await forceTerminateBrowsersByFingerprintArg(fingerprintArg);
|
|
5539
|
-
};
|
|
5540
|
-
const cleanup = async () => {
|
|
5541
|
-
await closeActiveBrowsers();
|
|
5542
|
-
await forceTerminateActiveProcesses();
|
|
5543
|
-
};
|
|
5544
|
-
return {
|
|
5545
|
-
headless,
|
|
5546
|
-
launchOptions,
|
|
5547
|
-
fingerprintArg,
|
|
5548
|
-
crawlerOptions,
|
|
5549
|
-
closeActiveBrowsers,
|
|
5550
|
-
forceTerminateActiveProcesses,
|
|
5551
|
-
cleanup
|
|
5552
|
-
};
|
|
5553
|
-
}
|
|
5554
|
-
};
|
|
5555
|
-
|
|
5556
|
-
// src/launch.js
|
|
5557
|
-
var launchStrategies = {
|
|
5558
|
-
[Mode.Default]: DefaultLaunch,
|
|
5559
|
-
[Mode.Cloak]: CloakLaunch
|
|
5560
|
-
};
|
|
5561
|
-
var Launch = withModeReflect("Launch", launchStrategies);
|
|
5562
|
-
|
|
5563
5074
|
// src/live-view.js
|
|
5564
5075
|
import express from "express";
|
|
5565
5076
|
import { Actor } from "apify";
|
|
5566
|
-
var
|
|
5077
|
+
var logger9 = createInternalLogger("LiveView");
|
|
5567
5078
|
async function startLiveViewServer(liveViewKey) {
|
|
5568
5079
|
const app = express();
|
|
5569
5080
|
app.get("/", async (req, res) => {
|
|
@@ -5588,13 +5099,13 @@ async function startLiveViewServer(liveViewKey) {
|
|
|
5588
5099
|
</html>
|
|
5589
5100
|
`);
|
|
5590
5101
|
} catch (error) {
|
|
5591
|
-
|
|
5102
|
+
logger9.fail("Live View Server", error);
|
|
5592
5103
|
res.status(500).send(`\u65E0\u6CD5\u52A0\u8F7D\u5C4F\u5E55\u622A\u56FE: ${error.message}`);
|
|
5593
5104
|
}
|
|
5594
5105
|
});
|
|
5595
5106
|
const port = process.env.APIFY_CONTAINER_PORT || 4321;
|
|
5596
5107
|
app.listen(port, () => {
|
|
5597
|
-
|
|
5108
|
+
logger9.success("startLiveViewServer", `\u76D1\u542C\u7AEF\u53E3 ${port}`);
|
|
5598
5109
|
});
|
|
5599
5110
|
}
|
|
5600
5111
|
async function takeLiveScreenshot(liveViewKey, page, logMessage) {
|
|
@@ -5602,10 +5113,10 @@ async function takeLiveScreenshot(liveViewKey, page, logMessage) {
|
|
|
5602
5113
|
const buffer = await capturePageScreenshot(page, { type: "png" });
|
|
5603
5114
|
await Actor.setValue(liveViewKey, buffer, { contentType: "image/png" });
|
|
5604
5115
|
if (logMessage) {
|
|
5605
|
-
|
|
5116
|
+
logger9.info(`(\u622A\u56FE): ${logMessage}`);
|
|
5606
5117
|
}
|
|
5607
5118
|
} catch (e) {
|
|
5608
|
-
|
|
5119
|
+
logger9.warn(`\u65E0\u6CD5\u6355\u83B7 Live View \u5C4F\u5E55\u622A\u56FE: ${e.message}`);
|
|
5609
5120
|
}
|
|
5610
5121
|
}
|
|
5611
5122
|
var useLiveView = (liveViewKey = PresetOfLiveViewKey) => {
|
|
@@ -5622,6 +5133,9 @@ var LiveView = {
|
|
|
5622
5133
|
useLiveView
|
|
5623
5134
|
};
|
|
5624
5135
|
|
|
5136
|
+
// src/chaptcha.js
|
|
5137
|
+
import { v4 as uuidv4 } from "uuid";
|
|
5138
|
+
|
|
5625
5139
|
// src/internals/captcha/bytedance.js
|
|
5626
5140
|
import { mkdir, writeFile } from "fs/promises";
|
|
5627
5141
|
import path2 from "path";
|
|
@@ -5711,7 +5225,7 @@ var dragCaptchaAction = async (page, sourceLocator, targetLocator, options = {})
|
|
|
5711
5225
|
};
|
|
5712
5226
|
|
|
5713
5227
|
// src/internals/captcha/bytedance.js
|
|
5714
|
-
var
|
|
5228
|
+
var logger10 = createInternalLogger("Captcha");
|
|
5715
5229
|
var DEFAULT_BYTEDANCE_CAPTCHA_OPTIONS = Object.freeze({
|
|
5716
5230
|
apiType: "31234",
|
|
5717
5231
|
maxRetries: 3,
|
|
@@ -5843,7 +5357,7 @@ var collectCaptchaDebugInfo = async (page, frame, iframeLocator, attempt, phase,
|
|
|
5843
5357
|
}
|
|
5844
5358
|
await writeFile(infoPath, JSON.stringify(payload, null, 2), "utf8");
|
|
5845
5359
|
}
|
|
5846
|
-
|
|
5360
|
+
logger10.info(`\u5DF2\u5199\u51FA\u9A8C\u8BC1\u7801\u8C03\u8BD5\u4EA7\u7269\uFF1A${debugDir}`);
|
|
5847
5361
|
};
|
|
5848
5362
|
var maybeCollectCaptchaDebugInfo = async (page, frame, iframeLocator, attempt, phase, options, extra = null) => {
|
|
5849
5363
|
if (!options.debugArtifacts) {
|
|
@@ -5880,14 +5394,14 @@ var getVerifycenterCaptchaContext = async (page, options) => {
|
|
|
5880
5394
|
if (!isContainerVisible) {
|
|
5881
5395
|
return null;
|
|
5882
5396
|
}
|
|
5883
|
-
|
|
5397
|
+
logger10.info("\u68C0\u6D4B\u5230\u9A8C\u8BC1\u7801\u5BB9\u5668\uFF0C\u5F00\u59CB\u7B49\u5F85 iframe \u52A0\u8F7D\u3002");
|
|
5884
5398
|
let iframeLocator = page.locator(options.iframeSelector).first();
|
|
5885
5399
|
let isIframeVisible = await waitForVisible(
|
|
5886
5400
|
iframeLocator,
|
|
5887
5401
|
options.iframeVisibleTimeoutMs
|
|
5888
5402
|
);
|
|
5889
5403
|
if (!isIframeVisible) {
|
|
5890
|
-
|
|
5404
|
+
logger10.warn("\u672A\u5728\u9884\u671F\u9009\u62E9\u5668\u4E2D\u627E\u5230 verifycenter iframe\uFF0C\u5C1D\u8BD5\u5BB9\u5668\u5185\u4EFB\u610F iframe\u3002");
|
|
5891
5405
|
iframeLocator = captchaContainer.locator(options.iframeFallbackSelector).first();
|
|
5892
5406
|
isIframeVisible = await waitForVisible(
|
|
5893
5407
|
iframeLocator,
|
|
@@ -5897,7 +5411,7 @@ var getVerifycenterCaptchaContext = async (page, options) => {
|
|
|
5897
5411
|
if (!isIframeVisible) {
|
|
5898
5412
|
throw new Error("verifycenter iframe not found inside captcha container.");
|
|
5899
5413
|
}
|
|
5900
|
-
|
|
5414
|
+
logger10.info("\u9A8C\u8BC1\u7801 iframe \u5DF2\u53EF\u89C1\uFF0C\u5F00\u59CB\u89E3\u6790\u5185\u5BB9 frame\u3002");
|
|
5901
5415
|
const frame = await resolveContentFrame(page, iframeLocator, options);
|
|
5902
5416
|
if (!frame) {
|
|
5903
5417
|
throw new Error("Failed to resolve verifycenter iframe content frame.");
|
|
@@ -6013,11 +5527,11 @@ var refreshCaptcha = async (page, frame, options) => {
|
|
|
6013
5527
|
const clicked = await clickCaptchaAction(frame, options.refreshTexts, {
|
|
6014
5528
|
...options,
|
|
6015
5529
|
page,
|
|
6016
|
-
logger:
|
|
5530
|
+
logger: logger10,
|
|
6017
5531
|
forceMouse: true
|
|
6018
5532
|
}).catch(() => false);
|
|
6019
5533
|
if (!clicked) {
|
|
6020
|
-
|
|
5534
|
+
logger10.warn("Refresh button not found.");
|
|
6021
5535
|
return false;
|
|
6022
5536
|
}
|
|
6023
5537
|
await page.waitForTimeout(options.refreshWaitMs);
|
|
@@ -6048,24 +5562,24 @@ var waitForCaptchaChallengeReady = async (page, frame, options) => {
|
|
|
6048
5562
|
const hasGuideMaskVisible = options.guideMaskSelector ? await frame.locator(options.guideMaskSelector).first().isVisible({ timeout: options.loadingIndicatorVisibleTimeoutMs }).catch(() => false) : false;
|
|
6049
5563
|
hasSeenGuideMask = hasSeenGuideMask || hasGuideMaskVisible;
|
|
6050
5564
|
if (hasGuideMaskVisible && !hasLoggedGuideMask) {
|
|
6051
|
-
|
|
5565
|
+
logger10.info("\u68C0\u6D4B\u5230\u9A8C\u8BC1\u7801\u64CD\u4F5C\u5F15\u5BFC\u5C42\uFF0C\u7B49\u5F85\u5176\u6D88\u5931\u540E\u518D\u5F00\u59CB\u8BC6\u522B\u3002");
|
|
6052
5566
|
hasLoggedGuideMask = true;
|
|
6053
5567
|
}
|
|
6054
5568
|
if (!isLoadingVisible && hasVisibleSourceImage && hasVisibleDropTarget && !hasGuideMaskVisible) {
|
|
6055
|
-
|
|
5569
|
+
logger10.info(
|
|
6056
5570
|
hasSeenGuideMask ? "\u9A8C\u8BC1\u7801\u56FE\u7247\u548C\u62D6\u62FD\u533A\u57DF\u5DF2\u5C31\u7EEA\uFF0C\u5F15\u5BFC\u5C42\u5DF2\u6D88\u5931\u3002" : hasSeenLoading ? "\u9A8C\u8BC1\u7801\u56FE\u7247\u5DF2\u52A0\u8F7D\u5B8C\u6210\u3002" : "\u9A8C\u8BC1\u7801\u56FE\u7247\u5DF2\u5C31\u7EEA\u3002"
|
|
6057
5571
|
);
|
|
6058
5572
|
return;
|
|
6059
5573
|
}
|
|
6060
5574
|
if (hasErrorTextVisible) {
|
|
6061
|
-
|
|
5575
|
+
logger10.warn("\u9A8C\u8BC1\u7801\u9762\u677F\u51FA\u73B0\u7F51\u7EDC\u5F02\u5E38\u6587\u6848\uFF0C\u5C1D\u8BD5\u7ACB\u5373\u5237\u65B0\u9898\u76EE\u3002");
|
|
6062
5576
|
await refreshCaptcha(page, frame, options);
|
|
6063
5577
|
refreshDeadline = Date.now() + options.challengeReadyRefreshTimeoutMs;
|
|
6064
5578
|
hasSeenLoading = false;
|
|
6065
5579
|
continue;
|
|
6066
5580
|
}
|
|
6067
5581
|
if ((!hasVisibleSourceImage || !hasVisibleDropTarget) && Date.now() >= refreshDeadline) {
|
|
6068
|
-
|
|
5582
|
+
logger10.warn(`\u9A8C\u8BC1\u7801\u9898\u76EE\u8D85\u8FC7 ${options.challengeReadyRefreshTimeoutMs}ms \u4ECD\u672A\u51C6\u5907\u597D\uFF0C\u5C1D\u8BD5\u5237\u65B0\u9898\u76EE\u3002`);
|
|
6069
5583
|
await refreshCaptcha(page, frame, options);
|
|
6070
5584
|
refreshDeadline = Date.now() + options.challengeReadyRefreshTimeoutMs;
|
|
6071
5585
|
hasSeenLoading = false;
|
|
@@ -6113,7 +5627,7 @@ var dragPromptCaptchaImage = async (page, frame, iframeLocator, sourceLocator, d
|
|
|
6113
5627
|
accepted
|
|
6114
5628
|
};
|
|
6115
5629
|
dragAttempts.push(attemptInfo);
|
|
6116
|
-
|
|
5630
|
+
logger10.info(
|
|
6117
5631
|
`\u9A8C\u8BC1\u7801\u62D6\u62FD\u7B2C ${visualIndex + 1} \u5F20\uFF0C\u65B9\u6848 ${plan.name}\uFF0Cbadge ${baselineState.badgeCount} -> ${afterState.badgeCount}\uFF0Cselected ${baselineState.selectedCount} -> ${afterState.selectedCount}`
|
|
6118
5632
|
);
|
|
6119
5633
|
if (accepted) {
|
|
@@ -6131,7 +5645,7 @@ var dragPromptCaptchaImage = async (page, frame, iframeLocator, sourceLocator, d
|
|
|
6131
5645
|
dragAttempts,
|
|
6132
5646
|
finalState: await readPromptCaptchaState(frame, options)
|
|
6133
5647
|
}).catch((error) => {
|
|
6134
|
-
|
|
5648
|
+
logger10.warn(`\u9A8C\u8BC1\u7801\u62D6\u62FD\u5931\u8D25\u8C03\u8BD5\u6293\u53D6\u5931\u8D25\uFF1A${error?.message || error}`);
|
|
6135
5649
|
});
|
|
6136
5650
|
return {
|
|
6137
5651
|
accepted: false,
|
|
@@ -6148,16 +5662,16 @@ async function solveCaptcha(page, options = {}, dependencies = {}) {
|
|
|
6148
5662
|
...options
|
|
6149
5663
|
};
|
|
6150
5664
|
if (!config.token) {
|
|
6151
|
-
|
|
5665
|
+
logger10.warn("\u7F3A\u5C11\u9A8C\u8BC1\u7801 token\uFF0C\u8DF3\u8FC7\u81EA\u52A8\u8BC6\u522B\u3002");
|
|
6152
5666
|
return false;
|
|
6153
5667
|
}
|
|
6154
|
-
|
|
5668
|
+
logger10.info("\u5F53\u524D\u4F7F\u7528\u672Ctool\u2014\u2014\u6D4B\u8BD5\u7248\u672C");
|
|
6155
5669
|
for (let attempt = 1; attempt <= config.maxRetries; attempt += 1) {
|
|
6156
|
-
|
|
5670
|
+
logger10.info(`\u5F00\u59CB\u7B2C ${attempt}/${config.maxRetries} \u6B21 verifycenter \u9A8C\u8BC1\u7801\u8BC6\u522B\u3002`);
|
|
6157
5671
|
try {
|
|
6158
5672
|
const captchaContext = await getVerifycenterCaptchaContext(page, config);
|
|
6159
5673
|
if (!captchaContext) {
|
|
6160
|
-
|
|
5674
|
+
logger10.info("Captcha container is not visible anymore.");
|
|
6161
5675
|
return true;
|
|
6162
5676
|
}
|
|
6163
5677
|
const { iframeLocator, frame } = captchaContext;
|
|
@@ -6170,7 +5684,7 @@ async function solveCaptcha(page, options = {}, dependencies = {}) {
|
|
|
6170
5684
|
"ready",
|
|
6171
5685
|
config
|
|
6172
5686
|
).catch((error) => {
|
|
6173
|
-
|
|
5687
|
+
logger10.warn(`\u9A8C\u8BC1\u7801\u8C03\u8BD5\u6293\u53D6\u5931\u8D25\uFF1A${error?.message || error}`);
|
|
6174
5688
|
});
|
|
6175
5689
|
await page.waitForTimeout(config.recognitionDelayMs);
|
|
6176
5690
|
const screenshotBuffer = await iframeLocator.screenshot();
|
|
@@ -6182,16 +5696,16 @@ async function solveCaptcha(page, options = {}, dependencies = {}) {
|
|
|
6182
5696
|
});
|
|
6183
5697
|
const serialNumbers = extractCaptchaSerialNumbers(apiResponse);
|
|
6184
5698
|
if (apiResponse?.code !== config.recognitionSuccessCode || serialNumbers.length === 0) {
|
|
6185
|
-
|
|
5699
|
+
logger10.warn(
|
|
6186
5700
|
`\u9A8C\u8BC1\u7801\u8BC6\u522B\u5931\u8D25\u3002code=${apiResponse?.code}, msg=${apiResponse?.msg || "unknown"}`
|
|
6187
5701
|
);
|
|
6188
5702
|
await refreshCaptcha(page, frame, config);
|
|
6189
5703
|
continue;
|
|
6190
5704
|
}
|
|
6191
|
-
|
|
5705
|
+
logger10.info(`\u9A8C\u8BC1\u7801\u8BC6\u522B\u6210\u529F\uFF0C\u5E8F\u53F7\uFF1A${serialNumbers.join(", ")}`);
|
|
6192
5706
|
const dropTarget = await findCaptchaDropTarget(frame, config);
|
|
6193
5707
|
if (!dropTarget) {
|
|
6194
|
-
|
|
5708
|
+
logger10.warn("\u672A\u627E\u5230\u9A8C\u8BC1\u7801\u62D6\u62FD\u76EE\u6807\u533A\u57DF\u3002");
|
|
6195
5709
|
await refreshCaptcha(page, frame, config);
|
|
6196
5710
|
continue;
|
|
6197
5711
|
}
|
|
@@ -6202,7 +5716,7 @@ async function solveCaptcha(page, options = {}, dependencies = {}) {
|
|
|
6202
5716
|
`Captcha image indexes could not be normalized. raw=${serialNumbers.join(", ")}, count=${orderedSourceImages.length}`
|
|
6203
5717
|
);
|
|
6204
5718
|
}
|
|
6205
|
-
|
|
5719
|
+
logger10.info(`\u9A8C\u8BC1\u7801\u89C6\u89C9\u4F4D\u5E8F\u6620\u5C04\uFF1A${normalizedIndexes.map((index) => index + 1).join(", ")}`);
|
|
6206
5720
|
for (const imageIndex of normalizedIndexes) {
|
|
6207
5721
|
if (imageIndex < 0 || imageIndex >= orderedSourceImages.length) {
|
|
6208
5722
|
throw new Error(
|
|
@@ -6234,55 +5748,52 @@ async function solveCaptcha(page, options = {}, dependencies = {}) {
|
|
|
6234
5748
|
}
|
|
6235
5749
|
}
|
|
6236
5750
|
const beforeSubmitState = await readPromptCaptchaState(frame, config);
|
|
6237
|
-
|
|
5751
|
+
logger10.info(
|
|
6238
5752
|
`\u63D0\u4EA4\u524D\u9A8C\u8BC1\u7801\u72B6\u6001\uFF1Abadge=${beforeSubmitState.badgeCount}, selected=${beforeSubmitState.selectedCount}, submitDisabled=${beforeSubmitState.submitDisabled}`
|
|
6239
5753
|
);
|
|
6240
5754
|
const submitted = await clickCaptchaAction(frame, config.submitTexts, {
|
|
6241
5755
|
...config,
|
|
6242
5756
|
page,
|
|
6243
|
-
logger:
|
|
5757
|
+
logger: logger10,
|
|
6244
5758
|
forceMouse: true,
|
|
6245
5759
|
actionVisibleTimeoutMs: config.submitReadyTimeoutMs
|
|
6246
5760
|
}).catch(() => false);
|
|
6247
5761
|
if (!submitted) {
|
|
6248
|
-
|
|
5762
|
+
logger10.warn("\u672A\u627E\u5230\u63D0\u4EA4\u6309\u94AE\uFF0C\u53EF\u80FD\u4F1A\u81EA\u52A8\u63D0\u4EA4\u3002");
|
|
6249
5763
|
}
|
|
6250
5764
|
await page.waitForTimeout(config.submitWaitMs);
|
|
6251
5765
|
const afterSubmitState = await readPromptCaptchaState(frame, config);
|
|
6252
|
-
|
|
5766
|
+
logger10.info(
|
|
6253
5767
|
`\u63D0\u4EA4\u540E\u9A8C\u8BC1\u7801\u72B6\u6001\uFF1Abadge=${afterSubmitState.badgeCount}, selected=${afterSubmitState.selectedCount}, submitDisabled=${afterSubmitState.submitDisabled}`
|
|
6254
5768
|
);
|
|
6255
5769
|
const stillVisible = await iframeLocator.isVisible({ timeout: config.containerVisibleTimeoutMs }).catch(() => false);
|
|
6256
5770
|
if (!stillVisible) {
|
|
6257
|
-
|
|
5771
|
+
logger10.info("\u9A8C\u8BC1\u7801\u8BC6\u522B\u5E76\u63D0\u4EA4\u6210\u529F\u3002");
|
|
6258
5772
|
return true;
|
|
6259
5773
|
}
|
|
6260
5774
|
await maybeCollectCaptchaDebugInfo(page, frame, iframeLocator, attempt, "submit-still-visible", config, {
|
|
6261
5775
|
beforeSubmitState,
|
|
6262
5776
|
afterSubmitState
|
|
6263
5777
|
}).catch((error) => {
|
|
6264
|
-
|
|
5778
|
+
logger10.warn(`\u63D0\u4EA4\u540E\u9A8C\u8BC1\u7801\u8C03\u8BD5\u6293\u53D6\u5931\u8D25\uFF1A${error?.message || error}`);
|
|
6265
5779
|
});
|
|
6266
|
-
|
|
5780
|
+
logger10.warn("\u63D0\u4EA4\u540E\u9A8C\u8BC1\u7801 iframe \u4ECD\u7136\u53EF\u89C1\uFF0C\u51C6\u5907\u5237\u65B0\u540E\u91CD\u8BD5\u3002");
|
|
6267
5781
|
await page.waitForTimeout(2e3);
|
|
6268
5782
|
await refreshCaptcha(page, frame, config);
|
|
6269
5783
|
} catch (error) {
|
|
6270
|
-
|
|
5784
|
+
logger10.error(`\u7B2C ${attempt}/${config.maxRetries} \u6B21\u9A8C\u8BC1\u7801\u8BC6\u522B\u5931\u8D25\uFF1A${error?.message || error}`);
|
|
6271
5785
|
}
|
|
6272
5786
|
if (attempt < config.maxRetries) {
|
|
6273
5787
|
await page.waitForTimeout(config.retryDelayBaseMs + attempt * config.retryDelayStepMs);
|
|
6274
5788
|
}
|
|
6275
5789
|
}
|
|
6276
|
-
|
|
5790
|
+
logger10.error(`\u91CD\u8BD5 ${config.maxRetries} \u6B21\u540E\uFF0C\u9A8C\u8BC1\u7801\u4ECD\u672A\u8BC6\u522B\u6210\u529F\u3002`);
|
|
6277
5791
|
return false;
|
|
6278
5792
|
}
|
|
6279
5793
|
var sloveCaptcha = solveCaptcha;
|
|
6280
5794
|
|
|
6281
5795
|
// src/chaptcha.js
|
|
6282
|
-
var
|
|
6283
|
-
var DOM_MONITOR_WAIT_TIMEOUT_MS = 1e3;
|
|
6284
|
-
var DOM_MONITOR_POST_DETECT_HIDDEN_WAIT_MS = 300;
|
|
6285
|
-
var DOM_MONITOR_RECOVERY_WAIT_MS = 100;
|
|
5796
|
+
var logger11 = createInternalLogger("Captcha");
|
|
6286
5797
|
var DEFAULT_CAPTCHA_RECOGNITION_OPTIONS = Object.freeze({
|
|
6287
5798
|
token: "eKJvBfwfN0YRav0-VD_44E2VBSfm7l0YtddUQ7cFySI",
|
|
6288
5799
|
apiUrl: "https://api.jfbym.com/api/YmServer/customApi"
|
|
@@ -6303,15 +5814,6 @@ var mergeDefinedOptions = (...sources) => {
|
|
|
6303
5814
|
}
|
|
6304
5815
|
return merged;
|
|
6305
5816
|
};
|
|
6306
|
-
var sleep = (ms) => new Promise((resolve) => {
|
|
6307
|
-
setTimeout(resolve, ms);
|
|
6308
|
-
});
|
|
6309
|
-
var getErrorMessage = (error) => String(error?.message || error || "");
|
|
6310
|
-
var isTimeoutError = (error) => error?.name === "TimeoutError" || getErrorMessage(error).includes("Timeout");
|
|
6311
|
-
var isPageLifecycleError = (error) => {
|
|
6312
|
-
const message = getErrorMessage(error);
|
|
6313
|
-
return message.includes("Execution context was destroyed") || message.includes("Frame was detached") || message.includes("Target page, context or browser has been closed") || message.includes("Target closed") || message.includes("Most likely the page has been closed");
|
|
6314
|
-
};
|
|
6315
5817
|
function useCaptchaMonitor(page, options) {
|
|
6316
5818
|
const { domSelector, urlPattern, onDetected } = options;
|
|
6317
5819
|
if (!domSelector && !urlPattern) {
|
|
@@ -6323,13 +5825,10 @@ function useCaptchaMonitor(page, options) {
|
|
|
6323
5825
|
let isStopped = false;
|
|
6324
5826
|
let isHandling = false;
|
|
6325
5827
|
let frameHandler = null;
|
|
6326
|
-
let
|
|
6327
|
-
let lastTriggeredAt = 0;
|
|
5828
|
+
let exposedFunctionName = null;
|
|
6328
5829
|
const triggerDetected = async () => {
|
|
6329
|
-
|
|
6330
|
-
if (isStopped || isHandling || now - lastTriggeredAt < 250) return;
|
|
5830
|
+
if (isStopped || isHandling) return;
|
|
6331
5831
|
isHandling = true;
|
|
6332
|
-
lastTriggeredAt = now;
|
|
6333
5832
|
try {
|
|
6334
5833
|
await onDetected();
|
|
6335
5834
|
} finally {
|
|
@@ -6338,38 +5837,60 @@ function useCaptchaMonitor(page, options) {
|
|
|
6338
5837
|
};
|
|
6339
5838
|
const cleanupFns = [];
|
|
6340
5839
|
if (domSelector) {
|
|
6341
|
-
|
|
6342
|
-
|
|
6343
|
-
|
|
6344
|
-
|
|
6345
|
-
|
|
6346
|
-
|
|
6347
|
-
|
|
6348
|
-
|
|
6349
|
-
|
|
6350
|
-
|
|
6351
|
-
|
|
6352
|
-
}).catch(() => {
|
|
6353
|
-
});
|
|
6354
|
-
} catch (error) {
|
|
6355
|
-
if (isStopped) break;
|
|
6356
|
-
if (page?.isClosed?.() && isPageLifecycleError(error)) break;
|
|
6357
|
-
if (isTimeoutError(error) || isPageLifecycleError(error)) {
|
|
6358
|
-
await sleep(DOM_MONITOR_RECOVERY_WAIT_MS);
|
|
6359
|
-
continue;
|
|
5840
|
+
exposedFunctionName = `__c_d_${uuidv4().replace(/-/g, "_")}`;
|
|
5841
|
+
const cleanerName = `__c_cleaner_${uuidv4().replace(/-/g, "_")}`;
|
|
5842
|
+
page.exposeFunction(exposedFunctionName, triggerDetected).catch(() => {
|
|
5843
|
+
});
|
|
5844
|
+
page.addInitScript(({ selector, callbackName, cleanerName: cleanupName }) => {
|
|
5845
|
+
(() => {
|
|
5846
|
+
let observer = null;
|
|
5847
|
+
const checkAndReport = () => {
|
|
5848
|
+
const element = document.querySelector(selector);
|
|
5849
|
+
if (!element) {
|
|
5850
|
+
return false;
|
|
6360
5851
|
}
|
|
6361
|
-
|
|
6362
|
-
|
|
6363
|
-
|
|
6364
|
-
|
|
6365
|
-
|
|
5852
|
+
if (window[callbackName]) {
|
|
5853
|
+
window[callbackName]();
|
|
5854
|
+
}
|
|
5855
|
+
return true;
|
|
5856
|
+
};
|
|
5857
|
+
checkAndReport();
|
|
5858
|
+
observer = new MutationObserver((mutations) => {
|
|
5859
|
+
const shouldCheck = mutations.some((mutation) => mutation.addedNodes.length > 0);
|
|
5860
|
+
if (shouldCheck && observer) {
|
|
5861
|
+
checkAndReport();
|
|
5862
|
+
}
|
|
5863
|
+
});
|
|
5864
|
+
const mountObserver = () => {
|
|
5865
|
+
const target = document.documentElement;
|
|
5866
|
+
if (target && observer) {
|
|
5867
|
+
observer.observe(target, { childList: true, subtree: true });
|
|
5868
|
+
}
|
|
5869
|
+
};
|
|
5870
|
+
if (document.readyState === "loading") {
|
|
5871
|
+
window.addEventListener("DOMContentLoaded", mountObserver);
|
|
5872
|
+
} else {
|
|
5873
|
+
mountObserver();
|
|
6366
5874
|
}
|
|
6367
|
-
|
|
6368
|
-
|
|
6369
|
-
|
|
5875
|
+
window[cleanupName] = () => {
|
|
5876
|
+
if (observer) {
|
|
5877
|
+
observer.disconnect();
|
|
5878
|
+
observer = null;
|
|
5879
|
+
}
|
|
5880
|
+
};
|
|
5881
|
+
})();
|
|
5882
|
+
}, { selector: domSelector, callbackName: exposedFunctionName, cleanerName });
|
|
5883
|
+
logger11.success("useCaptchaMonitor", `DOM \u76D1\u63A7\u5DF2\u542F\u7528\uFF1A${domSelector}`);
|
|
6370
5884
|
cleanupFns.push(async () => {
|
|
6371
|
-
|
|
6372
|
-
|
|
5885
|
+
try {
|
|
5886
|
+
await page.evaluate((name) => {
|
|
5887
|
+
if (window[name]) {
|
|
5888
|
+
window[name]();
|
|
5889
|
+
delete window[name];
|
|
5890
|
+
}
|
|
5891
|
+
}, cleanerName);
|
|
5892
|
+
} catch {
|
|
5893
|
+
}
|
|
6373
5894
|
});
|
|
6374
5895
|
}
|
|
6375
5896
|
if (urlPattern) {
|
|
@@ -6383,24 +5904,18 @@ function useCaptchaMonitor(page, options) {
|
|
|
6383
5904
|
}
|
|
6384
5905
|
};
|
|
6385
5906
|
page.on("framenavigated", frameHandler);
|
|
6386
|
-
|
|
6387
|
-
Promise.resolve().then(async () => {
|
|
6388
|
-
if (!isStopped && page.url().includes(urlPattern)) {
|
|
6389
|
-
await triggerDetected();
|
|
6390
|
-
}
|
|
6391
|
-
}).catch(() => {
|
|
6392
|
-
});
|
|
5907
|
+
logger11.success("useCaptchaMonitor", `URL \u76D1\u63A7\u5DF2\u542F\u7528\uFF1A${urlPattern}`);
|
|
6393
5908
|
cleanupFns.push(async () => {
|
|
6394
5909
|
page.off("framenavigated", frameHandler);
|
|
6395
5910
|
});
|
|
6396
5911
|
}
|
|
6397
5912
|
return {
|
|
6398
5913
|
stop: async () => {
|
|
6399
|
-
|
|
6400
|
-
isStopped = true;
|
|
5914
|
+
logger11.info("\u6B63\u5728\u505C\u6B62\u9A8C\u8BC1\u7801\u76D1\u63A7...");
|
|
6401
5915
|
for (const fn of cleanupFns) {
|
|
6402
5916
|
await fn();
|
|
6403
5917
|
}
|
|
5918
|
+
isStopped = true;
|
|
6404
5919
|
}
|
|
6405
5920
|
};
|
|
6406
5921
|
}
|
|
@@ -6435,7 +5950,7 @@ async function solveCaptchaWithStrategy(strategyName, page, options = {}) {
|
|
|
6435
5950
|
);
|
|
6436
5951
|
return strategy.sloveCaptcha(page, resolvedOptions, {
|
|
6437
5952
|
callCaptchaRecognitionApi,
|
|
6438
|
-
logger:
|
|
5953
|
+
logger: logger11
|
|
6439
5954
|
});
|
|
6440
5955
|
}
|
|
6441
5956
|
var Captcha = {
|
|
@@ -6445,15 +5960,15 @@ var Captcha = {
|
|
|
6445
5960
|
|
|
6446
5961
|
// src/mutation.js
|
|
6447
5962
|
import { createHash } from "node:crypto";
|
|
6448
|
-
import { v4 as
|
|
6449
|
-
var
|
|
5963
|
+
import { v4 as uuidv42 } from "uuid";
|
|
5964
|
+
var logger12 = createInternalLogger("Mutation");
|
|
6450
5965
|
var MUTATION_MONITOR_MODE = Object.freeze({
|
|
6451
5966
|
Added: "added",
|
|
6452
5967
|
Changed: "changed",
|
|
6453
5968
|
All: "all"
|
|
6454
5969
|
});
|
|
6455
5970
|
function generateKey(prefix) {
|
|
6456
|
-
return `__${prefix}_${
|
|
5971
|
+
return `__${prefix}_${uuidv42().replace(/-/g, "_")}`;
|
|
6457
5972
|
}
|
|
6458
5973
|
var Mutation = {
|
|
6459
5974
|
Mode: MUTATION_MONITOR_MODE,
|
|
@@ -6479,14 +5994,14 @@ var Mutation = {
|
|
|
6479
5994
|
const stableTime = options.stableTime ?? 5 * 1e3;
|
|
6480
5995
|
const timeout = options.timeout ?? 120 * 1e3;
|
|
6481
5996
|
const onMutation = options.onMutation;
|
|
6482
|
-
|
|
5997
|
+
logger12.start("waitForStable", `\u76D1\u63A7 ${selectorList.length} \u4E2A\u9009\u62E9\u5668, \u7A33\u5B9A\u65F6\u95F4=${stableTime}ms`);
|
|
6483
5998
|
if (initialTimeout > 0) {
|
|
6484
5999
|
const selectorQuery = selectorList.join(",");
|
|
6485
6000
|
try {
|
|
6486
6001
|
await page.waitForSelector(selectorQuery, { timeout: initialTimeout });
|
|
6487
|
-
|
|
6002
|
+
logger12.info(`waitForStable \u5DF2\u68C0\u6D4B\u5230\u5143\u7D20: ${selectorQuery}`);
|
|
6488
6003
|
} catch (e) {
|
|
6489
|
-
|
|
6004
|
+
logger12.warning(`waitForStable \u521D\u59CB\u7B49\u5F85\u8D85\u65F6 (${initialTimeout}ms): ${selectorQuery}`);
|
|
6490
6005
|
throw e;
|
|
6491
6006
|
}
|
|
6492
6007
|
}
|
|
@@ -6502,7 +6017,7 @@ var Mutation = {
|
|
|
6502
6017
|
return "__CONTINUE__";
|
|
6503
6018
|
}
|
|
6504
6019
|
});
|
|
6505
|
-
|
|
6020
|
+
logger12.info("waitForStable \u5DF2\u542F\u7528 onMutation \u56DE\u8C03");
|
|
6506
6021
|
} catch (e) {
|
|
6507
6022
|
}
|
|
6508
6023
|
}
|
|
@@ -6617,9 +6132,9 @@ var Mutation = {
|
|
|
6617
6132
|
{ selectorList, stableTime, timeout, callbackName, hasCallback: !!onMutation }
|
|
6618
6133
|
);
|
|
6619
6134
|
if (result.mutationCount === 0 && result.stableTime === 0) {
|
|
6620
|
-
|
|
6135
|
+
logger12.warning("waitForStable \u672A\u627E\u5230\u53EF\u76D1\u63A7\u7684\u5143\u7D20");
|
|
6621
6136
|
}
|
|
6622
|
-
|
|
6137
|
+
logger12.success("waitForStable", `DOM \u7A33\u5B9A, \u603B\u5171 ${result.mutationCount} \u6B21\u53D8\u5316${result.wasPaused ? ", \u66FE\u6682\u505C\u8BA1\u65F6" : ""}`);
|
|
6623
6138
|
return result;
|
|
6624
6139
|
},
|
|
6625
6140
|
/**
|
|
@@ -6643,7 +6158,7 @@ var Mutation = {
|
|
|
6643
6158
|
const overallTimeout = options.timeout ?? 180 * 1e3;
|
|
6644
6159
|
const onMutation = options.onMutation;
|
|
6645
6160
|
const pollInterval = 500;
|
|
6646
|
-
const
|
|
6161
|
+
const sleep = (ms) => new Promise((resolve) => {
|
|
6647
6162
|
setTimeout(resolve, ms);
|
|
6648
6163
|
});
|
|
6649
6164
|
const truncate = (value, max = 800) => {
|
|
@@ -6791,29 +6306,29 @@ var Mutation = {
|
|
|
6791
6306
|
return "__CONTINUE__";
|
|
6792
6307
|
}
|
|
6793
6308
|
};
|
|
6794
|
-
|
|
6309
|
+
logger12.start(
|
|
6795
6310
|
"waitForStableAcrossRoots",
|
|
6796
6311
|
`\u76D1\u63A7 ${selectorList.length} \u4E2A\u9009\u62E9\u5668(\u8DE8 root), \u7A33\u5B9A\u65F6\u95F4=${waitForStableTime}ms`
|
|
6797
6312
|
);
|
|
6798
6313
|
if (initialTimeout > 0) {
|
|
6799
6314
|
try {
|
|
6800
6315
|
await page.waitForSelector(selectorQuery, { timeout: initialTimeout });
|
|
6801
|
-
|
|
6316
|
+
logger12.info(`waitForStableAcrossRoots \u5DF2\u68C0\u6D4B\u5230\u5143\u7D20: ${selectorQuery}`);
|
|
6802
6317
|
} catch (e) {
|
|
6803
|
-
|
|
6318
|
+
logger12.warning(`waitForStableAcrossRoots \u521D\u59CB\u7B49\u5F85\u8D85\u65F6 (${initialTimeout}ms): ${selectorQuery}`);
|
|
6804
6319
|
throw e;
|
|
6805
6320
|
}
|
|
6806
6321
|
}
|
|
6807
|
-
let
|
|
6808
|
-
if (!
|
|
6809
|
-
|
|
6322
|
+
let state = await buildState();
|
|
6323
|
+
if (!state?.hasMatched) {
|
|
6324
|
+
logger12.warning("waitForStableAcrossRoots \u672A\u627E\u5230\u53EF\u76D1\u63A7\u7684\u5143\u7D20");
|
|
6810
6325
|
return { mutationCount: 0, stableTime: 0, wasPaused: false };
|
|
6811
6326
|
}
|
|
6812
6327
|
let mutationCount = 0;
|
|
6813
6328
|
let stableSince = 0;
|
|
6814
6329
|
let isPaused = false;
|
|
6815
6330
|
let wasPaused = false;
|
|
6816
|
-
let lastSnapshotKey =
|
|
6331
|
+
let lastSnapshotKey = state.snapshotKey;
|
|
6817
6332
|
const applyPauseSignal = (signal) => {
|
|
6818
6333
|
const nextPaused = signal === "__PAUSE__";
|
|
6819
6334
|
if (nextPaused) {
|
|
@@ -6827,15 +6342,15 @@ var Mutation = {
|
|
|
6827
6342
|
};
|
|
6828
6343
|
const initialSignal = await invokeMutationCallback({
|
|
6829
6344
|
mutationCount: 0,
|
|
6830
|
-
html:
|
|
6831
|
-
text:
|
|
6832
|
-
mutationNodes:
|
|
6345
|
+
html: state.html || "",
|
|
6346
|
+
text: state.text || "",
|
|
6347
|
+
mutationNodes: state.mutationNodes || []
|
|
6833
6348
|
});
|
|
6834
6349
|
applyPauseSignal(initialSignal);
|
|
6835
6350
|
const deadline = Date.now() + overallTimeout;
|
|
6836
|
-
let lastState =
|
|
6351
|
+
let lastState = state;
|
|
6837
6352
|
while (Date.now() < deadline) {
|
|
6838
|
-
await
|
|
6353
|
+
await sleep(pollInterval);
|
|
6839
6354
|
lastState = await buildState();
|
|
6840
6355
|
if (!lastState?.hasMatched) {
|
|
6841
6356
|
continue;
|
|
@@ -6843,7 +6358,7 @@ var Mutation = {
|
|
|
6843
6358
|
if (lastState.snapshotKey !== lastSnapshotKey) {
|
|
6844
6359
|
lastSnapshotKey = lastState.snapshotKey;
|
|
6845
6360
|
mutationCount += 1;
|
|
6846
|
-
|
|
6361
|
+
logger12.info(
|
|
6847
6362
|
`waitForStableAcrossRoots \u53D8\u5316#${mutationCount}, len=${lastState.snapshotLength}, path=${lastState.primaryPath || "unknown"}, preview="${truncate(lastState.text, 120)}"`
|
|
6848
6363
|
);
|
|
6849
6364
|
const signal = await invokeMutationCallback({
|
|
@@ -6856,7 +6371,7 @@ var Mutation = {
|
|
|
6856
6371
|
continue;
|
|
6857
6372
|
}
|
|
6858
6373
|
if (!isPaused && stableSince > 0 && Date.now() - stableSince >= waitForStableTime) {
|
|
6859
|
-
|
|
6374
|
+
logger12.success("waitForStableAcrossRoots", `DOM \u7A33\u5B9A, \u603B\u5171 ${mutationCount} \u6B21\u53D8\u5316${wasPaused ? ", \u66FE\u6682\u505C\u8BA1\u65F6" : ""}`);
|
|
6860
6375
|
return {
|
|
6861
6376
|
mutationCount,
|
|
6862
6377
|
stableTime: waitForStableTime,
|
|
@@ -6883,7 +6398,7 @@ var Mutation = {
|
|
|
6883
6398
|
const onMutation = options.onMutation;
|
|
6884
6399
|
const rawMode = String(options.mode || MUTATION_MONITOR_MODE.Added).toLowerCase();
|
|
6885
6400
|
const mode = [MUTATION_MONITOR_MODE.Added, MUTATION_MONITOR_MODE.Changed, MUTATION_MONITOR_MODE.All].includes(rawMode) ? rawMode : MUTATION_MONITOR_MODE.Added;
|
|
6886
|
-
|
|
6401
|
+
logger12.start("useMonitor", `\u76D1\u63A7 ${selectorList.length} \u4E2A\u9009\u62E9\u5668, mode=${mode}`);
|
|
6887
6402
|
const monitorKey = generateKey("pk_mon");
|
|
6888
6403
|
const callbackName = generateKey("pk_mon_cb");
|
|
6889
6404
|
const cleanerName = generateKey("pk_mon_clean");
|
|
@@ -7026,7 +6541,7 @@ var Mutation = {
|
|
|
7026
6541
|
return total;
|
|
7027
6542
|
};
|
|
7028
6543
|
}, { selectorList, monitorKey, callbackName, cleanerName, hasCallback: !!onMutation, mode });
|
|
7029
|
-
|
|
6544
|
+
logger12.success("useMonitor", "\u76D1\u63A7\u5668\u5DF2\u542F\u52A8");
|
|
7030
6545
|
return {
|
|
7031
6546
|
stop: async () => {
|
|
7032
6547
|
let totalMutations = 0;
|
|
@@ -7039,7 +6554,7 @@ var Mutation = {
|
|
|
7039
6554
|
}, cleanerName);
|
|
7040
6555
|
} catch (e) {
|
|
7041
6556
|
}
|
|
7042
|
-
|
|
6557
|
+
logger12.success("useMonitor.stop", `\u76D1\u63A7\u5DF2\u505C\u6B62, \u5171 ${totalMutations} \u6B21\u53D8\u5316`);
|
|
7043
6558
|
return { totalMutations };
|
|
7044
6559
|
}
|
|
7045
6560
|
};
|
|
@@ -7908,7 +7423,7 @@ var createTemplateLogger = (baseLogger = createBaseLogger()) => {
|
|
|
7908
7423
|
};
|
|
7909
7424
|
var getDefaultBaseLogger = () => createBaseLogger("");
|
|
7910
7425
|
var Logger = {
|
|
7911
|
-
setLogger: (
|
|
7426
|
+
setLogger: (logger16) => setDefaultLogger(logger16),
|
|
7912
7427
|
info: (message) => getDefaultBaseLogger().info(message),
|
|
7913
7428
|
success: (message) => getDefaultBaseLogger().success(message),
|
|
7914
7429
|
warning: (message) => getDefaultBaseLogger().warning(message),
|
|
@@ -7916,14 +7431,14 @@ var Logger = {
|
|
|
7916
7431
|
error: (message) => getDefaultBaseLogger().error(message),
|
|
7917
7432
|
debug: (message) => getDefaultBaseLogger().debug(message),
|
|
7918
7433
|
start: (message) => getDefaultBaseLogger().start(message),
|
|
7919
|
-
useTemplate: (
|
|
7920
|
-
if (
|
|
7434
|
+
useTemplate: (logger16) => {
|
|
7435
|
+
if (logger16) return createTemplateLogger(createBaseLogger("", logger16));
|
|
7921
7436
|
return createTemplateLogger();
|
|
7922
7437
|
}
|
|
7923
7438
|
};
|
|
7924
7439
|
|
|
7925
7440
|
// src/share.js
|
|
7926
|
-
import
|
|
7441
|
+
import delay4 from "delay";
|
|
7927
7442
|
|
|
7928
7443
|
// src/internals/watermarkify.js
|
|
7929
7444
|
var DEFAULT_TIMEZONE_OFFSET = 8;
|
|
@@ -7991,7 +7506,7 @@ var LOCATION_NETWORK_SUFFIX_PATTERNS = [
|
|
|
7991
7506
|
];
|
|
7992
7507
|
var cachedStripLogoSrcPromise = null;
|
|
7993
7508
|
var cachedEnrichmentByContext = /* @__PURE__ */ new WeakMap();
|
|
7994
|
-
var
|
|
7509
|
+
var logger13 = createInternalLogger("Watermarkify");
|
|
7995
7510
|
var normalizeText = (value) => String(value || "").trim();
|
|
7996
7511
|
var toInline = (value, maxLen = 200) => {
|
|
7997
7512
|
const text = normalizeText(value);
|
|
@@ -8233,9 +7748,9 @@ var resolveWithCustomResolver = async (page, baseMeta, options = {}) => {
|
|
|
8233
7748
|
location: toInline(resolved.location, 80)
|
|
8234
7749
|
};
|
|
8235
7750
|
if (enrichment.ip || enrichment.location) {
|
|
8236
|
-
|
|
7751
|
+
logger13.info(`\u81EA\u5B9A\u4E49 resolver \u547D\u4E2D: ip=${enrichment.ip || "-"}, loc=${enrichment.location || "-"}`);
|
|
8237
7752
|
} else {
|
|
8238
|
-
|
|
7753
|
+
logger13.warning("\u81EA\u5B9A\u4E49 resolver \u5DF2\u6267\u884C\uFF0C\u4F46\u672A\u8FD4\u56DE IP/Loc");
|
|
8239
7754
|
}
|
|
8240
7755
|
return enrichment;
|
|
8241
7756
|
} finally {
|
|
@@ -8419,17 +7934,14 @@ var buildWatermarkifyRenderHtml = ({ imageSrc, overlaySvg, width, height, imageH
|
|
|
8419
7934
|
</html>
|
|
8420
7935
|
`;
|
|
8421
7936
|
};
|
|
8422
|
-
var
|
|
8423
|
-
return String(value || "default").trim().toLowerCase() === "cloak" ? "cloak" : "default";
|
|
8424
|
-
};
|
|
8425
|
-
var composeScreenshotBufferWithBrowser = async (page, buffer, overlaySvg, imageInfo = {}, options = {}) => {
|
|
7937
|
+
var composeScreenshotBufferWithBrowser = async (page, buffer, overlaySvg, imageInfo = {}) => {
|
|
8426
7938
|
if (!page || typeof page.context !== "function") {
|
|
8427
|
-
|
|
7939
|
+
logger13.warning("watermarkify \u6D4F\u89C8\u5668\u5408\u6210\u8DF3\u8FC7: \u7F3A\u5C11\u53EF\u7528 page");
|
|
8428
7940
|
return buffer;
|
|
8429
7941
|
}
|
|
8430
7942
|
const renderScope = await openProbePage(page);
|
|
8431
7943
|
if (!renderScope?.page) {
|
|
8432
|
-
|
|
7944
|
+
logger13.warning("watermarkify \u6D4F\u89C8\u5668\u5408\u6210\u8DF3\u8FC7: \u65E0\u6CD5\u521B\u5EFA render page");
|
|
8433
7945
|
return buffer;
|
|
8434
7946
|
}
|
|
8435
7947
|
try {
|
|
@@ -8446,35 +7958,15 @@ var composeScreenshotBufferWithBrowser = async (page, buffer, overlaySvg, imageI
|
|
|
8446
7958
|
height: viewportHeight
|
|
8447
7959
|
}).catch(() => {
|
|
8448
7960
|
});
|
|
8449
|
-
|
|
8450
|
-
|
|
8451
|
-
|
|
8452
|
-
|
|
8453
|
-
|
|
8454
|
-
|
|
8455
|
-
|
|
8456
|
-
|
|
8457
|
-
|
|
8458
|
-
await renderPage.goto("about:blank", {
|
|
8459
|
-
waitUntil: "commit"
|
|
8460
|
-
}).catch(() => {
|
|
8461
|
-
});
|
|
8462
|
-
await renderPage.evaluate((html) => {
|
|
8463
|
-
document.open();
|
|
8464
|
-
document.write(html);
|
|
8465
|
-
document.close();
|
|
8466
|
-
}, renderHtml);
|
|
8467
|
-
} else {
|
|
8468
|
-
await renderPage.setContent(buildWatermarkifyRenderHtml({
|
|
8469
|
-
imageSrc: `data:${imageInfo.mimeType || "image/png"};base64,${buffer.toString("base64")}`,
|
|
8470
|
-
overlaySvg,
|
|
8471
|
-
width: safeWidth,
|
|
8472
|
-
height: safeHeight,
|
|
8473
|
-
imageHeight: safeImageHeight
|
|
8474
|
-
}), {
|
|
8475
|
-
waitUntil: "load"
|
|
8476
|
-
});
|
|
8477
|
-
}
|
|
7961
|
+
await renderPage.setContent(buildWatermarkifyRenderHtml({
|
|
7962
|
+
imageSrc: `data:${imageInfo.mimeType || "image/png"};base64,${buffer.toString("base64")}`,
|
|
7963
|
+
overlaySvg,
|
|
7964
|
+
width: safeWidth,
|
|
7965
|
+
height: safeHeight,
|
|
7966
|
+
imageHeight: safeImageHeight
|
|
7967
|
+
}), {
|
|
7968
|
+
waitUntil: "load"
|
|
7969
|
+
});
|
|
8478
7970
|
await renderPage.waitForFunction(() => {
|
|
8479
7971
|
const image = document.getElementById("pk-base-image");
|
|
8480
7972
|
return image instanceof HTMLImageElement && image.complete && image.naturalWidth > 0 && image.naturalHeight > 0;
|
|
@@ -8494,13 +7986,13 @@ var composeScreenshotBufferWithBrowser = async (page, buffer, overlaySvg, imageI
|
|
|
8494
7986
|
fullPage: true,
|
|
8495
7987
|
animations: "disabled"
|
|
8496
7988
|
}).catch((error) => {
|
|
8497
|
-
|
|
7989
|
+
logger13.warning(`watermarkify \u6D4F\u89C8\u5668\u5408\u6210\u5931\u8D25: ${error instanceof Error ? error.message : String(error)}`);
|
|
8498
7990
|
return null;
|
|
8499
7991
|
});
|
|
8500
7992
|
if (Buffer.isBuffer(composed) && composed.length > 0) {
|
|
8501
7993
|
return composed;
|
|
8502
7994
|
}
|
|
8503
|
-
|
|
7995
|
+
logger13.warning("watermarkify \u6D4F\u89C8\u5668\u5408\u6210\u5931\u8D25: \u672A\u5F97\u5230\u6709\u6548\u622A\u56FE\u7ED3\u679C");
|
|
8504
7996
|
return buffer;
|
|
8505
7997
|
} finally {
|
|
8506
7998
|
await renderScope.close().catch(() => {
|
|
@@ -8513,7 +8005,7 @@ var resolveWithIpLookup = async (page, options = {}) => {
|
|
|
8513
8005
|
}
|
|
8514
8006
|
const probeScope = await openProbePage(page);
|
|
8515
8007
|
if (!probeScope?.page) {
|
|
8516
|
-
|
|
8008
|
+
logger13.warning("ipLookup \u8DF3\u8FC7: \u65E0\u6CD5\u521B\u5EFA probe page");
|
|
8517
8009
|
return null;
|
|
8518
8010
|
}
|
|
8519
8011
|
const timeoutMs = Math.max(
|
|
@@ -8522,12 +8014,12 @@ var resolveWithIpLookup = async (page, options = {}) => {
|
|
|
8522
8014
|
);
|
|
8523
8015
|
try {
|
|
8524
8016
|
const probePage = probeScope.page;
|
|
8525
|
-
|
|
8017
|
+
logger13.info(`ipLookup \u5C1D\u8BD5: url=${DEFAULT_IP_LOOKUP_URL}, timeoutMs=${timeoutMs}`);
|
|
8526
8018
|
const response = await probePage.goto(DEFAULT_IP_LOOKUP_URL, {
|
|
8527
8019
|
waitUntil: "commit",
|
|
8528
8020
|
timeout: timeoutMs
|
|
8529
8021
|
}).catch((error) => {
|
|
8530
|
-
|
|
8022
|
+
logger13.warning(`ipLookup \u8BF7\u6C42\u5931\u8D25: url=${DEFAULT_IP_LOOKUP_URL}, error=${error instanceof Error ? error.message : String(error)}`);
|
|
8531
8023
|
return null;
|
|
8532
8024
|
});
|
|
8533
8025
|
const status = response && typeof response.status === "function" ? response.status() : 0;
|
|
@@ -8549,13 +8041,13 @@ var resolveWithIpLookup = async (page, options = {}) => {
|
|
|
8549
8041
|
}
|
|
8550
8042
|
const parsed = parseIpIpJsonResponse(rawText);
|
|
8551
8043
|
if (parsed?.ip || parsed?.location) {
|
|
8552
|
-
|
|
8044
|
+
logger13.info(`ipLookup \u6210\u529F: url=${DEFAULT_IP_LOOKUP_URL}, status=${status || "-"}, contentType=${contentType || "-"}, ip=${parsed.ip || "-"}, loc=${parsed.location || "-"}`);
|
|
8553
8045
|
return parsed;
|
|
8554
8046
|
}
|
|
8555
|
-
|
|
8047
|
+
logger13.warning(`ipLookup \u672A\u89E3\u6790\u51FA IP/Loc: url=${DEFAULT_IP_LOOKUP_URL}, status=${status || "-"}, contentType=${contentType || "-"}, preview=${shortenTail(rawText, 120) || "[empty]"}`);
|
|
8556
8048
|
return null;
|
|
8557
8049
|
} catch (error) {
|
|
8558
|
-
|
|
8050
|
+
logger13.warning(`ipLookup \u6267\u884C\u5F02\u5E38\uFF0C\u672A\u83B7\u5F97 IP/Loc: ${error instanceof Error ? error.message : String(error)}`);
|
|
8559
8051
|
return null;
|
|
8560
8052
|
} finally {
|
|
8561
8053
|
await probeScope.close().catch(() => {
|
|
@@ -8569,10 +8061,10 @@ var resolveEnrichment = async (page, baseMeta, options) => {
|
|
|
8569
8061
|
ip: toInline(options.ip, 80),
|
|
8570
8062
|
location: toInline(options.location, 80)
|
|
8571
8063
|
};
|
|
8572
|
-
|
|
8064
|
+
logger13.info(`enrichment \u5F00\u59CB: host=${baseMeta.hostname || "-"}, hasPresetIp=${Boolean(merged.ip)}, hasPresetLoc=${Boolean(merged.location)}, ipLookup=${options.ipLookup !== false}`);
|
|
8573
8065
|
if (!merged.ip || !merged.location) {
|
|
8574
8066
|
if (cached?.ip || cached?.location) {
|
|
8575
|
-
|
|
8067
|
+
logger13.info(`enrichment \u547D\u4E2D\u4E0A\u4E0B\u6587\u7F13\u5B58: ip=${cached.ip || "-"}, loc=${cached.location || "-"}`);
|
|
8576
8068
|
}
|
|
8577
8069
|
fillEnrichment(merged, cached);
|
|
8578
8070
|
}
|
|
@@ -8596,15 +8088,15 @@ var resolveEnrichment = async (page, baseMeta, options) => {
|
|
|
8596
8088
|
"x-geo-country"
|
|
8597
8089
|
]), 80);
|
|
8598
8090
|
if (!merged.location || isWeakLocationValue(merged.location) && headerLocation) {
|
|
8599
|
-
|
|
8091
|
+
logger13.info(`enrichment \u4F7F\u7528\u54CD\u5E94\u5934\u8865\u5145 Loc: ${headerLocation || "-"}`);
|
|
8600
8092
|
merged.location = headerLocation || merged.location;
|
|
8601
8093
|
}
|
|
8602
8094
|
}
|
|
8603
8095
|
writeCachedEnrichment(page, merged);
|
|
8604
8096
|
if (merged.ip || merged.location) {
|
|
8605
|
-
|
|
8097
|
+
logger13.info(`enrichment \u5B8C\u6210: ip=${merged.ip || "-"}, loc=${merged.location || "-"}`);
|
|
8606
8098
|
} else {
|
|
8607
|
-
|
|
8099
|
+
logger13.warning("enrichment \u5B8C\u6210: \u672A\u83B7\u5F97 IP/Loc");
|
|
8608
8100
|
}
|
|
8609
8101
|
return merged;
|
|
8610
8102
|
};
|
|
@@ -9409,7 +8901,7 @@ var buildWatermarkifySvg = (meta, imageWidth, imageHeight) => {
|
|
|
9409
8901
|
</svg>
|
|
9410
8902
|
`;
|
|
9411
8903
|
};
|
|
9412
|
-
var watermarkifyScreenshotBuffer = async (buffer, meta, page = null
|
|
8904
|
+
var watermarkifyScreenshotBuffer = async (buffer, meta, page = null) => {
|
|
9413
8905
|
const hasWatermark = meta?.watermark?.enabled !== false && normalizeText(meta?.watermarkText);
|
|
9414
8906
|
const hasStrip = meta?.strip?.enabled !== false && Array.isArray(meta?.stripSegments) && meta.stripSegments.length > 0;
|
|
9415
8907
|
if (!Buffer.isBuffer(buffer) || !meta || !hasWatermark && !hasStrip) {
|
|
@@ -9417,7 +8909,7 @@ var watermarkifyScreenshotBuffer = async (buffer, meta, page = null, options = {
|
|
|
9417
8909
|
}
|
|
9418
8910
|
const imageInfo = readImageInfo(buffer);
|
|
9419
8911
|
if (!imageInfo.width || !imageInfo.height || !imageInfo.mimeType) {
|
|
9420
|
-
|
|
8912
|
+
logger13.warning("watermarkify \u8DF3\u8FC7: \u65E0\u6CD5\u89E3\u6790\u622A\u56FE\u5C3A\u5BF8\u6216\u683C\u5F0F");
|
|
9421
8913
|
return buffer;
|
|
9422
8914
|
}
|
|
9423
8915
|
const isMobileStrip = normalizeDevice(meta.device) === Device.Mobile && hasStrip;
|
|
@@ -9430,12 +8922,12 @@ var watermarkifyScreenshotBuffer = async (buffer, meta, page = null, options = {
|
|
|
9430
8922
|
if (!overlaySvg) {
|
|
9431
8923
|
return buffer;
|
|
9432
8924
|
}
|
|
9433
|
-
return await composeScreenshotBufferWithBrowser(page, buffer, overlaySvg, outputImageInfo
|
|
8925
|
+
return await composeScreenshotBufferWithBrowser(page, buffer, overlaySvg, outputImageInfo);
|
|
9434
8926
|
};
|
|
9435
8927
|
|
|
9436
8928
|
// src/internals/compression.js
|
|
9437
8929
|
import { Jimp, JimpMime, ResizeStrategy } from "jimp";
|
|
9438
|
-
var
|
|
8930
|
+
var logger14 = createInternalLogger("Compression");
|
|
9439
8931
|
var DEFAULT_SCREENSHOT_MAX_BYTES = 5 * 1024 * 1024;
|
|
9440
8932
|
var DEFAULT_SCREENSHOT_OUTPUT_TYPE = "jpeg";
|
|
9441
8933
|
var DEFAULT_SCREENSHOT_QUALITY = 0.72;
|
|
@@ -9554,18 +9046,18 @@ var compressImageBufferToBase64 = async (buffer, compression) => {
|
|
|
9554
9046
|
return buffer.toString("base64");
|
|
9555
9047
|
}
|
|
9556
9048
|
const result = await compressImageBuffer(buffer, compression).catch((error) => {
|
|
9557
|
-
|
|
9049
|
+
logger14.warning(`captureScreen \u538B\u7F29\u5931\u8D25\uFF0C\u8FD4\u56DE\u539F\u56FE: ${error instanceof Error ? error.message : String(error)}`);
|
|
9558
9050
|
return null;
|
|
9559
9051
|
});
|
|
9560
9052
|
if (!result?.buffer) {
|
|
9561
9053
|
return buffer.toString("base64");
|
|
9562
9054
|
}
|
|
9563
9055
|
if (result.withinLimit) {
|
|
9564
|
-
|
|
9056
|
+
logger14.info(
|
|
9565
9057
|
`captureScreen \u5DF2\u538B\u7F29: ${originalBytes} -> ${result.bytes} bytes, format=${result.format}, quality=${result.quality}, scale=${result.scale}, size=${result.width}x${result.height}`
|
|
9566
9058
|
);
|
|
9567
9059
|
} else {
|
|
9568
|
-
|
|
9060
|
+
logger14.warning(
|
|
9569
9061
|
`captureScreen \u538B\u7F29\u540E\u4ECD\u8D85\u8FC7\u76EE\u6807: ${originalBytes} -> ${result.bytes} bytes, maxBytes=${compression.maxBytes}, format=${result.format}, quality=${result.quality}, scale=${result.scale}`
|
|
9570
9062
|
);
|
|
9571
9063
|
}
|
|
@@ -9573,7 +9065,7 @@ var compressImageBufferToBase64 = async (buffer, compression) => {
|
|
|
9573
9065
|
};
|
|
9574
9066
|
|
|
9575
9067
|
// src/share.js
|
|
9576
|
-
var
|
|
9068
|
+
var logger15 = createInternalLogger("Share");
|
|
9577
9069
|
var DEFAULT_TIMEOUT_MS2 = 50 * 1e3;
|
|
9578
9070
|
var DEFAULT_PAYLOAD_SNAPSHOT_MAX_LEN = 500;
|
|
9579
9071
|
var DEFAULT_POLL_INTERVAL_MS = 120;
|
|
@@ -9710,7 +9202,7 @@ var createDomShareMonitor = async (page, options = {}) => {
|
|
|
9710
9202
|
const onMatch = typeof options.onMatch === "function" ? options.onMatch : null;
|
|
9711
9203
|
const onTelemetry = typeof options.onTelemetry === "function" ? options.onTelemetry : null;
|
|
9712
9204
|
let matched = false;
|
|
9713
|
-
|
|
9205
|
+
logger15.info(`DOM \u76D1\u542C\u51C6\u5907\u6302\u8F7D: selectors=${toJsonInline(selectors, 120)}, mode=${mode}`);
|
|
9714
9206
|
const monitor = await Mutation.useMonitor(page, selectors, {
|
|
9715
9207
|
mode,
|
|
9716
9208
|
onMutation: (context = {}) => {
|
|
@@ -9728,12 +9220,12 @@ ${text}`;
|
|
|
9728
9220
|
});
|
|
9729
9221
|
}
|
|
9730
9222
|
if (mutationCount <= 5 || mutationCount % 50 === 0) {
|
|
9731
|
-
|
|
9223
|
+
logger15.info(`DOM \u53D8\u5316\u5DF2\u6355\u83B7: mutationCount=${mutationCount}, mutationNodes=${mutationNodes.length}`);
|
|
9732
9224
|
}
|
|
9733
9225
|
const [candidate] = Utils.parseLinks(rawDom, { prefix }) || [];
|
|
9734
9226
|
if (!candidate) return;
|
|
9735
9227
|
matched = true;
|
|
9736
|
-
|
|
9228
|
+
logger15.success("captureLink.domHit", `DOM \u547D\u4E2D\u5206\u4EAB\u94FE\u63A5: mutationCount=${mutationCount}, link=${candidate}`);
|
|
9737
9229
|
if (onMatch) {
|
|
9738
9230
|
onMatch({
|
|
9739
9231
|
link: candidate,
|
|
@@ -9749,7 +9241,7 @@ ${text}`;
|
|
|
9749
9241
|
return {
|
|
9750
9242
|
stop: async () => {
|
|
9751
9243
|
const result = await monitor.stop();
|
|
9752
|
-
|
|
9244
|
+
logger15.info(`DOM \u76D1\u542C\u5DF2\u505C\u6B62: totalMutations=${result?.totalMutations || 0}`);
|
|
9753
9245
|
return result;
|
|
9754
9246
|
}
|
|
9755
9247
|
};
|
|
@@ -9798,8 +9290,8 @@ var Share = {
|
|
|
9798
9290
|
if (share.mode === "response" && apiMatchers.length === 0) {
|
|
9799
9291
|
throw new Error("Share.captureLink requires share.xurl[0] api matcher when mode=response");
|
|
9800
9292
|
}
|
|
9801
|
-
|
|
9802
|
-
|
|
9293
|
+
logger15.start("captureLink", `mode=${share.mode}, timeoutMs=${timeoutDisabled ? "disabled" : timeoutMs}, prefix=${share.prefix}`);
|
|
9294
|
+
logger15.info(`captureLink \u914D\u7F6E: xurl=${toJsonInline(share.xurl)}, domMode=${domMode}, domSelectors=${toJsonInline(domSelectors, 120)}`);
|
|
9803
9295
|
const stats = {
|
|
9804
9296
|
actionTimedOut: false,
|
|
9805
9297
|
domMutationCount: 0,
|
|
@@ -9811,7 +9303,7 @@ var Share = {
|
|
|
9811
9303
|
responseSampleUrls: []
|
|
9812
9304
|
};
|
|
9813
9305
|
if (isAborted()) {
|
|
9814
|
-
|
|
9306
|
+
logger15.warning(`captureLink \u5DF2\u53D6\u6D88: ${abortReason()}`);
|
|
9815
9307
|
return {
|
|
9816
9308
|
link: null,
|
|
9817
9309
|
payloadText: "",
|
|
@@ -9834,7 +9326,7 @@ var Share = {
|
|
|
9834
9326
|
link: validated,
|
|
9835
9327
|
payloadText: String(payloadText || "")
|
|
9836
9328
|
};
|
|
9837
|
-
|
|
9329
|
+
logger15.info(`\u5019\u9009\u94FE\u63A5\u5DF2\u786E\u8BA4: source=${source}, link=${validated}`);
|
|
9838
9330
|
return true;
|
|
9839
9331
|
};
|
|
9840
9332
|
const resolveResponseCandidate = (responseText) => {
|
|
@@ -9869,7 +9361,7 @@ var Share = {
|
|
|
9869
9361
|
try {
|
|
9870
9362
|
await monitor.stop();
|
|
9871
9363
|
} catch (error) {
|
|
9872
|
-
|
|
9364
|
+
logger15.warning(`\u505C\u6B62 DOM \u76D1\u542C\u5931\u8D25: ${error instanceof Error ? error.message : String(error)}`);
|
|
9873
9365
|
}
|
|
9874
9366
|
};
|
|
9875
9367
|
const onResponse = async (response) => {
|
|
@@ -9883,29 +9375,29 @@ var Share = {
|
|
|
9883
9375
|
stats.responseSampleUrls.push(url);
|
|
9884
9376
|
}
|
|
9885
9377
|
if (stats.responseObserved <= 5) {
|
|
9886
|
-
|
|
9378
|
+
logger15.info(`\u63A5\u53E3\u54CD\u5E94\u91C7\u6837(${stats.responseObserved}): ${url}`);
|
|
9887
9379
|
}
|
|
9888
9380
|
if (!apiMatchers.some((matcher) => url.includes(matcher))) return;
|
|
9889
9381
|
stats.responseMatched += 1;
|
|
9890
9382
|
stats.lastMatchedUrl = url;
|
|
9891
|
-
|
|
9383
|
+
logger15.info(`\u63A5\u53E3\u547D\u4E2D\u5339\u914D(${stats.responseMatched}): ${url}`);
|
|
9892
9384
|
const text = await response.text();
|
|
9893
9385
|
const hit = resolveResponseCandidate(text);
|
|
9894
9386
|
if (!hit?.link) {
|
|
9895
9387
|
if (stats.responseMatched <= 3) {
|
|
9896
|
-
|
|
9388
|
+
logger15.info(`\u63A5\u53E3\u89E3\u6790\u5B8C\u6210\u4F46\u672A\u63D0\u53D6\u5230\u5206\u4EAB\u94FE\u63A5: payloadSize=${text.length}`);
|
|
9897
9389
|
}
|
|
9898
9390
|
return;
|
|
9899
9391
|
}
|
|
9900
9392
|
stats.responseResolved += 1;
|
|
9901
|
-
|
|
9393
|
+
logger15.success("captureLink.responseHit", `\u63A5\u53E3\u547D\u4E2D\u5206\u4EAB\u94FE\u63A5: url=${url}, link=${hit.link}`);
|
|
9902
9394
|
setCandidate("response", hit.link, hit.payloadText);
|
|
9903
9395
|
} catch (error) {
|
|
9904
|
-
|
|
9396
|
+
logger15.warning(`\u63A5\u53E3\u54CD\u5E94\u5904\u7406\u5F02\u5E38: ${error instanceof Error ? error.message : String(error)}`);
|
|
9905
9397
|
}
|
|
9906
9398
|
};
|
|
9907
9399
|
if (share.mode === "dom") {
|
|
9908
|
-
|
|
9400
|
+
logger15.info("\u5F53\u524D\u4E3A DOM \u6A21\u5F0F\uFF0C\u4EC5\u542F\u7528 DOM \u76D1\u542C");
|
|
9909
9401
|
domMonitor = await createDomShareMonitor(page, {
|
|
9910
9402
|
prefix: share.prefix,
|
|
9911
9403
|
selectors: domSelectors,
|
|
@@ -9920,17 +9412,17 @@ var Share = {
|
|
|
9920
9412
|
});
|
|
9921
9413
|
}
|
|
9922
9414
|
if (share.mode === "response") {
|
|
9923
|
-
|
|
9415
|
+
logger15.info(`\u5F53\u524D\u4E3A\u63A5\u53E3\u6A21\u5F0F\uFF0C\u6302\u8F7D response \u76D1\u542C: apiMatchers=${toJsonInline(apiMatchers, 160)}`);
|
|
9924
9416
|
page.on("response", onResponse);
|
|
9925
9417
|
}
|
|
9926
9418
|
if (share.mode === "custom") {
|
|
9927
|
-
|
|
9419
|
+
logger15.info("\u5F53\u524D\u4E3A custom \u6A21\u5F0F\uFF0C\u5C06\u4F7F\u7528 performActions \u8FD4\u56DE\u503C");
|
|
9928
9420
|
}
|
|
9929
9421
|
const deadline = timeoutDisabled ? Infinity : Date.now() + timeoutMs;
|
|
9930
9422
|
const getRemainingMs = () => timeoutDisabled ? Infinity : Math.max(0, deadline - Date.now());
|
|
9931
9423
|
try {
|
|
9932
9424
|
const actionTimeout = getRemainingMs();
|
|
9933
|
-
|
|
9425
|
+
logger15.start("captureLink.performActions", `\u6267\u884C\u52A8\u4F5C\u9884\u7B97=${timeoutDisabled ? "disabled" : `${actionTimeout}ms`}`);
|
|
9934
9426
|
let actionValue;
|
|
9935
9427
|
if (!isAborted() && actionTimeout > 0) {
|
|
9936
9428
|
let timer = null;
|
|
@@ -9943,30 +9435,30 @@ var Share = {
|
|
|
9943
9435
|
]);
|
|
9944
9436
|
if (timer) clearTimeout(timer);
|
|
9945
9437
|
if (actionResult.type === "error") {
|
|
9946
|
-
|
|
9438
|
+
logger15.fail("captureLink.performActions", actionResult.error);
|
|
9947
9439
|
throw actionResult.error;
|
|
9948
9440
|
}
|
|
9949
9441
|
if (actionResult.type === "timeout") {
|
|
9950
9442
|
stats.actionTimedOut = true;
|
|
9951
|
-
|
|
9443
|
+
logger15.warning(`performActions \u5DF2\u8D85\u65F6 (${actionTimeout}ms)\uFF0C\u52A8\u4F5C\u53EF\u80FD\u4ECD\u5728\u5F02\u6B65\u6267\u884C`);
|
|
9952
9444
|
} else {
|
|
9953
9445
|
actionValue = actionResult.result;
|
|
9954
|
-
|
|
9446
|
+
logger15.success("captureLink.performActions", "\u6267\u884C\u52A8\u4F5C\u5B8C\u6210");
|
|
9955
9447
|
}
|
|
9956
9448
|
}
|
|
9957
9449
|
if (share.mode === "custom") {
|
|
9958
9450
|
const customLink = typeof actionValue === "string" ? actionValue : actionValue?.link || actionValue?.payloadText;
|
|
9959
9451
|
const customPayloadText = typeof actionValue === "string" ? actionValue : actionValue?.payloadText;
|
|
9960
9452
|
if (setCandidate("custom", customLink, customPayloadText)) {
|
|
9961
|
-
|
|
9453
|
+
logger15.success("captureLink.customResult", `custom \u547D\u4E2D\u5206\u4EAB\u94FE\u63A5: link=${candidates.custom.link}`);
|
|
9962
9454
|
} else {
|
|
9963
|
-
|
|
9455
|
+
logger15.warning("performActions \u6267\u884C\u5B8C\u6210\u4F46\u672A\u8FD4\u56DE\u6709\u6548\u5206\u4EAB\u94FE\u63A5");
|
|
9964
9456
|
}
|
|
9965
9457
|
}
|
|
9966
9458
|
let nextProgressLogTs = Date.now() + 3e3;
|
|
9967
9459
|
while (true) {
|
|
9968
9460
|
if (isAborted()) {
|
|
9969
|
-
|
|
9461
|
+
logger15.warning(`captureLink \u5DF2\u53D6\u6D88: ${abortReason()}`);
|
|
9970
9462
|
return {
|
|
9971
9463
|
link: null,
|
|
9972
9464
|
payloadText: "",
|
|
@@ -9976,7 +9468,7 @@ var Share = {
|
|
|
9976
9468
|
}
|
|
9977
9469
|
const selected = candidates[share.mode];
|
|
9978
9470
|
if (selected?.link) {
|
|
9979
|
-
|
|
9471
|
+
logger15.success("captureLink", `\u6355\u83B7\u6210\u529F: source=${share.mode}, link=${selected.link}`);
|
|
9980
9472
|
return {
|
|
9981
9473
|
link: selected.link,
|
|
9982
9474
|
payloadText: selected.payloadText,
|
|
@@ -9989,19 +9481,19 @@ var Share = {
|
|
|
9989
9481
|
if (remaining <= 0) break;
|
|
9990
9482
|
const now = Date.now();
|
|
9991
9483
|
if (now >= nextProgressLogTs) {
|
|
9992
|
-
|
|
9484
|
+
logger15.info(
|
|
9993
9485
|
`captureLink \u7B49\u5F85\u4E2D: remaining=${timeoutDisabled ? "disabled" : `${remaining}ms`}, domMutationCount=${stats.domMutationCount}, responseMatched=${stats.responseMatched}`
|
|
9994
9486
|
);
|
|
9995
9487
|
nextProgressLogTs = now + 5e3;
|
|
9996
9488
|
}
|
|
9997
|
-
await
|
|
9489
|
+
await delay4(Math.max(0, Math.min(DEFAULT_POLL_INTERVAL_MS, remaining)));
|
|
9998
9490
|
}
|
|
9999
9491
|
if (!timeoutDisabled && share.mode === "response" && stats.responseMatched === 0) {
|
|
10000
|
-
|
|
9492
|
+
logger15.warning(
|
|
10001
9493
|
`\u63A5\u53E3\u76D1\u542C\u672A\u547D\u4E2D: apiMatchers=${toJsonInline(apiMatchers, 220)}, \u54CD\u5E94\u6837\u672CURLs=${toJsonInline(stats.responseSampleUrls, 420)}`
|
|
10002
9494
|
);
|
|
10003
9495
|
}
|
|
10004
|
-
|
|
9496
|
+
logger15.warning(
|
|
10005
9497
|
`captureLink ${timeoutDisabled ? "\u672A\u62FF\u5230\u94FE\u63A5" : "\u8D85\u65F6\u672A\u62FF\u5230\u94FE\u63A5"}: mode=${share.mode}, actionTimedOut=${stats.actionTimedOut}, domMutationCount=${stats.domMutationCount}, responseObserved=${stats.responseObserved}, responseMatched=${stats.responseMatched}, lastMatchedUrl=${stats.lastMatchedUrl || "none"}`
|
|
10006
9498
|
);
|
|
10007
9499
|
return {
|
|
@@ -10013,7 +9505,7 @@ var Share = {
|
|
|
10013
9505
|
} finally {
|
|
10014
9506
|
if (share.mode === "response") {
|
|
10015
9507
|
page.off("response", onResponse);
|
|
10016
|
-
|
|
9508
|
+
logger15.info("response \u76D1\u542C\u5DF2\u5378\u8F7D");
|
|
10017
9509
|
}
|
|
10018
9510
|
await stopDomMonitor();
|
|
10019
9511
|
}
|
|
@@ -10028,7 +9520,6 @@ var Share = {
|
|
|
10028
9520
|
* @param {number} [options.maxBytes] 默认 5MiB,返回 base64 超过后会压缩
|
|
10029
9521
|
* @param {'jpeg'|'jpg'} [options.type] 压缩输出格式,默认 jpeg
|
|
10030
9522
|
* @param {boolean|Object} [options.compression] 传 false 可关闭压缩
|
|
10031
|
-
* @param {'default'|'cloak'} [options.mode] 截图水印合成模式,默认 default
|
|
10032
9523
|
* @returns {Promise<string>} base64 image
|
|
10033
9524
|
*/
|
|
10034
9525
|
async captureScreen(page, options = {}) {
|
|
@@ -10049,9 +9540,7 @@ var Share = {
|
|
|
10049
9540
|
...screenshotWatermarkify,
|
|
10050
9541
|
capturedAt
|
|
10051
9542
|
});
|
|
10052
|
-
outputBuffer = await watermarkifyScreenshotBuffer(rawBuffer, watermarkifyMeta, page
|
|
10053
|
-
mode: options.mode
|
|
10054
|
-
});
|
|
9543
|
+
outputBuffer = await watermarkifyScreenshotBuffer(rawBuffer, watermarkifyMeta, page);
|
|
10055
9544
|
}
|
|
10056
9545
|
return await compressImageBufferToBase64(outputBuffer, compression);
|
|
10057
9546
|
}
|
|
@@ -10059,9 +9548,8 @@ var Share = {
|
|
|
10059
9548
|
|
|
10060
9549
|
// entrys/node.js
|
|
10061
9550
|
Logger.setLogger(crawleeLog);
|
|
10062
|
-
var usePlaywrightToolKit = (
|
|
10063
|
-
|
|
10064
|
-
const toolkit = {
|
|
9551
|
+
var usePlaywrightToolKit = () => {
|
|
9552
|
+
return {
|
|
10065
9553
|
ApifyKit,
|
|
10066
9554
|
AntiCheat,
|
|
10067
9555
|
DeviceInput,
|
|
@@ -10081,7 +9569,6 @@ var usePlaywrightToolKit = (mode = "default") => {
|
|
|
10081
9569
|
ByPass,
|
|
10082
9570
|
$Internals: { LOG_TEMPLATES, stripAnsi }
|
|
10083
9571
|
};
|
|
10084
|
-
return toolkit;
|
|
10085
9572
|
};
|
|
10086
9573
|
export {
|
|
10087
9574
|
usePlaywrightToolKit
|