@skrillex1224/playwright-toolkit 2.1.153 → 2.1.155
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 +15 -4
- package/dist/browser.js.map +2 -2
- package/dist/index.cjs +368 -89
- package/dist/index.cjs.map +4 -4
- package/dist/index.js +368 -89
- package/dist/index.js.map +4 -4
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -137,13 +137,24 @@ var ActorInfo = {
|
|
|
137
137
|
key: "douyin",
|
|
138
138
|
name: "\u6296\u97F3AI\u641C",
|
|
139
139
|
domain: "so.douyin.com",
|
|
140
|
-
path: "/
|
|
140
|
+
path: "/",
|
|
141
141
|
share: {
|
|
142
|
-
mode: "
|
|
142
|
+
mode: "dom",
|
|
143
143
|
prefix: "",
|
|
144
|
+
xurl: []
|
|
145
|
+
}
|
|
146
|
+
}),
|
|
147
|
+
lingguang: createActorInfo({
|
|
148
|
+
key: "lingguang",
|
|
149
|
+
name: "\u7075\u5149",
|
|
150
|
+
domain: "www.lingguang.com",
|
|
151
|
+
path: "/",
|
|
152
|
+
share: {
|
|
153
|
+
mode: "response",
|
|
154
|
+
prefix: "https://www.lingguang.com/share/",
|
|
144
155
|
xurl: [
|
|
145
|
-
"/
|
|
146
|
-
"
|
|
156
|
+
"/chat/shareChat.json",
|
|
157
|
+
"result"
|
|
147
158
|
]
|
|
148
159
|
}
|
|
149
160
|
}),
|
|
@@ -297,18 +308,18 @@ var fallbackLog = {
|
|
|
297
308
|
error: (...args) => console.error(...args),
|
|
298
309
|
debug: (...args) => console.debug ? console.debug(...args) : console.log(...args)
|
|
299
310
|
};
|
|
300
|
-
var resolveLogMethod = (
|
|
301
|
-
if (
|
|
302
|
-
return
|
|
311
|
+
var resolveLogMethod = (logger12, name) => {
|
|
312
|
+
if (logger12 && typeof logger12[name] === "function") {
|
|
313
|
+
return logger12[name].bind(logger12);
|
|
303
314
|
}
|
|
304
|
-
if (name === "warning" &&
|
|
305
|
-
return
|
|
315
|
+
if (name === "warning" && logger12 && typeof logger12.warn === "function") {
|
|
316
|
+
return logger12.warn.bind(logger12);
|
|
306
317
|
}
|
|
307
318
|
return fallbackLog[name];
|
|
308
319
|
};
|
|
309
320
|
var defaultLogger = null;
|
|
310
|
-
var setDefaultLogger = (
|
|
311
|
-
defaultLogger =
|
|
321
|
+
var setDefaultLogger = (logger12) => {
|
|
322
|
+
defaultLogger = logger12;
|
|
312
323
|
};
|
|
313
324
|
var resolveLogger = (explicitLogger) => {
|
|
314
325
|
if (explicitLogger && typeof explicitLogger.info === "function") {
|
|
@@ -335,8 +346,8 @@ var colorize = (text, color) => {
|
|
|
335
346
|
var createBaseLogger = (prefix = "", explicitLogger) => {
|
|
336
347
|
const name = prefix ? String(prefix) : "";
|
|
337
348
|
const dispatch = (methodName, icon, message, color) => {
|
|
338
|
-
const
|
|
339
|
-
const logFn = resolveLogMethod(
|
|
349
|
+
const logger12 = resolveLogger(explicitLogger);
|
|
350
|
+
const logFn = resolveLogMethod(logger12, methodName);
|
|
340
351
|
const timestamp = colorize(`[${formatTimestamp()}]`, ANSI.gray);
|
|
341
352
|
const line = formatLine(name, icon, message);
|
|
342
353
|
const coloredLine = colorize(line, color);
|
|
@@ -441,6 +452,20 @@ var CrawlerError = class _CrawlerError extends Error {
|
|
|
441
452
|
|
|
442
453
|
// src/apify-kit.js
|
|
443
454
|
import { serializeError as serializeError2 } from "serialize-error";
|
|
455
|
+
|
|
456
|
+
// src/traffic-runtime.js
|
|
457
|
+
var trafficMeter = null;
|
|
458
|
+
var setTrafficMeter = (meter) => {
|
|
459
|
+
trafficMeter = meter || null;
|
|
460
|
+
};
|
|
461
|
+
var getTrafficSnapshot = () => {
|
|
462
|
+
if (!trafficMeter || typeof trafficMeter.snapshot !== "function") {
|
|
463
|
+
return null;
|
|
464
|
+
}
|
|
465
|
+
return trafficMeter.snapshot();
|
|
466
|
+
};
|
|
467
|
+
|
|
468
|
+
// src/apify-kit.js
|
|
444
469
|
var logger = createInternalLogger("ApifyKit");
|
|
445
470
|
async function createApifyKit() {
|
|
446
471
|
let apify = null;
|
|
@@ -554,10 +579,12 @@ async function createApifyKit() {
|
|
|
554
579
|
* @param {Object} data - 要推送的数据对象
|
|
555
580
|
*/
|
|
556
581
|
async pushSuccess(data) {
|
|
582
|
+
const traffic = getTrafficSnapshot();
|
|
557
583
|
await Actor2.pushData({
|
|
558
584
|
// 固定为0
|
|
559
585
|
code: Code.Success,
|
|
560
586
|
status: Status.Success,
|
|
587
|
+
...traffic ? { traffic } : {},
|
|
561
588
|
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
562
589
|
data
|
|
563
590
|
});
|
|
@@ -574,10 +601,12 @@ async function createApifyKit() {
|
|
|
574
601
|
const isCrawlerError = CrawlerError.isCrawlerError(error);
|
|
575
602
|
const code = isCrawlerError ? error.code : Code.UnknownError;
|
|
576
603
|
const context = isCrawlerError ? error.context : {};
|
|
604
|
+
const traffic = getTrafficSnapshot();
|
|
577
605
|
await Actor2.pushData({
|
|
578
606
|
// 如果是 CrawlerError,使用其 code,否则使用默认 Failed code
|
|
579
607
|
code,
|
|
580
608
|
status: Status.Failed,
|
|
609
|
+
...traffic ? { traffic } : {},
|
|
581
610
|
error: serializeError2(error),
|
|
582
611
|
meta,
|
|
583
612
|
context,
|
|
@@ -1197,9 +1226,12 @@ var Humanize = {
|
|
|
1197
1226
|
}
|
|
1198
1227
|
};
|
|
1199
1228
|
|
|
1200
|
-
// src/
|
|
1229
|
+
// src/proxy-bypass.js
|
|
1201
1230
|
import picomatch from "picomatch";
|
|
1202
|
-
var
|
|
1231
|
+
var normalizeByPassDomains = (domains) => {
|
|
1232
|
+
if (!Array.isArray(domains)) return [];
|
|
1233
|
+
return domains.map((item) => String(item || "").trim()).filter(Boolean);
|
|
1234
|
+
};
|
|
1203
1235
|
var buildByPassDomainRule = (rawPattern) => {
|
|
1204
1236
|
const pattern = String(rawPattern || "").trim().toLowerCase();
|
|
1205
1237
|
if (!pattern) return null;
|
|
@@ -1214,10 +1246,255 @@ var buildByPassDomainRule = (rawPattern) => {
|
|
|
1214
1246
|
test: (hostname) => matcher(String(hostname || "").toLowerCase())
|
|
1215
1247
|
};
|
|
1216
1248
|
};
|
|
1217
|
-
var
|
|
1218
|
-
|
|
1219
|
-
return domains.map((item) => String(item || "").trim()).filter(Boolean);
|
|
1249
|
+
var buildByPassDomainRules = (domains = []) => {
|
|
1250
|
+
return normalizeByPassDomains(domains).map((domain) => buildByPassDomainRule(domain)).filter(Boolean);
|
|
1220
1251
|
};
|
|
1252
|
+
var findMatchedByPassRule = (rules = [], requestUrl = "") => {
|
|
1253
|
+
let hostname = "";
|
|
1254
|
+
try {
|
|
1255
|
+
hostname = new URL(String(requestUrl || "")).hostname.toLowerCase();
|
|
1256
|
+
} catch {
|
|
1257
|
+
return null;
|
|
1258
|
+
}
|
|
1259
|
+
for (const rule of rules) {
|
|
1260
|
+
if (rule && typeof rule.test === "function" && rule.test(hostname)) {
|
|
1261
|
+
return {
|
|
1262
|
+
rule,
|
|
1263
|
+
hostname
|
|
1264
|
+
};
|
|
1265
|
+
}
|
|
1266
|
+
}
|
|
1267
|
+
return {
|
|
1268
|
+
rule: null,
|
|
1269
|
+
hostname
|
|
1270
|
+
};
|
|
1271
|
+
};
|
|
1272
|
+
var resolveRouteByProxy = ({
|
|
1273
|
+
requestUrl = "",
|
|
1274
|
+
enableProxy = false,
|
|
1275
|
+
byPassRules = []
|
|
1276
|
+
}) => {
|
|
1277
|
+
if (!enableProxy) {
|
|
1278
|
+
return { route: "direct", matchedRule: null, hostname: "" };
|
|
1279
|
+
}
|
|
1280
|
+
const matched = findMatchedByPassRule(byPassRules, requestUrl);
|
|
1281
|
+
if (!matched) {
|
|
1282
|
+
return { route: "proxy", matchedRule: null, hostname: "" };
|
|
1283
|
+
}
|
|
1284
|
+
if (matched.rule) {
|
|
1285
|
+
return { route: "direct", matchedRule: matched.rule, hostname: matched.hostname };
|
|
1286
|
+
}
|
|
1287
|
+
return { route: "proxy", matchedRule: null, hostname: matched.hostname };
|
|
1288
|
+
};
|
|
1289
|
+
|
|
1290
|
+
// src/traffic-meter.js
|
|
1291
|
+
var logger5 = createInternalLogger("TrafficMeter");
|
|
1292
|
+
var encoder = new TextEncoder();
|
|
1293
|
+
var toSafeNumber = (value) => {
|
|
1294
|
+
if (typeof value !== "number" || !Number.isFinite(value) || value <= 0) return 0;
|
|
1295
|
+
return Math.round(value);
|
|
1296
|
+
};
|
|
1297
|
+
var byteLength = (value) => {
|
|
1298
|
+
const text = String(value || "");
|
|
1299
|
+
if (!text) return 0;
|
|
1300
|
+
try {
|
|
1301
|
+
return encoder.encode(text).length;
|
|
1302
|
+
} catch {
|
|
1303
|
+
return text.length;
|
|
1304
|
+
}
|
|
1305
|
+
};
|
|
1306
|
+
var normalizeHeaderValue = (value) => {
|
|
1307
|
+
if (Array.isArray(value)) return value.join(",");
|
|
1308
|
+
if (value === null || value === void 0) return "";
|
|
1309
|
+
return String(value);
|
|
1310
|
+
};
|
|
1311
|
+
var estimateRequestBytes = (request = {}) => {
|
|
1312
|
+
const method = String(request.method || "GET");
|
|
1313
|
+
const url = String(request.url || "");
|
|
1314
|
+
let total = byteLength(`${method} ${url} HTTP/1.1\r
|
|
1315
|
+
`);
|
|
1316
|
+
const headers = request.headers && typeof request.headers === "object" ? request.headers : {};
|
|
1317
|
+
Object.entries(headers).forEach(([key, value]) => {
|
|
1318
|
+
total += byteLength(`${key}: ${normalizeHeaderValue(value)}\r
|
|
1319
|
+
`);
|
|
1320
|
+
});
|
|
1321
|
+
total += 2;
|
|
1322
|
+
if (typeof request.postData === "string" && request.postData) {
|
|
1323
|
+
total += byteLength(request.postData);
|
|
1324
|
+
}
|
|
1325
|
+
return total;
|
|
1326
|
+
};
|
|
1327
|
+
var createTrafficState = () => ({
|
|
1328
|
+
totalRequests: 0,
|
|
1329
|
+
proxyRequests: 0,
|
|
1330
|
+
directRequests: 0,
|
|
1331
|
+
totalUploadBytes: 0,
|
|
1332
|
+
proxyUploadBytes: 0,
|
|
1333
|
+
directUploadBytes: 0,
|
|
1334
|
+
totalDownloadBytes: 0,
|
|
1335
|
+
proxyDownloadBytes: 0,
|
|
1336
|
+
directDownloadBytes: 0
|
|
1337
|
+
});
|
|
1338
|
+
var ensureRoute = (route) => route === "proxy" ? "proxy" : "direct";
|
|
1339
|
+
var addRequests = (state, route, count = 1) => {
|
|
1340
|
+
const c = toSafeNumber(count);
|
|
1341
|
+
if (c <= 0) return;
|
|
1342
|
+
const normalizedRoute = ensureRoute(route);
|
|
1343
|
+
state.totalRequests += c;
|
|
1344
|
+
if (normalizedRoute === "proxy") {
|
|
1345
|
+
state.proxyRequests += c;
|
|
1346
|
+
return;
|
|
1347
|
+
}
|
|
1348
|
+
state.directRequests += c;
|
|
1349
|
+
};
|
|
1350
|
+
var addUploadBytes = (state, route, bytes = 0) => {
|
|
1351
|
+
const b = toSafeNumber(bytes);
|
|
1352
|
+
if (b <= 0) return;
|
|
1353
|
+
const normalizedRoute = ensureRoute(route);
|
|
1354
|
+
state.totalUploadBytes += b;
|
|
1355
|
+
if (normalizedRoute === "proxy") {
|
|
1356
|
+
state.proxyUploadBytes += b;
|
|
1357
|
+
return;
|
|
1358
|
+
}
|
|
1359
|
+
state.directUploadBytes += b;
|
|
1360
|
+
};
|
|
1361
|
+
var addDownloadBytes = (state, route, bytes = 0) => {
|
|
1362
|
+
const b = toSafeNumber(bytes);
|
|
1363
|
+
if (b <= 0) return;
|
|
1364
|
+
const normalizedRoute = ensureRoute(route);
|
|
1365
|
+
state.totalDownloadBytes += b;
|
|
1366
|
+
if (normalizedRoute === "proxy") {
|
|
1367
|
+
state.proxyDownloadBytes += b;
|
|
1368
|
+
return;
|
|
1369
|
+
}
|
|
1370
|
+
state.directDownloadBytes += b;
|
|
1371
|
+
};
|
|
1372
|
+
var createTrafficMeter = ({
|
|
1373
|
+
enableProxy = false,
|
|
1374
|
+
byPassRules = []
|
|
1375
|
+
} = {}) => {
|
|
1376
|
+
const state = createTrafficState();
|
|
1377
|
+
const requestMap = /* @__PURE__ */ new Map();
|
|
1378
|
+
const wsRouteMap = /* @__PURE__ */ new Map();
|
|
1379
|
+
const resolveRoute = (url = "") => {
|
|
1380
|
+
return resolveRouteByProxy({
|
|
1381
|
+
requestUrl: url,
|
|
1382
|
+
enableProxy,
|
|
1383
|
+
byPassRules
|
|
1384
|
+
}).route;
|
|
1385
|
+
};
|
|
1386
|
+
const recordRequest = (params = {}) => {
|
|
1387
|
+
const requestId = String(params.requestId || "");
|
|
1388
|
+
const request = params.request && typeof params.request === "object" ? params.request : {};
|
|
1389
|
+
const route = resolveRoute(request.url || "");
|
|
1390
|
+
addRequests(state, route, 1);
|
|
1391
|
+
const uploadBytes = estimateRequestBytes(request);
|
|
1392
|
+
addUploadBytes(state, route, uploadBytes);
|
|
1393
|
+
if (requestId) {
|
|
1394
|
+
requestMap.set(requestId, {
|
|
1395
|
+
route
|
|
1396
|
+
});
|
|
1397
|
+
}
|
|
1398
|
+
};
|
|
1399
|
+
const recordLoadingFinished = (params = {}) => {
|
|
1400
|
+
const requestId = String(params.requestId || "");
|
|
1401
|
+
const requestState = requestId ? requestMap.get(requestId) : null;
|
|
1402
|
+
const route = requestState?.route || "direct";
|
|
1403
|
+
const downloadBytes = toSafeNumber(params.encodedDataLength);
|
|
1404
|
+
addDownloadBytes(state, route, downloadBytes);
|
|
1405
|
+
if (requestId) {
|
|
1406
|
+
requestMap.delete(requestId);
|
|
1407
|
+
}
|
|
1408
|
+
};
|
|
1409
|
+
const recordRequestFailed = (params = {}) => {
|
|
1410
|
+
const requestId = String(params.requestId || "");
|
|
1411
|
+
if (requestId) {
|
|
1412
|
+
requestMap.delete(requestId);
|
|
1413
|
+
}
|
|
1414
|
+
};
|
|
1415
|
+
const bindWebSocketRoute = (params = {}) => {
|
|
1416
|
+
const requestId = String(params.requestId || "");
|
|
1417
|
+
if (!requestId) return;
|
|
1418
|
+
const route = resolveRoute(params.url || "");
|
|
1419
|
+
wsRouteMap.set(requestId, route);
|
|
1420
|
+
};
|
|
1421
|
+
const clearWebSocketRoute = (params = {}) => {
|
|
1422
|
+
const requestId = String(params.requestId || "");
|
|
1423
|
+
if (!requestId) return;
|
|
1424
|
+
wsRouteMap.delete(requestId);
|
|
1425
|
+
};
|
|
1426
|
+
const getWebSocketRoute = (requestId = "") => {
|
|
1427
|
+
if (!requestId) return "direct";
|
|
1428
|
+
return wsRouteMap.get(requestId) || "direct";
|
|
1429
|
+
};
|
|
1430
|
+
const recordWebSocketFrameSent = (params = {}) => {
|
|
1431
|
+
const requestId = String(params.requestId || "");
|
|
1432
|
+
const route = getWebSocketRoute(requestId);
|
|
1433
|
+
const payload = params.response && typeof params.response === "object" ? params.response.payloadData : "";
|
|
1434
|
+
const bytes = byteLength(payload || "");
|
|
1435
|
+
addUploadBytes(state, route, bytes);
|
|
1436
|
+
};
|
|
1437
|
+
const recordWebSocketFrameReceived = (params = {}) => {
|
|
1438
|
+
const requestId = String(params.requestId || "");
|
|
1439
|
+
const route = getWebSocketRoute(requestId);
|
|
1440
|
+
const payload = params.response && typeof params.response === "object" ? params.response.payloadData : "";
|
|
1441
|
+
const bytes = byteLength(payload || "");
|
|
1442
|
+
addDownloadBytes(state, route, bytes);
|
|
1443
|
+
};
|
|
1444
|
+
const attachPage = async (page) => {
|
|
1445
|
+
if (!page || typeof page.context !== "function") return;
|
|
1446
|
+
try {
|
|
1447
|
+
const context = page.context();
|
|
1448
|
+
if (!context || typeof context.newCDPSession !== "function") {
|
|
1449
|
+
return;
|
|
1450
|
+
}
|
|
1451
|
+
const session = await context.newCDPSession(page);
|
|
1452
|
+
await session.send("Network.enable");
|
|
1453
|
+
session.on("Network.requestWillBeSent", recordRequest);
|
|
1454
|
+
session.on("Network.loadingFinished", recordLoadingFinished);
|
|
1455
|
+
session.on("Network.loadingFailed", recordRequestFailed);
|
|
1456
|
+
session.on("Network.webSocketCreated", bindWebSocketRoute);
|
|
1457
|
+
session.on("Network.webSocketClosed", clearWebSocketRoute);
|
|
1458
|
+
session.on("Network.webSocketFrameSent", recordWebSocketFrameSent);
|
|
1459
|
+
session.on("Network.webSocketFrameReceived", recordWebSocketFrameReceived);
|
|
1460
|
+
} catch (error) {
|
|
1461
|
+
logger5.warn(`CDP \u76D1\u542C\u6CE8\u518C\u5931\u8D25: ${error?.message || error}`);
|
|
1462
|
+
}
|
|
1463
|
+
};
|
|
1464
|
+
const snapshot = () => {
|
|
1465
|
+
const totalBytes = state.totalUploadBytes + state.totalDownloadBytes;
|
|
1466
|
+
const proxyBytes = state.proxyUploadBytes + state.proxyDownloadBytes;
|
|
1467
|
+
const directBytes = state.directUploadBytes + state.directDownloadBytes;
|
|
1468
|
+
return {
|
|
1469
|
+
meter: "cdp",
|
|
1470
|
+
totalRequests: state.totalRequests,
|
|
1471
|
+
proxyRequests: state.proxyRequests,
|
|
1472
|
+
directRequests: state.directRequests,
|
|
1473
|
+
totalUploadBytes: state.totalUploadBytes,
|
|
1474
|
+
proxyUploadBytes: state.proxyUploadBytes,
|
|
1475
|
+
directUploadBytes: state.directUploadBytes,
|
|
1476
|
+
totalDownloadBytes: state.totalDownloadBytes,
|
|
1477
|
+
proxyDownloadBytes: state.proxyDownloadBytes,
|
|
1478
|
+
directDownloadBytes: state.directDownloadBytes,
|
|
1479
|
+
totalBytes,
|
|
1480
|
+
proxyBytes,
|
|
1481
|
+
directBytes
|
|
1482
|
+
};
|
|
1483
|
+
};
|
|
1484
|
+
const reset = () => {
|
|
1485
|
+
Object.assign(state, createTrafficState());
|
|
1486
|
+
requestMap.clear();
|
|
1487
|
+
wsRouteMap.clear();
|
|
1488
|
+
};
|
|
1489
|
+
return {
|
|
1490
|
+
attachPage,
|
|
1491
|
+
snapshot,
|
|
1492
|
+
reset
|
|
1493
|
+
};
|
|
1494
|
+
};
|
|
1495
|
+
|
|
1496
|
+
// src/launch.js
|
|
1497
|
+
var logger6 = createInternalLogger("Launch");
|
|
1221
1498
|
var resolveProxyLaunchOptions = (proxyConfiguration = {}) => {
|
|
1222
1499
|
const config = proxyConfiguration && typeof proxyConfiguration === "object" && !Array.isArray(proxyConfiguration) ? proxyConfiguration : {};
|
|
1223
1500
|
const proxyUrl = String(config.proxy_url || "").trim();
|
|
@@ -1251,6 +1528,12 @@ var Launch = {
|
|
|
1251
1528
|
log: logOptions = null
|
|
1252
1529
|
} = normalizedOptions;
|
|
1253
1530
|
const { launchProxy, byPassDomains, enableProxy, proxyUrl } = resolveProxyLaunchOptions(proxyConfiguration);
|
|
1531
|
+
const byPassRules = buildByPassDomainRules(byPassDomains);
|
|
1532
|
+
const trafficMeter2 = createTrafficMeter({
|
|
1533
|
+
enableProxy: Boolean(launchProxy),
|
|
1534
|
+
byPassRules
|
|
1535
|
+
});
|
|
1536
|
+
setTrafficMeter(trafficMeter2);
|
|
1254
1537
|
const launchOptions = {
|
|
1255
1538
|
args: [
|
|
1256
1539
|
...AntiCheat.getLaunchArgs(),
|
|
@@ -1263,15 +1546,15 @@ var Launch = {
|
|
|
1263
1546
|
}
|
|
1264
1547
|
const enableByPassLogger = Boolean(logOptions && logOptions.enable);
|
|
1265
1548
|
if (enableByPassLogger && launchProxy) {
|
|
1266
|
-
|
|
1549
|
+
logger6.info(
|
|
1267
1550
|
`[\u4EE3\u7406\u5DF2\u542F\u7528] \u4EE3\u7406\u670D\u52A1=${launchProxy.server} \u76F4\u8FDE\u57DF\u540D=${(byPassDomains || []).join(",")}`
|
|
1268
1551
|
);
|
|
1269
1552
|
} else if (enableByPassLogger && enableProxy && !launchProxy) {
|
|
1270
|
-
|
|
1553
|
+
logger6.info(
|
|
1271
1554
|
`[\u4EE3\u7406\u672A\u542F\u7528] enable_proxy=true \u4F46 proxy_url \u4E3A\u7A7A`
|
|
1272
1555
|
);
|
|
1273
1556
|
} else if (enableByPassLogger && !enableProxy && proxyUrl) {
|
|
1274
|
-
|
|
1557
|
+
logger6.info(
|
|
1275
1558
|
`[\u4EE3\u7406\u672A\u542F\u7528] enable_proxy=false \u4E14 proxy_url \u5DF2\u914D\u7F6E`
|
|
1276
1559
|
);
|
|
1277
1560
|
}
|
|
@@ -1279,21 +1562,17 @@ var Launch = {
|
|
|
1279
1562
|
const recommendedGotoOptions = {
|
|
1280
1563
|
waitUntil: "domcontentloaded"
|
|
1281
1564
|
};
|
|
1565
|
+
if (page && typeof page.on === "function") {
|
|
1566
|
+
trafficMeter2.attachPage(page);
|
|
1567
|
+
}
|
|
1282
1568
|
if (!enableByPassLogger || byPassDomains.length === 0 || !page || typeof page.on !== "function") {
|
|
1283
1569
|
return recommendedGotoOptions;
|
|
1284
1570
|
}
|
|
1285
|
-
const byPassRules = byPassDomains.map((domain) => buildByPassDomainRule(domain)).filter(Boolean);
|
|
1286
1571
|
const requestHandler = (req) => {
|
|
1287
1572
|
const requestUrl = req.url();
|
|
1288
|
-
|
|
1289
|
-
|
|
1290
|
-
|
|
1291
|
-
} catch {
|
|
1292
|
-
return;
|
|
1293
|
-
}
|
|
1294
|
-
const matchedRule = byPassRules.find((rule) => rule.test(hostname));
|
|
1295
|
-
if (!matchedRule) return;
|
|
1296
|
-
logger5.info(`[\u76F4\u8FDE\u547D\u4E2D] \u89C4\u5219=${matchedRule.pattern} \u57DF\u540D=${hostname} \u8D44\u6E90\u7C7B\u578B=${req.resourceType()} \u65B9\u6CD5=${req.method()} \u5730\u5740=${requestUrl}`);
|
|
1573
|
+
const matched = findMatchedByPassRule(byPassRules, requestUrl);
|
|
1574
|
+
if (!matched || !matched.rule) return;
|
|
1575
|
+
logger6.info(`[\u76F4\u8FDE\u547D\u4E2D] \u89C4\u5219=${matched.rule.pattern} \u57DF\u540D=${matched.hostname} \u8D44\u6E90\u7C7B\u578B=${req.resourceType()} \u65B9\u6CD5=${req.method()} \u5730\u5740=${requestUrl}`);
|
|
1297
1576
|
};
|
|
1298
1577
|
page.on("request", requestHandler);
|
|
1299
1578
|
return recommendedGotoOptions;
|
|
@@ -1312,7 +1591,7 @@ var Launch = {
|
|
|
1312
1591
|
// src/live-view.js
|
|
1313
1592
|
import express from "express";
|
|
1314
1593
|
import { Actor } from "apify";
|
|
1315
|
-
var
|
|
1594
|
+
var logger7 = createInternalLogger("LiveView");
|
|
1316
1595
|
async function startLiveViewServer(liveViewKey) {
|
|
1317
1596
|
const app = express();
|
|
1318
1597
|
app.get("/", async (req, res) => {
|
|
@@ -1337,13 +1616,13 @@ async function startLiveViewServer(liveViewKey) {
|
|
|
1337
1616
|
</html>
|
|
1338
1617
|
`);
|
|
1339
1618
|
} catch (error) {
|
|
1340
|
-
|
|
1619
|
+
logger7.fail("Live View Server", error);
|
|
1341
1620
|
res.status(500).send(`\u65E0\u6CD5\u52A0\u8F7D\u5C4F\u5E55\u622A\u56FE: ${error.message}`);
|
|
1342
1621
|
}
|
|
1343
1622
|
});
|
|
1344
1623
|
const port = process.env.APIFY_CONTAINER_PORT || 4321;
|
|
1345
1624
|
app.listen(port, () => {
|
|
1346
|
-
|
|
1625
|
+
logger7.success("startLiveViewServer", `\u76D1\u542C\u7AEF\u53E3 ${port}`);
|
|
1347
1626
|
});
|
|
1348
1627
|
}
|
|
1349
1628
|
async function takeLiveScreenshot(liveViewKey, page, logMessage) {
|
|
@@ -1351,10 +1630,10 @@ async function takeLiveScreenshot(liveViewKey, page, logMessage) {
|
|
|
1351
1630
|
const buffer = await page.screenshot({ type: "png" });
|
|
1352
1631
|
await Actor.setValue(liveViewKey, buffer, { contentType: "image/png" });
|
|
1353
1632
|
if (logMessage) {
|
|
1354
|
-
|
|
1633
|
+
logger7.info(`(\u622A\u56FE): ${logMessage}`);
|
|
1355
1634
|
}
|
|
1356
1635
|
} catch (e) {
|
|
1357
|
-
|
|
1636
|
+
logger7.warn(`\u65E0\u6CD5\u6355\u83B7 Live View \u5C4F\u5E55\u622A\u56FE: ${e.message}`);
|
|
1358
1637
|
}
|
|
1359
1638
|
}
|
|
1360
1639
|
var useLiveView = (liveViewKey = PresetOfLiveViewKey) => {
|
|
@@ -1373,7 +1652,7 @@ var LiveView = {
|
|
|
1373
1652
|
|
|
1374
1653
|
// src/captcha-monitor.js
|
|
1375
1654
|
import { v4 as uuidv4 } from "uuid";
|
|
1376
|
-
var
|
|
1655
|
+
var logger8 = createInternalLogger("Captcha");
|
|
1377
1656
|
function useCaptchaMonitor(page, options) {
|
|
1378
1657
|
const { domSelector, urlPattern, onDetected } = options;
|
|
1379
1658
|
if (!domSelector && !urlPattern) {
|
|
@@ -1446,7 +1725,7 @@ function useCaptchaMonitor(page, options) {
|
|
|
1446
1725
|
};
|
|
1447
1726
|
})();
|
|
1448
1727
|
}, { selector: domSelector, callbackName: exposedFunctionName, cleanerName });
|
|
1449
|
-
|
|
1728
|
+
logger8.success("useCaptchaMonitor", `DOM \u76D1\u63A7\u5DF2\u542F\u7528: ${domSelector}`);
|
|
1450
1729
|
cleanupFns.push(async () => {
|
|
1451
1730
|
try {
|
|
1452
1731
|
await page.evaluate((name) => {
|
|
@@ -1469,14 +1748,14 @@ function useCaptchaMonitor(page, options) {
|
|
|
1469
1748
|
}
|
|
1470
1749
|
};
|
|
1471
1750
|
page.on("framenavigated", frameHandler);
|
|
1472
|
-
|
|
1751
|
+
logger8.success("useCaptchaMonitor", `URL \u76D1\u63A7\u5DF2\u542F\u7528: ${urlPattern}`);
|
|
1473
1752
|
cleanupFns.push(async () => {
|
|
1474
1753
|
page.off("framenavigated", frameHandler);
|
|
1475
1754
|
});
|
|
1476
1755
|
}
|
|
1477
1756
|
return {
|
|
1478
1757
|
stop: async () => {
|
|
1479
|
-
|
|
1758
|
+
logger8.info("useCaptchaMonitor", "\u6B63\u5728\u505C\u6B62\u76D1\u63A7...");
|
|
1480
1759
|
for (const fn of cleanupFns) {
|
|
1481
1760
|
await fn();
|
|
1482
1761
|
}
|
|
@@ -1491,7 +1770,7 @@ var Captcha = {
|
|
|
1491
1770
|
// src/sse.js
|
|
1492
1771
|
import https from "https";
|
|
1493
1772
|
import { URL as URL2 } from "url";
|
|
1494
|
-
var
|
|
1773
|
+
var logger9 = createInternalLogger("Sse");
|
|
1495
1774
|
var Sse = {
|
|
1496
1775
|
/**
|
|
1497
1776
|
* 解析 SSE 流文本
|
|
@@ -1510,11 +1789,11 @@ var Sse = {
|
|
|
1510
1789
|
events.push(JSON.parse(jsonContent));
|
|
1511
1790
|
}
|
|
1512
1791
|
} catch (e) {
|
|
1513
|
-
|
|
1792
|
+
logger9.debug("parseSseStream", `JSON \u89E3\u6790\u5931\u8D25: ${e.message}, line: ${line.substring(0, 100)}...`);
|
|
1514
1793
|
}
|
|
1515
1794
|
}
|
|
1516
1795
|
}
|
|
1517
|
-
|
|
1796
|
+
logger9.success("parseSseStream", `\u89E3\u6790\u5B8C\u6210, events \u6570\u91CF: ${events.length}`);
|
|
1518
1797
|
return events;
|
|
1519
1798
|
},
|
|
1520
1799
|
/**
|
|
@@ -1564,7 +1843,7 @@ var Sse = {
|
|
|
1564
1843
|
if (!autoUnroute) return;
|
|
1565
1844
|
if (unrouteRequested) return;
|
|
1566
1845
|
unrouteRequested = true;
|
|
1567
|
-
|
|
1846
|
+
logger9.info("[MITM] autoUnroute: \u53D6\u6D88\u540E\u7EED\u62E6\u622A");
|
|
1568
1847
|
page.unroute(urlPattern, routeHandler).catch(() => {
|
|
1569
1848
|
});
|
|
1570
1849
|
};
|
|
@@ -1584,19 +1863,19 @@ var Sse = {
|
|
|
1584
1863
|
};
|
|
1585
1864
|
const routeHandler = async (route) => {
|
|
1586
1865
|
if (firstMatchOnly && hasMatchedOnce) {
|
|
1587
|
-
|
|
1866
|
+
logger9.info(`[MITM] firstMatchOnly: \u653E\u884C\u540E\u7EED\u8BF7\u6C42: ${route.request().url()}`);
|
|
1588
1867
|
route.continue().catch(() => {
|
|
1589
1868
|
});
|
|
1590
1869
|
return;
|
|
1591
1870
|
}
|
|
1592
1871
|
if (firstMatchOnly && !hasMatchedOnce) {
|
|
1593
1872
|
hasMatchedOnce = true;
|
|
1594
|
-
|
|
1873
|
+
logger9.info("[MITM] firstMatchOnly: \u547D\u4E2D\u9996\u4E2A\u8BF7\u6C42\uFF0C\u53D6\u6D88\u540E\u7EED\u62E6\u622A");
|
|
1595
1874
|
page.unroute(urlPattern, routeHandler).catch(() => {
|
|
1596
1875
|
});
|
|
1597
1876
|
}
|
|
1598
1877
|
const request = route.request();
|
|
1599
|
-
|
|
1878
|
+
logger9.info(`[MITM] \u5DF2\u62E6\u622A\u8BF7\u6C42: ${request.url()}`);
|
|
1600
1879
|
try {
|
|
1601
1880
|
const headers = await request.allHeaders();
|
|
1602
1881
|
const postData = request.postData();
|
|
@@ -1621,7 +1900,7 @@ var Sse = {
|
|
|
1621
1900
|
clearTimeout(initialTimer);
|
|
1622
1901
|
initialTimer = null;
|
|
1623
1902
|
}
|
|
1624
|
-
|
|
1903
|
+
logger9.debug("[Intercept] \u5DF2\u63A5\u6536\u521D\u59CB\u6570\u636E");
|
|
1625
1904
|
}
|
|
1626
1905
|
chunks.push(chunk);
|
|
1627
1906
|
const textChunk = chunk.toString("utf-8");
|
|
@@ -1630,18 +1909,18 @@ var Sse = {
|
|
|
1630
1909
|
try {
|
|
1631
1910
|
onData(textChunk, safeResolve, accumulatedText);
|
|
1632
1911
|
} catch (e) {
|
|
1633
|
-
|
|
1912
|
+
logger9.fail(`onData \u9519\u8BEF`, e);
|
|
1634
1913
|
}
|
|
1635
1914
|
}
|
|
1636
1915
|
});
|
|
1637
1916
|
res.on("end", () => {
|
|
1638
|
-
|
|
1917
|
+
logger9.info("[MITM] \u4E0A\u6E38\u54CD\u5E94\u7ED3\u675F");
|
|
1639
1918
|
clearAllTimers();
|
|
1640
1919
|
if (onEnd) {
|
|
1641
1920
|
try {
|
|
1642
1921
|
onEnd(accumulatedText, safeResolve);
|
|
1643
1922
|
} catch (e) {
|
|
1644
|
-
|
|
1923
|
+
logger9.fail(`onEnd \u9519\u8BEF`, e);
|
|
1645
1924
|
}
|
|
1646
1925
|
} else if (!onData) {
|
|
1647
1926
|
safeResolve(accumulatedText);
|
|
@@ -1722,7 +2001,7 @@ var Sse = {
|
|
|
1722
2001
|
|
|
1723
2002
|
// src/mutation.js
|
|
1724
2003
|
import { v4 as uuidv42 } from "uuid";
|
|
1725
|
-
var
|
|
2004
|
+
var logger10 = createInternalLogger("Mutation");
|
|
1726
2005
|
var MUTATION_MONITOR_MODE = Object.freeze({
|
|
1727
2006
|
Added: "added",
|
|
1728
2007
|
Changed: "changed",
|
|
@@ -1755,14 +2034,14 @@ var Mutation = {
|
|
|
1755
2034
|
const stableTime = options.stableTime ?? 5 * 1e3;
|
|
1756
2035
|
const timeout = options.timeout ?? 120 * 1e3;
|
|
1757
2036
|
const onMutation = options.onMutation;
|
|
1758
|
-
|
|
2037
|
+
logger10.start("waitForStable", `\u76D1\u63A7 ${selectorList.length} \u4E2A\u9009\u62E9\u5668, \u7A33\u5B9A\u65F6\u95F4=${stableTime}ms`);
|
|
1759
2038
|
if (initialTimeout > 0) {
|
|
1760
2039
|
const selectorQuery = selectorList.join(",");
|
|
1761
2040
|
try {
|
|
1762
2041
|
await page.waitForSelector(selectorQuery, { timeout: initialTimeout });
|
|
1763
|
-
|
|
2042
|
+
logger10.info(`waitForStable \u5DF2\u68C0\u6D4B\u5230\u5143\u7D20: ${selectorQuery}`);
|
|
1764
2043
|
} catch (e) {
|
|
1765
|
-
|
|
2044
|
+
logger10.warning(`waitForStable \u521D\u59CB\u7B49\u5F85\u8D85\u65F6 (${initialTimeout}ms): ${selectorQuery}`);
|
|
1766
2045
|
throw e;
|
|
1767
2046
|
}
|
|
1768
2047
|
}
|
|
@@ -1778,7 +2057,7 @@ var Mutation = {
|
|
|
1778
2057
|
return "__CONTINUE__";
|
|
1779
2058
|
}
|
|
1780
2059
|
});
|
|
1781
|
-
|
|
2060
|
+
logger10.info("waitForStable \u5DF2\u542F\u7528 onMutation \u56DE\u8C03");
|
|
1782
2061
|
} catch (e) {
|
|
1783
2062
|
}
|
|
1784
2063
|
}
|
|
@@ -1893,9 +2172,9 @@ var Mutation = {
|
|
|
1893
2172
|
{ selectorList, stableTime, timeout, callbackName, hasCallback: !!onMutation }
|
|
1894
2173
|
);
|
|
1895
2174
|
if (result.mutationCount === 0 && result.stableTime === 0) {
|
|
1896
|
-
|
|
2175
|
+
logger10.warning("waitForStable \u672A\u627E\u5230\u53EF\u76D1\u63A7\u7684\u5143\u7D20");
|
|
1897
2176
|
}
|
|
1898
|
-
|
|
2177
|
+
logger10.success("waitForStable", `DOM \u7A33\u5B9A, \u603B\u5171 ${result.mutationCount} \u6B21\u53D8\u5316${result.wasPaused ? ", \u66FE\u6682\u505C\u8BA1\u65F6" : ""}`);
|
|
1899
2178
|
return result;
|
|
1900
2179
|
},
|
|
1901
2180
|
/**
|
|
@@ -1915,7 +2194,7 @@ var Mutation = {
|
|
|
1915
2194
|
const onMutation = options.onMutation;
|
|
1916
2195
|
const rawMode = String(options.mode || MUTATION_MONITOR_MODE.Added).toLowerCase();
|
|
1917
2196
|
const mode = [MUTATION_MONITOR_MODE.Added, MUTATION_MONITOR_MODE.Changed, MUTATION_MONITOR_MODE.All].includes(rawMode) ? rawMode : MUTATION_MONITOR_MODE.Added;
|
|
1918
|
-
|
|
2197
|
+
logger10.start("useMonitor", `\u76D1\u63A7 ${selectorList.length} \u4E2A\u9009\u62E9\u5668, mode=${mode}`);
|
|
1919
2198
|
const monitorKey = generateKey("pk_mon");
|
|
1920
2199
|
const callbackName = generateKey("pk_mon_cb");
|
|
1921
2200
|
const cleanerName = generateKey("pk_mon_clean");
|
|
@@ -2058,7 +2337,7 @@ var Mutation = {
|
|
|
2058
2337
|
return total;
|
|
2059
2338
|
};
|
|
2060
2339
|
}, { selectorList, monitorKey, callbackName, cleanerName, hasCallback: !!onMutation, mode });
|
|
2061
|
-
|
|
2340
|
+
logger10.success("useMonitor", "\u76D1\u63A7\u5668\u5DF2\u542F\u52A8");
|
|
2062
2341
|
return {
|
|
2063
2342
|
stop: async () => {
|
|
2064
2343
|
let totalMutations = 0;
|
|
@@ -2071,7 +2350,7 @@ var Mutation = {
|
|
|
2071
2350
|
}, cleanerName);
|
|
2072
2351
|
} catch (e) {
|
|
2073
2352
|
}
|
|
2074
|
-
|
|
2353
|
+
logger10.success("useMonitor.stop", `\u76D1\u63A7\u5DF2\u505C\u6B62, \u5171 ${totalMutations} \u6B21\u53D8\u5316`);
|
|
2075
2354
|
return { totalMutations };
|
|
2076
2355
|
}
|
|
2077
2356
|
};
|
|
@@ -2940,7 +3219,7 @@ var createTemplateLogger = (baseLogger = createBaseLogger()) => {
|
|
|
2940
3219
|
};
|
|
2941
3220
|
var getDefaultBaseLogger = () => createBaseLogger("");
|
|
2942
3221
|
var Logger = {
|
|
2943
|
-
setLogger: (
|
|
3222
|
+
setLogger: (logger12) => setDefaultLogger(logger12),
|
|
2944
3223
|
info: (message) => getDefaultBaseLogger().info(message),
|
|
2945
3224
|
success: (message) => getDefaultBaseLogger().success(message),
|
|
2946
3225
|
warning: (message) => getDefaultBaseLogger().warning(message),
|
|
@@ -2948,15 +3227,15 @@ var Logger = {
|
|
|
2948
3227
|
error: (message) => getDefaultBaseLogger().error(message),
|
|
2949
3228
|
debug: (message) => getDefaultBaseLogger().debug(message),
|
|
2950
3229
|
start: (message) => getDefaultBaseLogger().start(message),
|
|
2951
|
-
useTemplate: (
|
|
2952
|
-
if (
|
|
3230
|
+
useTemplate: (logger12) => {
|
|
3231
|
+
if (logger12) return createTemplateLogger(createBaseLogger("", logger12));
|
|
2953
3232
|
return createTemplateLogger();
|
|
2954
3233
|
}
|
|
2955
3234
|
};
|
|
2956
3235
|
|
|
2957
3236
|
// src/share.js
|
|
2958
3237
|
import delay2 from "delay";
|
|
2959
|
-
var
|
|
3238
|
+
var logger11 = createInternalLogger("Share");
|
|
2960
3239
|
var DEFAULT_TIMEOUT_MS = 50 * 1e3;
|
|
2961
3240
|
var DEFAULT_PAYLOAD_SNAPSHOT_MAX_LEN = 500;
|
|
2962
3241
|
var DEFAULT_POLL_INTERVAL_MS = 120;
|
|
@@ -3076,7 +3355,7 @@ var createDomShareMonitor = async (page, options = {}) => {
|
|
|
3076
3355
|
const onMatch = typeof options.onMatch === "function" ? options.onMatch : null;
|
|
3077
3356
|
const onTelemetry = typeof options.onTelemetry === "function" ? options.onTelemetry : null;
|
|
3078
3357
|
let matched = false;
|
|
3079
|
-
|
|
3358
|
+
logger11.info(`DOM \u76D1\u542C\u51C6\u5907\u6302\u8F7D: selectors=${toJsonInline(selectors, 120)}, mode=${mode}`);
|
|
3080
3359
|
const monitor = await Mutation.useMonitor(page, selectors, {
|
|
3081
3360
|
mode,
|
|
3082
3361
|
onMutation: (context = {}) => {
|
|
@@ -3094,12 +3373,12 @@ ${text}`;
|
|
|
3094
3373
|
});
|
|
3095
3374
|
}
|
|
3096
3375
|
if (mutationCount <= 5 || mutationCount % 50 === 0) {
|
|
3097
|
-
|
|
3376
|
+
logger11.info(`DOM \u53D8\u5316\u5DF2\u6355\u83B7: mutationCount=${mutationCount}, mutationNodes=${mutationNodes.length}`);
|
|
3098
3377
|
}
|
|
3099
3378
|
const [candidate] = Utils.parseLinks(rawDom, { prefix }) || [];
|
|
3100
3379
|
if (!candidate) return;
|
|
3101
3380
|
matched = true;
|
|
3102
|
-
|
|
3381
|
+
logger11.success("captureLink.domHit", `DOM \u547D\u4E2D\u5206\u4EAB\u94FE\u63A5: mutationCount=${mutationCount}, link=${candidate}`);
|
|
3103
3382
|
if (onMatch) {
|
|
3104
3383
|
onMatch({
|
|
3105
3384
|
link: candidate,
|
|
@@ -3115,7 +3394,7 @@ ${text}`;
|
|
|
3115
3394
|
return {
|
|
3116
3395
|
stop: async () => {
|
|
3117
3396
|
const result = await monitor.stop();
|
|
3118
|
-
|
|
3397
|
+
logger11.info(`DOM \u76D1\u542C\u5DF2\u505C\u6B62: totalMutations=${result?.totalMutations || 0}`);
|
|
3119
3398
|
return result;
|
|
3120
3399
|
}
|
|
3121
3400
|
};
|
|
@@ -3155,8 +3434,8 @@ var Share = {
|
|
|
3155
3434
|
if (share.mode === "response" && apiMatchers.length === 0) {
|
|
3156
3435
|
throw new Error("Share.captureLink requires share.xurl[0] api matcher when mode=response");
|
|
3157
3436
|
}
|
|
3158
|
-
|
|
3159
|
-
|
|
3437
|
+
logger11.start("captureLink", `mode=${share.mode}, timeoutMs=${timeoutMs}, prefix=${share.prefix}`);
|
|
3438
|
+
logger11.info(`captureLink \u914D\u7F6E: xurl=${toJsonInline(share.xurl)}, domMode=${domMode}, domSelectors=${toJsonInline(domSelectors, 120)}`);
|
|
3160
3439
|
const stats = {
|
|
3161
3440
|
actionTimedOut: false,
|
|
3162
3441
|
domMutationCount: 0,
|
|
@@ -3181,7 +3460,7 @@ var Share = {
|
|
|
3181
3460
|
link: validated,
|
|
3182
3461
|
payloadText: String(payloadText || "")
|
|
3183
3462
|
};
|
|
3184
|
-
|
|
3463
|
+
logger11.info(`\u5019\u9009\u94FE\u63A5\u5DF2\u786E\u8BA4: source=${source}, link=${validated}`);
|
|
3185
3464
|
return true;
|
|
3186
3465
|
};
|
|
3187
3466
|
const resolveResponseCandidate = (responseText) => {
|
|
@@ -3216,7 +3495,7 @@ var Share = {
|
|
|
3216
3495
|
try {
|
|
3217
3496
|
await monitor.stop();
|
|
3218
3497
|
} catch (error) {
|
|
3219
|
-
|
|
3498
|
+
logger11.warning(`\u505C\u6B62 DOM \u76D1\u542C\u5931\u8D25: ${error instanceof Error ? error.message : String(error)}`);
|
|
3220
3499
|
}
|
|
3221
3500
|
};
|
|
3222
3501
|
const onResponse = async (response) => {
|
|
@@ -3229,29 +3508,29 @@ var Share = {
|
|
|
3229
3508
|
stats.responseSampleUrls.push(url);
|
|
3230
3509
|
}
|
|
3231
3510
|
if (stats.responseObserved <= 5) {
|
|
3232
|
-
|
|
3511
|
+
logger11.info(`\u63A5\u53E3\u54CD\u5E94\u91C7\u6837(${stats.responseObserved}): ${url}`);
|
|
3233
3512
|
}
|
|
3234
3513
|
if (!apiMatchers.some((matcher) => url.includes(matcher))) return;
|
|
3235
3514
|
stats.responseMatched += 1;
|
|
3236
3515
|
stats.lastMatchedUrl = url;
|
|
3237
|
-
|
|
3516
|
+
logger11.info(`\u63A5\u53E3\u547D\u4E2D\u5339\u914D(${stats.responseMatched}): ${url}`);
|
|
3238
3517
|
const text = await response.text();
|
|
3239
3518
|
const hit = resolveResponseCandidate(text);
|
|
3240
3519
|
if (!hit?.link) {
|
|
3241
3520
|
if (stats.responseMatched <= 3) {
|
|
3242
|
-
|
|
3521
|
+
logger11.info(`\u63A5\u53E3\u89E3\u6790\u5B8C\u6210\u4F46\u672A\u63D0\u53D6\u5230\u5206\u4EAB\u94FE\u63A5: payloadSize=${text.length}`);
|
|
3243
3522
|
}
|
|
3244
3523
|
return;
|
|
3245
3524
|
}
|
|
3246
3525
|
stats.responseResolved += 1;
|
|
3247
|
-
|
|
3526
|
+
logger11.success("captureLink.responseHit", `\u63A5\u53E3\u547D\u4E2D\u5206\u4EAB\u94FE\u63A5: url=${url}, link=${hit.link}`);
|
|
3248
3527
|
setCandidate("response", hit.link, hit.payloadText);
|
|
3249
3528
|
} catch (error) {
|
|
3250
|
-
|
|
3529
|
+
logger11.warning(`\u63A5\u53E3\u54CD\u5E94\u5904\u7406\u5F02\u5E38: ${error instanceof Error ? error.message : String(error)}`);
|
|
3251
3530
|
}
|
|
3252
3531
|
};
|
|
3253
3532
|
if (share.mode === "dom") {
|
|
3254
|
-
|
|
3533
|
+
logger11.info("\u5F53\u524D\u4E3A DOM \u6A21\u5F0F\uFF0C\u4EC5\u542F\u7528 DOM \u76D1\u542C");
|
|
3255
3534
|
domMonitor = await createDomShareMonitor(page, {
|
|
3256
3535
|
prefix: share.prefix,
|
|
3257
3536
|
selectors: domSelectors,
|
|
@@ -3266,14 +3545,14 @@ var Share = {
|
|
|
3266
3545
|
});
|
|
3267
3546
|
}
|
|
3268
3547
|
if (share.mode === "response") {
|
|
3269
|
-
|
|
3548
|
+
logger11.info(`\u5F53\u524D\u4E3A\u63A5\u53E3\u6A21\u5F0F\uFF0C\u6302\u8F7D response \u76D1\u542C: apiMatchers=${toJsonInline(apiMatchers, 160)}`);
|
|
3270
3549
|
page.on("response", onResponse);
|
|
3271
3550
|
}
|
|
3272
3551
|
const deadline = Date.now() + timeoutMs;
|
|
3273
3552
|
const getRemainingMs = () => Math.max(0, deadline - Date.now());
|
|
3274
3553
|
try {
|
|
3275
3554
|
const actionTimeout = getRemainingMs();
|
|
3276
|
-
|
|
3555
|
+
logger11.start("captureLink.performActions", `\u6267\u884C\u52A8\u4F5C\u9884\u7B97=${actionTimeout}ms`);
|
|
3277
3556
|
if (actionTimeout > 0) {
|
|
3278
3557
|
let timer = null;
|
|
3279
3558
|
let actionError = null;
|
|
@@ -3287,21 +3566,21 @@ var Share = {
|
|
|
3287
3566
|
const actionResult = await Promise.race([actionPromise, timeoutPromise]);
|
|
3288
3567
|
if (timer) clearTimeout(timer);
|
|
3289
3568
|
if (actionResult === "__ACTION_ERROR__") {
|
|
3290
|
-
|
|
3569
|
+
logger11.fail("captureLink.performActions", actionError);
|
|
3291
3570
|
throw actionError;
|
|
3292
3571
|
}
|
|
3293
3572
|
if (actionResult === "__ACTION_TIMEOUT__") {
|
|
3294
3573
|
stats.actionTimedOut = true;
|
|
3295
|
-
|
|
3574
|
+
logger11.warning(`performActions \u5DF2\u8D85\u65F6 (${actionTimeout}ms)\uFF0C\u52A8\u4F5C\u53EF\u80FD\u4ECD\u5728\u5F02\u6B65\u6267\u884C`);
|
|
3296
3575
|
} else {
|
|
3297
|
-
|
|
3576
|
+
logger11.success("captureLink.performActions", "\u6267\u884C\u52A8\u4F5C\u5B8C\u6210");
|
|
3298
3577
|
}
|
|
3299
3578
|
}
|
|
3300
3579
|
let nextProgressLogTs = Date.now() + 3e3;
|
|
3301
3580
|
while (true) {
|
|
3302
3581
|
const selected = share.mode === "dom" ? candidates.dom : candidates.response;
|
|
3303
3582
|
if (selected?.link) {
|
|
3304
|
-
|
|
3583
|
+
logger11.success("captureLink", `\u6355\u83B7\u6210\u529F: source=${share.mode}, link=${selected.link}`);
|
|
3305
3584
|
return {
|
|
3306
3585
|
link: selected.link,
|
|
3307
3586
|
payloadText: selected.payloadText,
|
|
@@ -3313,7 +3592,7 @@ var Share = {
|
|
|
3313
3592
|
if (remaining <= 0) break;
|
|
3314
3593
|
const now = Date.now();
|
|
3315
3594
|
if (now >= nextProgressLogTs) {
|
|
3316
|
-
|
|
3595
|
+
logger11.info(
|
|
3317
3596
|
`captureLink \u7B49\u5F85\u4E2D: remaining=${remaining}ms, domMutationCount=${stats.domMutationCount}, responseMatched=${stats.responseMatched}`
|
|
3318
3597
|
);
|
|
3319
3598
|
nextProgressLogTs = now + 5e3;
|
|
@@ -3321,11 +3600,11 @@ var Share = {
|
|
|
3321
3600
|
await delay2(Math.max(0, Math.min(DEFAULT_POLL_INTERVAL_MS, remaining)));
|
|
3322
3601
|
}
|
|
3323
3602
|
if (share.mode === "response" && stats.responseMatched === 0) {
|
|
3324
|
-
|
|
3603
|
+
logger11.warning(
|
|
3325
3604
|
`\u63A5\u53E3\u76D1\u542C\u672A\u547D\u4E2D: apiMatchers=${toJsonInline(apiMatchers, 220)}, \u54CD\u5E94\u6837\u672CURLs=${toJsonInline(stats.responseSampleUrls, 420)}`
|
|
3326
3605
|
);
|
|
3327
3606
|
}
|
|
3328
|
-
|
|
3607
|
+
logger11.warning(
|
|
3329
3608
|
`captureLink \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"}`
|
|
3330
3609
|
);
|
|
3331
3610
|
return {
|
|
@@ -3337,7 +3616,7 @@ var Share = {
|
|
|
3337
3616
|
} finally {
|
|
3338
3617
|
if (share.mode === "response") {
|
|
3339
3618
|
page.off("response", onResponse);
|
|
3340
|
-
|
|
3619
|
+
logger11.info("response \u76D1\u542C\u5DF2\u5378\u8F7D");
|
|
3341
3620
|
}
|
|
3342
3621
|
await stopDomMonitor();
|
|
3343
3622
|
}
|