[英]Python Requests URL with Unicode Parameters
我目前正在嘗試使用請求庫在python中使用日語字符和短語來訪問google tts url, http: //translate.google.com/translate_tts。
這是一個例子:
http://translate.google.com/translate_tts?tl=ja&q =ひとつ
但是,當我嘗試使用python請求庫下載端點返回的mp3時,生成的mp3為空。 我已經驗證我可以在使用非unicode字符(通過romanji)的請求中點擊此URL並獲得正確的響應。
這是我用來發出請求的代碼的一部分
langs = {'japanese': 'ja',
'english': 'en'}
def get_sound_file_for_text(text, download=False, lang='japanese'):
r = StringIO()
glang = langs[lang]
text = text.replace('*', '')
text = text.replace('/', '')
text = text.replace('x', '')
url = 'http://translate.google.com/translate_tts'
if download:
result = requests.get(url, params={'tl': glang, 'q': text})
r.write(result.content)
r.seek(0)
return r
else:
return url
此外,如果我在此代碼段中打印text
或url
,則在我的控制台中正確呈現假名/漢字。
編輯:
如果我嘗試對unicode進行編碼並引用它,我仍會得到相同的響應。
# -*- coding: utf-8 -*-
from StringIO import StringIO
import urllib
import requests
__author__ = 'jacob'
langs = {'japanese': 'ja',
'english': 'en'}
def get_sound_file_for_text(text, download=False, lang='japanese'):
r = StringIO()
glang = langs[lang]
text = text.replace('*', '')
text = text.replace('/', '')
text = text.replace('x', '')
text = urllib.quote(text.encode('utf-8'))
url = 'http://translate.google.com/translate_tts?tl=%(glang)s&q=%(text)s' % locals()
print url
if download:
result = requests.get(url)
r.write(result.content)
r.seek(0)
return r
else:
return url
哪個返回:
http://translate.google.com/translate_tts?tl=ja&q=%E3%81%B2%E3%81%A8%E3%81%A4
這看起來應該有效,但事實並非如此。
編輯2:
如果我嘗試使用urlllb / urllib2,我會收到403錯誤。
編輯3:
因此,似乎此問題/行為僅限於此端點。 如果我嘗試以下URL,則使用不同的端點。
http://www.kanjidamage.com/kanji/13-un-%E4%B8%8D
從請求和我的瀏覽器中,我得到相同的響應(它們匹配)。 如果我甚至嘗試ascii字符到服務器,像這個網址。
http://translate.google.com/translate_tts?tl=ja&q=sayonara
我也得到相同的反應(他們再次匹配)。 但是如果我嘗試將unicode字符發送到此URL,我會在瀏覽器上獲得正確的音頻文件,但不是來自發送音頻文件但沒有聲音的請求。
http://translate.google.com/translate_tts?tl=ja&q=%E3%81%B2%E3%81%A8%E3%81%A4
那么,似乎這種行為僅限於Google TTL網址?
用戶代理可以是問題的一部分,但是,在這種情況下不是。 translate_tts
服務拒絕(使用HTTP 403)一些用戶代理,例如任何以Python
, curl
, wget
和其他可能開始的用戶代理。 這就是為什么在使用urllib2.urlopen()
時看到HTTP 403響應的原因 - 它將用戶代理設置為Python-urllib/2.7
(版本可能會有所不同)。
您發現將用戶代理設置為Mozilla/5.0
解決問題,但這可能有效,因為API可能會假定基於用戶代理的特定編碼。
您實際應該做的是使用ie
字段顯式指定URL字符編碼。 您的網址請求應如下所示:
http://translate.google.com/translate_tts?ie=UTF-8&tl=ja&q=%E3%81%B2%E3%81%A8%E3%81%A4
注意ie=UTF-8
明確設置URL字符編碼。 規范確實聲明UTF-8是默認值,但似乎並不完全正確,因此您應該始終在請求中設置ie
。
API支持漢字,平假名和片假名(可能還有其他?)。 這些URL都產生“nihongo”,盡管為平假名輸入產生的音頻與其他視頻的變化略有不同。
import requests
one = u'\u3072\u3068\u3064'
kanji = u'\u65e5\u672c\u8a9e'
hiragana = u'\u306b\u307b\u3093\u3054'
katakana = u'\u30cb\u30db\u30f3\u30b4'
url = 'http://translate.google.com/translate_tts'
for text in one, kanji, hiragana, katakana:
r = requests.get(url, params={'ie': 'UTF-8', 'tl': 'ja', 'q': text})
print u"{} -> {}".format(text, r.url)
open(u'/tmp/{}.mp3'.format(text), 'wb').write(r.content)
之前我用這個小方法來幫助我使用UTF-8編碼。 我遇到了將cyrllic和CJK語言打印到csvs的問題,這就是訣竅。
def assist(unicode_string):
utf8 = unicode_string.encode('utf-8')
read = utf8.decode('string_escape')
return read ## UTF-8 encoded string
另外,請確保在.py的開頭有這兩行。
#!/usr/bin/python
# -*- coding: utf-8 -*-
第一行只是一個很好的python習慣,它指定在.py上使用哪個編譯器(實際上只有在你的機器上加載了多個版本的python時才有用)。 第二行指定python文件的編碼。 這里給出了稍長的答案。
將User-Agent設置為Mozilla / 5.0可修復此問題。
from StringIO import StringIO
import urllib
import requests
__author__ = 'jacob'
langs = {'japanese': 'ja',
'english': 'en'}
def get_sound_file_for_text(text, download=False, lang='japanese'):
r = StringIO()
glang = langs[lang]
text = text.replace('*', '')
text = text.replace('/', '')
text = text.replace('x', '')
url = 'http://translate.google.com/translate_tts'
if download:
result = requests.get(url, params={'tl': glang, 'q': text}, headers={'User-Agent': 'Mozilla/5.0'})
r.write(result.content)
r.seek(0)
return r
else:
return url
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.