我正在使用Django Rest Framework。在权限类中,我检查两个自定义http标头的值:mt_api_token
和mt_api_key
。
在测试中,我使用自定义标头调用API。 sign_request()
返回{'mt_api_key': api_client.client_id, 'mt_api_token': token}
。
class APIv1SimpleTestCase(APITestCase):
[...]
response = self.client.get(url, format='json', **sign_request("", api_client=oauth2_client))
这是一个遗留系统,标题必须包含下划线而不是短划线。
权限类:
class AuthPermissions(permissions.BasePermission):
def is_token_valid(self, request):
mt_api_token = request.META['mt_api_token']
[...]
测试通过。 但是,如果我使用httpie:
调用api$ http :8000/api/v1/endpoint1/ mt_api_key:0a9..66 mt_api_token:7b2...8
我收到keyError异常,因为request.META['mt_api_key']
和request.META['mt_api_token']
不存在。
我必须使用request.META['HTTP_MT_API_TOKEN']
,这根据DRF documentation for request.META
有意义,但我无法找出为什么测试通过。如果我将实现更改为request.META ['HTTP _...']我的测试失败。
答案 0 :(得分:1)
这在测试中运行良好,因为测试是手动设置request.META
键以匹配您传入的内容,mt_api_token
和mt_api_key
。您没有看到任何错误,因为这完全有效,但它并不符合您的预期。这在Django advanced testing documentation中非常简短地介绍,但基本上额外的参数是directly added到META
字典。
当您的请求通过Django提供的WSGI处理程序时,任何HTTP标头都会自动以HTTP_
per the WSGI specification为前缀。这适用于大多数客户端提供的HTTP标头,包括Authorization
标头,通常用于在API上授权用户(使用基本身份验证,OAuth等),该标头放入request.META
字典为HTTP_AUTHORIZATION
。请注意,键也始终为大写,因为HTTP标头名称不区分大小写。
您可以通过sign_request
方法将密钥返回为HTTP_MT_API_TOKEN
和HTTP_MT_API_KEY
来修复测试,这些密钥是通过浏览器传递的。您还需要调整视图代码以引用这些新密钥。