関数のデプロイとランタイム オプションを管理する

Firebase CLI コマンドを使用するか、関数のソースコードでランタイム オプションを設定することにより、関数をデプロイ、削除、変更できます。

関数をデプロイする

関数をデプロイするには、次の Firebase CLI コマンドを実行します。

$ firebase deploy --only functions

デフォルトでは、Firebase CLI によって index.js 内のすべての関数が同時にデプロイされます。プロジェクトに 6 つ以上の関数が含まれている場合は、特定の関数名で --only フラグを使用して、編集した関数のみをデプロイすることをおすすめします。このようにして特定の関数をデプロイすると、デプロイ プロセスが迅速化され、デプロイの割り当ての問題を回避できます。次に例を示します。

$ firebase deploy --only functions:addMessage,functions:makeUppercase

多くの関数をデプロイすると、標準の割り当てを超過し、HTTP 429 または 500 エラー メッセージが表示されることがあります。これを解決するには、10 個以下のグループで関数をデプロイします。

使用可能なコマンドの一覧については、Firebase CLI リファレンスをご覧ください。

デフォルトでは、Firebase CLI によって functions/ フォルダ内でソースコードが検索されます。別のフォルダを指定するには、firebase.json に次の行を追加します。

"functions": {
  "source": "another-folder"
}

関数を削除する

過去にデプロイした関数は、次の 2 つの方法で削除できます。

  • functions:delete を使用して Firebase CLI で明示的に行う
  • Firebase コンソールの関数リストにあるコンテキスト メニューを使用して明示的に削除する
  • デプロイの前に index.js から関数を削除して 暗黙的に行う

本番環境から関数を削除しようとするたびに、削除操作の確認を求められます。

Firebase CLI で明示的に関数を削除する方法では、複数の引数だけでなく関数のグループもサポートされ、特定のリージョンで実行されている関数を指定できます。また、確認メッセージをオーバーライドすることもできます。

# Delete all functions that match the specified name in all regions.
$ firebase functions:delete myFunction

# Delete a specified function running in a specific region.
$ firebase functions:delete myFunction --region us-east-1

# Delete more than one function
$ firebase functions:delete myFunction myOtherFunction

# Delete a specified functions group.
$ firebase functions:delete groupA

# Bypass the confirmation prompt.
$ firebase functions:delete myFunction --force

暗黙的に関数を削除する方法では、firebase deploy により index.js が解析され、ファイルから削除されたすべてのファンクションが本番環境から削除されます。

関数の名前、リージョン、トリガーを変更する

本番環境のトラフィックを処理している関数のリージョンまたはトリガー(またはそれらの名前)を変更する場合は、このセクションの手順に沿って、変更中にイベントが失われないようにしてください。以下の手順を行う前に、まず関数がべき等であることを確認します。これは、関数の新旧両方のバージョンが変更中に同時に実行されるためです。

関数の名前を変更する

関数の名前を変更するには、関数の名前を変更した新しいバージョンを index.js に作成してから、2 つの別々のデプロイ コマンドを実行します。最初のコマンドは新しい名前の関数をデプロイし、2 番目のコマンドは以前にデプロイされたバージョンを削除します。たとえば、webhook という関数の名前を webhookNew に変更する場合は、次のようにコードを変更します。

// before
const functions = require('firebase-functions');

exports.webhook = functions.https.onRequest((req, res) => {
    res.send("Hello");
});

// after
const functions = require('firebase-functions');

exports.webhookNew = functions.https.onRequest((req, res) => {
    res.send("Hello");
});

続いて、次のコマンドを実行して新しい関数をデプロイします。

# Deploy new function called webhookNew
$ firebase deploy --only functions:webhookNew

# Wait until deployment is done; now both webhookNew and webhook are running

# Delete webhook
$ firebase functions:delete webhook

関数のリージョンを変更する

本番環境トラフィックを処理している関数のリージョンを変更する場合は、以下の手順を順番に実施すると、イベントが失われないようにできます。

  1. 関数の名前とリージョンを任意に変更します。
  2. 名前を変更した関数をデプロイします。これにより、一時的に両方のリージョンで関数が実行されます。
  3. 前の関数を削除します。

たとえば、現時点でデフォルトの関数リージョン us-central1webhook という関数があり、それを asia-northeast1 に移行する場合は、ソースコードを変更して関数の名前を変更してからリージョンを変更する必要があります。

// before
const functions = require('firebase-functions');

exports.webhook = functions
    .https.onRequest((req, res) => {
            res.send("Hello");
    });

// after
const functions = require('firebase-functions');

exports.webhookAsia = functions
    .region('asia-northeast1')
    .https.onRequest((req, res) => {
            res.send("Hello");
    });

続いて、次のコマンドを実行してデプロイします。

$ firebase deploy --only functions:webhookAsia

これで 2 つの同じ関数が実行されます。webhookus-central1 で実行され、webhookAsiaasia-northeast1 で実行されます。

次に、webhook を削除します。

$ firebase functions:delete webhook

これで、関数は asia-northeast1 で実行される webhookAsia だけになります。

関数のトリガータイプを変更する

Cloud Functions for Firebase デプロイの開発の進展に応じて、さまざまな理由により関数のトリガータイプを変更する必要が生じる場合があります。たとえば、次のような必要が生じることがあります。

  • 従来のストレージの onChange イベントから onFinalizeonDeleteonArchiveonMetadataUpdate に変更する(詳しくは、ベータ版から v1 または v2 へのアップグレード ガイドをご覧ください)。
  • あるタイプの Firebase Realtime Database または Cloud Firestore イベントから別のイベントに変更する(汎用の onWrite イベントをきめ細かな onCreate イベントに変更するなど)。

ソースコードを変更して firebase deploy を実行するだけでは、関数のイベントタイプを変更できません。エラーを回避するために、次の手順に従って関数のトリガータイプを変更します。

  1. 目的のトリガータイプを使用する新しい関数が含まれるように、ソースコードを変更します。
  2. 関数をデプロイします。これにより、一時的に新旧両方の関数が実行されます。
  3. Firebase CLI を使用して、本番環境から古い関数を明示的に削除します。

たとえば、従来の onChange イベントタイプを使用する objectChanged 関数があり、それを onFinalize に変更する場合は、まず関数の名前を変更して、onFinalize イベントタイプを使用するように編集します。

// before
const functions = require('firebase-functions');

exports.objectChanged = functions.storage.object().onChange((object) => {
    return console.log('File name is: ', object.name);
});

// after
const functions = require('firebase-functions');

exports.objectFinalized = functions.storage.object().onFinalize((object) => {
    return console.log('File name is: ', object.name);
});

続いて、古い関数を削除する前に、先に次のコマンドを実行して新しい関数を作成します。

# Create new function objectFinalized
$ firebase deploy --only functions:objectFinalized

# Wait until deployment is done; now both objectChanged and objectFinalized are running

# Delete objectChanged
$ firebase functions:delete objectChanged

ランタイム オプションを設定する

Cloud Functions for Firebase では、ランタイム オプション(Node.js ランタイムのバージョン、関数ごとのタイムアウト、メモリ割り当てなど)を選択できます。

Node.js のバージョンを設定する

Firebase SDK for Cloud Functions 2.0.0 以降では、Node.js ランタイムを選択できます。プロジェクト内のすべての関数を、サポートされている以下のいずれかの Node.js バージョンに対応するランタイム環境のみで実行するように選択できます。

  • Node.js 12(ベータ版)
  • Node.js 10

  • Node.js 8(2020 年 6 月 8 日に非推奨) Node.js 8 関数は、2020 年 2 月 15 日以降はデプロイできなくなります。すでにデプロイされている Node.js 8 関数は、2021 年 3 月 15 日をもって実行できなくなります。Node.js 8 ランタイムに関数をデプロイしている場合は、Node.js 10 ランタイムにアップグレードすることをおすすめします。

Node.js のバージョンを設定するには:

初期化時に functions/ ディレクトリに作成された package.json ファイルの engines フィールドにバージョンを設定します。たとえば、バージョン 10 のみを使用するには、package.json の次の行を編集します。

  "engines": {"node": "10"}

engines フィールドは必須です。関数をデプロイして実行するには、サポートされているいずれかの Node.js バージョンを指定する必要があります。現在、firebase init functions はこのフィールドを 10 に設定します。

Node.js ランタイムをアップグレードする

Node.js ランタイムをアップグレードするには:

  1. Blaze 従量課金制の料金プランを利用していることを確認します。
  2. Firebase CLI バージョン 8.1.0 以降を使用していることを確認します。
  3. 初期化時に functions/ ディレクトリに作成された package.json ファイルの engines の値を変更します。たとえば、バージョン 8 からバージョン 10 にアップグレードする場合、エントリは次のようになります。"engines": {"node": "10"}
  4. 必要に応じて、Firebase エミュレータを使用して変更をテストします。
  5. Firebase CLI v8.1.0 以降を使用して関数を再デプロイします。

タイムアウトとメモリ割り当てを設定する

場合によっては、長いタイムアウト値や大容量のメモリ割り当てに関して、関数に特別な要件が存在することがあります。これらの値は、Google Cloud Console または関数のソースコード(Firebase のみ)で設定できます。

関数のソースコードでメモリ割り当てとタイムアウトを設定するには、Firebase SDK for Cloud Functions 2.0.0 で導入された runWith パラメータを使用します。このランタイム オプションは、RuntimeOptions インターフェースに準拠する JSON オブジェクトを受け入れます。これにより、timeoutSecondsmemory の値が定義されます。たとえば、次のストレージ関数は 1 GB のメモリを使用し、300 秒経過するとタイムアウトします。

const runtimeOpts = {
  timeoutSeconds: 300,
  memory: '1GB'
}

exports.myStorageFunction = functions
  .runWith(runtimeOpts)
  .storage
  .object()
  .onFinalize((object) = > {
    // do some complicated things that take a lot of memory and time
  });

timeoutSeconds の最大値は 540 または 9 分です。memory の有効な値は次のとおりです。

  • 128MB
  • 256MB
  • 512MB
  • 1GB
  • 2GB

Google Cloud Platform Console でメモリ割り当てとタイムアウトを設定するには:

  1. Google Cloud Platform Console で、左側のメニューから [Cloud Functions] を選択します。
  2. 関数のリストで関数名をクリックして、関数を選択します。
  3. トップメニューの [編集] アイコンをクリックします。
  4. [割り当てられるメモリ] というプルダウン メニューから、メモリ割り当てを選択します。
  5. [詳細] をクリックして詳細オプションを表示し、[タイムアウト] テキスト ボックスに秒数を入力します。
  6. [保存] をクリックして関数を更新します。