🗣️
AWS re:Invent 2023のために英日同時通訳アプリを試作した
概要
AWS re:Invent 2023に行くけど英語に自信がない人(自分)用に同時通訳アプリを作りました。
趣味の延長で試作したプロトタイプ版なので改善点はいっぱいありますが、「英語音声から日本語訳文に変換する」という最低限の部分は実装済みです。
※もっとよくしたいところ
を後述しています
アーキテクチャ
解説
画面
画面はこんな感じ。
STARTボタンを押すと録音が開始されます。
翻訳結果と英語原文を上下でリアルタイムに表示します。
使用技術
- AWS
- Amazon Transcribe
- Amazon Translate
- Amazon S3
- AWS Lambda
- Application
- Go(gin)
- HTML/CSS/JS(Vanilla JS)
ソースコードはこちら↓
ロジック
ロジックの流れをざっくり記載します。
1.JSで音声データを取得してWebSocket通信でバックエンドに送信
let mediaRecorder;
document.querySelector("#startRecord").addEventListener("click", function () {
navigator.mediaDevices.getUserMedia({ audio: true })
.then(stream => {
mediaRecorder = new MediaRecorder(stream);
audioChunks = [];
mediaRecorder.ondataavailable = event => {
ws.send(event.data);
// WebSocket.OPEN: 1
if (ws.readyState === 1) {
ws.send(event.data);
console.log("send audio data");
} else {
console.log("Failed to send audio data.");
}
};
startRecording();
getTranslateResult();
getTranscribeResult();
});
});
2.バックエンド処理で.webm → .mp3に変換
func toMp3(inputFile string) ([]byte, error) {
cmd := exec.Command("ffmpeg", "-i", inputFile, "-f", "mp3", "-")
var out bytes.Buffer
var stderr bytes.Buffer
cmd.Stdout = &out
cmd.Stderr = &stderr
if err := cmd.Run(); err != nil {
return nil, fmt.Errorf("error encoding audio: %v (stderr: %s)", err, stderr.String())
}
return out.Bytes(), nil
}
3.S3にmp3をアップロード
func uploadToS3(sess *session.Session, bucket, key string, data []byte) error {
s3Svc := s3.New(sess)
input := &s3.PutObjectInput{
Bucket: aws.String(bucket),
Key: aws.String(key),
Body: bytes.NewReader(data),
}
_, err := s3Svc.PutObject(input)
return err
}
4.mp3をAmazon Transcribeが解析して英文文字列のJSONに変換
5.英文JSONをAmazon Translateが日本語に翻訳して結果をS3にアップロード(JSON)
もっとよくしたいところ
-
MediaRecorder.start(timeslice)
を使って連続的に録音処理をしたい- 現アプリはtimesliceなしで
MediaRecorder.start()
→MediaRecorder.stop()
を5秒毎に繰り返して録音を実施している - これではstop →startの間の数ミリ秒間の音声が拾えない
-
MediaRecorder.start(timeslice)
でtimeslice秒ごとに音声データを区切ってPOSTできそう - しかし、区切ると音声データ(.webmファイル)のヘッダー情報が2個目以降欠損する
- ヘッダがないとバックエンド(Go)で解析に失敗する
- 参考:https://www.slideshare.net/slideshow/embed_code/key/3dL9PrhnQ3hVQ7
- 現アプリはtimesliceなしで
- 翻訳結果の取得をAPI GatewayのWebSocket APIでやりたい
- 現アプリは定期的にS3を見に行っている
- WebSocket通信で翻訳結果到着を検知してリアルタイムに取得したい
- API Gateway力が足らんかった
- GoアプリをAWSサービス上で動かしたい
- 現状localhostで動かすことしかできない
- ECSで動かしてみたい
- テストコード書きたい
- 書け
Discussion