为什么这段代码:
import requests
response = requests.post('http://evds.tcmb.gov.tr/cgi-bin/famecgi', data={
'cgi': '$ozetweb',
'ARAVERIGRUP': 'bie_yymkpyuk.db',
'DIL': 'UK',
'ONDALIK': '5',
'wfmultiple_selection': 'ZAMANSERILERI',
'f_begdt': '07-01-2005',
'f_enddt': '07-10-2016',
'ZAMANSERILERI': ['TP.PYUK1', 'TP.PYUK2', 'TP.PYUK21', 'TP.PYUK22', 'TP.PYUK3', 'TP.PYUK4', 'TP.PYUK5', 'TP.PYUK6'],
'YON': '3',
'SUBMITDEG': 'Report',
'GRTYPE': '1',
'EPOSTA': 'xxx',
'RESIMPOSTA': '***',
})
print(response.text)
在Python 2(2.7.12
)和Python 3(3.5.2
)中产生不同的结果?我正在使用requests==2.11.1
。由于requests
库支持具有相同API的两个Python版本,我想结果应该是相同的。
预期的结果是通过Python 2运行代码获得的结果。它每次都有效。当使用Python 3运行时,服务器有时会返回错误,有时它会起作用。 (这是有趣的部分。)
由于它适用于Python 2,我认为错误必须发生在客户端。有什么需要注意Python 3如何处理编码或通过套接字发送数据,我应该知道吗?
编辑:在下面的评论中,有人能够重现此问题并确认存在此问题。
答案 0 :(得分:1)
由于python3.3和至少需要 cgi 字段的服务器首先出现,所以python2与python3中的dicts之间的差异似乎与Hash randomization is enabled by default不同。以下可以重现:
good = requests.post('http://evds.tcmb.gov.tr/cgi-bin/famecgi', data=([
('cgi', '$ozetweb'),
('ARAVERIGRUP', 'bie_yymkpyuk.db'),
('DIL', 'UK'),
('ONDALIK', '5'),
('wfmultiple_selection', 'ZAMANSERILERI'),
('f_begdt', '07-01-2005'),
('f_enddt', '07-10-2016'),
('ZAMANSERILERI',
['TP.PYUK1', 'TP.PYUK2', 'TP.PYUK21', 'TP.PYUK22', 'TP.PYUK3', 'TP.PYUK4', 'TP.PYUK5', 'TP.PYUK6']),
('YON', '3'),
('SUBMITDEG', 'Report'),
('GRTYPE', '1'),
('EPOSTA', 'xxx'),
('RESIMPOSTA', '***')]))
bad = requests.post('http://evds.tcmb.gov.tr/cgi-bin/famecgi', data=([
('ARAVERIGRUP', 'bie_yymkpyuk.db'),
('cgi', '$ozetweb'),
('DIL', 'UK'),
('wfmultiple_selection', 'ZAMANSERILERI'),
('ONDALIK', '5'),
('f_begdt', '07-01-2005'),
('f_enddt', '07-10-2016'),
('ZAMANSERILERI',
['TP.PYUK1', 'TP.PYUK2', 'TP.PYUK21', 'TP.PYUK22', 'TP.PYUK3', 'TP.PYUK4', 'TP.PYUK5', 'TP.PYUK6']),
('YON', '3'),
('SUBMITDEG', 'Report'),
('GRTYPE', '1'),
('EPOSTA', 'xxx'),
('RESIMPOSTA', '***')]))
使用python2运行上面的代码:
In [6]: print(good.request.body)
...: print(bad.request.body)
...:
...: print(len(good.text), len(bad.text))
...:
cgi=%24ozetweb&ARAVERIGRUP=bie_yymkpyuk.db&DIL=UK&ONDALIK=5&wfmultiple_selection=ZAMANSERILERI&f_begdt=07-01-2005&f_enddt=07-10-2016&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6&YON=3&SUBMITDEG=Report&GRTYPE=1&EPOSTA=xxx&RESIMPOSTA=%2A%2A%2A
ARAVERIGRUP=bie_yymkpyuk.db&cgi=%24ozetweb&DIL=UK&wfmultiple_selection=ZAMANSERILERI&ONDALIK=5&f_begdt=07-01-2005&f_enddt=07-10-2016&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6&YON=3&SUBMITDEG=Report&GRTYPE=1&EPOSTA=xxx&RESIMPOSTA=%2A%2A%2A
(71299, 134)
和python3:
In [4]: print(good.request.body)
...: print(bad.request.body)
...:
...: print(len(good.text), len(bad.text))
...:
cgi=%24ozetweb&ARAVERIGRUP=bie_yymkpyuk.db&DIL=UK&ONDALIK=5&wfmultiple_selection=ZAMANSERILERI&f_begdt=07-01-2005&f_enddt=07-10-2016&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6&YON=3&SUBMITDEG=Report&GRTYPE=1&EPOSTA=xxx&RESIMPOSTA=%2A%2A%2A
ARAVERIGRUP=bie_yymkpyuk.db&cgi=%24ozetweb&DIL=UK&wfmultiple_selection=ZAMANSERILERI&ONDALIK=5&f_begdt=07-01-2005&f_enddt=07-10-2016&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6&YON=3&SUBMITDEG=Report&GRTYPE=1&EPOSTA=xxx&RESIMPOSTA=%2A%2A%2A
71299 134
传递你在python2中发布的dict:
In [4]: response.request.body
Out[4]: 'cgi=%24ozetweb&DIL=UK&f_enddt=07-10-2016&YON=3&RESIMPOSTA=%2A%2A%2A&wfmultiple_selection=ZAMANSERILERI&ARAVERIGRUP=bie_yymkpyuk.db&GRTYPE=1&SUBMITDEG=Report&f_begdt=07-01-2005&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6&ONDALIK=5&EPOSTA=xxx'
In [5]: len(response.text)
Out[5]: 71299
和python3中的相同词典:
In [3]: response.request.body
Out[3]: 'EPOSTA=xxx&ARAVERIGRUP=bie_yymkpyuk.db&DIL=UK&SUBMITDEG=Report&cgi=%24ozetweb&GRTYPE=1&f_enddt=07-10-2016&wfmultiple_selection=ZAMANSERILERI&ONDALIK=5&f_begdt=07-01-2005&RESIMPOSTA=%2A%2A%2A&YON=3&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6'
In [4]: len(response.text)
Out[4]: 134
在启动另一个ipython2 shell之前运行~$ export PYTHONHASHSEED=1234
:
In [4]: response.request.body
Out[4]: 'DIL=UK&GRTYPE=1&ARAVERIGRUP=bie_yymkpyuk.db&f_begdt=07-01-2005&RESIMPOSTA=%2A%2A%2A&ONDALIK=5&EPOSTA=xxx&YON=3&SUBMITDEG=Report&wfmultiple_selection=ZAMANSERILERI&cgi=%24ozetweb&ZAMANSERILERI=TP.PYUK1&ZAMANSERILERI=TP.PYUK2&ZAMANSERILERI=TP.PYUK21&ZAMANSERILERI=TP.PYUK22&ZAMANSERILERI=TP.PYUK3&ZAMANSERILERI=TP.PYUK4&ZAMANSERILERI=TP.PYUK5&ZAMANSERILERI=TP.PYUK6&f_enddt=07-10-2016'
In [5]: os.environ["PYTHONHASHSEED"]
Out[5]: '1234'
In [6]: len(response.text)
Out[6]: 134
你可以多次运行代码到同一端,但绝对('cgi', '$ozetweb')
首先是代码工作必不可少的,它碰巧间歇性地使用python3,因为键的顺序有时会放在 cgi 首先。 hashing topic