🎤

WhisperとGoogle Colaboratoryで音声の文字起こしをやってみた

2022/09/24に公開
27

AI 業界の進化が著しい昨今、AI の研究開発企業として名高い OpenAI から Whisper というとんでもない自動音声認識モデルの発表がありました。(2022/09/22)Whisper は 68 万時間かけてトレーニングされた自動音声認識モデルでなんとオープンソース化されています。
https://openai.com/blog/whisper/
https://github.com/openai/whisper

公開されているサンプルでは早口や K-POP、フランス語、アクセントのある会話などを問題なく処理できることが示されています。また日本語に関しても高い精度を保持していることがグラフから見て取れます。

Whisper
Whisper の GitHub リポジトリより引用

この記事で行うこと

この記事では Whisper を Google が提供する Colaboratory で利用し、文字起こしツールを作成していきたいと思います。
今回やりたいことは以下の 3 つになります。

  • 音声データから文字起こしができる
  • 文字起こしする言語が指定でき、自動翻訳が行える
  • 文字起こししたデータをテキストデータとして出力し、ダウンロードできる

この時点ですぐに試してみたいと思われてる方は実行環境を以下に作っているのでコピーして利用してみてください。

https://colab.research.google.com/gist/Kazuki-tam/04e85708e4fd1c4b8af180d317977f4d/whisper-mock-en.ipynb

Google Colaboratory の用意

まずは Google Colaboratory の環境を用意したいと思います。Google ドライブのメニューから「Google Colaboratory」を選択してください。
Google Drive

Colaboratory の編集 > ノートブックの設定を展開し、ハードウェアアクセラレータに GPU を選択します。
Colaboratoryメニュー

試しに以下のコードを実行してみてください。GPU のスペックが表示されれば OK です。

!nvidia-smi

パッケージのインストール

以下コードを実行し、このプロジェクトで必要なパッケージをインストールします。

# Install packages
!pip install git+https://github.com/openai/whisper.git

フォルダーの作成

音声ファイルをアップロードするフォルダーとダウンロード用のフォルダーを作成します。
手動で作成してもいいのですが、せっかくなのでコードベースでフォルダーを作成する処理を記載します。

import os

# Add folders
checkContentFolder = os.path.exists("content")
checkDownLoadFolder = os.path.exists("download")
if not checkContentFolder:
  os.mkdir("content")
if not checkDownLoadFolder:
  os.mkdir("download")

記載できればこちらの処理も実行しておきます。

音声ファイルのアップロード

「フォルダーの作成」まで処理を実行できていれば左ナビのフォルダーにcontentdownloadフォルダーが作成されているはずです。
フォルダーの作成

音声ファイルを用意し、contentフォルダーへアップロードしてください。ファイルはドラッグ&ドロップでもアップロードできます。

文字起こし処理

fileNameにアップロードしたファイル名を記載し、langには出力時の言語を指定してください。
ここではsample.m4aという音声ファイル名を指定し、言語をenに指定しています。この場合、日本語の音声ファイルを読み込ませると英語に翻訳されて出力されます。もうお分かりかと思いますが、日本語出力の場合はjaを指定します。

import whisper

fileName = "sample.m4a"
lang = "en"
model = whisper.load_model("base")

# Load audio
audio = whisper.load_audio(f"content/{fileName}")
audio = whisper.pad_or_trim(audio)

mel = whisper.log_mel_spectrogram(audio).to(model.device)

# Output the recognized text
options = whisper.DecodingOptions(language=lang, without_timestamps=True)
result = whisper.decode(model, mel, options)
print(result.text)

# Write into a text file
with open(f"download/{fileName}.txt", "w") as f:
  f.write(f"▼ Transcription of {fileName}\n")
  f.write(result.text)

準備ができれば試しに実行してみましょう。
文字起こしテキストが出力され、ダウンロードフォルダーにテキストファイルが作成されていれば OK です。

テキストファイルのダウンロード

最後に文字起こししたテキストファイルがダウンロードできる処理を記載してみましょう。
以下を実行すると Zip 形式でダウンロードされるはずです。

from google.colab import files
!zip -r download.zip download
files.download("download.zip")

以上でチュートリアルは完了です。もし途中で詰まったという方は以下を参考にしてみてください。
https://gist.github.com/Kazuki-tam/04e85708e4fd1c4b8af180d317977f4d

Tips

Google Colabratory では次のようにテキスト入力フォームやセレクトボックスなど UI 要素を表示できます。GUI で操作できるようになるので、非エンジニアの方にも使ってもらい易くなります。
Colaboratory

入力フォーム

#@param {type:"string"}で文字列型の入力値を受け付けます。

fileName = "sample.m4a"#@param {type:"string"}

セレクトボックス

#@param ["en", "ja"]で選択肢を表示できます。

lang = "en"#@param ["en", "ja"]

https://qiita.com/john-rocky/items/e5802cdd15dc2e34cb84

まとめ

2022 年は Stable Diffusion や Whisper の発表など AI 業界で凄まじい変化が起こってますね。
新しい情報についていくのは大変ですが、今後もできる限りキャッチアップしていきたいと思います。

TAM

Discussion

TakatsuTakatsu

とても有益な投稿で助かりました!
すばらしい情報ありがとうございます!

さっそく使用してみて恐縮ですが、最後のファイルにした際のテキストを、
文字列ごとに改行することは可能なのでしょうか?
現状、全てつながっている状況です。

プログラミング無知なためご教授いただけると幸いです。

TakatsuTakatsu

ありがとうございます!

早速試してみたいと思います。

あみあみ

初めまして、非エンジニアですが、Whisperをどうしても使いたくて
Google Colaboratoryに挑戦中です。

最終段階までできて、txtをダウンロードしてみたら、
画像のようになりました。

▼ Transcription of test.MP3

スタッフの上に、スタッフの上に、スタッフの上に、……

音声ファイルは会議で1時間以上のものです。
どうすればいいのか教えていただけないでしょうか?

あみあみ

ありがとうございます。
読ませていただきます。

あみあみ

このページのサンプルをコピーさせていただいて、使用しております。

12 mel = whisper.log_mel_spectrogram(audio).to(model.device)
の下に、
result = model.transcribe(audio, verbose=True, temperature=0.8, language=lang)
を追加しました。

temperatureの数値を0.6~1.2ぐらいに変更してみましたが、
0.8が一番合っているような感じですが、やはり26秒ぐらいしか
文字起こしができませんでした。

しかも、日本語には見えますが、話している話題とはだいぶ違う感じでした。
句読点が入っているのがちょっとうれしいです。
やはりGoogle Colaboratoryでは、30秒ぐらいが限界ですか?

Kazuki YonemotoKazuki Yonemoto

文字起こしを以下のようにループ処理にしてみると、30秒以上の音声にも対応できるかもしれません。1時間の音声では試せていないですが、数分程度であれば書き出せました。

#@title 文字起こし
import whisper

fileName = "sample.m4a"#@param {type:"string"}
lang = "ja"#@param ["ja", "en"]
model_size = "medium"#@param ["tiny", "base", "small", "medium", "large"]
model = whisper.load_model(model_size)

# オーディオファイル読み込み
audio = whisper.load_audio(f"content/{fileName}")
outputTextsArr = []

while audio.size > 0:
  tirmedAudio = whisper.pad_or_trim(audio)
  startIdx = tirmedAudio.size
  audio = audio[startIdx:]

  mel = whisper.log_mel_spectrogram(tirmedAudio).to(model.device)

  options = whisper.DecodingOptions(language=lang, without_timestamps=True)
  result = whisper.decode(model, mel, options)
  outputTextsArr.append(result.text)

outputTexts = ' '.join(outputTextsArr)
print(outputTexts)

# テキストファイル書込み
with open(f'download/{fileName}.txt', 'w') as f:
  f.write(f'▼{fileName}の書き起こし\n')
  f.write(outputTexts)
あみあみ

ビックリしました~そんなことまで簡単にできてしまうのですね。
私は、ファイルを30秒ごとに分割して・・・
なんてカメの思考でおりました。ぜひ、試してみます。

ところで、こんな記事があります。この方は14分ほど
起こしをされているようですね。
https://yasutakeyohei.com/blog/moji-okosi-whisper-surprised/

ChatGPTの案が役に立つとは思いませんでした(^^;
冗談かと思いました。。。

Kazuki YonemotoKazuki Yonemoto

厳密にいうと30秒毎に処理が切れてしまうので、途切れたタイミングで残りが0になるまで処理を繰り返しているイメージです。

  1. 音声ファイルを読み込み、30秒区画で書き起こして outputTextsArr の配列へ追加
  2. 音声ファイルがまだ続いている場合は途切れた箇所から 1. の処理を再開
  3. 最後まで処理が終わったらoutputTextsArr に格納されたの要素を全て連結
あみあみ

ChatGPTに聞いてみたらこんなお答えでした💦 あまり役には立たないかな?

あみあみ

ありがとうございます(^^)v
最初の部分で、図のようになりましたが、
そのあとだいぶ長いこと、文章化されました。
「medium」になってたので、全部ではない気がしますが、
どこまでできたか、明日検証します。

また、largeも試してみますね。
1日でできるとは思いませんでした。
おかげ様で、少しわかってきました。
ありがとうございます(o*。_。)oペコッ

あみあみ

結果をお知らせします。
・全体のデータは1:46:26
 ①mp3アップロードに10分弱
 ②文字起こしにMediumで11分、largeで16分でした。
── 音質がいいとは言えない状況なので、結構、手直しは必要です。

・largeの原稿をざっと見ましたが、句読点少な目で段落は入れてもらえませんが、
 1:39:47の会議が終わるまで、文字起こしされていました。
・会議が終わったあとの、ザワザワも多少拾っていました。
「お疲れ様」や「お腹が空いた」など。
・会場が広く多少ガサガサしている部分もあり、音質は良いとは言えなかったのですが、少しマイクから遠い人の発言も精度はなかなか良かったです。(遠すぎる人はダメです)

※ 残る課題は、固有名詞や名前、地域、専門用語、使われている略語など、わかる範囲で登録できるといいなと思いました。あと、たまに飛んでいる部分があり、半角スペースが入っていた感じです。
── 最終課題は、話者の活舌と録音状態ですね~

今回は、録音状態あまり良くなかったので、飛ばされている箇所やマイクが遠く聞き取りミスも結構あったのですが、録音状態が良ければ、かなり使えると思います♪
本当に、ありがとうございました。
最先端をお試しできてメチャクチャうれしいです!
とりあえず、ご報告まで。

Kazuki YonemotoKazuki Yonemoto

おお!なんとか使えそうなところまで行けたようで良かったです🎉
バッジもありがとうございます!🙇🏻‍♂️

あみあみ

今まで、複数の文字起こしツール試してみましたけど、これが一番早くて素晴らしいです。
今後が楽しみです~ 本当にありがとうございました。今後ともどうぞよろしくお願いします。

あみあみ

こんにちは。段落をつけてみたくて、ChatGPTに相談して、ここまで作ったのですがうまくいきません。output.txtをダウンロードすることまでできましたが、何も変化がありません💦

【Windows 11+Google Colaboratoryです】

追伸 Wordにコピーしたら「\n」がそのまま転写されていたので、

f.write(paragraph + "\n") # 段落ごとに改行する
👇
f.write(paragraph + "^p") # 段落ごとに改行する

にしたら、段落ができたものもありますが、できないものも結構あります。
また、行頭のスペースがありませんが、"^p"のあとに" " を追加しただけでは、ダメかな?

お時間のあるときに、見ていただけますか? [共有リンク]
https://colab.research.google.com/drive/1By-6ZWYIesSxdbmZO07W9tbWLfFREKfN?usp=sharing

あみあみ

ありがとうございます。まだ見ていなかったので参考にさせていただきます。

みのりんみのりん

お世話になっております。非エンジニアなのですが、参考にさせていただき、文字起こしの仕組み構築にチャレンジしています。

以下のエラーになってしまうのですが、ご助言いただくことは可能でしょうか?
念のため、model_sizeをlargeとmediumの両方試したのですが、共にエラーになってしまいました。

音声ファイルは約15分の会議音声で153MBです。


PCのスペックは、以下になります。
・Intel(R) Core(TM) i7-10510U CPU @ 1.80GHz 2.30 GHz
・実装 RAM 16.0 GB (15.8 GB 使用可能)
・システムの種類 64 ビット オペレーティング システム、x64 ベース プロセッサ
・エディション Windows 10 Enterprise

みのりんみのりん

ありがとうございます!
一応、ご提示くださったリンク先からのコピペだったのですが、エラーになってしまうのですよね。”OutOfMemoryError”という文言があるので、PCのスペックは高い方だと思うのですが、足らないということなのでしょうかね(泣)

Kazuki YonemotoKazuki Yonemoto

Colaboratoryはクラウド環境で動作するため、利用されているPCのスペック自体が影響することはないかと思います。
一度以下を試してみてください。

  1. 「ランタイム>ランタイムを接続解除して削除」をクリック
  2. 再度一からライブラリのインストール等を実行
ナルヘッソスナルヘッソス

記事を参考に文字起こしされたファイルを生成することができました。有意義な情報ありがとうございます。

2点質問があります。

もし分かればで良いので、お手すきの際にでも良いので教えていただけますと幸いです。

(1)なぜ無料なのか?
ネットで検索した情報によりopen.ai のサイトで、有料登録を行い、apiキーを手に入れました。api経由で同様の処理を行った場合は従量課金されるようですが、このgoogle colabを用いた方法では、colabの環境上にインストールして処理を行うため無料ということなのでしょうか?apiへの課金が必要と思ってopen.aiのサイトにカード登録しましたが、この方法で文字起こしが無料で実行できるなら必要ないなと思っています。

(2)録音ファイルの扱い
google colab  上にアップロードした音声ファイル自体は、あくまでcolab環境のみにストレージされるのみで、open.ai側には渡っていないと思っておいてよいでしょうか?colabに環境構築して実行しているのであくまでcolabのみに留まっている認識です。(試そうとしている音声ファイルがopen.ai 側にも渡ってもし万が一、流出したら嫌だなと思い・・・)

Kazuki YonemotoKazuki Yonemoto

(1)なぜ無料なのか?
はい、こちら書いてもらってある通りです。モデルはMITライセンスでオープンソースで公開されているのと、本来はモデルがあったとしてもそれを動かした際、確実にコストはかかっているのですが、Googleさんが寛大にも無料である程度使えるようにしてくれているために実現できています。

このgoogle colabを用いた方法では、colabの環境上にインストールして処理を行うため無料ということなのでしょうか?

https://github.com/openai/whisper
https://colab.research.google.com/signup/pricing?utm_source=dialog&utm_medium=link&utm_campaign=settings_page&hl=ja

(2)録音ファイルの扱い
これもOpenAIのリソースは利用していないので、認識の通りです。

アップロードした音声ファイル自体は、あくまでcolab環境のみにストレージされるのみで、open.ai側には渡っていないと思っておいてよいでしょうか?

ナルヘッソスナルヘッソス

当方の返事が遅くなり申し訳ありません。回答いただいた内容で疑問点が解消できました。
ご丁寧に回答くださりありがとうございました。感謝いたします。