2011-12-15 3 views
8

私はGoogle Checkout APIを使いこなしています。私はDjangoアプリに取り込みたいと思っています。基本的なHTTP認証を使用してGoogleにデータを送信する必要があります。Pythonでの生データの投稿

curl -d "$(cat mytest.xml)" -u username:password https://url 

をそして、それはGoogleに私のテストXMLファイルの内容をポスト:私はこのようcurlでこれをテストしてきました。そしてそれはうまく動作します!

しかし、私はこの単純な行をPythonに移植する際に問題があります。私はいくつかの異なる方法(httplib2、urllib2、pycurl)をパスワードと接続して何かを投稿していますが、resposeは常に400 Bad Requestです。

HTTP Basic認証サーバーにテキストのブロックを投稿するためのpythonに相当するものはありますか?私は私の頭を強打するために壁を使い果たしている。


コードを追加しないことをお詫びします。ここに私の最高のヒット曲がいくつかあります。それぞれ、DATAはXML文字列です。 URL,USERNAMEおよびPASSWORDは一定である。

req = urllib2.Request(URL) 
req.add_header("Authorization", "Basic %s" % base64.encodestring('%s:%s'%(USERNAME, PASSWORD))) 
u = urllib2.urlopen(req, DATA) 

は私に素敵なHTTP Error 400: Bad Request


passman = urllib2.HTTPPasswordMgrWithDefaultRealm() 
passman.add_password(None, URL, USERNAME, PASSWORD) 
authhandler = urllib2.HTTPBasicAuthHandler(passman) 
opener = urllib2.build_opener(authhandler) 
urllib2.install_opener(opener) 
pagehandle = urllib2.urlopen(URL, DATA) 

を与えますPOSTFIELDとしてDATA文字列を渡すと格闘しているようだHTTP Error 401: Unauthorized


pycurl.global_init(pycurl.GLOBAL_DEFAULT) 
c = pycurl.Curl() 
c.setopt(pycurl.URL, URL) 
c.setopt(pycurl.USERPWD, "%s:%s" % (USERNAME,PASSWORD)) 
c.setopt(pycurl.POST, 1) 
c.setopt(pycurl.HTTPHEADER, ["Content-type: text/xml"]) 
c.setopt(pycurl.POSTFIELDS, DATA) 
b = StringIO.StringIO() 
c.setopt(pycurl.WRITEFUNCTION, b.write) 
c.perform() 

を与えます。私はいくつかの異なる方法でデータをINGのurllib.urlencode()を試みたが、


h = httplib2.Http() 
h.add_credentials(USERNAME, PASSWORD) 
print = h.request(URL, "POST", body=base64.encodestring(DATA)) 

てきた資格情報は何もしていないようだ - 私は戻ってGoogleからの不正なメッセージが表示されます。

さらに多くのものがありますが、それらはすべてこれらに基づいています。

答えて

12

私はsomoneoneが指摘するまで、基本的なHTTP認証やその他の認証をサポートする素晴らしいrequestsを指摘するまで、stdlibパッケージと同様の混乱を経験しています。そして、それは美しくてシンプルなAPIを持っています!それは、他の必要な機能のホストをサポートしてい

requests.post(url, data=DATA, headers=HEADERS_DICT, auth=(username, password)) 

(例えばHTTPS、ダイジェスト認証など)uがしなければならない場合は、それをチェックしてみて下さい...

2

uroid2を使用して基本認証を使用した場合、Voidspaceはan excellent articleになります。下記の適切なコードスニペットをコピーし、POSTを使用するように変更しました。

import urllib2 

theurl = 'http://www.someserver.com/toplevelurl/somepage.htm' 
username = 'johnny' 
password = 'XXXXXX' 

passman = urllib2.HTTPPasswordMgrWithDefaultRealm() 
passman.add_password(None, theurl, username, password) 

authhandler = urllib2.HTTPBasicAuthHandler(passman) 

opener = urllib2.build_opener(authhandler) 

urllib2.install_opener(opener) 

pagehandle = urllib2.urlopen(theurl, open("mytext.xml").read()) 

あなたのコードを見ることなく、なぜあなたが400の応答を得ているのかは分かりません。いくつかのソースが含まれるように私のポストを編集中

+0

私は同意します!私があなたに言っていないなら、私が試したことを知るのは非常に難しい。謝罪いたします。私は今、メソッドの主要なグループを持っています(私はおそらくそれぞれの "メソッド"について約5つの順列を持っています)。この方法では、許可していませんでした。 Password Managerが何かをやっているようには見えませんでした。しかし、私は 'httplib2'を(投稿されたように)修正しましたので、うまくいけば別の方法を使う必要はありません。 – Oli

2

は、私は(それが比較的小さく、かなり他の人に比べてだ主な理由は)で別の亀裂を持っているだろうと思って、そのadd_credentials(..)方法はない、実際にないことにa gaping bugがあることに気づきました何でもする。

resp, content = httplib2.Http().request(URL, "POST", body=DATA, headers={ 
    "Authorization": "Basic %s" % base64.encodestring('%s:%s' %(USERNAME, PASSWORD) 
}) 

そして、これは動作します(私は urllib2で行ったように)あなたはこのようにヘッダを指定することでこの問題を回避することができます。