尝试使用请求库登录航空公司网站时出现Python 10054错误

时间:2012-12-23 01:09:56

标签: python web-scraping urllib python-requests

我正在学习python,作为我的第一个项目,我想登录几个航空公司网站并抓取我的常旅客Mile信息。我已成功登录并刮过美国航空公司和美联航,但我无法在达美航空,美国航空和英国航空公司的航空公司上航行。

我一直在使用的方法是观看来自Fiddler2,Chrome或Firebug的网络流量。 Wireshark目前似乎太复杂了。

为了让我的脚本与美国和美国联合使用,我所做的只是观察fiddler2上的流量,复制FORM DATA和REQUEST HEADER DATA,然后使用python第三方请求库来访问数据。非常简单。很容易。另一家航空公司的网站给我带来了很多麻烦。

让我们具体谈谈英国航空公司。下面是我登录虚拟BA帐户时从提琴手处拿走的FORM DATA和REQUEST HEADER DATA的图片。我还包括了我一直在使用的测试脚本。我写了两个不同的版本。一个使用Requests库,一个使用urllib。它们都会产生相同的错误,但我认为如果他们没有导入Requests库,我会提供两者来帮助我更容易帮助我。使用你想要的那个。

基本上,当我发出请求时,我得到了一个

10054,'远程主机'错误地强行关闭了现有连接。

我不知道发生了什么事。一直在寻找3天,什么都没有。我希望有人可以帮助我。以下代码使用我的虚拟BA帐户信息。用户名:python_noob密码:p4ssword。随意使用并测试它。

以下是fiddler2数据的一些图片

http://i.imgur.com/iOL91.jpg?1

http://i.imgur.com/meLHL.jpg?1

import requests

import urllib


def get_BA_login_using_requests ():
    url_loginSubmit1 = 'https://www.britishairways.com/travel/loginr/public/en_us'

    url_viewaccount1 = 'https://www.britishairways.com/travel/viewaccount/public/en_us?eId=106011'
    url_viewaccount2 = 'https://www.britishairways.com/travel/viewaccount/execclub/_gf/en_us?eId=106011'


    form_data = {
        'Directional_Login':'',
        'eId':'109001',
        'password':'p4ssword',
        'membershipNumber':'python_noob',
        }


    request_headers= {
        'Cache-Control':'max-age=0',
        'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
        'Accept-Charset':'ISO-8859-1,utf-8;q=0.7,*;q=0.3',
        'Accept-Encoding':'gzip,deflate,sdch',
        'Accept-Language':'en-US,en;q=0.8',
        'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.97 Safari/537.11',

        'Cookie': 'BIGipServerba.com-port80=997762723.20480.0000; v1st=EDAB42A278BE913B; BASessionA=kDtBQWGclJymXtlsTXyYtykDLLsy3KQKvd3wMrbygd7JZZPJfJz2!-1893405604!clx42al01-wl01.baplc.com!7001!-1!-407095676!clx43al01-wl01.baplc.com!7001!-1; BIGipServerba.com-port81=997762723.20736.0000; BA_COUNTRY_CHOICE_COOKIE=us; Allow_BA_Cookies=accepted; BA_COUNTRY_CHOICE_COOKIE=US; opvsreferrer=functional/home/home_us.jsp; realreferrer=; __utma=28787695.2144676753.1356203603.1356203603.1356203603.1; __utmb=28787695.1.10.1356203603; __utmc=28787695; __utmz=28787695.1356203603.1.1.utmcsr=(direct)|utmccn=(direct)|utmcmd=(none); fsr.s={"v":-2,"rid":"d464cf7-82608645-1f31-3926-49807","ru":"http://www.britishairways.com/travel/globalgateway.jsp/global/public/en_","r":"www.britishairways.com","st":"","to":3,"c":"http://www.britishairways.com/travel/home/public/en_us","pv":1,"lc":{"d0":{"v":1,"s":false}},"cd":0}',

        'Content-Length':'78',
        'Content-Type':'application/x-www-form-urlencoded',

        'Origin':'https://www.britishairways.com',
        'Referer':'https://www.britishairways.com/travel/loginr/public/en_us',

        'Connection':'keep-alive',
        'Host':'www.britishairways.com',
        }



    print ('Trying to login to British Airways using Requests Library (takes about 1 minute for error to occur)')


    try:
        r1 = requests.post(url_loginSubmit1, data = form_data, headers = request_headers)
    print ('it worked')
    except Exception as e:
        msg = "An exception of type {0} occured, these were the arguments:\n{1!r}"
        print (msg.format(type(e).__name__, e.args))


    return







def get_BA_login_using_urllib():
    """Tries to request the URL. Returns True if the request was successful; false otherwise.
    https://www.britishairways.com/travel/loginr/public/en_us

    response -- After the function has finished, will possibly contain the response to the request.

    """
    response = None
    print ('Trying to login to British Airways using urllib Library (takes about 1 minute for error to occur)')
    # Create request to URL.
    req = urllib.request.Request("https://www.britishairways.com/travel/loginr/public/en_us")

    # Set request headers.
    req.add_header("Connection", "keep-alive")
    req.add_header("Cache-Control", "max-age=0")
    req.add_header("Origin", "https://www.britishairways.com")
    req.add_header("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.97 Safari/537.11")
    req.add_header("Content-Type", "application/x-www-form-urlencoded")
    req.add_header("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8")
    req.add_header("Referer", "https://www.britishairways.com/travel/home/public/en_us")
    req.add_header("Accept-Encoding", "gzip,deflate,sdch")
    req.add_header("Accept-Language", "en-US,en;q=0.8")
    req.add_header("Accept-Charset", "ISO-8859-1,utf-8;q=0.7,*;q=0.3")
    req.add_header("Cookie", 'BIGipServerba.com-port80=997762723.20480.0000; v1st=EDAB42A278BE913B; BIGipServerba.com-port81=997762723.20736.0000; BA_COUNTRY_CHOICE_COOKIE=us; Allow_BA_Cookies=accepted; BA_COUNTRY_CHOICE_COOKIE=US; BAAUTHKEY=BA4760A2434L; BA_ENROLMENT_APPLICATION_COOKIE=1356219482491AT; BASessionA=wKG4QWGSTggNGnsLTnrgQnMxGMyzvspGLCYpjdSZgv2pSgYN1YRn!-1893405604!clx42al01-wl01.baplc.com!7001!-1!-407095676!clx43al01-wl01.baplc.com!7001!-1; HOME_AD_DISPLAY=1; previousCountryInfo=us; opvsreferrer=functional/home/home_us.jsp; realreferrer=; __utma=28787695.2144676753.1356203603.1356216924.1356219076.6; __utmb=28787695.15.10.1356219076; __utmc=28787695; __utmz=28787695.1356203603.1.1.utmcsr=(direct)|utmccn=(direct)|utmcmd=(none); fsr.s={"v":-2,"rid":"d464cf7-82608645-1f31-3926-49807","ru":"http://www.britishairways.com/travel/globalgateway.jsp/global/public/en_","r":"www.britishairways.com","st":"","to":5,"c":"https://www.britishairways.com/travel/home/public/en_us","pv":31,"lc":{"d0":{"v":31,"s":true}},"cd":0,"f":1356219889982,"sd":0}')

    # Set request body.
    body = b"Directional_Login=&eId=109001&password=p4ssword&membershipNumber=python_noob"

    # Get response to request.


    try:
        response = urllib.request.urlopen(req, body)
        print ('it worked')
    except Exception as e:
        msg = "An exception of type {0} occured, these were the arguments:\n{1!r}"
        print (msg.format(type(e).__name__, e.args))

    return



def main():
    get_BA_login_using_urllib()
    print()
    get_BA_login_using_requests()
    return


main()

2 个答案:

答案 0 :(得分:1)

另一方面,我说你设法创建了一个格式错误或非法的请求,而另一方的服务器(甚至代理)只是拒绝处理它。

  1. 使用requests库。这很棒。 Urllib 相当过时(而且,根本不使用它。)

  2. 摆脱几乎所有自定义标头。特别是Content-LengthKeep-AliveConnectionCookie。前三个应该让请求库处理,因为它们是HTTP 1.1协议的一部分。关于Cookie:这也将由requests库处理,具体取决于您使用会话的方式。 (您可能需要查阅那里的文档。)如果没有任何以前的cookie,当您尝试访问该站点时,您可能会获得类似401的内容,或者您​​将(透明地)重定向到登录页面。登录将设置正确的cookie,之后您应该可以重新尝试原始请求。

  3. 如果您对后期数据使用dict,则也不需要Content-Type标题。您可能想尝试在所述dict中使用unicode-values。我发现这有时会产生影响。

  4. 换句话说:尝试尽可能多地删除,然后从那里构建它。做这样的事情通常不应该花费少数几行。现在,抓一个网页,这是另一回事:为此尝试'beautifulsoup'。

    P.S。:不要永远在公共论坛上发布Cookie数据:它们可能包含阴影角色可能会滥用的个人或其他敏感数据。

答案 1 :(得分:0)

似乎在Python 3.3的Windows版本中存在一个导致我出现问题的错误。我用过这里的答案

HTTPS request results in reset connection in Windows with Python 3

使用urllib版本的脚本取得进展。我想使用请求所以我需要弄清楚如何使用该模块进行SSL降级工作。我会把它作为一个单独的线程。如果有人对此有答案,你也可以在这里发帖。 THX。