認証、JSON RPCとPython
皆さんこんにちは、
HTTP認証でjsonrpcか同様のものを動作させている人はいるだろうか? PythonからJSON-RPCでBitcoinサーバーにアクセスしようとしているのだが、当然ながら新しいサーバーから認証エラーが出ている。
意外にもこれについてオンラインであまり情報が見つからなかったので、ここで聞いてみようと思った。
情報ありがとう、興味深いが、自分の問題とは違うようだ。
以下が現在のコードだ(Google App Engineで動作)
postdata = jsonrpc.dumps({“method”: ‘getbalance’, “params”:”,‘id’:‘jsonrpc’})
req = urllib2.Request(‘http://127.0.0.1:8332’, postdata)
userpass = ‘user:a’.encode(‘base64’)[:-1]
authheader = “Basic %s” % userpass
req.add_header(“Authorization”,authheader)
handle = urllib2.urlopen(req)
json_response = handle.read()
self.response.out.write (json_response)
これはHTTPError: HTTP Error 500: Internal Server Errorを返す。
GAEのローカルPythonスクリプトからだ。
以下を使ってもpostdata = jsonrpc.dumps([{“jsonrpc”: “2.0”,“method”: ‘getbalance’, “params”:”,‘id’:‘1’}])
同じ結果になる。
情報ありがとう、興味深いが、自分の問題とは違うようだ。
以下が現在のコードだ(Google App Engineで動作)
postdata = jsonrpc.dumps({“method”: ‘getbalance’, “params”:”,‘id’:‘jsonrpc’}) req = urllib2.Request(‘
http://127.0.0.1:8332’, postdata) userpass = ‘user:a’.encode(‘base64’)[:-1] authheader = “Basic %s” % userpass req.add_header(“Authorization”,authheader) handle = urllib2.urlopen(req) json_response = handle.read() self.response.out.write (json_response)これはHTTPError: HTTP Error 500: Internal Server Errorを返す。
これはbitcoinの確認済みバグだ。
bitcoinはContent-Lengthヘッダーを必要とするが、いくつかのJSON-RPCライブラリはそれを提供しない。Content-Lengthヘッダーがない場合、bitcoinは500 Internal Server Errorを返す。
bitcoinはContent-Lengthヘッダーを必要とするが、いくつかのJSON-RPCライブラリはそれを提供しない。Content-Lengthヘッダーがない場合、bitcoinは500 Internal Server Errorを返す。
どのJSONライブラリがContent-Lengthを提供しないか、もう少し具体的に教えてもらえないか? ドキュメントに記載できると助かる。
JGジェフ・ガージックの投稿(2010年8月3日18:09 UTC)bitcoinはContent-Lengthヘッダーを必要とするが、いくつかのJSON-RPCライブラリはそれを提供しない。Content-Lengthヘッダーがない場合、bitcoinは500 Internal Server Errorを返す。
どのJSONライブラリがContent-Lengthを提供しないか、もう少し具体的に教えてもらえないか? ドキュメントに記載できると助かる。
CPAN(Perl)で利用可能な2つのJSON RPCライブラリと、動作を検証するために私がローカルで書いた準拠Cライブラリだ。
bitcoindのJSON-RPCで気づいた別の問題として、デフォルトでユーザーが設定されておらず、PHPのfopen()はユーザーが指定されていないと認証情報を送信しようとしない。
例えば、このURLは動作しない: しかしこちらは動作する:
PHPと連携させるために、ノードのbitcoin.confファイルに”rpcuser”を設定する必要があった。
こちらでも同じ問題に遭遇した:ユーザーが設定されていない場合にどのような認証文字列が受け入れられるべきかのドキュメントがない。
将来のバージョンではrpcuserとrpcpasswordを必須にするのが最善だと思う。これはHTTP Authで一般的に期待されていることだ。
JGジェフ・ガージックの投稿(2010年8月3日18:09 UTC)bitcoinはContent-Lengthヘッダーを必要とするが、いくつかのJSON-RPCライブラリはそれを提供しない。Content-Lengthヘッダーがない場合、bitcoinは500 Internal Server Errorを返す。
どのJSONライブラリがContent-Lengthを提供しないか、もう少し具体的に教えてもらえないか? ドキュメントに記載できると助かる。
Content-Lengthパラメーターがない場合のサポートを試みるべきだろう。ただし、ストリームを全面的に書き換えたくはない。1文字ずつ読む必要があっても構わない。
編集:つまり、Content-Lengthをサポートしないライブラリが実際にある場合の話だが。
CPAN(Perl)で利用可能な2つのJSON RPCライブラリと、動作を検証するために私がローカルで書いた準拠Cライブラリだ。
PerlのLWPモジュールは間違いなくContent-Lengthヘッダーを設定している。HTTP 1.0では必須で、HTTP 1.1の仕様でもクライアントは「SHOULD」設定すべきとされているので、設定していなかったらむしろ驚きだ。
少し格闘した末に、CPANの最初のJSON::RPCライブラリで動かすことができた:
use JSON::RPC::Client;
use Data::Dumper;
my $client = new JSON::RPC::Client;
$client->ua->credentials(
'localhost:8332', 'jsonrpc', 'my rpcusername' => 'my rpcpassword' # Replace with real user/pass
);
my @foo = $client->ua->credentials('localhost:8332', 'jsonrpc');
print "@foo\n";
my $uri = 'http://localhost:8332/';
my $obj = {
method => 'getinfo',
params => [],
};
my $res = $client->call( $uri, $obj );
if($res){
if ($res->is_error) {
print "Error : ", $res->error_message;
}
else {
print Dumper($res->result);
}
}
else {
print $client->status_line;
}
苦労したのはrealmを ‘jsonrpc’ に設定する点だ(ここがうるさい)。これはwikiにドキュメントとして書いておく。
Fedora 12とFedora 13ではContent-Lengthが送られていないのは間違いない。さらに調査する。RHEL/CentOSも確認する。