If you've ever built an API with complex search or filtering, you've probably run into the same annoying choice: use GET and cram your filters into a URL, or use POST and lose all the guarantees that make GET useful in the first place.

For many years, that was just something you lived with. Then, on June 2026, the IETF published RFC 10008: The HTTP QUERY Method. The first genuinely new HTTP method since PATCH arrived back in 2010. It's a small addition to the protocol, but it quietly fixes a problem many API developer has bumped into.

The problem it solves

HTTP methods aren't just labels, they carry meaning that browsers, proxies, caches, and CDNs all rely on.

GET is safe (it doesn't change server state) and idempotent (repeating it has no extra effect), which is exactly why it's cacheable and safe to retry automatically.

The catch: everything has to travel in the URL. Filter objects turn into long query strings, URL length limits vary unpredictably across servers and proxies, and URLs tend to get logged more often than request bodies do, not great if your "query" contains anything sensitive.

A filter object that's perfectly reasonable as JSON:

{
  "search": "distributed systems",
  "category": "books",
  "tags": ["networking", "architecture"],
  "publishedAfter": "2025-01-01",
  "sort": "relevance"
}

turns into this once it's squeezed into a GET URL:

GET /articles?search=distributed+systems&category=books&tags=networking,architecture&publishedAfter=2025-01-01&sort=relevance HTTP/1.1

That's still a fairly small example. Add a few more filters, or a nested object, and it gets unreadable fast, before you've even hit a proxy's URL length limit.

POST solves the size and structure problem, you can send a rich JSON body describing exactly what you want. But POST carries no promise of safety. Nothing in the protocol tells a cache, proxy, or browser "this is just a read", so none of them treat it that way, even when the request really is just a lookup dressed up as a POST.

The same filter object fits neatly into a POST body, no URL gymnastics required:

POST /articles/search HTTP/1.1
Host: curiousthoughts.blog
Content-Type: application/json

{
  "search": "distributed systems",
  "category": "books",
  "tags": ["networking", "architecture"],
  "publishedAfter": "2025-01-01",
  "sort": "relevance"
}

Structurally, this is fine. The problem is invisible to anything sitting between the client and the server: a cache can't tell this apart from a POST that creates an order or charges a card, so it won't cache the response, and a proxy retrying a timed-out request has no way to know that resending it is harmless. The request is a read, nothing in the method says so.

Developers have been picking whichever downside they could live with. QUERY exists so they don't have to.

What QUERY actually is

QUERY is best understood as a hybrid: it has the request body of a POST, and the safety and idempotency guarantees of a GET. A server should treat a QUERY request as read-only, meaning it can be retried, cached, or repeated automatically without any risk of partial or duplicate state changes.

The request body (combined with its Content-Type) is what defines the query. The server determines the shape and scope of the query based on that content, similarly to how it decides what to do with a POST body. If the Content-Type header is missing or doesn't match the actual content, a compliant server should reject the request outright, since it has no reliable way to interpret it.

A minimal example looks like this:

QUERY /articles HTTP/1.1
Host: curiousthoughts.blog
Content-Type: application/json
Accept: application/json

{
  "search": "http query method",
  "filters": {
    "tags": ["http", "networking"],
    "publishedAfter": "2026-01-01"
  },
  "limit": 10
}

And the response is just a normal HTTP response:

HTTP/1.1 200 OK
Content-Type: application/json

[
  { "title": "HTTP Finally Got a New Method", "slug": "http-query-method" }
]

From JavaScript, it looks almost identical to a fetch POST, the only difference is the method name:

const response = await fetch("https://api.example.com/articles", {
  method: "QUERY",
  headers: { "Content-Type": "application/json" },
  body: JSON.stringify({
    search: "http query method",
    filters: { tags: ["http", "networking"] },
    limit: 10
  })
});

const results = await response.json();

Or with curl:

curl -X QUERY https://api.example.com/articles \
  -H "Content-Type: application/json" \
  -d '{"search":"http query method","limit":10}'

Nothing exotic, it's designed to be a drop-in feel for anyone who already knows POST.

The catches worth knowing about

A new method doesn't slot into the existing web instantly, and there are a few things worth being deliberate about before shipping QUERY into a real API:

  • Caching needs the body, not just the URL. Since two QUERY requests to the same URL can carry entirely different bodies (and therefore mean entirely different things), any cache sitting in front of your API needs to include the request body in its cache key. Get that normalization wrong, and you risk cache poisoning or serving one user's query result to another.

  • Middleware may not recognize it yet. WAFs, API gateways, load balancers, and CSRF protections are often written against an explicit list of methods: GET, POST, PUT, DELETE, PATCH. QUERY is new enough that some of that infrastructure may reject it outright or, worse, handle it inconsistently. Worth checking your stack before relying on it in production.

  • Browsers will preflight it. QUERY isn't on the CORS "safelist" of methods (only GET, POST, and HEAD get that treatment without conditions), so any cross-origin QUERY request from browser JavaScript will trigger a preflight OPTIONS request first, same as a custom POST with non-standard headers would.

  • It's still early days. RFC 10008 is a Proposed Standard, meaning it's been through IETF consensus and IESG approval, the same process HTTP/1.1, HTTP/2, and HTTP/3 went through. That makes it official, but real-world adoption across frameworks, browsers, and infrastructure is only just getting started, so don't be surprised if some tools you rely on don't fully support it yet.

Should you use it?

If you're designing a new API today and have search or filtering endpoints that are outgrowing GET's URL-based limits, QUERY is worth trying. It's the method that actually matches what you're doing: a safe, cacheable, retryable read, just expressed with a body instead of a query string.

For existing APIs, it's less about removing POST endpoints overnight and more about knowing the option now exists, so the next time you're stuck choosing between "unwieldy URL" and "technically a POST," there's a third option that was purpose-built for exactly that gap.