さて、最初に、あなたの質問に直接答えないが、役立つかもしれないいくつかのポイント:
1)urllib2.urlopenを呼び出してから、返されたaddinfourlオブジェクトを読み取るまで待つ必要はないと確信しています。http://docs.python.org/library/urllib2.html#examplesの例には、そのようなスリープは含まれていません。
2)
json.loads(urlobject.read().decode("utf-8"))
単純化して
json.load(urlobject)
これはよりシンプルで読みやすいです。基本的に、.loadは引数としてファイルのようなオブジェクトを取りますが、.loadsは文字列を取ります。utf-8からデータをデコードするには、最初にデータをread()する必要があると思われたかもしれませんが、.loadはデフォルトで、読み取っているオブジェクトがasciiまたはutf-であると想定しているため、これは実際には問題ありません。 8エンコードされています(http://docs.python.org/library/json.html#json.loadを参照)。
3)現在の目的には関係ないかもしれませんが、ここでの例外処理は悪いと思います。「try:」ブロック中に問題が発生した場合、変数jsondataは割り当てられていません。次に、try / exceptionブロックの終了後にそれを返そうとすると、割り当てられていない変数を使用しようとしたためにNameErrorが発生します。つまり、アプリケーション内の他の関数がreturnJSONQuestionを呼び出して例外が発生した場合、外部関数が認識するのは元の例外ではなくNameErrorであり、外部関数が生成するトレースバックはその場所を指しません。本当の問題が発生しました。これは、何がうまくいかなかったかを理解しようとするときに、簡単に混乱を引き起こす可能性があります。したがって、ここでの「を除く」すべてのブロックが「レイズ」で終了した方がよいでしょう。
4)Pythonでは、関数がdocstringとして何をするか( http://www.python.org/dev/peps/pep-0257/#what-is-a-docstringを参照)というコメントを付けることをお勧めします。関数の上のコメントとして。
とにかく、実際にあなたの質問に答えるために...
さまざまな理由でURLを開こうとすると、一見ランダムなURLErrorが発生する可能性があります。リクエストの処理中にサーバーにバグがあった可能性があります。接続に問題があり、一部のデータがドロップされた可能性があります。管理者の1人が設定を変更したり、更新をプッシュしたりしているときに、サーバーが数秒間ダウンした可能性があります。多分完全に何か他のもの。少しWeb開発を行った後、一部のサーバーは他のサーバーよりもはるかに信頼性が高いことに気付きましたが、ほとんどの実際の目的では、おそらく理由を心配する必要はないと思います。最も簡単な方法は、成功するまでリクエストを再試行することです。
上記のすべてを念頭に置いて、以下のコードはおそらく必要なことを実行します。
def returnJSONQuestion(questionId):
"""return the json question for given question id"""
url = 'http://answers.yahooapis.com/AnswersService/V1/getQuestion?appid=APPIDREMOVED8&question_id={0}&output=json'
format_url = url.format(questionId)
try:
request = urllib2.Request(format_url)
# Try to get the data and json.load it 5 times, then give up
tries = 5
while tries >= 0:
try:
urlobject = urllib2.urlopen(request)
jsondata = json.load(urlobject)
print jsondata
return jsondata
except:
if tries == 0:
# If we keep failing, raise the exception for the outer exception
# handling to deal with
raise
else:
# Wait a few seconds before retrying and hope the problem goes away
time.sleep(3)
tries -= 1
continue
except urllib2.HTTPError, e:
print e.code
logging.exception("Exception")
raise
except urllib2.URLError, e:
print e.reason
logging.exception("Exception")
raise
except(json.decoder.JSONDecodeError,ValueError):
print 'Question ID ' + questionId + ' Decode JSON has failed'
logging.info("This qid didn't work " + questionId)
raise
お役に立てれば!プログラムでさまざまなWebリクエストを作成する場合は、この「例外の再試行リクエスト」ロジックをどこかの関数に抽象化して、定型的な再試行を行う必要がないようにすることをお勧めします。ロジックが他のものと混ざり合っています。:)