@blamejs/blamejs-shop 0.5.19 → 0.5.21
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/CHANGELOG.md +4 -0
- package/README.md +1 -0
- package/SECURITY.md +17 -0
- package/lib/addresses.js +2 -2
- package/lib/admin.js +49 -45
- package/lib/affiliates.js +7 -23
- package/lib/announcement-bar.js +5 -22
- package/lib/api-keys.js +4 -13
- package/lib/asset-manifest.json +1 -1
- package/lib/banner-ab-tests.js +5 -9
- package/lib/blog-articles.js +8 -26
- package/lib/captcha-gate.js +7 -17
- package/lib/carrier-accounts.js +3 -10
- package/lib/catalog-drafts.js +5 -12
- package/lib/category-navigation.js +4 -20
- package/lib/cms-blocks.js +4 -7
- package/lib/compliance-export.js +4 -11
- package/lib/consent-ledger.js +2 -4
- package/lib/cost-layers.js +56 -21
- package/lib/customer-import.js +2 -2
- package/lib/customer-notes.js +7 -23
- package/lib/customer-roles.js +3 -5
- package/lib/customer-segments.js +17 -14
- package/lib/customer-surveys.js +7 -14
- package/lib/customers.js +2 -4
- package/lib/dispute-resolution.js +5 -13
- package/lib/dropship-forwarding.js +3 -5
- package/lib/dunning.js +2 -7
- package/lib/email-ab-tests.js +4 -8
- package/lib/email-campaigns.js +25 -14
- package/lib/email-warmup.js +2 -7
- package/lib/experiments.js +6 -10
- package/lib/externaldb-d1.js +78 -44
- package/lib/geolocation.js +18 -28
- package/lib/gift-options.js +5 -23
- package/lib/knowledge-base.js +7 -22
- package/lib/line-gift-wrap.js +3 -17
- package/lib/live-chat.js +5 -18
- package/lib/metered-usage.js +3 -8
- package/lib/notifications.js +3 -7
- package/lib/operator-accounts.js +3 -5
- package/lib/operator-approvals.js +6 -8
- package/lib/operator-audit-log.js +2 -7
- package/lib/operator-help-center.js +5 -21
- package/lib/operator-inbox.js +4 -11
- package/lib/operator-roles.js +5 -7
- package/lib/order-escalation.js +2 -2
- package/lib/order-export.js +24 -20
- package/lib/order-notes.js +4 -14
- package/lib/order-ratings.js +4 -10
- package/lib/payment-methods.js +5 -13
- package/lib/payment-retries.js +2 -7
- package/lib/payment.js +103 -58
- package/lib/pixel-events.js +8 -23
- package/lib/plan-changes.js +2 -7
- package/lib/product-qa.js +4 -8
- package/lib/promo-banners.js +7 -15
- package/lib/purchase-orders.js +3 -6
- package/lib/push-notifications.js +7 -32
- package/lib/pwa-manifest.js +6 -11
- package/lib/quotes.js +5 -9
- package/lib/referrals.js +10 -6
- package/lib/reviews.js +4 -10
- package/lib/robots-config.js +6 -14
- package/lib/sales-tax-filings.js +2 -2
- package/lib/search-facets.js +5 -5
- package/lib/search-ranking.js +4 -7
- package/lib/search-synonyms.js +7 -21
- package/lib/security-middleware.js +125 -70
- package/lib/seller-signup.js +10 -26
- package/lib/sidebar-widgets.js +6 -15
- package/lib/site-redirects.js +49 -137
- package/lib/sitemap-generator.js +3 -7
- package/lib/sms-dispatcher.js +7 -23
- package/lib/stock-receipts.js +4 -10
- package/lib/storefront-dashboards.js +2 -10
- package/lib/storefront-forms.js +9 -22
- package/lib/storefront-pages.js +6 -20
- package/lib/storefront.js +21 -23
- package/lib/subscription-billing.js +3 -8
- package/lib/subscription-controls.js +2 -7
- package/lib/suggestion-box.js +9 -26
- package/lib/support-tickets.js +6 -24
- package/lib/tax-remittance.js +2 -2
- package/lib/tenants.js +2 -7
- package/lib/text-guard.js +137 -35
- package/lib/theme-assets.js +4 -16
- package/lib/translations.js +3 -6
- package/lib/trust-badges.js +4 -7
- package/lib/vendor/MANIFEST.json +107 -97
- package/lib/vendor/blamejs/CHANGELOG.md +180 -0
- package/lib/vendor/blamejs/NOTICE +14 -10
- package/lib/vendor/blamejs/README.md +17 -5
- package/lib/vendor/blamejs/index.js +2 -0
- package/lib/vendor/blamejs/lib/acme.js +9 -9
- package/lib/vendor/blamejs/lib/api-snapshot.js +35 -16
- package/lib/vendor/blamejs/lib/app-shutdown.js +1 -1
- package/lib/vendor/blamejs/lib/archive-adapters.js +1 -1
- package/lib/vendor/blamejs/lib/archive.js +13 -24
- package/lib/vendor/blamejs/lib/auth/access-lock.js +2 -1
- package/lib/vendor/blamejs/lib/auth/bot-challenge.js +3 -6
- package/lib/vendor/blamejs/lib/auth/ciba.js +32 -3
- package/lib/vendor/blamejs/lib/auth/oauth.js +65 -8
- package/lib/vendor/blamejs/lib/auth/password.js +1 -1
- package/lib/vendor/blamejs/lib/auth/saml.js +21 -3
- package/lib/vendor/blamejs/lib/auth-bot-challenge.js +3 -3
- package/lib/vendor/blamejs/lib/backup/index.js +5 -5
- package/lib/vendor/blamejs/lib/case-fold-classes.js +491 -0
- package/lib/vendor/blamejs/lib/codepoint-class.js +131 -0
- package/lib/vendor/blamejs/lib/constants.js +79 -0
- package/lib/vendor/blamejs/lib/db-declare-view.js +8 -2
- package/lib/vendor/blamejs/lib/error-page.js +20 -1
- package/lib/vendor/blamejs/lib/external-db.js +5 -1
- package/lib/vendor/blamejs/lib/flag-evaluation-context.js +24 -6
- package/lib/vendor/blamejs/lib/flag.js +28 -2
- package/lib/vendor/blamejs/lib/framework-schema.js +14 -3
- package/lib/vendor/blamejs/lib/guard-regex.js +2345 -89
- package/lib/vendor/blamejs/lib/http-client.js +217 -40
- package/lib/vendor/blamejs/lib/mail-bimi.js +1 -1
- package/lib/vendor/blamejs/lib/mail-crypto-pgp.js +3 -2
- package/lib/vendor/blamejs/lib/mail-dav.js +26 -26
- package/lib/vendor/blamejs/lib/mail-deploy.js +10 -10
- package/lib/vendor/blamejs/lib/mail-scan.js +3 -0
- package/lib/vendor/blamejs/lib/mail-store.js +7 -1
- package/lib/vendor/blamejs/lib/mail.js +5 -1
- package/lib/vendor/blamejs/lib/middleware/age-gate.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/api-encrypt.js +1 -1
- package/lib/vendor/blamejs/lib/middleware/assetlinks.js +2 -1
- package/lib/vendor/blamejs/lib/middleware/asyncapi-serve.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/bearer-auth.js +2 -1
- package/lib/vendor/blamejs/lib/middleware/compression.js +1 -1
- package/lib/vendor/blamejs/lib/middleware/cors.js +1 -1
- package/lib/vendor/blamejs/lib/middleware/csp-report.js +5 -5
- package/lib/vendor/blamejs/lib/middleware/csrf-protect.js +2 -1
- package/lib/vendor/blamejs/lib/middleware/daily-byte-quota.js +2 -2
- package/lib/vendor/blamejs/lib/middleware/deny-response.js +2 -1
- package/lib/vendor/blamejs/lib/middleware/dpop.js +2 -2
- package/lib/vendor/blamejs/lib/middleware/fetch-metadata.js +2 -1
- package/lib/vendor/blamejs/lib/middleware/flag-context.js +17 -0
- package/lib/vendor/blamejs/lib/middleware/idempotency-key.js +10 -8
- package/lib/vendor/blamejs/lib/middleware/openapi-serve.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/require-aal.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/require-auth.js +4 -3
- package/lib/vendor/blamejs/lib/middleware/require-bound-key.js +4 -3
- package/lib/vendor/blamejs/lib/middleware/require-content-type.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/require-methods.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/require-mtls.js +3 -2
- package/lib/vendor/blamejs/lib/middleware/security-txt.js +2 -1
- package/lib/vendor/blamejs/lib/middleware/web-app-manifest.js +2 -1
- package/lib/vendor/blamejs/lib/network-dns-resolver.js +1 -1
- package/lib/vendor/blamejs/lib/network-dns.js +3 -3
- package/lib/vendor/blamejs/lib/network-nts.js +35 -14
- package/lib/vendor/blamejs/lib/network-proxy.js +42 -4
- package/lib/vendor/blamejs/lib/network-smtp-policy.js +1 -1
- package/lib/vendor/blamejs/lib/network-tls.js +341 -11
- package/lib/vendor/blamejs/lib/nist-crosswalk.js +2 -2
- package/lib/vendor/blamejs/lib/ntp-check.js +30 -19
- package/lib/vendor/blamejs/lib/object-store/azure-blob.js +1 -1
- package/lib/vendor/blamejs/lib/object-store/gcs.js +1 -1
- package/lib/vendor/blamejs/lib/object-store/http-put.js +2 -1
- package/lib/vendor/blamejs/lib/object-store/sigv4-bucket-ops.js +5 -5
- package/lib/vendor/blamejs/lib/object-store/sigv4.js +2 -2
- package/lib/vendor/blamejs/lib/observability-otlp-exporter.js +4 -2
- package/lib/vendor/blamejs/lib/openapi.js +1 -1
- package/lib/vendor/blamejs/lib/pqc-agent.js +4 -7
- package/lib/vendor/blamejs/lib/problem-details.js +2 -1
- package/lib/vendor/blamejs/lib/redis-client.js +12 -1
- package/lib/vendor/blamejs/lib/regex-linear.js +1349 -0
- package/lib/vendor/blamejs/lib/render.js +531 -7
- package/lib/vendor/blamejs/lib/request-helpers.js +181 -5
- package/lib/vendor/blamejs/lib/router.js +37 -13
- package/lib/vendor/blamejs/lib/safe-async.js +142 -0
- package/lib/vendor/blamejs/lib/safe-icap.js +3 -0
- package/lib/vendor/blamejs/lib/safe-sql.js +15 -3
- package/lib/vendor/blamejs/lib/self-update.js +2 -2
- package/lib/vendor/blamejs/lib/testing.js +54 -7
- package/lib/vendor/blamejs/lib/validate-opts.js +56 -0
- package/lib/vendor/blamejs/lib/vendor/MANIFEST.json +62 -25
- package/lib/vendor/blamejs/lib/vendor/blamejs-pki.cjs +2004 -142
- package/lib/vendor/blamejs/lib/vendor/browser/noble-ciphers.mjs +727 -0
- package/lib/vendor/blamejs/lib/vendor/browser/noble-hashes.mjs +1070 -0
- package/lib/vendor/blamejs/lib/vendor/browser/noble-post-quantum.mjs +1090 -0
- package/lib/vendor/blamejs/lib/vendor/noble-post-quantum.cjs +510 -227
- package/lib/vendor/blamejs/lib/webhook-hmac.js +19 -2
- package/lib/vendor/blamejs/lib/webhook.js +1 -1
- package/lib/vendor/blamejs/lib/ws-client.js +24 -2
- package/lib/vendor/blamejs/package.json +1 -1
- package/lib/vendor/blamejs/sbom.cdx.json +6 -6
- package/lib/vendor-invoices.js +3 -6
- package/lib/vendors.js +5 -19
- package/lib/webhook-receiver.js +46 -83
- package/lib/webhook-subscriptions.js +3 -13
- package/lib/wishlist-sharing.js +5 -10
- package/package.json +1 -1
|
@@ -296,6 +296,9 @@ function create(opts) {
|
|
|
296
296
|
var threats = [];
|
|
297
297
|
if (parsed.threatName) threats.push(parsed.threatName);
|
|
298
298
|
resolve({
|
|
299
|
+
// ICAP's own codes (RFC 3507): 200 with the message returned, 204
|
|
300
|
+
// when it needed no change. They are not HTTP statuses, so they are
|
|
301
|
+
// not named as though they were.
|
|
299
302
|
verdict: parsed.threatFound ? "infected" : (parsed.statusCode === 200 || parsed.statusCode === 204 ? "clean" : "error"),
|
|
300
303
|
icapResponse: parsed,
|
|
301
304
|
threats: threats,
|
|
@@ -158,7 +158,13 @@ function create(opts) {
|
|
|
158
158
|
// expressions (the decrement update + the accumulate-on-conflict upsert),
|
|
159
159
|
// which a structured set()/value cell cannot express. Every other table
|
|
160
160
|
// identifier emits through the b.sql builders above with quoteName.
|
|
161
|
-
|
|
161
|
+
// The name is built from an operator `tablePrefix`, so it is quoted the way
|
|
162
|
+
// every other operator-supplied identifier is. It changes nothing today and
|
|
163
|
+
// is not meant to: `create()` refuses a reserved-word prefix outright, and
|
|
164
|
+
// the `_quota` suffix means this name could not be a bare keyword anyway.
|
|
165
|
+
// It is here so the rule reads the same at every call site rather than
|
|
166
|
+
// depending on a reader re-deriving those two facts.
|
|
167
|
+
var qQuota = safeSql.quoteIdentifier(quotaTable, "sqlite", { allowReserved: true });
|
|
162
168
|
|
|
163
169
|
var maxMessageBytes = opts.maxMessageBytes !== undefined ? opts.maxMessageBytes : DEFAULT_MAX_MESSAGE_BYTES;
|
|
164
170
|
var maxBodyBytes = opts.maxBodyBytes !== undefined ? opts.maxBodyBytes : DEFAULT_MAX_BODY_BYTES;
|
|
@@ -819,7 +819,11 @@ function _dotStuffForData(msg) {
|
|
|
819
819
|
function _smtpTlsOpts(cfg, extra) {
|
|
820
820
|
var out = Object.assign(networkTls().outboundPosture(), cfg.tlsOpts);
|
|
821
821
|
if (extra) Object.assign(out, extra);
|
|
822
|
-
|
|
822
|
+
// The posture advertises RFC 8879 certificate compression, which is a TLS
|
|
823
|
+
// 1.3 extension. An SMTP peer that only speaks TLS 1.2 is common enough
|
|
824
|
+
// that operators cap this dial; Node refuses the whole options object
|
|
825
|
+
// rather than ignoring an extension it cannot use.
|
|
826
|
+
return networkTls()._stripUnreachableCertCompression(out, cfg.tlsOpts);
|
|
823
827
|
}
|
|
824
828
|
|
|
825
829
|
function smtpTransport(opts) {
|
|
@@ -37,6 +37,7 @@
|
|
|
37
37
|
* router.use(gate);
|
|
38
38
|
*/
|
|
39
39
|
|
|
40
|
+
var C = require("../constants");
|
|
40
41
|
var defineClass = require("../framework-error").defineClass;
|
|
41
42
|
var lazyRequire = require("../lazy-require");
|
|
42
43
|
var validateOpts = require("../validate-opts");
|
|
@@ -165,8 +166,8 @@ function create(opts) {
|
|
|
165
166
|
denyResponse(req, res, {
|
|
166
167
|
onDeny: onDeny,
|
|
167
168
|
problem: problemMode,
|
|
168
|
-
status:
|
|
169
|
-
info: { status:
|
|
169
|
+
status: C.HTTP.STATUS.UNAVAILABLE_FOR_LEGAL_REASONS, // HTTP 451 Unavailable For Legal Reasons
|
|
170
|
+
info: { status: C.HTTP.STATUS.UNAVAILABLE_FOR_LEGAL_REASONS, reason: "parental-consent-required",
|
|
170
171
|
age: age, classification: classification, requireAge: requireAge },
|
|
171
172
|
problemCode: "parental-consent-required",
|
|
172
173
|
problemTitle: "Unavailable For Legal Reasons",
|
|
@@ -376,7 +376,7 @@ function create(opts) {
|
|
|
376
376
|
}
|
|
377
377
|
numericBounds.requirePositiveFiniteInt(sessionMaxResponses,
|
|
378
378
|
"apiEncrypt: sessionMaxResponses", ApiEncryptError, "BAD_OPT", null,
|
|
379
|
-
{ permanent: true, statusCode:
|
|
379
|
+
{ permanent: true, statusCode: C.HTTP.STATUS.INTERNAL_SERVER_ERROR });
|
|
380
380
|
// sessionStore — duck-typed handle exposing { get, set, delete }. The
|
|
381
381
|
// helper optionalObjectWithMethod only checks one method; here we need
|
|
382
382
|
// three. Inline shape kept; not a generic enough pattern to warrant a
|
|
@@ -27,6 +27,7 @@
|
|
|
27
27
|
* multiple statement entries.
|
|
28
28
|
*/
|
|
29
29
|
|
|
30
|
+
var C = require("../constants");
|
|
30
31
|
var lazyRequire = require("../lazy-require");
|
|
31
32
|
var safeJson = require("../safe-json");
|
|
32
33
|
var validateOpts = require("../validate-opts");
|
|
@@ -114,7 +115,7 @@ function create(opts) {
|
|
|
114
115
|
denyResponse.methodNotAllowed(res, "GET, HEAD");
|
|
115
116
|
return;
|
|
116
117
|
}
|
|
117
|
-
res.writeHead(
|
|
118
|
+
res.writeHead(C.HTTP.STATUS.OK, { // HTTP 200 status
|
|
118
119
|
"Content-Type": "application/json; charset=utf-8",
|
|
119
120
|
"Content-Length": bodyBuf.length,
|
|
120
121
|
"Cache-Control": "public, max-age=86400",
|
|
@@ -21,6 +21,7 @@
|
|
|
21
21
|
* paths / methods.
|
|
22
22
|
*/
|
|
23
23
|
|
|
24
|
+
var C = require("../constants");
|
|
24
25
|
var nodeCrypto = require("node:crypto");
|
|
25
26
|
var validateOpts = require("../validate-opts");
|
|
26
27
|
var lazyRequire = require("../lazy-require");
|
|
@@ -157,7 +158,7 @@ function create(opts) {
|
|
|
157
158
|
function _writeBody(req, res, body, etag, contentType) {
|
|
158
159
|
var requestEtag = (req.headers && req.headers["if-none-match"]) || null;
|
|
159
160
|
if (requestEtag && requestEtag === etag) {
|
|
160
|
-
res.writeHead(
|
|
161
|
+
res.writeHead(C.HTTP.STATUS.NOT_MODIFIED, { "ETag": etag, "Cache-Control": cacheControl }); // HTTP 304
|
|
161
162
|
res.end();
|
|
162
163
|
return;
|
|
163
164
|
}
|
|
@@ -174,7 +175,7 @@ function create(opts) {
|
|
|
174
175
|
// origin to another's request (Fetch Standard §3.2.1).
|
|
175
176
|
if (allowOriginHeader !== "*") headers["Vary"] = "Origin";
|
|
176
177
|
}
|
|
177
|
-
res.writeHead(
|
|
178
|
+
res.writeHead(C.HTTP.STATUS.OK, headers); // HTTP 200
|
|
178
179
|
// HEAD carries the GET headers (incl. Content-Length) with no body
|
|
179
180
|
// (RFC 9110 §9.3.2).
|
|
180
181
|
if ((req.method || "GET").toUpperCase() === "HEAD") { res.end(); return; }
|
|
@@ -36,6 +36,7 @@
|
|
|
36
36
|
* route).
|
|
37
37
|
*/
|
|
38
38
|
|
|
39
|
+
var C = require("../constants");
|
|
39
40
|
var lazyRequire = require("../lazy-require");
|
|
40
41
|
var requestHelpers = require("../request-helpers");
|
|
41
42
|
var validateOpts = require("../validate-opts");
|
|
@@ -56,7 +57,7 @@ function _refuse(req, res, status, challenge, bodyObj, reason, problemExt, onDen
|
|
|
56
57
|
status: status,
|
|
57
58
|
info: Object.assign({ status: status, reason: reason }, problemExt || {}),
|
|
58
59
|
problemCode: "bearer-" + reason,
|
|
59
|
-
problemTitle: status ===
|
|
60
|
+
problemTitle: status === C.HTTP.STATUS.FORBIDDEN ? "Forbidden" : "Unauthorized",
|
|
60
61
|
problemDetail: typeof bodyObj.error === "string" ? bodyObj.error : ("bearer authentication failed: " + reason),
|
|
61
62
|
problemExt: problemExt || null,
|
|
62
63
|
headers: { "WWW-Authenticate": challenge },
|
|
@@ -334,7 +334,7 @@ function create(opts) {
|
|
|
334
334
|
// UNtransformed (RFC 7233 §4.1) — compressing it drops Content-Length but
|
|
335
335
|
// leaves Content-Range advertising an uncompressed byte interval over a
|
|
336
336
|
// now-compressed body, corrupting range-assembling clients.
|
|
337
|
-
if (statusCode ===
|
|
337
|
+
if (statusCode === C.HTTP.STATUS.PARTIAL_CONTENT) { compress = false; return; }
|
|
338
338
|
var crRange = (headersObj && headersObj["content-range"]) ||
|
|
339
339
|
(originalGetHeader && originalGetHeader("Content-Range"));
|
|
340
340
|
if (crRange) { compress = false; return; }
|
|
@@ -296,7 +296,7 @@ function create(opts) {
|
|
|
296
296
|
onDeny: onDeny,
|
|
297
297
|
problem: problemMode,
|
|
298
298
|
status: requestHelpers.HTTP_STATUS.FORBIDDEN,
|
|
299
|
-
info: Object.assign({ status:
|
|
299
|
+
info: Object.assign({ status: C.HTTP.STATUS.FORBIDDEN, reason: reason }, ext || {}),
|
|
300
300
|
problemCode: "cors-refused",
|
|
301
301
|
problemTitle: "Forbidden",
|
|
302
302
|
problemDetail: body,
|
|
@@ -175,7 +175,7 @@ function create(opts) {
|
|
|
175
175
|
|
|
176
176
|
return async function cspReport(req, res, _next) {
|
|
177
177
|
if (req.method !== "POST") {
|
|
178
|
-
res.writeHead(
|
|
178
|
+
res.writeHead(C.HTTP.STATUS.METHOD_NOT_ALLOWED, { "Allow": "POST" }); // HTTP 405 status
|
|
179
179
|
res.end();
|
|
180
180
|
_emitReject(req, res, 405, "method-not-allowed");
|
|
181
181
|
return;
|
|
@@ -184,7 +184,7 @@ function create(opts) {
|
|
|
184
184
|
try {
|
|
185
185
|
body = await safeBuffer.collectStream(req, { maxBytes: maxBytes });
|
|
186
186
|
} catch (_e) {
|
|
187
|
-
res.writeHead(
|
|
187
|
+
res.writeHead(C.HTTP.STATUS.CONTENT_TOO_LARGE); // HTTP 413 status
|
|
188
188
|
res.end();
|
|
189
189
|
_emitReject(req, res, 413, "payload-too-large");
|
|
190
190
|
return;
|
|
@@ -192,7 +192,7 @@ function create(opts) {
|
|
|
192
192
|
var parsed;
|
|
193
193
|
try { parsed = safeJson.parse(body.toString("utf8")); }
|
|
194
194
|
catch (_e) {
|
|
195
|
-
res.writeHead(
|
|
195
|
+
res.writeHead(C.HTTP.STATUS.BAD_REQUEST); // HTTP 400 status
|
|
196
196
|
res.end();
|
|
197
197
|
_emitReject(req, res, 400, "invalid-json");
|
|
198
198
|
return;
|
|
@@ -204,7 +204,7 @@ function create(opts) {
|
|
|
204
204
|
// unauthenticated caller can force. A throwing/absent audit or hook is
|
|
205
205
|
// unaffected — nothing is processed on this path.
|
|
206
206
|
if (reports.length > maxReports) {
|
|
207
|
-
res.writeHead(
|
|
207
|
+
res.writeHead(C.HTTP.STATUS.CONTENT_TOO_LARGE); // HTTP 413 status
|
|
208
208
|
res.end();
|
|
209
209
|
_emitReject(req, res, 413, "too-many-reports");
|
|
210
210
|
return;
|
|
@@ -225,7 +225,7 @@ function create(opts) {
|
|
|
225
225
|
try { onReport(normalized); } catch (_e) { /* hook best-effort */ }
|
|
226
226
|
}
|
|
227
227
|
}
|
|
228
|
-
res.writeHead(
|
|
228
|
+
res.writeHead(C.HTTP.STATUS.NO_CONTENT); // HTTP 204 status
|
|
229
229
|
res.end();
|
|
230
230
|
};
|
|
231
231
|
}
|
|
@@ -68,6 +68,7 @@
|
|
|
68
68
|
* audit: true
|
|
69
69
|
* }
|
|
70
70
|
*/
|
|
71
|
+
var C = require("../constants");
|
|
71
72
|
var lazyRequire = require("../lazy-require");
|
|
72
73
|
var pick = require("../pick");
|
|
73
74
|
var forms = require("../forms");
|
|
@@ -235,7 +236,7 @@ function _writeReject(req, res, message, reason, onDeny, problemMode) {
|
|
|
235
236
|
onDeny: onDeny,
|
|
236
237
|
problem: problemMode,
|
|
237
238
|
status: requestHelpers.HTTP_STATUS.FORBIDDEN,
|
|
238
|
-
info: { status:
|
|
239
|
+
info: { status: C.HTTP.STATUS.FORBIDDEN, reason: reason },
|
|
239
240
|
problemCode: "csrf-refused",
|
|
240
241
|
problemTitle: "Forbidden",
|
|
241
242
|
problemDetail: message,
|
|
@@ -158,7 +158,7 @@ function create(opts) {
|
|
|
158
158
|
_emitMetric("refused", 1, { reason: "quota-exceeded" });
|
|
159
159
|
_emitAudit("refused", "denied", { key: key, total: total, quota: bytesPerDay });
|
|
160
160
|
var info = {
|
|
161
|
-
status:
|
|
161
|
+
status: C.HTTP.STATUS.TOO_MANY_REQUESTS,
|
|
162
162
|
reason: "quota-exceeded",
|
|
163
163
|
quota: bytesPerDay,
|
|
164
164
|
total: total,
|
|
@@ -167,7 +167,7 @@ function create(opts) {
|
|
|
167
167
|
denyResponse(req, res, {
|
|
168
168
|
onDeny: onDeny,
|
|
169
169
|
problem: problemMode,
|
|
170
|
-
status:
|
|
170
|
+
status: C.HTTP.STATUS.TOO_MANY_REQUESTS,
|
|
171
171
|
info: info,
|
|
172
172
|
problemCode: "daily-byte-quota-exceeded",
|
|
173
173
|
problemTitle: "Too Many Requests",
|
|
@@ -35,6 +35,7 @@
|
|
|
35
35
|
* middleware that composes it.
|
|
36
36
|
*/
|
|
37
37
|
|
|
38
|
+
var C = require("../constants");
|
|
38
39
|
var problemDetails = require("../problem-details");
|
|
39
40
|
var validateOpts = require("../validate-opts");
|
|
40
41
|
|
|
@@ -158,7 +159,7 @@ function denyResponse(req, res, ctx) {
|
|
|
158
159
|
// "GET, HEAD").
|
|
159
160
|
function methodNotAllowed(res, allow) {
|
|
160
161
|
var bodyMsg = "Method Not Allowed";
|
|
161
|
-
res.writeHead(
|
|
162
|
+
res.writeHead(C.HTTP.STATUS.METHOD_NOT_ALLOWED, { // HTTP 405 status
|
|
162
163
|
"Allow": allow,
|
|
163
164
|
"Content-Type": "text/plain; charset=utf-8",
|
|
164
165
|
"Content-Length": Buffer.byteLength(bodyMsg),
|
|
@@ -64,8 +64,8 @@ function _writeUnauthorized(req, res, errorCode, description, freshNonce, onDeny
|
|
|
64
64
|
denyResponse(req, res, {
|
|
65
65
|
onDeny: onDeny,
|
|
66
66
|
problem: problemMode,
|
|
67
|
-
status:
|
|
68
|
-
info: { status:
|
|
67
|
+
status: C.HTTP.STATUS.UNAUTHORIZED, // HTTP 401 status
|
|
68
|
+
info: { status: C.HTTP.STATUS.UNAUTHORIZED, reason: errorCode, error_description: description },
|
|
69
69
|
problemCode: "dpop-" + errorCode.replace(/_/g, "-"),
|
|
70
70
|
problemTitle: "Unauthorized",
|
|
71
71
|
problemDetail: description,
|
|
@@ -35,6 +35,7 @@
|
|
|
35
35
|
* own auth threat model.
|
|
36
36
|
*/
|
|
37
37
|
|
|
38
|
+
var C = require("../constants");
|
|
38
39
|
var requestHelpers = require("../request-helpers");
|
|
39
40
|
var validateOpts = require("../validate-opts");
|
|
40
41
|
var lazyRequire = require("../lazy-require");
|
|
@@ -100,7 +101,7 @@ function _writeReject(req, res, message, reason, onDeny, problemMode) {
|
|
|
100
101
|
onDeny: onDeny,
|
|
101
102
|
problem: problemMode,
|
|
102
103
|
status: requestHelpers.HTTP_STATUS.FORBIDDEN,
|
|
103
|
-
info: { status:
|
|
104
|
+
info: { status: C.HTTP.STATUS.FORBIDDEN, reason: reason },
|
|
104
105
|
problemCode: "fetch-metadata-refused",
|
|
105
106
|
problemTitle: "Forbidden",
|
|
106
107
|
problemDetail: message,
|
|
@@ -31,6 +31,7 @@ var { defineClass } = require("../framework-error");
|
|
|
31
31
|
var FlagError = defineClass("FlagError", { alwaysPermanent: true });
|
|
32
32
|
|
|
33
33
|
var contextMod = lazyRequire(function () { return require("../flag-evaluation-context"); });
|
|
34
|
+
var requestHelpers = lazyRequire(function () { return require("../request-helpers"); });
|
|
34
35
|
|
|
35
36
|
/**
|
|
36
37
|
* @primitive b.middleware.flagContext
|
|
@@ -70,6 +71,7 @@ function create(opts) {
|
|
|
70
71
|
opts = opts || {};
|
|
71
72
|
validateOpts(opts, [
|
|
72
73
|
"userKey", "userKeyHeader", "extractAttributes", "tenantKeyHeader",
|
|
74
|
+
"trustedProxies", "forwardedHeaders", "clientIpResolver",
|
|
73
75
|
], "middleware.flagContext");
|
|
74
76
|
if (opts.extractAttributes != null && typeof opts.extractAttributes !== "function") {
|
|
75
77
|
throw new FlagError("flag/bad-opt",
|
|
@@ -84,6 +86,14 @@ function create(opts) {
|
|
|
84
86
|
var explicitUserKey = (typeof opts.userKey === "string" && opts.userKey.length > 0)
|
|
85
87
|
? opts.userKey
|
|
86
88
|
: null;
|
|
89
|
+
var declaredTrust = opts.trustedProxies !== undefined ||
|
|
90
|
+
opts.forwardedHeaders !== undefined ||
|
|
91
|
+
opts.clientIpResolver !== undefined;
|
|
92
|
+
var trustedIp = declaredTrust ? requestHelpers().trustedClientIp({
|
|
93
|
+
trustedProxies: opts.trustedProxies,
|
|
94
|
+
forwardedHeaders: opts.forwardedHeaders,
|
|
95
|
+
clientIpResolver: opts.clientIpResolver,
|
|
96
|
+
}) : null;
|
|
87
97
|
|
|
88
98
|
return function flagContextMiddleware(req, res, next) {
|
|
89
99
|
var headers = req.headers || {};
|
|
@@ -104,6 +114,13 @@ function create(opts) {
|
|
|
104
114
|
augment.tenantId = headers[tenantKeyHeader];
|
|
105
115
|
}
|
|
106
116
|
fromReqOpts.extra = augment;
|
|
117
|
+
// A request with no identified user is keyed by its client address, and
|
|
118
|
+
// that key picks the rollout bucket. Behind a reverse proxy the operator
|
|
119
|
+
// has to say which proxies and which header, or every anonymous caller
|
|
120
|
+
// arrives as the proxy and shares one bucket. Same options as
|
|
121
|
+
// flag.middleware; the resolver is built once, so a malformed CIDR fails
|
|
122
|
+
// at boot rather than on the first request.
|
|
123
|
+
if (trustedIp) fromReqOpts.clientIpResolver = trustedIp.resolve;
|
|
107
124
|
req.flagCtx = contextMod().fromRequest(req, fromReqOpts);
|
|
108
125
|
return next();
|
|
109
126
|
};
|
|
@@ -734,7 +734,7 @@ function create(opts) {
|
|
|
734
734
|
var missing = problemDetails().create({
|
|
735
735
|
type: problemDetails().getBase() + "/idempotency/missing-key",
|
|
736
736
|
title: "Idempotency-Key header required",
|
|
737
|
-
status:
|
|
737
|
+
status: C.HTTP.STATUS.BAD_REQUEST, // HTTP status 400 Bad Request
|
|
738
738
|
detail: "This endpoint requires an Idempotency-Key header (draft-ietf-httpapi-idempotency-key).",
|
|
739
739
|
});
|
|
740
740
|
_emitAudit("idempotency.missing_key", { method: method, path: req.url }, "denied");
|
|
@@ -745,7 +745,7 @@ function create(opts) {
|
|
|
745
745
|
var bad = problemDetails().create({
|
|
746
746
|
type: problemDetails().getBase() + "/idempotency/bad-key",
|
|
747
747
|
title: "Idempotency-Key malformed",
|
|
748
|
-
status:
|
|
748
|
+
status: C.HTTP.STATUS.BAD_REQUEST, // HTTP status 400
|
|
749
749
|
detail: "Idempotency-Key must be ASCII printable, length 1.." + KEY_MAX_LEN + " (draft §2).",
|
|
750
750
|
});
|
|
751
751
|
_emitAudit("idempotency.bad_key", { method: method, keyLen: key.length }, "denied");
|
|
@@ -816,7 +816,7 @@ function create(opts) {
|
|
|
816
816
|
var missingBody = problemDetails().create({
|
|
817
817
|
type: problemDetails().getBase() + "/idempotency/missing-body-fingerprint",
|
|
818
818
|
title: "Idempotency body fingerprint unavailable",
|
|
819
|
-
status:
|
|
819
|
+
status: C.HTTP.STATUS.BAD_REQUEST, // HTTP status 400 Bad Request
|
|
820
820
|
detail: "The idempotency middleware could not derive a body fingerprint for this " +
|
|
821
821
|
"request. Mount body-parser BEFORE the idempotency middleware, OR provide an " +
|
|
822
822
|
"opts.bodyFingerprint(req) hook. To restore the pre-0.9.58 method+path-only " +
|
|
@@ -844,7 +844,7 @@ function create(opts) {
|
|
|
844
844
|
var mismatch = problemDetails().create({
|
|
845
845
|
type: problemDetails().getBase() + "/idempotency/key-reuse-mismatch",
|
|
846
846
|
title: "Idempotency-Key reused with different request",
|
|
847
|
-
status:
|
|
847
|
+
status: C.HTTP.STATUS.UNPROCESSABLE_CONTENT, // HTTP status 422 Unprocessable Content (RFC 9110)
|
|
848
848
|
detail: "The Idempotency-Key matches a prior request but the request body/method/path differs (draft §4.3).",
|
|
849
849
|
});
|
|
850
850
|
_emitAudit("idempotency.key_reuse_mismatch",
|
|
@@ -900,10 +900,12 @@ function create(opts) {
|
|
|
900
900
|
if (!captured) {
|
|
901
901
|
captured = true;
|
|
902
902
|
_pushChunk(chunk, encoding);
|
|
903
|
-
var status = res.statusCode ||
|
|
904
|
-
// Only persist
|
|
905
|
-
//
|
|
906
|
-
|
|
903
|
+
var status = res.statusCode || C.HTTP.STATUS.OK;
|
|
904
|
+
// Only persist what the SERVER settled: a success, a redirect, or the
|
|
905
|
+
// caller's own mistake. A 5xx is transient infrastructure failure that
|
|
906
|
+
// should be retried fresh rather than replayed from a cache.
|
|
907
|
+
if (!oversized &&
|
|
908
|
+
(C.HTTP.success(status) || C.HTTP.redirect(status) || C.HTTP.clientError(status))) {
|
|
907
909
|
var headerMap = {};
|
|
908
910
|
try {
|
|
909
911
|
var allHeaders = typeof res.getHeaders === "function" ? res.getHeaders() : {};
|
|
@@ -29,6 +29,7 @@
|
|
|
29
29
|
* origin is validated and echoed verbatim with `Vary: Origin`.
|
|
30
30
|
*/
|
|
31
31
|
|
|
32
|
+
var C = require("../constants");
|
|
32
33
|
var nodeCrypto = require("node:crypto");
|
|
33
34
|
var validateOpts = require("../validate-opts");
|
|
34
35
|
var lazyRequire = require("../lazy-require");
|
|
@@ -163,7 +164,7 @@ function create(opts) {
|
|
|
163
164
|
function _writeBody(req, res, body, etag, contentType) {
|
|
164
165
|
var requestEtag = (req.headers && req.headers["if-none-match"]) || null;
|
|
165
166
|
if (requestEtag && requestEtag === etag) {
|
|
166
|
-
res.writeHead(
|
|
167
|
+
res.writeHead(C.HTTP.STATUS.NOT_MODIFIED, { "ETag": etag, "Cache-Control": cacheControl }); // HTTP 304
|
|
167
168
|
res.end();
|
|
168
169
|
return;
|
|
169
170
|
}
|
|
@@ -180,7 +181,7 @@ function create(opts) {
|
|
|
180
181
|
// origin to another's request (Fetch Standard §3.2.1).
|
|
181
182
|
if (allowOriginHeader !== "*") headers["Vary"] = "Origin";
|
|
182
183
|
}
|
|
183
|
-
res.writeHead(
|
|
184
|
+
res.writeHead(C.HTTP.STATUS.OK, headers); // HTTP 200
|
|
184
185
|
// HEAD carries the GET headers (incl. Content-Length) with no body
|
|
185
186
|
// (RFC 9110 §9.3.2).
|
|
186
187
|
if ((req.method || "GET").toUpperCase() === "HEAD") { res.end(); return; }
|
|
@@ -20,6 +20,7 @@
|
|
|
20
20
|
* auth.aal.denied — request below the required minimum
|
|
21
21
|
*/
|
|
22
22
|
|
|
23
|
+
var C = require("../constants");
|
|
23
24
|
var lazyRequire = require("../lazy-require");
|
|
24
25
|
var requestHelpers = require("../request-helpers");
|
|
25
26
|
var validateOpts = require("../validate-opts");
|
|
@@ -42,8 +43,8 @@ function _writeUnauthorized(req, res, requiredBand, actualBand, realm, onDeny, p
|
|
|
42
43
|
denyResponse(req, res, {
|
|
43
44
|
onDeny: onDeny,
|
|
44
45
|
problem: problemMode,
|
|
45
|
-
status:
|
|
46
|
-
info: { status:
|
|
46
|
+
status: C.HTTP.STATUS.UNAUTHORIZED, // HTTP 401 status
|
|
47
|
+
info: { status: C.HTTP.STATUS.UNAUTHORIZED, reason: "step_up_required",
|
|
47
48
|
required_aal: requiredBand, actual_aal: actualBand || null },
|
|
48
49
|
problemCode: "step-up-required",
|
|
49
50
|
problemTitle: "Step-Up Authentication Required",
|
|
@@ -38,6 +38,7 @@
|
|
|
38
38
|
* audit: true (emit auth.required.denied on reject)
|
|
39
39
|
* }
|
|
40
40
|
*/
|
|
41
|
+
var C = require("../constants");
|
|
41
42
|
var lazyRequire = require("../lazy-require");
|
|
42
43
|
var requestHelpers = require("../request-helpers");
|
|
43
44
|
var validateOpts = require("../validate-opts");
|
|
@@ -118,7 +119,7 @@ function create(opts) {
|
|
|
118
119
|
// before the default content-negotiation runs.
|
|
119
120
|
if (onDeny) {
|
|
120
121
|
try {
|
|
121
|
-
var returned = onDeny(req, res, { status:
|
|
122
|
+
var returned = onDeny(req, res, { status: C.HTTP.STATUS.UNAUTHORIZED, reason: "no-authenticated-user", redirectTo: redirectTo });
|
|
122
123
|
if (res.writableEnded) return returned;
|
|
123
124
|
} catch (_e) {
|
|
124
125
|
if (res.writableEnded) return;
|
|
@@ -138,7 +139,7 @@ function create(opts) {
|
|
|
138
139
|
if (!wantsJson && redirectTo) {
|
|
139
140
|
if (!res.writableEnded && typeof res.writeHead === "function") {
|
|
140
141
|
// 302 Found — RFC 7231 §6.4.3. Not in HTTP_STATUS table.
|
|
141
|
-
res.writeHead(
|
|
142
|
+
res.writeHead(C.HTTP.STATUS.FOUND, { "Location": redirectTo, "Cache-Control": "no-store" });
|
|
142
143
|
res.end();
|
|
143
144
|
}
|
|
144
145
|
return;
|
|
@@ -146,7 +147,7 @@ function create(opts) {
|
|
|
146
147
|
denyResponse(req, res, {
|
|
147
148
|
problem: problemMode,
|
|
148
149
|
status: requestHelpers.HTTP_STATUS.UNAUTHORIZED,
|
|
149
|
-
info: { status:
|
|
150
|
+
info: { status: C.HTTP.STATUS.UNAUTHORIZED, reason: "no-authenticated-user" },
|
|
150
151
|
problemCode: "authentication-required",
|
|
151
152
|
problemTitle: "Unauthorized",
|
|
152
153
|
problemDetail: msg,
|
|
@@ -50,6 +50,7 @@
|
|
|
50
50
|
* undefined → refused with reason "resolver-unavailable".
|
|
51
51
|
*/
|
|
52
52
|
|
|
53
|
+
var C = require("../constants");
|
|
53
54
|
var defineClass = require("../framework-error").defineClass;
|
|
54
55
|
var lazyRequire = require("../lazy-require");
|
|
55
56
|
var validateOpts = require("../validate-opts");
|
|
@@ -177,12 +178,12 @@ function create(opts) {
|
|
|
177
178
|
// are not authentication challenges, so they advertise the scheme
|
|
178
179
|
// without an (incorrect) auth-error code.
|
|
179
180
|
function _bearerChallenge(status, reason) {
|
|
180
|
-
if (status ===
|
|
181
|
+
if (status === C.HTTP.STATUS.UNAUTHORIZED) {
|
|
181
182
|
if (reason === "no-bearer-token") return 'Bearer realm="api"';
|
|
182
183
|
return 'Bearer realm="api", error="invalid_token"';
|
|
183
184
|
}
|
|
184
|
-
if (status ===
|
|
185
|
-
if (status ===
|
|
185
|
+
if (status === C.HTTP.STATUS.FORBIDDEN) return 'Bearer realm="api", error="insufficient_scope"';
|
|
186
|
+
if (status === C.HTTP.STATUS.BAD_REQUEST) return 'Bearer realm="api", error="invalid_request"'; // HTTP 400
|
|
186
187
|
return 'Bearer realm="api"';
|
|
187
188
|
}
|
|
188
189
|
|
|
@@ -19,6 +19,7 @@
|
|
|
19
19
|
* `methods` to override.
|
|
20
20
|
*/
|
|
21
21
|
|
|
22
|
+
var C = require("../constants");
|
|
22
23
|
var lazyRequire = require("../lazy-require");
|
|
23
24
|
var denyResponse = require("./deny-response").denyResponse;
|
|
24
25
|
var { defineClass } = require("../framework-error");
|
|
@@ -100,8 +101,8 @@ function create(allowed, opts) {
|
|
|
100
101
|
denyResponse(req, res, {
|
|
101
102
|
onDeny: onDeny,
|
|
102
103
|
problem: problemMode,
|
|
103
|
-
status:
|
|
104
|
-
info: { status:
|
|
104
|
+
status: C.HTTP.STATUS.UNSUPPORTED_MEDIA_TYPE,
|
|
105
|
+
info: { status: C.HTTP.STATUS.UNSUPPORTED_MEDIA_TYPE, reason: "unsupported-media-type",
|
|
105
106
|
contentType: bare || null, accepted: normalized },
|
|
106
107
|
problemCode: "unsupported-media-type",
|
|
107
108
|
problemTitle: "Unsupported Media Type",
|
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
* RFC 9110 §15.5.6.
|
|
18
18
|
*/
|
|
19
19
|
|
|
20
|
+
var C = require("../constants");
|
|
20
21
|
var lazyRequire = require("../lazy-require");
|
|
21
22
|
var denyResponse = require("./deny-response").denyResponse;
|
|
22
23
|
var { defineClass } = require("../framework-error");
|
|
@@ -84,8 +85,8 @@ function create(allowed, opts) {
|
|
|
84
85
|
denyResponse(req, res, {
|
|
85
86
|
onDeny: onDeny,
|
|
86
87
|
problem: problemMode,
|
|
87
|
-
status:
|
|
88
|
-
info: { status:
|
|
88
|
+
status: C.HTTP.STATUS.METHOD_NOT_ALLOWED,
|
|
89
|
+
info: { status: C.HTTP.STATUS.METHOD_NOT_ALLOWED, reason: "method-not-allowed", method: m, allowed: normalized },
|
|
89
90
|
problemCode: "method-not-allowed",
|
|
90
91
|
problemTitle: "Method Not Allowed",
|
|
91
92
|
problemDetail: "The " + m + " method is not allowed on this resource.",
|
|
@@ -47,6 +47,7 @@
|
|
|
47
47
|
* allow-list ALSO requires the fingerprint to match.
|
|
48
48
|
*/
|
|
49
49
|
|
|
50
|
+
var C = require("../constants");
|
|
50
51
|
var nodeCrypto = require("node:crypto");
|
|
51
52
|
var defineClass = require("../framework-error").defineClass;
|
|
52
53
|
var lazyRequire = require("../lazy-require");
|
|
@@ -164,8 +165,8 @@ function create(opts) {
|
|
|
164
165
|
denyResponse(req, res, {
|
|
165
166
|
onDeny: onDeny,
|
|
166
167
|
problem: problemMode,
|
|
167
|
-
status:
|
|
168
|
-
info: Object.assign({ status:
|
|
168
|
+
status: C.HTTP.STATUS.UNAUTHORIZED,
|
|
169
|
+
info: Object.assign({ status: C.HTTP.STATUS.UNAUTHORIZED, reason: reason }, metadata || {}),
|
|
169
170
|
problemCode: "client-certificate-required",
|
|
170
171
|
problemTitle: "Unauthorized",
|
|
171
172
|
problemDetail: errorMessage,
|
|
@@ -27,6 +27,7 @@
|
|
|
27
27
|
* also throws when the operator-supplied `expires` is in the past.
|
|
28
28
|
*/
|
|
29
29
|
|
|
30
|
+
var C = require("../constants");
|
|
30
31
|
var lazyRequire = require("../lazy-require");
|
|
31
32
|
var validateOpts = require("../validate-opts");
|
|
32
33
|
var denyResponse = require("./deny-response");
|
|
@@ -149,7 +150,7 @@ function create(opts) {
|
|
|
149
150
|
denyResponse.methodNotAllowed(res, "GET, HEAD");
|
|
150
151
|
return;
|
|
151
152
|
}
|
|
152
|
-
res.writeHead(
|
|
153
|
+
res.writeHead(C.HTTP.STATUS.OK, { // HTTP 200 status
|
|
153
154
|
"Content-Type": "text/plain; charset=utf-8",
|
|
154
155
|
"Content-Length": bodyBuf.length,
|
|
155
156
|
"Cache-Control": "public, max-age=86400",
|
|
@@ -28,6 +28,7 @@
|
|
|
28
28
|
* of those are missing.
|
|
29
29
|
*/
|
|
30
30
|
|
|
31
|
+
var C = require("../constants");
|
|
31
32
|
var lazyRequire = require("../lazy-require");
|
|
32
33
|
var safeJson = require("../safe-json");
|
|
33
34
|
var validateOpts = require("../validate-opts");
|
|
@@ -141,7 +142,7 @@ function create(opts) {
|
|
|
141
142
|
denyResponse.methodNotAllowed(res, "GET, HEAD");
|
|
142
143
|
return;
|
|
143
144
|
}
|
|
144
|
-
res.writeHead(
|
|
145
|
+
res.writeHead(C.HTTP.STATUS.OK, { // HTTP 200 status
|
|
145
146
|
"Content-Type": "application/manifest+json",
|
|
146
147
|
"Content-Length": bodyBuf.length,
|
|
147
148
|
"Cache-Control": "public, max-age=86400",
|
|
@@ -557,7 +557,7 @@ async function _wireLookup(name, qtype, timeoutMs) {
|
|
|
557
557
|
res.on("end", function () {
|
|
558
558
|
try {
|
|
559
559
|
if (pushFailed) { _fail(pushFailed); return; }
|
|
560
|
-
if (res.statusCode !==
|
|
560
|
+
if (res.statusCode !== C.HTTP.STATUS.OK) { // HTTP 200 OK
|
|
561
561
|
_fail(new ResolverError("resolver/upstream-http",
|
|
562
562
|
"DoH HTTP " + res.statusCode + " for " + name));
|
|
563
563
|
return;
|
|
@@ -581,7 +581,7 @@ async function _dohLookup(host, family) {
|
|
|
581
581
|
try {
|
|
582
582
|
if (pushFailed) { reject(pushFailed); return; }
|
|
583
583
|
var body = collector.result();
|
|
584
|
-
if (res.statusCode !==
|
|
584
|
+
if (res.statusCode !== C.HTTP.STATUS.OK) {
|
|
585
585
|
reject(new DnsError("dns/doh-http", "DoH HTTP " + res.statusCode + " for " + host));
|
|
586
586
|
return;
|
|
587
587
|
}
|
|
@@ -641,7 +641,7 @@ async function _dohLookupSecure(host, family) {
|
|
|
641
641
|
try {
|
|
642
642
|
if (pushFailed) { reject(pushFailed); return; }
|
|
643
643
|
var body = collector.result();
|
|
644
|
-
if (res.statusCode !==
|
|
644
|
+
if (res.statusCode !== C.HTTP.STATUS.OK) { // HTTP 200 OK
|
|
645
645
|
reject(new DnsError("dns/doh-http", "DoH HTTP " + res.statusCode + " for " + host));
|
|
646
646
|
return;
|
|
647
647
|
}
|
|
@@ -1005,7 +1005,7 @@ async function _dohRawQuery(host, qtype) {
|
|
|
1005
1005
|
res.on("end", function () {
|
|
1006
1006
|
try {
|
|
1007
1007
|
if (pushFailed) { reject(pushFailed); return; }
|
|
1008
|
-
if (res.statusCode !==
|
|
1008
|
+
if (res.statusCode !== C.HTTP.STATUS.OK) { // HTTP 200 OK
|
|
1009
1009
|
reject(new DnsError("dns/doh-http", "DoH HTTP " + res.statusCode + " for " + host));
|
|
1010
1010
|
return;
|
|
1011
1011
|
}
|