我正在为现场Heroku服务器编写Django测试,并且无法让Django通过重定向识别POST请求。
在我的测试服务器上,一切正常:
views.py
def detect_post(request):
"""
Detect whether this is a POST or a GET request.
"""
if request.method == 'POST':
return HttpResponse(
json.dumps({"POST request": "POST request detected"}),
content_type="application/json"
)
# If this is a GET request, return an error
else:
return HttpResponse(
json.dumps({"Access denied": "You are not permitted to access this page."}),
content_type="application/json"
)
python manage.py shell
>>> from django.urls import reverse
>>> from django.test import Client
>>> c = Client()
# GET request returns an error, as expected:
>>> response = c.get(reverse('detectpost'), follow=True)
>>> response.status_code
200
>>> response.content
b'{"Access denied": "You are not permitted to access this page."}'
# POST request returns success, as expected
>>> response = c.post(reverse('detectpost'))
>>> response.status_code
200
>>> response.content
b'{"POST request": "POST request detected"}'
然而,当我搬到我的生产服务器时,我遇到了问题。我认为这是因为我的生产服务器有SECURE_SSL_REDIRECT
,所以所有页面都重定向到同一页面的启用SSL的版本。以下是当我尝试在生产服务器上运行相同的测试代码时会发生什么:
heroku运行python manage.py shell
>>> from django.urls import reverse
>>> from django.test import Client
>>> c = Client()
# GET request returns an error, as expected:
>>> response = c.get(reverse('detectpost'), follow=True)
>>> response.status_code
200
>>> response.content
b'{"Access denied": "You are not permitted to access this page."}'
# POST request, however, has problems
>>> response = c.post(reverse('detectpost'), follow=True)
>>> response.status_code
200
>>> response.content
b'{"Access denied": "You are not permitted to access this page."}'
>>> response.redirect_chain
[('https://testserver/testpost/', 301)]
# I believe that the POST request isn't being detected because my site uses redirects
>>> response = c.post(reverse('detectpost'))
>>> response.status_code
301
如何通过重定向让我的Django TestClient注册POST请求?我期望follow=True
标志能够实现这一点,但它似乎没有起作用。
答案 0 :(得分:2)
使用client.post
时,您可以通过设置https
来模拟secure=True
网址的请求。
response = c.post(reverse('detectpost'), follow=True, secure=True)
当Django安全中间件返回从http
到https
的301重定向时,即使原始请求是POST请求,浏览器也会向新URL发出GET请求。
有307 response告诉浏览器不要更改方法。但是我不会尝试让Django返回307.只需按照我的建议更改client.post()
来电使用secure=True
。