yagish履歴書で、お問合せ用にGoogleフォームは設置しているけど、もっと気軽な問合せフォームみたいのを作りたい。
でも、メールで送るのも、受け取るのもちょっと面倒なので、チャットに来ればいいやと考えた。
Slackも使っているけど、会社でG Suiteを使っていることもあり、せっかくなのでHangouts Chatを使ってみることにした。
全体の流れとしては下記のような感じ。
1. Firebaseでログインしているユーザーがテキストフォームに書き込んで送信
2. Firestoreの新規ドキュメントに問い合わせ内容を書き込む
3. Hangouts ChatのWEB Hook URLを取得。
4. FunctionsのonCreateで2を受け取ってChatのAPIにPOSTする。
1はyagish履歴書で出来ているので省く。ほんとはログインなしでも書き込みさせたいけど、スパム対策とユーザーごとのディレクトリで管理しているのでそれをそのまま使いたいため、ログイン必須にする。
またログイン必須にすると名前とかメールアドレスを入れなくていいので、メッセージ蘭だけになり、シンプルにできる利点も。
2. Firestoreへの書き込み
普通にaddする。
Cloud Firestore にデータを追加する | Firebase
以下疑似コード。
今後運営からお返事を書くかもしれないので、データにはユーザー情報も持たせておく。あと最新順に並び替えるようにtimestampも持たせておく。
const postCardData = { content: message, author: { uid: user.uid, email: user.email }, timestamp: firebase.firestore.FieldValue.serverTimestamp() } // {uid}は仮、ちゃんと入れないとダメ db.collection('/userdir/{uid}/postcards/').add(postCardData)
4. FunctionsのonCreateで2を受け取ってChatのAPIにPOST
公式通り、Firebase Functions環境を準備する。
Firebase Cloud Functions | Firebase
Hangouts ChatのWEB Hookについては公式参照。
Using incoming webhooks | Hangouts Chat API | Google Developers
リクエストにはrequestを使った。
www.npmjs.com
jsonという専用パラメータで送るのが分からずしばらくハマった。
jsonにオブジェクトを入れるとstringifyして送ってくれる。
まだログもいろいろ出してて、完成じゃないけどコードは下記のような感じ。
本文を作るところは何かしらテンプレート的なものを使った方がよさそう。
const functions = require('firebase-functions'); const request = require('request'); // https://firebase.google.com/docs/functions/manage-functions?hl=ja const runtimeOptions = { timeoutSeconds: 30, memory: '128MB' } const WEBHOOK_URL = "https://chat.googleapis.com/v1/spaces/XXXXXXXXXXXXXXXXXXXXXXX" exports.sendPostCard2Chat = functions .runWith(runtimeOptions) .firestore .document('/userdir/{uId}/postcards/{postCardId}') .onCreate((snap, context) => { console.log('snap', snap) console.log('context', context) const val = snap.data(); console.log('bodyText', bodyText) const options = { url: WEBHOOK_URL, headers: { 'Content-Type': 'application/json; charset=UTF-8' }, json: {text: 'email: ' + val.author.email + ' \n' + 'uid: ' + val.author.uid + ' \n' + 'site: ' + val.site + ' \n' + 'message:\n' + val.content} }; request.post(options, (e, r, body) => { console.log('callback e:', e) console.log('callback r:', r) console.log('callback body:', body) } ) });
ハマりどころとして、タイムアウトとか、メモリ、リージョンもこのコード上で指定できるが、リージョンを日本にしてしまうと動かなかった。
おそらくFirestoreがus-centralだからかなぁと思ったがよく調べてない。
これで、いまどきのサーバーレス&チャットで簡単なメッセージフォームができた。
データもチャットだけでなくFirestoreにも残せるので夢が広がる。
問題としてはこれだけのために普段使ってないHangouts Chatを開かねばいけないところ。
あと注意点としてFirestoreもFunctionsもβなので、大事なお問合せには使わない方がよさそう。
Vue.jsとFirebaseで作るミニWebサービス (技術書典シリーズ(NextPublishing))
- 作者: 渡邊達明
- 出版社/メーカー: インプレスR&D
- 発売日: 2018/07/13
- メディア: Kindle版
- この商品を含むブログを見る