動機
Udemyで面白そうな講座見っけ!!
うわっ!日本語字幕ないじゃん...
英語の勉強は面倒だから
日本語に翻訳しますか!!!
はじめに
筆者は激怒した。
必ず、かの邪智暴虐の王を除かなければならぬと決意した。
筆者には英語がわからぬ。
筆者は、駆け出しの新人プログラマーである。
キーボードを叩き、マウスを転がし暮して来た。
けれども面倒なことに対しては、人一倍に敏感であった。
(すみません、やってみたかっただけです)
筆者にも多少の英語の読み書き能力はあるので、まったく読めないわけじゃない。
ただしネイティブのスピードにはついていけないので逐一動画を止めて辞書片手に翻訳する必要がある。
だが、そんな非効率的なことは面倒なのでしたくない。
なので、現在の字幕を自動的に日本語に翻訳してみる。
英語字幕の取得
Udemyの多くの動画には英語字幕が存在し、動画の右下にある下記のボタンを押せばその動画のすべての字幕が表示される。
そして、講師がしゃべっている個所の字幕は薄い水色でハイライトされる。
つまり、このハイライトされている字幕を取得できれば翻訳できるはず。
スクレイピング
ネットで「Python スクレイピング」と検索したらSeleniumというモジュールがあることがわかったのでこれを使ってみる。
PythonでSeleniumを使ってスクレイピング (基礎)
上記の記事を見るに、どうやらidやclass,nameで要素を取得できるらしい。
筆者はHTMLやCSSはあまりやったことがないのでよくわからないが、
とりあえず欲しい字幕のidやclassがわかればなんとか取得できそうだ。
欲しい要素について
Udemyの適当な講座ページに移動して、デベロッパーツールでハイライトされている字幕を少し調べてみた。
ハイライトのついている字幕
<span data-purpose="cue-text" class="transcript--highlight-cue--1bEgq">Highlight text</span>
ハイライトのついていない字幕
<span data-purpose="cue-text" class="">Non highlight text</span>
実際に動画を再生しながら確認してみたら、普通の字幕とハイライトされた字幕ではclassの中が変わっていた。
どうやらハイライトされている要素のclassはtranscript--highlight-cue--1bEgq
になるらしい。
字幕取得のソースコード
実際に以下のコードを用いてSeleniumで字幕を取得した。
import time
from selenium import webdriver
from selenium.common.exceptions import NoSuchElementException
driver = webdriver.Chrome(driver_path)
driver.get(r'https://www.udemy.com/join/login-popup/?next=/home/my-courses/learning/')
last_text = None
while True:
try:
ret = driver.find_element_by_class_name('transcript--highlight-cue--1bEgq')
#0.2秒間隔で要素を取得しているので前回取得した要素と違う時だけprintする
if ret.text != last_text:
last_text = ret.text
print(last_text)
except NoSuchElementException:
#要素が見つからない場合は例外が発生するのでこの時だけ握りつぶす
pass
except Exception as e:
#それ以外の例外のときはとりあえず終了する
print(e)
print('終了します')
exit()
#0.2秒は適当
time.sleep(0.2)
無事に取得できていそうなのでとりあえず次へ。
日本語への翻訳
翻訳といえばGoogle先生。
調べてみたらPythonでGoogle翻訳が可能らしい。
上記の記事を参考にソースコードを追記した。
最終的なソースコード
import time
from selenium import webdriver
from selenium.common.exceptions import NoSuchElementException
from googletrans import Translator
driver = webdriver.Chrome(driver_path)
driver.get(r'https://www.udemy.com/join/login-popup/?next=/home/my-courses/learning/')
last_text = None
translator = Translator()
while True:
try:
ret = driver.find_element_by_class_name('transcript--highlight-cue--1bEgq')
#0.2秒間隔で要素を取得しているので前回取得した要素と違う時だけprintする
if ret.text is not None and ret.text != last_text:
last_text = ret.text
print(last_text)
print(translator.translate(last_text, dest='ja').text)
except NoSuchElementException:
#要素が見つからない場合は例外が発生するのでこの時だけ握りつぶす
pass
except Exception as e:
#それ以外の例外のときはとりあえず終了する
print(e)
print('終了します')
exit()
#0.2秒は適当
time.sleep(0.2)
最後に
とりあえず、リアルタイムで日本語に翻訳できたのでヨシ!
スクリプト実行するたびにログインする必要があったり、たまに謎の例外で終了したり、そもそもの英語字幕が間違っている影響で日本語がめちゃくちゃになったりするが、辞書片手に翻訳するよりもストレスなくできるのでこれからも使っていこうと思う。