@prosopo/provider 5.14.0 → 5.15.0
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/.turbo/turbo-build$colon$cjs.log +20 -22
- package/.turbo/turbo-build$colon$tsc.log +27 -30
- package/.turbo/turbo-build.log +21 -26
- package/CHANGELOG.md +128 -0
- package/LICENSE +201 -0
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/constants.d.ts +2 -1
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/constants.d.ts.map +1 -1
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/constants.js +11 -2
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/constants.js.map +1 -1
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/handler.d.ts.map +1 -1
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/handler.js +15 -8
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/handler.js.map +1 -1
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.d.ts +5 -0
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.d.ts.map +1 -0
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.js +20 -0
- package/dist/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.js.map +1 -0
- package/dist/api/captcha/getPuzzleCaptchaChallenge.d.ts.map +1 -1
- package/dist/api/captcha/getPuzzleCaptchaChallenge.js +24 -0
- package/dist/api/captcha/getPuzzleCaptchaChallenge.js.map +1 -1
- package/dist/api/captcha/submitPoWCaptchaSolution.d.ts +4 -11
- package/dist/api/captcha/submitPoWCaptchaSolution.d.ts.map +1 -1
- package/dist/api/captcha/submitPoWCaptchaSolution.js +12 -17
- package/dist/api/captcha/submitPoWCaptchaSolution.js.map +1 -1
- package/dist/api/rawTlsSignalsMiddleware.d.ts +14 -1
- package/dist/api/rawTlsSignalsMiddleware.d.ts.map +1 -1
- package/dist/api/rawTlsSignalsMiddleware.js +111 -23
- package/dist/api/rawTlsSignalsMiddleware.js.map +1 -1
- package/dist/api/startProviderApi.js +2 -2
- package/dist/cjs/api/captcha/getFrictionlessCaptchaChallenge/constants.cjs +10 -0
- package/dist/cjs/api/captcha/getFrictionlessCaptchaChallenge/handler.cjs +14 -7
- package/dist/cjs/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.cjs +20 -0
- package/dist/cjs/api/captcha/getPuzzleCaptchaChallenge.cjs +24 -0
- package/dist/cjs/api/captcha/submitPoWCaptchaSolution.cjs +10 -15
- package/dist/cjs/api/rawTlsSignalsMiddleware.cjs +111 -22
- package/dist/cjs/api/startProviderApi.cjs +2 -2
- package/dist/cjs/compositeIpAddress.cjs +21 -7
- package/dist/cjs/tasks/captchaManager.cjs +15 -0
- package/dist/cjs/tasks/captchaTypeSelection.cjs +23 -2
- package/dist/cjs/tasks/frictionless/frictionlessTasks.cjs +26 -23
- package/dist/cjs/tasks/imgCaptcha/imgCaptchaTasks.cjs +2 -9
- package/dist/cjs/tasks/powCaptcha/powTasks.cjs +7 -11
- package/dist/cjs/tasks/powCaptcha/powTasksUtils.cjs +2 -0
- package/dist/cjs/tasks/puzzle/backgroundBuffer.cjs +3 -3
- package/dist/cjs/tasks/puzzle/nativeBackground.cjs +12 -5
- package/dist/cjs/tasks/puzzle/puzzleRenderer.cjs +4 -3
- package/dist/cjs/tasks/puzzleCaptcha/puzzleTasks.cjs +2 -9
- package/dist/compositeIpAddress.d.ts.map +1 -1
- package/dist/compositeIpAddress.js +21 -7
- package/dist/compositeIpAddress.js.map +1 -1
- package/dist/tasks/captchaManager.d.ts.map +1 -1
- package/dist/tasks/captchaManager.js +16 -1
- package/dist/tasks/captchaManager.js.map +1 -1
- package/dist/tasks/captchaTypeSelection.d.ts +3 -1
- package/dist/tasks/captchaTypeSelection.d.ts.map +1 -1
- package/dist/tasks/captchaTypeSelection.js +23 -3
- package/dist/tasks/captchaTypeSelection.js.map +1 -1
- package/dist/tasks/frictionless/frictionlessTasks.d.ts +3 -1
- package/dist/tasks/frictionless/frictionlessTasks.d.ts.map +1 -1
- package/dist/tasks/frictionless/frictionlessTasks.js +28 -25
- package/dist/tasks/frictionless/frictionlessTasks.js.map +1 -1
- package/dist/tasks/frictionless/routingMachine.d.ts +1 -2
- package/dist/tasks/frictionless/routingMachine.d.ts.map +1 -1
- package/dist/tasks/frictionless/routingMachine.js.map +1 -1
- package/dist/tasks/imgCaptcha/imgCaptchaTasks.d.ts.map +1 -1
- package/dist/tasks/imgCaptcha/imgCaptchaTasks.js +2 -9
- package/dist/tasks/imgCaptcha/imgCaptchaTasks.js.map +1 -1
- package/dist/tasks/powCaptcha/powTasks.d.ts.map +1 -1
- package/dist/tasks/powCaptcha/powTasks.js +8 -12
- package/dist/tasks/powCaptcha/powTasks.js.map +1 -1
- package/dist/tasks/powCaptcha/powTasksUtils.d.ts +1 -0
- package/dist/tasks/powCaptcha/powTasksUtils.d.ts.map +1 -1
- package/dist/tasks/powCaptcha/powTasksUtils.js +2 -1
- package/dist/tasks/powCaptcha/powTasksUtils.js.map +1 -1
- package/dist/tasks/puzzle/backgroundBuffer.d.ts +3 -2
- package/dist/tasks/puzzle/backgroundBuffer.d.ts.map +1 -1
- package/dist/tasks/puzzle/backgroundBuffer.js +3 -3
- package/dist/tasks/puzzle/backgroundBuffer.js.map +1 -1
- package/dist/tasks/puzzle/nativeBackground.d.ts +5 -1
- package/dist/tasks/puzzle/nativeBackground.d.ts.map +1 -1
- package/dist/tasks/puzzle/nativeBackground.js +12 -5
- package/dist/tasks/puzzle/nativeBackground.js.map +1 -1
- package/dist/tasks/puzzle/puzzleRenderer.d.ts +2 -0
- package/dist/tasks/puzzle/puzzleRenderer.d.ts.map +1 -1
- package/dist/tasks/puzzle/puzzleRenderer.js +4 -3
- package/dist/tasks/puzzle/puzzleRenderer.js.map +1 -1
- package/dist/tasks/puzzleCaptcha/puzzleTasks.d.ts.map +1 -1
- package/dist/tasks/puzzleCaptcha/puzzleTasks.js +2 -9
- package/dist/tasks/puzzleCaptcha/puzzleTasks.js.map +1 -1
- package/dist/tests/integration/clientSettingsPersistence.integration.test.js +2 -0
- package/dist/tests/integration/clientSettingsPersistence.integration.test.js.map +1 -1
- package/dist/tests/unit/api/captcha/getFrictionlessCaptchaChallenge/constants.unit.test.js +35 -2
- package/dist/tests/unit/api/captcha/getFrictionlessCaptchaChallenge/constants.unit.test.js.map +1 -1
- package/dist/tests/unit/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.unit.test.d.ts +2 -0
- package/dist/tests/unit/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.unit.test.d.ts.map +1 -0
- package/dist/tests/unit/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.unit.test.js +45 -0
- package/dist/tests/unit/api/captcha/getFrictionlessCaptchaChallenge/refreshLineage.unit.test.js.map +1 -0
- package/dist/tests/unit/api/captcha/submitPoWCaptchaSolution.escalation.unit.test.js +15 -1
- package/dist/tests/unit/api/captcha/submitPoWCaptchaSolution.escalation.unit.test.js.map +1 -1
- package/dist/tests/unit/api/getFrictionlessCaptchaChallenge.unit.test.js +148 -0
- package/dist/tests/unit/api/getFrictionlessCaptchaChallenge.unit.test.js.map +1 -1
- package/dist/tests/unit/api/rawTlsSignalsMiddleware.unit.test.js +96 -1
- package/dist/tests/unit/api/rawTlsSignalsMiddleware.unit.test.js.map +1 -1
- package/dist/tests/unit/compositeIpAddress.unit.test.js +12 -3
- package/dist/tests/unit/compositeIpAddress.unit.test.js.map +1 -1
- package/dist/tests/unit/tasks/captchaManager.unit.test.js +51 -0
- package/dist/tests/unit/tasks/captchaManager.unit.test.js.map +1 -1
- package/dist/tests/unit/tasks/captchaTypeSelection.unit.test.js +20 -1
- package/dist/tests/unit/tasks/captchaTypeSelection.unit.test.js.map +1 -1
- package/dist/tests/unit/tasks/frictionless/allowedCaptchaTypes.unit.test.d.ts +2 -0
- package/dist/tests/unit/tasks/frictionless/allowedCaptchaTypes.unit.test.d.ts.map +1 -0
- package/dist/tests/unit/tasks/frictionless/allowedCaptchaTypes.unit.test.js +94 -0
- package/dist/tests/unit/tasks/frictionless/allowedCaptchaTypes.unit.test.js.map +1 -0
- package/dist/tests/unit/tasks/frictionless/refreshSwitch.unit.test.d.ts +2 -0
- package/dist/tests/unit/tasks/frictionless/refreshSwitch.unit.test.d.ts.map +1 -0
- package/dist/tests/unit/tasks/frictionless/refreshSwitch.unit.test.js +103 -0
- package/dist/tests/unit/tasks/frictionless/refreshSwitch.unit.test.js.map +1 -0
- package/dist/tests/unit/tasks/powCaptcha/powTasksUtils.unit.test.js +23 -1
- package/dist/tests/unit/tasks/powCaptcha/powTasksUtils.unit.test.js.map +1 -1
- package/dist/tests/unit/tasks/puzzle/backgroundBuffer.unit.test.js +1 -4
- package/dist/tests/unit/tasks/puzzle/backgroundBuffer.unit.test.js.map +1 -1
- package/dist/tests/unit/tasks/puzzle/nativeBackground.unit.test.js +10 -3
- package/dist/tests/unit/tasks/puzzle/nativeBackground.unit.test.js.map +1 -1
- package/dist/tests/unit/tasks/puzzle/puzzleRenderer.unit.test.d.ts +2 -0
- package/dist/tests/unit/tasks/puzzle/puzzleRenderer.unit.test.d.ts.map +1 -0
- package/dist/tests/unit/tasks/puzzle/puzzleRenderer.unit.test.js +35 -0
- package/dist/tests/unit/tasks/puzzle/puzzleRenderer.unit.test.js.map +1 -0
- package/dist/tests/unit/tasks/puzzleDifficultyDeviceCap.unit.test.d.ts +2 -0
- package/dist/tests/unit/tasks/puzzleDifficultyDeviceCap.unit.test.d.ts.map +1 -0
- package/dist/tests/unit/tasks/puzzleDifficultyDeviceCap.unit.test.js +49 -0
- package/dist/tests/unit/tasks/puzzleDifficultyDeviceCap.unit.test.js.map +1 -0
- package/dist/tests/unit/testUtils/mockProviderEnv.d.ts +17 -14
- package/dist/tests/unit/testUtils/mockProviderEnv.d.ts.map +1 -1
- package/dist/tests/unit/testUtils/mockProviderEnv.js.map +1 -1
- package/package.json +105 -103
|
@@ -7,9 +7,44 @@ var HEADER_ACK_NS = "x-tls-ack-ns";
|
|
|
7
7
|
var HEADER_OBSERVED_TTL = "x-tls-observed-ttl";
|
|
8
8
|
var HEADER_TCP_MSS = "x-tls-tcp-mss";
|
|
9
9
|
var HEADER_TCP_WSCALE = "x-tls-tcp-wscale";
|
|
10
|
+
var HEADER_TCP_WINDOW = "x-tls-tcp-window";
|
|
11
|
+
var HEADER_TCP_OPTS_KINDS = "x-tls-tcp-opts-kinds";
|
|
12
|
+
var HEADER_TCP_OPTS_PRESENT = "x-tls-tcp-opts-present";
|
|
13
|
+
var HEADER_TCP_OPTS_COUNT = "x-tls-tcp-opts-count";
|
|
14
|
+
var HEADER_TCP_TSVAL = "x-tls-tcp-tsval";
|
|
15
|
+
var HEADER_TCP_TSECR = "x-tls-tcp-tsecr";
|
|
16
|
+
var HEADER_TCP_FLAGS = "x-tls-tcp-flags";
|
|
17
|
+
var HEADER_TCP_DATA_OFFSET_RESV = "x-tls-tcp-data-offset-resv";
|
|
18
|
+
var HEADER_TCP_URG_PTR = "x-tls-tcp-urg-ptr";
|
|
19
|
+
var HEADER_IP_IDENT = "x-tls-ip-ident";
|
|
20
|
+
var HEADER_IP_TOTAL_LEN = "x-tls-ip-total-len";
|
|
21
|
+
var HEADER_IP_FRAG_FLAGS = "x-tls-ip-frag-flags";
|
|
22
|
+
var HEADER_IP_TOS = "x-tls-ip-tos";
|
|
10
23
|
var HEADER_TCP_OPTS_FLAGS = "x-tls-tcp-opts-flags";
|
|
11
24
|
var HEADER_TCP_OPTS_ORDER = "x-tls-tcp-opts-order";
|
|
12
|
-
var
|
|
25
|
+
var RAW_TLS_SIGNAL_KEYS = [
|
|
26
|
+
"synNs",
|
|
27
|
+
"synackNs",
|
|
28
|
+
"ackNs",
|
|
29
|
+
"observedTtl",
|
|
30
|
+
"tcpMss",
|
|
31
|
+
"tcpWscale",
|
|
32
|
+
"tcpWindow",
|
|
33
|
+
"tcpOptsKinds",
|
|
34
|
+
"tcpOptsPresent",
|
|
35
|
+
"tcpOptsCount",
|
|
36
|
+
"tcpTsval",
|
|
37
|
+
"tcpTsecr",
|
|
38
|
+
"tcpFlags",
|
|
39
|
+
"tcpDataOffsetResv",
|
|
40
|
+
"tcpUrgPtr",
|
|
41
|
+
"ipIdent",
|
|
42
|
+
"ipTotalLen",
|
|
43
|
+
"ipFragFlags",
|
|
44
|
+
"ipTos",
|
|
45
|
+
"tcpOptsFlags",
|
|
46
|
+
"tcpOptsOrder"
|
|
47
|
+
];
|
|
13
48
|
var parseIntHeader = (raw, logger, headerName, max) => {
|
|
14
49
|
if (raw === void 0) return;
|
|
15
50
|
const value = Array.isArray(raw) ? raw[0] : raw;
|
|
@@ -31,6 +66,46 @@ var MAX_NS = 2 ** 63;
|
|
|
31
66
|
var MAX_U8 = 255;
|
|
32
67
|
var MAX_U16 = 65535;
|
|
33
68
|
var MAX_U32 = 4294967295;
|
|
69
|
+
var OPTS_KINDS_SLOTS = 8;
|
|
70
|
+
var MAX_U64 = (1n << 64n) - 1n;
|
|
71
|
+
var parseOptsKindsHeader = (raw, logger) => {
|
|
72
|
+
if (raw === void 0) return;
|
|
73
|
+
const value = Array.isArray(raw) ? raw[0] : raw;
|
|
74
|
+
if (value === void 0 || !/^\d+$/.test(value)) {
|
|
75
|
+
if (value !== void 0) logger.debug(() => ({
|
|
76
|
+
msg: "Ignoring malformed raw TLS signal header",
|
|
77
|
+
data: {
|
|
78
|
+
header: HEADER_TCP_OPTS_KINDS,
|
|
79
|
+
raw: value
|
|
80
|
+
}
|
|
81
|
+
}));
|
|
82
|
+
return;
|
|
83
|
+
}
|
|
84
|
+
let packed;
|
|
85
|
+
try {
|
|
86
|
+
packed = BigInt(value);
|
|
87
|
+
} catch {
|
|
88
|
+
return;
|
|
89
|
+
}
|
|
90
|
+
if (packed > MAX_U64) {
|
|
91
|
+
logger.debug(() => ({
|
|
92
|
+
msg: "Ignoring out-of-range raw TLS signal header",
|
|
93
|
+
data: {
|
|
94
|
+
header: HEADER_TCP_OPTS_KINDS,
|
|
95
|
+
raw: value
|
|
96
|
+
}
|
|
97
|
+
}));
|
|
98
|
+
return;
|
|
99
|
+
}
|
|
100
|
+
if (packed === 0n) return;
|
|
101
|
+
const kinds = [];
|
|
102
|
+
for (let slot = 0; slot < OPTS_KINDS_SLOTS; slot++) {
|
|
103
|
+
const kind = Number(packed >> BigInt(slot * 8) & 255n);
|
|
104
|
+
if (kind === 0) break;
|
|
105
|
+
kinds.push(kind);
|
|
106
|
+
}
|
|
107
|
+
return kinds.length > 0 ? kinds : void 0;
|
|
108
|
+
};
|
|
34
109
|
var getRawTlsSignals = (headers, logger) => {
|
|
35
110
|
const log = logger ?? (0, _prosopo_logger.getLogger)("info", "provider:raw-tls-signals");
|
|
36
111
|
return {
|
|
@@ -40,37 +115,50 @@ var getRawTlsSignals = (headers, logger) => {
|
|
|
40
115
|
observedTtl: parseIntHeader(headers[HEADER_OBSERVED_TTL], log, HEADER_OBSERVED_TTL, MAX_U8),
|
|
41
116
|
tcpMss: parseIntHeader(headers[HEADER_TCP_MSS], log, HEADER_TCP_MSS, MAX_U16),
|
|
42
117
|
tcpWscale: parseIntHeader(headers[HEADER_TCP_WSCALE], log, HEADER_TCP_WSCALE, MAX_U8),
|
|
118
|
+
tcpWindow: parseIntHeader(headers[HEADER_TCP_WINDOW], log, HEADER_TCP_WINDOW, MAX_U16),
|
|
119
|
+
tcpOptsKinds: parseOptsKindsHeader(headers[HEADER_TCP_OPTS_KINDS], log),
|
|
120
|
+
tcpOptsPresent: parseIntHeader(headers[HEADER_TCP_OPTS_PRESENT], log, HEADER_TCP_OPTS_PRESENT, MAX_U16),
|
|
121
|
+
tcpOptsCount: parseIntHeader(headers[HEADER_TCP_OPTS_COUNT], log, HEADER_TCP_OPTS_COUNT, MAX_U8),
|
|
122
|
+
tcpTsval: parseIntHeader(headers[HEADER_TCP_TSVAL], log, HEADER_TCP_TSVAL, MAX_U32),
|
|
123
|
+
tcpTsecr: parseIntHeader(headers[HEADER_TCP_TSECR], log, HEADER_TCP_TSECR, MAX_U32),
|
|
124
|
+
tcpFlags: parseIntHeader(headers[HEADER_TCP_FLAGS], log, HEADER_TCP_FLAGS, MAX_U8),
|
|
125
|
+
tcpDataOffsetResv: parseIntHeader(headers[HEADER_TCP_DATA_OFFSET_RESV], log, HEADER_TCP_DATA_OFFSET_RESV, MAX_U8),
|
|
126
|
+
tcpUrgPtr: parseIntHeader(headers[HEADER_TCP_URG_PTR], log, HEADER_TCP_URG_PTR, MAX_U16),
|
|
127
|
+
ipIdent: parseIntHeader(headers[HEADER_IP_IDENT], log, HEADER_IP_IDENT, MAX_U16),
|
|
128
|
+
ipTotalLen: parseIntHeader(headers[HEADER_IP_TOTAL_LEN], log, HEADER_IP_TOTAL_LEN, MAX_U16),
|
|
129
|
+
ipFragFlags: parseIntHeader(headers[HEADER_IP_FRAG_FLAGS], log, HEADER_IP_FRAG_FLAGS, MAX_U16),
|
|
130
|
+
ipTos: parseIntHeader(headers[HEADER_IP_TOS], log, HEADER_IP_TOS, MAX_U8),
|
|
43
131
|
tcpOptsFlags: parseIntHeader(headers[HEADER_TCP_OPTS_FLAGS], log, HEADER_TCP_OPTS_FLAGS, MAX_U8),
|
|
44
|
-
tcpOptsOrder: parseIntHeader(headers[HEADER_TCP_OPTS_ORDER], log, HEADER_TCP_OPTS_ORDER, MAX_U32)
|
|
45
|
-
tcpWindow: parseIntHeader(headers[HEADER_TCP_WINDOW], log, HEADER_TCP_WINDOW, MAX_U16)
|
|
132
|
+
tcpOptsOrder: parseIntHeader(headers[HEADER_TCP_OPTS_ORDER], log, HEADER_TCP_OPTS_ORDER, MAX_U32)
|
|
46
133
|
};
|
|
47
134
|
};
|
|
48
|
-
var rawTlsSignalsForSession = (req) =>
|
|
135
|
+
var rawTlsSignalsForSession = (req) => rawTlsSignalsFromRecord(req);
|
|
136
|
+
/**
|
|
137
|
+
* Pull the raw TLS signals out of a persisted Session — or anything shaped
|
|
138
|
+
* like one — for a decision machine's `raw` bag, or to carry forward onto a
|
|
139
|
+
* new Session record.
|
|
140
|
+
*
|
|
141
|
+
* Six call sites used to name every field by hand, so adding one to the
|
|
142
|
+
* probe meant remembering six places; the fields that were forgotten read as
|
|
143
|
+
* `undefined` and the rules gating on them silently never fired.
|
|
144
|
+
*/
|
|
145
|
+
var rawTlsSignalsFromRecord = (record) => {
|
|
49
146
|
const out = {};
|
|
50
|
-
if (
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
if (req.tcpWscale !== void 0) out.tcpWscale = req.tcpWscale;
|
|
56
|
-
if (req.tcpOptsFlags !== void 0) out.tcpOptsFlags = req.tcpOptsFlags;
|
|
57
|
-
if (req.tcpOptsOrder !== void 0) out.tcpOptsOrder = req.tcpOptsOrder;
|
|
58
|
-
if (req.tcpWindow !== void 0) out.tcpWindow = req.tcpWindow;
|
|
147
|
+
if (!record) return out;
|
|
148
|
+
for (const key of RAW_TLS_SIGNAL_KEYS) {
|
|
149
|
+
const value = record[key];
|
|
150
|
+
if (value !== void 0) Object.assign(out, { [key]: value });
|
|
151
|
+
}
|
|
59
152
|
return out;
|
|
60
153
|
};
|
|
61
154
|
var rawTlsSignalsMiddleware = (env) => {
|
|
62
155
|
return async (req, res, next) => {
|
|
63
156
|
try {
|
|
64
157
|
const signals = getRawTlsSignals(req.headers, req.logger);
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
if (signals.tcpMss !== void 0) req.tcpMss = signals.tcpMss;
|
|
70
|
-
if (signals.tcpWscale !== void 0) req.tcpWscale = signals.tcpWscale;
|
|
71
|
-
if (signals.tcpOptsFlags !== void 0) req.tcpOptsFlags = signals.tcpOptsFlags;
|
|
72
|
-
if (signals.tcpOptsOrder !== void 0) req.tcpOptsOrder = signals.tcpOptsOrder;
|
|
73
|
-
if (signals.tcpWindow !== void 0) req.tcpWindow = signals.tcpWindow;
|
|
158
|
+
for (const key of RAW_TLS_SIGNAL_KEYS) {
|
|
159
|
+
const value = signals[key];
|
|
160
|
+
if (value !== void 0) Object.assign(req, { [key]: value });
|
|
161
|
+
}
|
|
74
162
|
if (Object.values(signals).some((v) => v !== void 0)) req.logger = req.logger.with(signals, "rawTlsSignals");
|
|
75
163
|
next();
|
|
76
164
|
} catch (err) {
|
|
@@ -81,4 +169,5 @@ var rawTlsSignalsMiddleware = (env) => {
|
|
|
81
169
|
//#endregion
|
|
82
170
|
exports.getRawTlsSignals = getRawTlsSignals;
|
|
83
171
|
exports.rawTlsSignalsForSession = rawTlsSignalsForSession;
|
|
172
|
+
exports.rawTlsSignalsFromRecord = rawTlsSignalsFromRecord;
|
|
84
173
|
exports.rawTlsSignalsMiddleware = rawTlsSignalsMiddleware;
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
const require_runtime = require("../_virtual/_rolldown/runtime.cjs");
|
|
2
2
|
const require_metrics = require("./metrics.cjs");
|
|
3
|
+
const require_rawTlsSignalsMiddleware = require("./rawTlsSignalsMiddleware.cjs");
|
|
3
4
|
const require_blacklistRequestInspector = require("./blacklistRequestInspector.cjs");
|
|
4
5
|
const require_bundlePool = require("../tasks/detection/bundlePool.cjs");
|
|
5
6
|
const require_block = require("./block.cjs");
|
|
6
|
-
const require_rawTlsSignalsMiddleware = require("./rawTlsSignalsMiddleware.cjs");
|
|
7
7
|
const require_captcha = require("./captcha.cjs");
|
|
8
8
|
const require_verify = require("./verify.cjs");
|
|
9
9
|
const require_ja4Middleware = require("./ja4Middleware.cjs");
|
|
@@ -20,13 +20,13 @@ const require_ipInfoMiddleware = require("./ipInfoMiddleware.cjs");
|
|
|
20
20
|
const require_robotsMiddleware = require("./robotsMiddleware.cjs");
|
|
21
21
|
let _prosopo_logger = require("@prosopo/logger");
|
|
22
22
|
let _prosopo_types = require("@prosopo/types");
|
|
23
|
+
let _prosopo_api_express_router = require("@prosopo/api-express-router");
|
|
23
24
|
let node_fs = require("node:fs");
|
|
24
25
|
node_fs = require_runtime.__toESM(node_fs, 1);
|
|
25
26
|
let node_path = require("node:path");
|
|
26
27
|
node_path = require_runtime.__toESM(node_path, 1);
|
|
27
28
|
let node_https = require("node:https");
|
|
28
29
|
node_https = require_runtime.__toESM(node_https, 1);
|
|
29
|
-
let _prosopo_api_express_router = require("@prosopo/api-express-router");
|
|
30
30
|
let express = require("express");
|
|
31
31
|
express = require_runtime.__toESM(express, 1);
|
|
32
32
|
let node_url = require("node:url");
|
|
@@ -4,6 +4,11 @@ let ip_address = require("ip-address");
|
|
|
4
4
|
//#region src/compositeIpAddress.ts
|
|
5
5
|
var V6_SHIFT = 64n;
|
|
6
6
|
var v6_LOWER_MASK = (1n << V6_SHIFT) - 1n;
|
|
7
|
+
/**
|
|
8
|
+
* The part of a v4 address treated as the host rather than the network, for
|
|
9
|
+
* the purposes of `isSameIpOrigin`. 8 bits — a /24.
|
|
10
|
+
*/
|
|
11
|
+
var V4_HOST_BITS = 8n;
|
|
7
12
|
var getCompositeIpAddress = (ip) => {
|
|
8
13
|
let ipAddress;
|
|
9
14
|
try {
|
|
@@ -60,10 +65,19 @@ var isUnknownIp = (ip) => ip.type === _prosopo_types.IpAddressType.v4 && readPar
|
|
|
60
65
|
/**
|
|
61
66
|
* Do two observations of a client come from the same place on the network?
|
|
62
67
|
*
|
|
63
|
-
*
|
|
64
|
-
*
|
|
65
|
-
*
|
|
66
|
-
*
|
|
68
|
+
* Both families are compared on the network part and neither on the host part.
|
|
69
|
+
*
|
|
70
|
+
* v6 is the /64 prefix: the interface identifier in the low 64 bits is designed
|
|
71
|
+
* to rotate (RFC 8981 privacy extensions), often several times a day on one
|
|
72
|
+
* unchanged connection, so comparing it would call an ordinary phone a
|
|
73
|
+
* different host.
|
|
74
|
+
*
|
|
75
|
+
* v4 is the /24. A carrier NAT or mobile pool reassigns the low octet mid
|
|
76
|
+
* session — an EE subscriber was observed moving one address in four seconds —
|
|
77
|
+
* so comparing the whole address called every rotating mobile and CGNAT client
|
|
78
|
+
* a different host, which is the opposite of the leniency this check is for.
|
|
79
|
+
* The /24 still separates an unrelated network, which is the case worth
|
|
80
|
+
* catching: a challenge handed to a second host to farm the work out.
|
|
67
81
|
*
|
|
68
82
|
* A value we do not actually have counts as the same — one that will not
|
|
69
83
|
* parse, or the all-zero v4 `getCompositeIpAddress` returns when handed an
|
|
@@ -73,13 +87,13 @@ var isUnknownIp = (ip) => ip.type === _prosopo_types.IpAddressType.v4 && readPar
|
|
|
73
87
|
var isSameIpOrigin = (a, b) => {
|
|
74
88
|
if (isUnknownIp(a) || isUnknownIp(b)) return true;
|
|
75
89
|
if (a.type !== b.type) return false;
|
|
76
|
-
const
|
|
90
|
+
const sameNetwork = (left, right, hostBits) => {
|
|
77
91
|
const leftPart = readPart(left);
|
|
78
92
|
const rightPart = readPart(right);
|
|
79
93
|
if (leftPart === void 0 || rightPart === void 0) return true;
|
|
80
|
-
return leftPart === rightPart;
|
|
94
|
+
return leftPart >> hostBits === rightPart >> hostBits;
|
|
81
95
|
};
|
|
82
|
-
return a.type === _prosopo_types.IpAddressType.v6 ?
|
|
96
|
+
return a.type === _prosopo_types.IpAddressType.v6 ? sameNetwork(a.upper, b.upper, 0n) : sameNetwork(a.lower, b.lower, V4_HOST_BITS);
|
|
83
97
|
};
|
|
84
98
|
var never = () => {
|
|
85
99
|
throw new Error("Unhandled type");
|
|
@@ -225,6 +225,21 @@ var CaptchaManager = class CaptchaManager {
|
|
|
225
225
|
sessionId
|
|
226
226
|
}
|
|
227
227
|
}));
|
|
228
|
+
if (!(0, _prosopo_types.isCaptchaTypeFeatureEnabled)(requestedCaptchaType, clientSettings.settings?.captchaTypeFeatureFlags)) {
|
|
229
|
+
this.logger.warn(() => ({
|
|
230
|
+
msg: "Captcha type is switched off for this site",
|
|
231
|
+
data: {
|
|
232
|
+
account: clientSettings.account,
|
|
233
|
+
requestedCaptchaType,
|
|
234
|
+
sessionId
|
|
235
|
+
}
|
|
236
|
+
}));
|
|
237
|
+
return {
|
|
238
|
+
valid: false,
|
|
239
|
+
reason: _prosopo_types.ResultReason.INCORRECT_CAPTCHA_TYPE,
|
|
240
|
+
type: requestedCaptchaType
|
|
241
|
+
};
|
|
242
|
+
}
|
|
228
243
|
if (sessionId) {
|
|
229
244
|
const cachedBeforeRemove = this.writeQueue ? await this.writeQueue.getCachedSession(sessionId) : null;
|
|
230
245
|
const cachedHash = typeof cachedBeforeRemove?.userSitekeyIpHash === "string" ? cachedBeforeRemove.userSitekeyIpHash : void 0;
|
|
@@ -18,12 +18,16 @@ let _prosopo_types = require("@prosopo/types");
|
|
|
18
18
|
* Restrict rules, traffic-filter category policies, routing-machine actions
|
|
19
19
|
* and detector-generated rules.
|
|
20
20
|
*
|
|
21
|
+
* Pass `allowedTypes` from `resolveAllowedCaptchaTypes`, so Prosopo's
|
|
22
|
+
* per-site captcha type feature flags are applied alongside the site owner's
|
|
23
|
+
* own `frictionlessTypes`. Absent means every type is allowed.
|
|
24
|
+
*
|
|
21
25
|
* Coercion only ever narrows. A disabled type falls back to the other
|
|
22
26
|
* interactive type if that is permitted, and to PoW otherwise — never the
|
|
23
27
|
* reverse, so this can't hand a user a harder challenge than was asked for.
|
|
24
28
|
*/
|
|
25
|
-
var coerceToEnabledCaptchaType = (requested,
|
|
26
|
-
const types = (0, _prosopo_types.resolveFrictionlessTypes)(
|
|
29
|
+
var coerceToEnabledCaptchaType = (requested, allowedTypes, logger) => {
|
|
30
|
+
const types = (0, _prosopo_types.resolveFrictionlessTypes)(allowedTypes);
|
|
27
31
|
const puzzleAllowed = types.puzzle && require_puzzleRenderer.isPuzzleRenderAvailable();
|
|
28
32
|
const imageAllowed = types.image;
|
|
29
33
|
const resolved = (() => {
|
|
@@ -49,5 +53,22 @@ var coerceToEnabledCaptchaType = (requested, frictionlessTypes, logger) => {
|
|
|
49
53
|
}));
|
|
50
54
|
return resolved;
|
|
51
55
|
};
|
|
56
|
+
/**
|
|
57
|
+
* Swap a puzzle for an image challenge once the user has refreshed it
|
|
58
|
+
* `PUZZLE_REFRESHES_BEFORE_IMAGE` times in a row.
|
|
59
|
+
*
|
|
60
|
+
* A user who keeps refreshing either cannot solve this kind of puzzle or is a
|
|
61
|
+
* solver shopping for an easy instance. The image challenge answers both.
|
|
62
|
+
*
|
|
63
|
+
* The refresh count is client-reported, so this only moves one way: from
|
|
64
|
+
* puzzle to image, never back. Lying about it can only earn a harder
|
|
65
|
+
* challenge. Leaving it out looks like a fresh visit, which is what a page
|
|
66
|
+
* reload already gets.
|
|
67
|
+
*
|
|
68
|
+
* A site that has not enabled image keeps its puzzle. Serving a type the site
|
|
69
|
+
* turned off is exactly what `coerceToEnabledCaptchaType` exists to stop.
|
|
70
|
+
*/
|
|
71
|
+
var switchTypeAfterRefreshes = (resolved, refreshCount, allowedTypes) => _prosopo_types.CaptchaType.puzzle === resolved && (refreshCount ?? 0) >= 3 && (0, _prosopo_types.resolveFrictionlessTypes)(allowedTypes).image ? _prosopo_types.CaptchaType.image : resolved;
|
|
52
72
|
//#endregion
|
|
53
73
|
exports.coerceToEnabledCaptchaType = coerceToEnabledCaptchaType;
|
|
74
|
+
exports.switchTypeAfterRefreshes = switchTypeAfterRefreshes;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
const require_usageCounters = require("../../util/usageCounters.cjs");
|
|
2
2
|
const require_decisionMachineRunner = require("../decisionMachine/decisionMachineRunner.cjs");
|
|
3
3
|
const require_dnsEventUrl = require("../../api/dnsEventUrl.cjs");
|
|
4
|
+
const require_rawTlsSignalsMiddleware = require("../../api/rawTlsSignalsMiddleware.cjs");
|
|
4
5
|
const require_lang = require("../../rules/lang.cjs");
|
|
5
6
|
const require_clientMetaData = require("../../utils/clientMetaData.cjs");
|
|
6
7
|
const require_captchaManager = require("../captchaManager.cjs");
|
|
@@ -33,6 +34,15 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
33
34
|
this.routingContext = ctx;
|
|
34
35
|
}
|
|
35
36
|
/**
|
|
37
|
+
* The types this site may be served, from `resolveAllowedCaptchaTypes`.
|
|
38
|
+
* Set before any path can mint a session, including the short-circuits
|
|
39
|
+
* that skip routing, so the site's feature flags hold on every path.
|
|
40
|
+
* Unset means every type is allowed.
|
|
41
|
+
*/
|
|
42
|
+
setAllowedCaptchaTypes(allowed) {
|
|
43
|
+
this.allowedCaptchaTypes = allowed;
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
36
46
|
* Evaluate the configured routing machine without going through
|
|
37
47
|
* `sendCaptcha`. Returns the supplied baseline on any failure (no machine,
|
|
38
48
|
* machine throws, counter fetch failure), matching applyRouter's contract.
|
|
@@ -63,15 +73,10 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
63
73
|
d: params.d,
|
|
64
74
|
tcpToChelloUs: params.tcpToChelloUs,
|
|
65
75
|
chelloToHandshakeUs: params.chelloToHandshakeUs,
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
tcpMss: params.tcpMss,
|
|
71
|
-
tcpWscale: params.tcpWscale,
|
|
72
|
-
tcpOptsFlags: params.tcpOptsFlags,
|
|
73
|
-
tcpOptsOrder: params.tcpOptsOrder,
|
|
74
|
-
tcpWindow: params.tcpWindow
|
|
76
|
+
...require_rawTlsSignalsMiddleware.rawTlsSignalsFromRecord(params),
|
|
77
|
+
refreshOf: params.refreshOf,
|
|
78
|
+
refreshCount: params.refreshCount,
|
|
79
|
+
refreshedAfterMs: params.refreshedAfterMs
|
|
75
80
|
};
|
|
76
81
|
}
|
|
77
82
|
/**
|
|
@@ -91,7 +96,7 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
91
96
|
return require_lang.checkLangRules(this.config, acceptLanguage);
|
|
92
97
|
}
|
|
93
98
|
async createSession(input) {
|
|
94
|
-
const { token, score, threshold, scoreComponents, ipAddress, captchaType, siteKey, mode, solvedImagesCount, powDifficulty, userSitekeyIpHash, reason, blocked, deleted, ipInfo, headers, bundleId, currentUrl, iframeUrl, d, tcpToChelloUs, chelloToHandshakeUs,
|
|
99
|
+
const { token, score, threshold, scoreComponents, ipAddress, captchaType, siteKey, mode, solvedImagesCount, powDifficulty, userSitekeyIpHash, reason, blocked, deleted, ipInfo, headers, bundleId, currentUrl, iframeUrl, d, tcpToChelloUs, chelloToHandshakeUs, simdReadings, puzzleTolerance, puzzle, isEscalation, originSessionId, refreshOf, refreshCount, refreshedAfterMs, isProtect, matchedRule, clientMetaData, webView = false, iFrame = false, decryptedHeadHash = "" } = input;
|
|
95
100
|
const sessionRecord = {
|
|
96
101
|
sessionId: `${getSessionIDPrefix(this.config.host)}-${(0, uuid.v4)()}`,
|
|
97
102
|
createdAt: /* @__PURE__ */ new Date(),
|
|
@@ -111,6 +116,9 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
111
116
|
iFrame,
|
|
112
117
|
...isEscalation && { isEscalation: true },
|
|
113
118
|
...originSessionId && { originSessionId },
|
|
119
|
+
...refreshOf && { refreshOf },
|
|
120
|
+
...refreshCount !== void 0 && { refreshCount },
|
|
121
|
+
...refreshedAfterMs !== void 0 && { refreshedAfterMs },
|
|
114
122
|
decryptedHeadHash,
|
|
115
123
|
bundleId,
|
|
116
124
|
reason,
|
|
@@ -127,15 +135,7 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
127
135
|
d,
|
|
128
136
|
tcpToChelloUs,
|
|
129
137
|
chelloToHandshakeUs,
|
|
130
|
-
|
|
131
|
-
synackNs,
|
|
132
|
-
ackNs,
|
|
133
|
-
observedTtl,
|
|
134
|
-
tcpMss,
|
|
135
|
-
tcpWscale,
|
|
136
|
-
tcpOptsFlags,
|
|
137
|
-
tcpOptsOrder,
|
|
138
|
-
tcpWindow,
|
|
138
|
+
...require_rawTlsSignalsMiddleware.rawTlsSignalsFromRecord(input),
|
|
139
139
|
...matchedRule && { matchedRule },
|
|
140
140
|
...clientMetaData && { clientMetaData }
|
|
141
141
|
};
|
|
@@ -247,14 +247,16 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
247
247
|
powDifficulty: captchaType === _prosopo_types.CaptchaType.pow ? effectiveParams.powDifficulty : void 0
|
|
248
248
|
};
|
|
249
249
|
const routed = this.routingContext ? await require_routingMachine.applyRouter(this.decisionMachineRunner, this.usageCounters, baseline, this.routingContext, this.logger) : baseline;
|
|
250
|
-
const
|
|
250
|
+
const enabledCaptchaType = require_captchaTypeSelection.coerceToEnabledCaptchaType(routed.captchaType, this.allowedCaptchaTypes, this.logger);
|
|
251
|
+
const finalCaptchaType = require_captchaTypeSelection.switchTypeAfterRefreshes(enabledCaptchaType, effectiveParams.refreshCount, this.allowedCaptchaTypes);
|
|
252
|
+
const switchedByRefreshes = finalCaptchaType !== enabledCaptchaType;
|
|
251
253
|
const requestedSolvedImagesCount = routed.solvedImagesCount ?? effectiveParams.solvedImagesCount;
|
|
252
254
|
const imageRoundsBounds = this.routingContext ?? {};
|
|
253
255
|
const finalSolvedImagesCount = finalCaptchaType === _prosopo_types.CaptchaType.image ? requestedSolvedImagesCount !== void 0 ? (0, _prosopo_types.clampImageRounds)(requestedSolvedImagesCount, imageRoundsBounds) : requestedSolvedImagesCount : void 0;
|
|
254
256
|
const finalPowDifficulty = finalCaptchaType === _prosopo_types.CaptchaType.pow ? routed.powDifficulty ?? effectiveParams.powDifficulty : void 0;
|
|
255
|
-
const finalReason = routed.reason ?? effectiveParams.reason;
|
|
257
|
+
const finalReason = switchedByRefreshes ? _prosopo_types.FrictionlessReason.PUZZLE_REFRESH_LIMIT : routed.reason ?? effectiveParams.reason;
|
|
256
258
|
const finalPuzzleOverrides = finalCaptchaType === _prosopo_types.CaptchaType.puzzle ? (() => {
|
|
257
|
-
const maxLevel = this.routingContext?.puzzleMaxDifficulty ?? _prosopo_types.puzzleMaxDifficultyDefault;
|
|
259
|
+
const maxLevel = (0, _prosopo_captcha_severity.resolveMaxEscalationLevel)(this.routingContext?.puzzleMaxDifficulty ?? _prosopo_types.puzzleMaxDifficultyDefault, this.routingContext?.platform.isMobile ?? false);
|
|
258
260
|
const level = finalReason !== void 0 && _prosopo_types.NO_MEASUREMENT_REASONS.has(finalReason) ? 0 : (0, _prosopo_captcha_severity.severityToPuzzleDifficulty)(requestedSolvedImagesCount, this.routingContext?.baseImageRounds ?? this.config.captchas.solved.count, maxLevel);
|
|
259
261
|
const difficulty = level > 0 ? require_puzzleDifficulty.samplePuzzleDifficulty(level, _prosopo_puzzle_assets.DEFAULT_RENDER_SETTINGS.holeDarken) : void 0;
|
|
260
262
|
const tolerance = routed.puzzleTolerance ?? difficulty?.tolerance;
|
|
@@ -264,7 +266,8 @@ var FrictionlessManager = class extends require_captchaManager.CaptchaManager {
|
|
|
264
266
|
} : void 0;
|
|
265
267
|
return {
|
|
266
268
|
...tolerance !== void 0 && { puzzleTolerance: tolerance },
|
|
267
|
-
...puzzle !== void 0 && { puzzle }
|
|
269
|
+
...puzzle !== void 0 && { puzzle },
|
|
270
|
+
...difficulty !== void 0 && { puzzleLevel: difficulty.level }
|
|
268
271
|
};
|
|
269
272
|
})() : {};
|
|
270
273
|
const blocked = finalCaptchaType === _prosopo_types.CaptchaType.image ? effectiveParams.blocked : void 0;
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const require_usageCounters = require("../../util/usageCounters.cjs");
|
|
2
2
|
const require_decisionMachineRunner = require("../decisionMachine/decisionMachineRunner.cjs");
|
|
3
|
+
const require_rawTlsSignalsMiddleware = require("../../api/rawTlsSignalsMiddleware.cjs");
|
|
3
4
|
const require_lang = require("../../rules/lang.cjs");
|
|
4
5
|
const require_clientMetaData = require("../../utils/clientMetaData.cjs");
|
|
5
6
|
const require_compositeIpAddress = require("../../compositeIpAddress.cjs");
|
|
@@ -566,15 +567,7 @@ var ImgCaptchaManager = class extends require_captchaManager.CaptchaManager {
|
|
|
566
567
|
currentUrl: sessionRecord?.currentUrl,
|
|
567
568
|
iframeUrl: sessionRecord?.iframeUrl,
|
|
568
569
|
coords: solution.coords,
|
|
569
|
-
|
|
570
|
-
synackNs: sessionRecord?.synackNs,
|
|
571
|
-
ackNs: sessionRecord?.ackNs,
|
|
572
|
-
observedTtl: sessionRecord?.observedTtl,
|
|
573
|
-
tcpMss: sessionRecord?.tcpMss,
|
|
574
|
-
tcpWscale: sessionRecord?.tcpWscale,
|
|
575
|
-
tcpOptsFlags: sessionRecord?.tcpOptsFlags,
|
|
576
|
-
tcpOptsOrder: sessionRecord?.tcpOptsOrder,
|
|
577
|
-
tcpWindow: sessionRecord?.tcpWindow,
|
|
570
|
+
...require_rawTlsSignalsMiddleware.rawTlsSignalsFromRecord(sessionRecord),
|
|
578
571
|
trafficPolicies: require_devicePlatform.deriveTrafficPolicies(trafficFilter)
|
|
579
572
|
};
|
|
580
573
|
try {
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const require_usageCounters = require("../../util/usageCounters.cjs");
|
|
2
2
|
const require_decisionMachineRunner = require("../decisionMachine/decisionMachineRunner.cjs");
|
|
3
|
+
const require_rawTlsSignalsMiddleware = require("../../api/rawTlsSignalsMiddleware.cjs");
|
|
3
4
|
const require_clientMetaData = require("../../utils/clientMetaData.cjs");
|
|
4
5
|
const require_compositeIpAddress = require("../../compositeIpAddress.cjs");
|
|
5
6
|
const require_enrichDnsEvent = require("../dnsEvent/enrichDnsEvent.cjs");
|
|
@@ -209,7 +210,8 @@ var PowCaptchaManager = class extends require_captchaManager.CaptchaManager {
|
|
|
209
210
|
let routingOutput = this.postPowContext ? await this.runPostPowRouting({
|
|
210
211
|
challengeRecord,
|
|
211
212
|
challengeSplit,
|
|
212
|
-
behavioralDataPacked: decryptedBehavioralDataPacked
|
|
213
|
+
behavioralDataPacked: decryptedBehavioralDataPacked,
|
|
214
|
+
coords
|
|
213
215
|
}) : void 0;
|
|
214
216
|
if ((escalateForMissingCoords || escalateForIpChange) && routingOutput?.captchaType !== _prosopo_types.CaptchaType.image && routingOutput?.captchaType !== _prosopo_types.CaptchaType.puzzle) routingOutput = {
|
|
215
217
|
captchaType: _prosopo_types.CaptchaType.image,
|
|
@@ -228,7 +230,7 @@ var PowCaptchaManager = class extends require_captchaManager.CaptchaManager {
|
|
|
228
230
|
*/
|
|
229
231
|
async runPostPowRouting(args) {
|
|
230
232
|
if (!this.postPowContext) return void 0;
|
|
231
|
-
const { challengeRecord, challengeSplit, behavioralDataPacked } = args;
|
|
233
|
+
const { challengeRecord, challengeSplit, behavioralDataPacked, coords } = args;
|
|
232
234
|
if (!challengeRecord.sessionId) {
|
|
233
235
|
this.logger.debug(() => ({ msg: "Skipping post-pow routing: PoW record has no linked session" }));
|
|
234
236
|
return;
|
|
@@ -259,6 +261,8 @@ var PowCaptchaManager = class extends require_captchaManager.CaptchaManager {
|
|
|
259
261
|
raw: {
|
|
260
262
|
...this.postPowContext.raw,
|
|
261
263
|
...behavioralDataPacked && { behavioralDataPacked },
|
|
264
|
+
...sessionRecord.mode && { mode: sessionRecord.mode },
|
|
265
|
+
coordsAllZero: require_powTasksUtils.isCoordsAllZero(coords),
|
|
262
266
|
...sessionRecord.simdReadings && { simd: sessionRecord.simdReadings },
|
|
263
267
|
...sessionRecord.currentUrl && { currentUrl: sessionRecord.currentUrl },
|
|
264
268
|
...sessionRecord.iframeUrl && { iframeUrl: sessionRecord.iframeUrl }
|
|
@@ -518,15 +522,7 @@ var PowCaptchaManager = class extends require_captchaManager.CaptchaManager {
|
|
|
518
522
|
currentUrl: sessionRecord?.currentUrl,
|
|
519
523
|
iframeUrl: sessionRecord?.iframeUrl,
|
|
520
524
|
coords: challengeRecord.coords,
|
|
521
|
-
|
|
522
|
-
synackNs: sessionRecord?.synackNs,
|
|
523
|
-
ackNs: sessionRecord?.ackNs,
|
|
524
|
-
observedTtl: sessionRecord?.observedTtl,
|
|
525
|
-
tcpMss: sessionRecord?.tcpMss,
|
|
526
|
-
tcpWscale: sessionRecord?.tcpWscale,
|
|
527
|
-
tcpOptsFlags: sessionRecord?.tcpOptsFlags,
|
|
528
|
-
tcpOptsOrder: sessionRecord?.tcpOptsOrder,
|
|
529
|
-
tcpWindow: sessionRecord?.tcpWindow,
|
|
525
|
+
...require_rawTlsSignalsMiddleware.rawTlsSignalsFromRecord(sessionRecord),
|
|
530
526
|
trafficPolicies: require_devicePlatform.deriveTrafficPolicies(trafficFilter)
|
|
531
527
|
};
|
|
532
528
|
const decision = await this.decisionMachineRunner.decide(decisionInput, logger);
|
|
@@ -15,6 +15,8 @@ var checkPowSignature = (message, signature, address, signatureType) => {
|
|
|
15
15
|
signatureType
|
|
16
16
|
} });
|
|
17
17
|
};
|
|
18
|
+
var isCoordsAllZero = (coords) => coords !== void 0 && coords.length > 0 && coords.every((group) => group.length > 0 && group.every(([x, y]) => x === 0 && y === 0));
|
|
18
19
|
//#endregion
|
|
19
20
|
exports.checkPowSignature = checkPowSignature;
|
|
21
|
+
exports.isCoordsAllZero = isCoordsAllZero;
|
|
20
22
|
exports.validateSolution = validateSolution;
|
|
@@ -15,12 +15,12 @@ var createPuzzleBackgroundBuffer = (options = {}) => {
|
|
|
15
15
|
timer.unref?.();
|
|
16
16
|
return {
|
|
17
17
|
take() {
|
|
18
|
-
const
|
|
19
|
-
if (!
|
|
18
|
+
const background = ready.pop();
|
|
19
|
+
if (!background) {
|
|
20
20
|
starved++;
|
|
21
21
|
return require_nativeBackground.createBackgroundNative(geometry);
|
|
22
22
|
}
|
|
23
|
-
return
|
|
23
|
+
return background;
|
|
24
24
|
},
|
|
25
25
|
depth: () => ready.length,
|
|
26
26
|
starvations: () => starved,
|
|
@@ -15,15 +15,22 @@ var nativePuzzle = (() => {
|
|
|
15
15
|
* Byte-identical to `createBackground` from @prosopo/puzzle-assets given the
|
|
16
16
|
* same seed — the JS remains the reference implementation and the contract
|
|
17
17
|
* the differential test pins. Single-use is unchanged and still the caller's
|
|
18
|
-
* responsibility
|
|
19
|
-
*
|
|
18
|
+
* responsibility.
|
|
19
|
+
*
|
|
20
|
+
* The seed is returned so the challenge record can keep it and the portal can
|
|
21
|
+
* regenerate this background later. See the secrecy note in prng.ts for where
|
|
22
|
+
* it may and may not go.
|
|
20
23
|
*/
|
|
21
24
|
var createBackgroundNative = (geometry = _prosopo_puzzle_assets.DEFAULT_GEOMETRY) => {
|
|
22
25
|
const { width, height } = geometry;
|
|
26
|
+
const seed = (0, _prosopo_puzzle_assets.createSeed)();
|
|
23
27
|
return {
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
28
|
+
image: {
|
|
29
|
+
data: require_metrics.measureSync("puzzle_background", () => nativePuzzle.generateBackground(seed, width, height)),
|
|
30
|
+
width,
|
|
31
|
+
height
|
|
32
|
+
},
|
|
33
|
+
seed
|
|
27
34
|
};
|
|
28
35
|
};
|
|
29
36
|
//#endregion
|
|
@@ -79,15 +79,16 @@ var isPuzzleRenderAvailable = () => {
|
|
|
79
79
|
};
|
|
80
80
|
var renderPuzzleImages = async (placement, settings = _prosopo_puzzle_assets.DEFAULT_RENDER_SETTINGS, pieceSize) => {
|
|
81
81
|
const background = (require_backgroundBuffer.getPuzzleBackgroundBuffer() ?? require_backgroundBuffer.initPuzzleBackgroundBuffer()).take();
|
|
82
|
-
|
|
83
|
-
const rendered = await require_metrics.measureSync("puzzle_render", () => (0, _prosopo_puzzle_assets.renderPuzzle)(background, placement, pieceSize !== void 0 ? {
|
|
82
|
+
const rendered = await require_metrics.measureSync("puzzle_render", () => (0, _prosopo_puzzle_assets.renderPuzzle)(background.image, placement, pieceSize !== void 0 ? {
|
|
84
83
|
..._prosopo_puzzle_assets.DEFAULT_GEOMETRY,
|
|
85
84
|
pieceSize
|
|
86
85
|
} : _prosopo_puzzle_assets.DEFAULT_GEOMETRY, settings));
|
|
87
86
|
return {
|
|
88
87
|
background: (0, _prosopo_puzzle_assets.toDataUri)(rendered.background),
|
|
89
88
|
piece: (0, _prosopo_puzzle_assets.toDataUri)(rendered.piece),
|
|
90
|
-
pieceSize: rendered.pieceSize
|
|
89
|
+
pieceSize: rendered.pieceSize,
|
|
90
|
+
backgroundSeed: background.seed.toString("hex"),
|
|
91
|
+
renderSeed: rendered.seed.toString("hex")
|
|
91
92
|
};
|
|
92
93
|
};
|
|
93
94
|
//#endregion
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const require_usageCounters = require("../../util/usageCounters.cjs");
|
|
2
2
|
const require_decisionMachineRunner = require("../decisionMachine/decisionMachineRunner.cjs");
|
|
3
|
+
const require_rawTlsSignalsMiddleware = require("../../api/rawTlsSignalsMiddleware.cjs");
|
|
3
4
|
const require_clientMetaData = require("../../utils/clientMetaData.cjs");
|
|
4
5
|
const require_compositeIpAddress = require("../../compositeIpAddress.cjs");
|
|
5
6
|
const require_enrichDnsEvent = require("../dnsEvent/enrichDnsEvent.cjs");
|
|
@@ -470,15 +471,7 @@ var PuzzleCaptchaManager = class extends require_captchaManager.CaptchaManager {
|
|
|
470
471
|
iframeUrl: sessionRecord?.iframeUrl,
|
|
471
472
|
coords: challengeRecord.coords,
|
|
472
473
|
puzzleEvents: challengeRecord.puzzleEvents,
|
|
473
|
-
|
|
474
|
-
synackNs: sessionRecord?.synackNs,
|
|
475
|
-
ackNs: sessionRecord?.ackNs,
|
|
476
|
-
observedTtl: sessionRecord?.observedTtl,
|
|
477
|
-
tcpMss: sessionRecord?.tcpMss,
|
|
478
|
-
tcpWscale: sessionRecord?.tcpWscale,
|
|
479
|
-
tcpOptsFlags: sessionRecord?.tcpOptsFlags,
|
|
480
|
-
tcpOptsOrder: sessionRecord?.tcpOptsOrder,
|
|
481
|
-
tcpWindow: sessionRecord?.tcpWindow,
|
|
474
|
+
...require_rawTlsSignalsMiddleware.rawTlsSignalsFromRecord(sessionRecord),
|
|
482
475
|
trafficPolicies: require_devicePlatform.deriveTrafficPolicies(trafficFilter)
|
|
483
476
|
};
|
|
484
477
|
const decision = await this.decisionMachineRunner.decide(decisionInput, logger);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"compositeIpAddress.d.ts","sourceRoot":"","sources":["../src/compositeIpAddress.ts"],"names":[],"mappings":"AAcA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAChD,OAAO,EAAE,KAAK,kBAAkB,EAAiB,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"compositeIpAddress.d.ts","sourceRoot":"","sources":["../src/compositeIpAddress.ts"],"names":[],"mappings":"AAcA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAChD,OAAO,EAAE,KAAK,kBAAkB,EAAiB,MAAM,gBAAgB,CAAC;AAaxE,eAAO,MAAM,qBAAqB,OAC7B,MAAM,GAAG,SAAS,KACpB,kBAaF,CAAC;AAuBF,eAAO,MAAM,yBAAyB,uBACjB,kBAAkB,KACpC,SAaF,CAAC;AAgDF,eAAO,MAAM,cAAc,MACvB,kBAAkB,KAClB,kBAAkB,KACnB,OAoBF,CAAC"}
|