薬剤師が教えるGoogleHomeアプリにアスナとシリカの歌声を実装する方法

# GoogleHomeアプリにストリーミングを実装したい
[薬局お茶の水ファーマシー](https://xn--t8jvd551n2lnn90a6cd.jp/)で薬局薬剤師をしながら、薬局向けサービスをつくっている薬剤師です（[株式会社ファーマクラウド](https://www.pharmacloud.co.jp/): **エンジニア募集中**）。pythonとJSがちょっとだけ書けます。薬局でこんなのがあればいいなというものがあったら、本職のエンジニアにお願いする前に簡単に動くものをつくってみるように心がけています。今回はGoogleHomeアプリでradiko的なものをつくってみたいと思い立ちました。
ということで、[色々説明は省略します](https://ja.wikipedia.org/wiki/%E3%82%BD%E3%83%BC%E3%83%89%E3%82%A2%E3%83%BC%E3%83%88%E3%83%BB%E3%82%AA%E3%83%B3%E3%83%A9%E3%82%A4%E3%83%B3)が、界隈で人気のアスナをGoogleHomeで歌わせてみることにしました。去年購入した[「劇場版ソードアート・オンライン-オーディナル・スケール-」完全生産限定版DVD](http://sao-movie.net/bddvd/)の特典CDにある「Ubiquitous dB –special ver.-」をmp3にして、自作したGoogleHomeアプリ[「ファーマシストオンライン」](https://assistant.google.com/services/a/uid/0000004ac2960a72)（注意: 薬剤師でないと使いこなせません）に実装してみた手順をつらつらと書いていきます。**技術的に難しいことは一切やってないので予めご了承ください。**
一応[「薬剤師が教えるGoogle Homeのデモ用botのつくりかた」](https://qiita.com/yousuke_yamaguchi/items/fd736f33d9b20f5853ca)の続編的な記事なので、Actions on googleとかDialogFlowとかわかんない方は、手前味噌で恐縮ですが前回記事をご覧頂くか、適宜ググっていただくようお願いします。

# Cloud Storageに音声ファイルをアップロードする
自分が管理するサーバにアップロード（https必須）しておけばいいでしょうが、せっかくなのでActions on googleで作成したプロジェクトにひもづいたGoogle Cloud Storageに保存してみましょう。[GCPのコンソール](https://console.cloud.google.com/)にアクセスして、左メニュー -> Storage -> ブラウザに移動します。
<img width="1280" alt="スクリーンショット 2018-02-10 15.38.59.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/e26a9dd8-a819-3e99-2b2c-e786874dbcf9.png">

## バケットの作成
Cloud Strageに遷移したら「バケットの作成」をクリックして、バケット名を入力、デフォルトのストレージクラス・ロケーションを指定して「作成」を押します。ちなみにバケットというのは要はフォルダのことだ、と雑に理解しています。
<img width="1280" alt="スクリーンショット 2018-02-10 15.44.23.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/acdac94f-a393-b4fe-599a-9fcc8b9ab401.png">

## アップロード
バケットが作成されました。名前をクリックしてバケット内に入ります。`<your-project>.appspot.com`と`staging.<your-project>.appspot.com`はプロジェクトを作ったときに勝手に生成されるようです。今回、この2つは無視して進めます。
<img width="1280" alt="スクリーンショット 2018-02-10 16.16.48.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/b24e52b6-78d7-62d7-8e16-4cb2553e0116.png">

当然ですが中には何もありません。用意したmp3をここにアップロードします。アップロードしたら「公開リンク」にチェックを入れておきます。これで下準備は終わりです。
<img width="1280" alt="スクリーンショット 2018-02-10 16.26.57.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/6fd475ae-d1bb-9f33-b3ed-6145fab2b548.png">


# Intentをつくる
今回はサクッと実装するのが目的なので、複雑なことはしません。Webhookは使わずにDialogflow内で完結させます。アプリを起動して、あるフレーズに反応してmp3が流れればそれでOKです。ということで、Dialogflowの左メニューのIntentsの＋をクリックして、Intent nameに適当な名前を入力します。
<img width="1280" alt="スクリーンショット 2018-02-10 16.59.54.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/ed4b978d-9e87-23f2-5861-df22639f36a7.png">

## User saysは適当に
気の利いたことはしません。「ソードアートオンラインを流して」「ソードアートオンラインを聞きたい」としました。
<img width="1280" alt="スクリーンショット 2018-02-10 17.01.16.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/2a1ad1e9-ade7-ba5b-f6a2-f05e80d11532.png">

## Text responseにSSMLを記述する
本記事の目玉はここかなと思います。SSML(speech-synthsis-markup-language)をText responseに記述します。ちなみに2018年2月10日現在で、Qiitaで`SSML`のタグが付いた記事は[この記事](https://qiita.com/megadreams14/items/d8112c21de10541e3537)と[この記事](https://qiita.com/pepo/items/cbd6037c0dbe78a3cc5b)のみ。本記事が3つ目です。関係ないですが、スマートスピーカーがもっと普及したらSSML職人なる方々が登場するんじゃないかと思っています。

### audioタグ
アプリ起動後、「ソードアートオンラインを流して」と言ったら「SAOを再生します。」と返事して曲が流れる・・・という流れを考えました。User saysで「ソードアートオンラインを流して」まではできているので、その後の返事をText responseに書いていきます。リンクは保存したmp3ファイルを右クリック -> リンクのアドレスをコピーで取得します。

```html
<speach>
  SAOを再生します。
  <audio src="https://storage.cloud.google.com/<your-bucket-name>/<your-mp3-file-name1>.mp3" />
</speach>
```
これでSAVEして、早速GoogleHomeでアプリを起動、「ソードアートオンラインを流して」と言ってみたら2点問題が。
1. そもそも再生されない。
2. SAOの記述が「さお」と発音される。

### ドメインを修正
結論から言うとドメインが違う。ブラウザでは再生されるのに理由は不明。以下のように`storage.cloud.google.com`を`storage.googleapis.com`に変更すると再生されるようになりました。

```html
<speach>
  SAOを再生します。
  <audio src="https://storage.googleapis.com/<your-bucket-name>/<your-mp3-file-name1>.mp3" />
</speach>
```
次は「さお」問題をやっつけます。

### SAOをエスエーオーと読ませる
say-asタグを使います。`<say-as interpret-as="characters">SAO</say-as>`とすると、ローマ字読みではなくアルファベットを1文字ずつ読み上げてくれるようになります。

```html
<speach>
  <say-as interpret-as="characters">SAO</say-as>を再生します。
  <audio src="https://storage.googleapis.com/<your-bucket-name>/<your-mp3-file-name1>.mp3" />
</speach>
```

### audioタグを続けたらどうなるか？
audioタグを連続したら続けて再生されるか興味が湧いたので書いてみました。結果、隙間なく再生されました。ダウンロードというより、やはりストリーミングのようです。

```html
<speach>
  <say-as interpret-as="characters">SAO</say-as>を再生します。
  <audio src="https://storage.googleapis.com/<your-bucket-name>/<your-mp3-file-name1>.mp3" />
  <audio src="https://storage.googleapis.com/<your-bucket-name>/<your-mp3-file-name2>.mp3" />
</speach>
```

### Text responseの最終型
ガーッと書いたので汚いですがこんなかんじです。
<img width="637" alt="スクリーンショット 2018-02-10 17.49.27.png" src="https://qiita-image-store.s3.amazonaws.com/0/160946/fdef1f6c-c0d8-f972-4a07-8ed65b3285d9.png">

## End conversationにチェックを入れる
曲が終わったらアプリも終了させる。というときは、一番下のGoogle Assistantの右にある矢印をクリックすると`End conversation`が出現するのでチェックを入れます。ここはお好みで。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/160946/1f020172-56d1-1738-3db8-2cb457b69efc.png)


# 最後にどうでもいい情報
ぼくはリズ推しです。

# 参考
[Actions on GoogleのSSMLドキュメント](https://developers.google.com/actions/reference/ssml)
[ねぇ Google、 Rebuild.fmを流して（がやりたかった話）](https://qiita.com/yamazako/items/8d72475012c68355162a)