Add 'query' to View.http_method_names per RFC 10008
- Dominant language
- No language data
- Stars
- 188
- Forks
- 7
- PR merge metrics
- No merged PRs in 30d
Description
### Code of Conduct
- [x] I agree to follow Django's Code of Conduct
### Feature Description
Add `"query"` to `View.http_method_names` and `Client.query()` to the
test client to support the HTTP QUERY method defined in RFC 10008
(published June 2026 by IETF).
### Problem
RFC 10008 standardizes the HTTP QUERY method as an official IETF standard.
QUERY fills a long-standing gap: it allows sending a request body (like POST)
while being explicitly safe and idempotent (like GET), making responses
cacheable and retries automatic.
Currently Django does not recognize QUERY as a valid HTTP method. Developers
who want to handle QUERY requests must manually override `http_method_names`
on every view:
class MyView(View):
http_method_names = [
"get", "post", "put", "patch",
"delete", "head", "options", "trace",
"query", # manual workaround
]
This workaround should not be necessary for a method that is now part of
the HTTP standard. Other parts of the ecosystem are already adopting it:
axios added native support in v1.16.0 (May 2026).
The fix is minimal: add `"query"` to `View.http_method_names` in
`django/views/generic/base.py` and a `Client.query()` helper in
`django/test/client.py`, following the same pattern as existing methods.
Reference: https://www.rfc-editor.org/rfc/rfc10008
### Request or proposal
proposal
### Additional Details
_No response_
### Implementation Suggestions
The change is minimal and follows the exact same pattern as existing methods.
**1. `django/views/generic/base.py`**
Add `"query"` to `http_method_names`:
```python
# Before
http_method_names = [
"get", "post", "put", "patch",
"delete", "head", "options", "trace",
]
# After
http_method_names = [
"get", "post", "put", "patch",
"delete", "head", "options", "trace",
"query", # RFC 10008
]
```
**2. `django/test/client.py`**
Add a `query()` helper following the same pattern as `post()` and `put()`:
```python
def query(self, path, data=None, content_type="application/json", **extra):
"""Construct a QUERY request."""
post_data = self._encode_json(data or {}, content_type)
return self.generic("QUERY", path, post_data, content_type, **extra)
```
**3. Tests**
```python
class QueryMethodTests(SimpleTestCase):
def test_query_in_http_method_names(self):
self.assertIn("query", View.http_method_names)
def test_dispatches_to_query_method(self):
response = self.client.query(
"/test/",
data={"filter": "active"},
)
self.assertEqual(response.status_code, 200)
def test_missing_query_handler_returns_405(self):
# View with no query() method should return 405
response = self.client.query("/test/")
self.assertEqual(response.status_code, 405)
```
No changes needed to the dispatcher logic — `dispatch()` already does
`getattr(self, request.method.lower(), self.http_method_not_allowed)`
so adding `"query"` to the allowed list is sufficient for routing to work.
Contributor guide
No contributing guide indexed for this repository
Research direction
Start with django/views/generic/base.py and django/test/client.py, comparing the existing HTTP methods and client helpers. Run the proposed QueryMethodTests and relevant view-dispatch tests. Done means QUERY is recognized and dispatched, Client.query() sends request data, and views without a query handler return 405.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- python
- Domain
- api, backend
- Issue type
- Feature
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Activity status
- Quiet
- Clarity
- Clearly specified
- Newbie friendliness
- 75/100