Edited at

Cloud Functions for Firebase の関数をスケジューラから定期的に呼び出す

Firebase、、イイですね。。とくに Cloud Functions for Firebase とてもよいです。AWS Lambdaにくらべてシンプルですし。。

さて今回は、Firebaseに登録した関数を定期的に呼び出してみます。

FirebaseとGoogle Cloud Platform をさわれる環境を構築する で作った環境をつかって、Cloud Functions for Firebaseに登録した関数を、Cloud Scheduler ベータ版 というGCPのスケジューラから定期的に呼び出してみます。

Cloud Functions for Firebase を呼び出すには Cloud Functions for Firebase でジョブをスケジューリング(cron)する にある「App EngineのCron機能を使う」ってBest Practice?があるみたいなのですが、2019/02/04時点ではCloud Scheduler ってのがベータ版ながらあるので、今回はそれをつかいます。

具体的には「testTopic」へのPublishに反応する関数を作成し、そこで実行したいロジックを呼び出します。そして、スケジューラからそのTopicへのPublishを定期的に行うことで、関数の定期実行を実現します。


環境

FirebaseとGoogle Cloud Platform をさわれる環境を構築する で環境を作るとこんな感じになってるとおもいます。

$ tree -a

.
├── .firebaserc
├── .gitignore
├── README.md
├── firebase.json
└── functions
├── .eslintrc.json
├── .gitignore
├── package.json
├── src
│ └── index.ts
└── tsconfig.json

もしくはGithubにコードをあげてあるので、そちらからコード取得してください。環境構築は以下の通り:

$ git clone --branch pub_sub_trigger https://github.com/masatomix/fb_function_samples.git

$ cd fb_function_samples/functions/
$ npm install
$ cd ../


やってみる


呼び出したい関数を作成してデプロイする

まずは実行したいロジックを作成します。


src/logic.ts

export function want_to_execute() {

console.log('実行したいロジック!')
}

つづいて index.tsにPub/Subトリガーの関数を定義して、そこで上記ロジックを呼び出します。


src/index.ts

import * as functions from 'firebase-functions'

// // Start writing Firebase Functions
// // https://firebase.google.com/docs/functions/typescript
//
// export const helloWorld = functions.https.onRequest((request, response) => {
// response.send("Hello from Firebase!");
// });

import * as logic from './logic'

export const helloPubSub = functions.pubsub
.topic('testTopic').onPublish(message => {
logic.want_to_execute()
})


いつものコマンドでFirebaseへ関数をデプロイします。

$ firebase deploy --only functions

✔ functions: functions folder uploaded successfully
i functions: updating Node.js 8 function helloPubSub(us-central1)...
✔ functions[helloPubSub(us-central1)]: Successful update operation.

✔ Deploy complete!
Please note that it can take up to 30 seconds for your updated functions to propagate.


スケジューラを設定する

つづいてスケジューラにスケジュールを登録します。もちろん画面からも登録できるのですが、今回はコマンドラインからやってみましょう。。

gcloud beta scheduler jobs create pubsub を参考にコマンドを打ってみます

$ gcloud beta scheduler jobs list

ID LOCATION SCHEDULE (TZ) TARGET_TYPE STATE
test us-central1 * * * * * (Asia/Tokyo) HTTP ENABLED <- 前に追加していたヤツ
topicTest us-central1 * * * * * (Asia/Tokyo) Pub/Sub ENABLED <- 前に追加していたヤツ
$

$ gcloud beta scheduler jobs create pubsub testJob \
--topic testTopic \
--message-body='test' \
--schedule '* * * * *' \
--time-zone='Asia/Tokyo'

name: projects/xxxxx-xxxxxxx/locations/us-central1/jobs/testJob
pubsubTarget:
data: dGVzdA==
topicName: projects/xxxxx-xxxxxxx/topics/testTopic
retryConfig:
maxBackoffDuration: 3600s
maxDoublings: 16
maxRetryDuration: 0s
minBackoffDuration: 5s
schedule: '* * * * *'
state: ENABLED
timeZone: Asia/Tokyo
userUpdateTime: '2019-02-03T15:55:14Z'

$ gcloud beta scheduler jobs list
ID LOCATION SCHEDULE (TZ) TARGET_TYPE STATE
test us-central1 * * * * * (Asia/Tokyo) HTTP ENABLED
topicTest us-central1 * * * * * (Asia/Tokyo) Pub/Sub ENABLED
testJob us-central1 * * * * * (Asia/Tokyo) Pub/Sub ENABLED ←追加された!
$

おおお、追加されたようですね。Scheduleは「* * * * *」で登録したので、1分おきにPublishが行われるはずです。

ちなみに message-body はカラだと怒られたので、適当に値を入れてます。

また、デプロイされた関数がListenしているTopic「testTopic」は、関数をデプロイしたときに自動で作成されるようです。

画面でも登録を確認してみましょう。

https://console.cloud.google.com/cloudscheduler にアクセスしてみると、、、

image.png

確かに追加されてますね。よさそうです。

さて、最後にちゃんと定期的に実行されているか、関数のコンソールログを見てみましょう。

GCPの画面のメニューから、Cloud Functionsを選択 。

image.png

関数の一覧が表示されるので「helloPubSub」をクリック。

image.png

次の画面の右上に「ログの表示」とあるのでクリックすると、、、、

image.png

たしかに1分ごとに関数が呼び出されているようですね!!


まとめ

はじめFirebase Functionsのトリガーに「時間トリガー」がなかったので、定期実行できないじゃん、っておもったのですが、Cloud Schedulerという機能が追加されたので、コレをつかえば問題なさそうです。

おつかれさまでした。


関連リンク