Fix: parse Accept header q-values in wpsc_get_accept_header()#1057
Open
thisismyurl wants to merge 1 commit into
Open
Fix: parse Accept header q-values in wpsc_get_accept_header()#1057thisismyurl wants to merge 1 commit into
thisismyurl wants to merge 1 commit into
Conversation
The previous implementation used a naive str_contains() check: if any known JSON media type appeared anywhere in the Accept header string, the request was classified as application/json. This ignored RFC 7231 §5.3.2 quality values (q=), so a valid HTML-preferring header such as the one sent by New Relic Synthetics — Accept: text/html,application/xhtml+xml,application/json;q=0.9,... — was misclassified as a JSON request. Two downstream effects: 1. wp_cache_serve_cache_file() refused to serve the cached file. 2. A separate application/json cache bucket was populated on every synthetic check, triggering a fresh page build each time. This commit extracts a new wpsc_parse_accept_header() helper that parses q-values and classifies the request as application/json only when a known JSON type has a strictly higher q-value than text/html. Ties resolve to text/html (safe default: serve the cached page). The wpsc_accept_headers filter continues to work — filtered types participate in the q-value comparison as JSON types. Fixes Automattic#1045
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fixes #1045 —
wpsc_get_accept_header()was using a naivestr_contains()check that matched any JSON media type anywhere in the Accept string, ignoring RFC 7231 §5.3.2 quality values. The result: monitoring tools like New Relic Synthetics (and Datadog/Pingdom/UptimeRobot) that send valid HTML-preferring headers such as:Accept: text/html,application/xhtml+xml,application/json;q=0.9,...
were misclassified as JSON requests. Two downstream effects:
wp_cache_serve_cache_file()refused to serve the cached file on every synthetic check.application/jsoncache bucket was populated on each check, triggering a fresh page build every time.Changes
wp-cache-phase2.phpwpsc_parse_accept_header( $raw_accept, $json_types )helper. It parses q-values per RFC 7231 §5.3.2 and classifies the request asapplication/jsononly when a known JSON type has a strictly higher q-value thantext/html. Ties resolve totext/html(safe default: serve the cached page).wpsc_get_accept_header()now delegates to this helper after the empty-header early-return. The static memoization andwpsc_accept_headersfilter contract are unchanged. Callers are unaffected.Edge cases handled:
q=1.0, no warning or fatal.*/*wildcard — provides effective html q-value only whentext/htmlis not explicitly present.tests/php/WpscParseAcceptHeaderTest.php(new file)14 unit tests covering the seven acceptance criteria from the issue brief plus additional edge cases (wildcard behaviour, custom types via the filter, typical browser headers, out-of-range q-values). The test exercises
wpsc_parse_accept_header()directly — it has no WordPress dependencies, so no WP test scaffolding is required.PHPUnit 12.5.28 — 14 / 14 (100%) — 0.003s
Acceptance criteria from the issue brief
text/htmlimplicit q=1.0,application/json;q=0.9) →text/htmlAccept: application/jsonalone →application/jsonAccept: text/html,application/json(tie, both q=1.0) →text/htmlAccept: application/json,text/html;q=0.9(json strictly higher) →application/jsonAccept: application/ld+json;q=1.0,text/html;q=0.8(extended type via filter) →application/jsontext/htmlwpsc_accept_headersfilter types participate in q-value comparison