Python で DeepL API を使ってみた
2020-06-17DeepL の有料プラン (DeepL Pro) が利用可能になり、 API で翻訳などの DeepL のサービスを利用することが出来るようになりました。今回は Python で DeepL の API を実行してみます。
目次
DeepL Pro
DeepL の有料プラン (DeepL Pro) には次の 3 つがあります。
- 個人向け
- Starter
 - Advanced
 - Ultimate
 
 - チーム向け
- Starter
 - Advanced
 - Ultimate
 
 - 開発者向け
- DeepL API
 
 
それぞれ次のような料金設定になっています。(単位は 円)
個人向け
| 年払い (月換算) | 月払い | |
|---|---|---|
| Starter | 9,000 (750) | 1,200 | 
| Advanced | 30,000 (2,500) | 3,800 | 
| Ultimate | 60,000 (5,000) | 7,500 | 
チーム向け
| 年払い (月換算) | 月払い | |
|---|---|---|
| Starter | 9,000 (750) | 1,200 | 
| Advanced | 30,000 (2,500) | 3,800 | 
| Ultimate | 60,000 (5,000) | 7,500 | 
※ ユーザ 1 人あたりの料金です。
開発者向け
| 月払い + 利用分 | |
|---|---|
| DeepL API | 630 | 
※ 630 円/月 の基本料金に加えて、翻訳済みのテキスト 1,000,000 文字あたり 2,500 円の料金が追加されます。
個人向け・チーム向けの各プランの機能差については公式のプラン表を参照してください。
前提
今回は DeepL Pro の 開発者向け プランを利用します。
API の実行に必要な auth_token については、プラン契約後のマイページで確認・取得済みとします。
また、今回は Python 3.x で実装します。
Python で DeepL API を試す
DeepL API では、大きく分けて 3 種類の API が用意されています。
- Translating text
 - Translating Documents (beta)
 - Other functions
 
今回はこれらのうち、 Translating text と、 Other functions に含まれる Monitoring usage の API を試してみます。
Translating text
いわゆる普通の文字列翻訳です。
エンドポイントは https://api.deepl.com/v2/translate で、メソッドは POST 、他の翻訳サービスの API とほぼ同じで、 翻訳対象のテキスト 、 ターゲットとなる言語 、 API のトークン (auth_key) が必須のパラメータとなっています。
ただしリクエスト時の Content-Type は application/x-www-form-urlencoded となっています。その他、 API の詳細については下記のドキュメントを参照してください。
Python のサンプルコードはこんな感じになります。
import argparse
import json
import os
import sys
import urllib.parse
import urllib.request
with open(os.path.dirname(os.path.abspath(__file__)) + '/../config.json') as j:
    config = json.load(j)
AUTH_KEY = config['auth_key']
DEEPL_TRANSLATE_EP = 'https://api.deepl.com/v2/translate'
T_LANG_CODES = ["DE", "EN", "FR", "IT", "JA", "ES",
                "NL", "PL", "PT-PT", "PT-BR", "PT", "RU", "ZH"]
S_LANG_CODES = ["DE", "EN", "FR", "IT",
                "JA", "ES", "NL", "PL", "PT", "RU", "ZH"]
p = argparse.ArgumentParser()
p.add_argument('-m', '--message',
               help='text to translate. (Default: Hello World.)',
               default='Hello World.')
p.add_argument('-t', '--target',
               help=f'target language code (Default: JA). allowed lang code : {str(T_LANG_CODES)}',
               default='JA')
p.add_argument('-s', '--source',
               help=f'source language code (Default: auto). allowed lang code : {str(S_LANG_CODES)}',
               default='')
args = p.parse_args()
def translate(text, s_lang='', t_lang='JA'):
    headers = {
        'Content-Type': 'application/x-www-form-urlencoded; utf-8'
    }
    params = {
        'auth_key': AUTH_KEY,
        'text': text,
        'target_lang': t_lang
    }
    if s_lang != '':
        params['source_lang'] = s_lang
    req = urllib.request.Request(
        DEEPL_TRANSLATE_EP,
        method='POST',
        data=urllib.parse.urlencode(params).encode('utf-8'),
        headers=headers
    )
    try:
        with urllib.request.urlopen(req) as res:
            res_json = json.loads(res.read().decode('utf-8'))
            print(json.dumps(res_json, indent=2, ensure_ascii=False))
    except urllib.error.HTTPError as e:
        print(e)
if __name__ == '__main__':
    t_lang = args.target
    s_lang = args.source
    text = args.message
    if t_lang not in T_LANG_CODES:
        print((
            f'ERROR: Invalid target language code "{t_lang}". \n'
            f'Alloed lang code are following. \n{str(T_LANG_CODES)}'
        ))
        sys.exit(1)
    if s_lang != '' and s_lang not in S_LANG_CODES:
        print((
            f'WARNING: Invalid source Language code "{s_lang}". \n'
            'The source language is automatically determined in this request. \n'
            f'Allowed source lang code are following. \n{str(S_LANG_CODES)} \n\n'
        ))
        s_lang = ''
    translate(text, t_lang=t_lang, s_lang=s_lang)
このスクリプト translate.py と、 auth_key を記述した config.json を下記のように配置します。
├── config.json
└── src
    └── translate.py
config.json の中身は下記のようにします。
{
  "auth_key": "your-deelpl-api-auth-token"
}
そして、次のように実行すると、翻訳結果が出力されます。
$ python3 src/translate.py -m "これは DeepL API のサンプルプログラムです。" -t EN
{
  "translations": [
    {
      "detected_source_language": "JA",
      "text": "This is a sample program for the DeepL API."
    }
  ]
}
Monitoring usage
続いては、 DeepL API の使用状況を取得する API を試してみます。
エンドポイントは https://api.deepl.com/v2/usage 、メソッドは POST 、パラメータは auth_key のみです。
Python のサンプルスクリプトは下記のようになります。
import json
import os
import urllib.parse
import urllib.request
with open(os.path.dirname(os.path.abspath(__file__)) + '/../config.json') as j:
    config = json.load(j)
AUTH_KEY = config['auth_key']
DEEPL_TRANSLATE_EP = 'https://api.deepl.com/v2/usage'
def monitor_usage():
    headers = {
        'Content-Type': 'application/x-www-form-urlencoded; utf-8'
    }
    params = {
        'auth_key': AUTH_KEY
    }
    req = urllib.request.Request(
        DEEPL_TRANSLATE_EP,
        method='POST',
        data=urllib.parse.urlencode(params).encode('utf-8'),
        headers=headers
    )
    try:
        with urllib.request.urlopen(req) as res:
            res_json = json.loads(res.read().decode('utf-8'))
            print(json.dumps(res_json, indent=2, ensure_ascii=False))
    except urllib.error.HTTPError as e:
        print(e)
if __name__ == '__main__':
    monitor_usage()
これを実行すると、現在の翻訳文字数の合計と制限文字数が取得できます。
$ python3 src/usage.py
{
  "character_count": 192,
  "character_limit": 1000000
}
まとめ
DeepL API を Python で実行してみた話でした。この記事で紹介したサンプルについては GitHub に置いています。
翻訳精度が Google 翻訳よりも優れているという評価もある DeepL ですが、有料プランとして API も利用可能になったことで Web アプリやネイティブアプリでの利用もしやすくなりました。翻訳制度に関しては翻訳する文章の性質 (専門用語が多い、話し言葉が多い など) によってしっかり吟味する必要がありますが、新しい選択肢として候補に入れておいても良さそうです。