python - [Digest Auth]:邮递员或带有自定义标头的请求,都可以;python3-requests(2.14.2) 失败
问题描述
我发送一个 POST 请求以注册到我的网站。
我使用邮递员,我得到 200 好
我自己发送了两次 POST 请求,使用自定义标头,我也得到 200 ok
当我使用 python3 包(请求)时,我得到 401。
以下是步骤:
我已经定义了一个函数来计算 md5 和自定义标题:
import re import hashlib def md5_utf8(x): if isinstance(x, str): x = x.encode('utf-8') return hashlib.md5(x).hexdigest() def make_digest_auth_headers(my_auth, uri): nonce = re.findall(r'nonce="(.*?)"', my_auth)[0] realm = re.findall(r'realm="(.*?)"', my_auth)[0] qop = re.findall(r'qop="(.*?)"', my_auth)[0] uri = uri method = "POST" nc = "00000001" cnonce = "0a4f113b" username = "my_user" pwd = "my_pwd" # cal HA1 HA1 = md5_utf8(username + ":" + realm + ":" + pwd) # cal HA2 HA2 = md5_utf8(method + ":" + uri) # cal client response response = md5_utf8(HA1 + ":" + nonce + ":" + nc + ":" + cnonce + ":" + qop + ":" + HA2) headers = { "Content-Type": "application/json;charset=utf-8", "HOST": "ip:port", "Accept": "application/json;charset=utf-8", "Accept-Encoding": "gzip, deflate", "Connection": "keep-alive", "cache-control": "no-cache", "Authorization": 'Digest username="' + username + '", realm="' + realm + '", nonce="' + nonce + '", uri="' + uri + '", algorithm=MD5, response="' + response + '", qop=' + qop + ', nc=' + nc + ', cnonce="' + cnonce + '"' } return headers
我发送了一个这样的 POST 请求。
import requests session = requests.Session() session.headers = { "Content-Type": "application/json;charset=utf-8", "Accept": "application/json;charset=utf-8" } uri = "/System/Register" data = { "RegisterObject": { "DeviceID": my_id } } r = session.post('http://my_ip:my_port/System/Register', json=data) headers = make_digest_auth_headers(r.headers['WWW-Authenticate'], uri) r = self.session.post(f'{url}/VIID/System/Register', json=data, headers=headers) print(r.json())
- 我得到了 200 好的响应
{'ResponseStatusObject': {'Id': 'my_id', 'LocalTime': '20190122090110', 'RequestURL': 'http://ip:port/System/Register', 'StatusCode': 0, 'StatusString': 'OK'}}
- 我使用 python3 请求:
import requests from requests.auth import HTTPDigestAuth session = requests.Session() session.auth = HTTPDigestAuth(my_user, my_pwd) session.headers = { "Content-Type": "application/json;charset=utf-8", "Accept": "application/json;charset=utf-8" } data = { "RegisterObject": { "DeviceID": my_id } } session.post('http://ip:port/System/Register', json=data)
- 我得到了 401:
{'ResponseStatusObject': {'Id': 'my_id', 'LocalTime': '20190122090110', 'RequestURL': 'http://ip:port/System/Register', 'StatusCode': 104, 'StatusString': 'Failed'}}
我不知道为什么?这么奇怪。谢谢。
解决方案
推荐阅读
- java - 我怎样才能让我的跳跃动画一次全部工作?
- java - Do While 循环问题
- django - Django 作为 socket.io 客户端
- abp - 我在哪里放置“业务逻辑”?
- scroll - 如何在 kivy ScrollEffect 中阻止“反弹”?
- animation - SwiftUI:使用 AnimatableModifier 时,隐式动画显示的动画与显式动画不同
- google-cloud-functions - 谷歌云功能没有显示任何调用活动
- google-kubernetes-engine - 从私有 GKE 集群连接到公有 Cloud SQL
- visual-studio - 带有 Visual Studio 代码的 Azure 函数 - 发布时没有选择操作系统的选项 (Python 3.7)
- amazon-web-services - 如何根据 Kubernetes 集群位置更改网站内容?