我使用的 API (wunderground) 要求日期格式为“2001-01-01 10:32:35”,(他们声称)应该将 URL 转义为“2000-01-01+10%” 3A32%3A35"。 HTTPX 和 Requests 都做得很好,只是它们将 + 编码为 %2B,这是 API 不期望的。如何防止请求或 HTTPX 对 + 进行编码?
示例代码:
auth = {
'ID': station,
'PASSWORD': stationKey,
'dateutc': 2024-08-07+19%3A58%3A43,
'tempf': 65.1,
'action': "updateraw"
}
r = httpx.get('https://weatherstation.wunderground.com/weatherstation/updateweatherstation.php', params=auth)
OR
r = requests.get('https://weatherstation.wunderground.com/weatherstation/updateweatherstation.php', params=auth)
print(r.url)
输出:
https://weatherstation.wunderground.com/weatherstation/updateweatherstation.php?ID=XXXX&PASSWORD=XXXXX&dateutc=2024-08-07%2B20%253A08%253A41&tempf=65.1&action=updateraw
是对的,HTTPX 和 Requests 会自动对 URL 中的特殊字符进行编码,包括加号 (
+
)。尽管根据标准,加号在 URL 中表示空格,并且应该被编码为
%2B
,但看起来 Wunderground 的 API 在这种情况下需要非标准的行为。
有两个选择来解决这个问题:
1. 手动构建 URL 参数字符串:
可以避免使用
params
参数,而是手动构建查询字符串,并完全按照 API 所需的方式对日期时间进行格式化。
import httpx
auth = {
'ID': station,
'PASSWORD': stationKey,
'tempf': 65.1,
'action': "updateraw"
}
dateutc = '2024-08-07+19%3A58%3A43'
url = f'https://weatherstation.wunderground.com/weatherstation/updateweatherstation.php?ID={auth["ID"]}&PASSWORD={auth["PASSWORD"]}&dateutc={dateutc}&tempf={auth["tempf"]}&action={auth["action"]}'
r = httpx.get(url)
print(r.url)
2. 使用
urllib.parse.quote
对日期时间进行编码,并指定
safe
参数:
可以使用
urllib.parse.quote
函数对日期时间字符串进行编码,并使用
safe
参数指定哪些字符不应被编码。
import httpx
from urllib.parse import quote
auth = {
'ID': station,
'PASSWORD': stationKey,
'dateutc': quote('2024-08-07+19:58:43', safe='+:'), # 保留 + 和 : 不编码
'tempf': 65.1,
'action': "updateraw"
}
r = httpx.get('https://weatherstation.wunderground.com/weatherstation/updateweatherstation.php', params=auth)
print(r.url)
这两种方法都可以解决问题,并生成 Wunderground API 所需的 URL 格式。
请注意,依赖于非标准 URL 编码的 API 可能会导致问题。 如果可能,最好联系 Wunderground 并询问他们是否可以更新其 API 以遵循标准做法。
标签:python,python-requests,httpx,wunderground From: 78845599