Nx Nrwl Firebase Functions

Damian Bielecki
MEAN Fire
Published in
3 min readFeb 21, 2019

Since Nrwl released its support for node applications I was looking forward to similar support for Firebase Functions. I have even created an issue on GitHub for that. At the time of writing it is still open, that’s why I have decided to create my own solution.

The problem

When you initialise Firebase Functions withfirebase init it creates functions subdirectory with its own package.json and node_modules. That is not good. We want to share code with functions and manage it using Nx.

Goal

  • Firebase Functions exist as a node app
  • There is only one package.json and node_modules
  • Functions can use shared code fromlibs

Prerequisites

We assume you have a working Nrwl Project with Angular application. It is also recommended that you have Firebase account and understand what Firebase Functions are.

Solution

Setup Firebase

If you haven’t already, install firebase-tools and login:

yarn global add firebase-tools
firebase login

Also add .firebaserc in the root dir to make it a Firebase project:

{
"projects": {
"default": "your-firebase-project-name"
}
}

Generate node-app

As stated in goal, Functions are to be based on node-app. To do so, create node-app named “functions”:

ng add @nrwl/node # Adds Node capabilities
ng g @nrwl/node:application functions

Configure Firebase Functions

Install Firebase Functions dependencies

yarn add firebase firebase-admin firebase-functions

Replace contents of apps/functions/src/main.ts with:

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!');
});

Above snippet is what Firebase generates when using firebase init.

To setup Firebase Functions so that they are understood create firebase.json in the root directory:

{
"functions": {
"predeploy": [
"yarn lint functions",
"yarn build functions --prod"
],
"source": "/"
}
}
  • predeploy just defines what is fired when you issue command firebase deploy --only functions. In this case it will run linter and production build for our “functions” project.
  • source points to the root of the project. Since we have only one package.json and it is in the root directory it needs to point there.

In package.json add following:

"main": "dist/apps/functions/main.js",
"engines": {
"node": "10"
},
  • main is required so that Firebase knows what to start after deployment. I have created a feature request to move it to firebase.json but at the time of writing it needs to be there.
  • engine is telling Firebase on which node version it should be run. At the time of writing node v10 is the newest supported. Also you CANNOT specify yarn or npm version in here because it will conflict with firebase.

Usage

Serving Firebase Functions is a little more complicated than typical node app. Add this dev dependancy:

yarn add concurrently -D

And these scripts to package.json:

"firebase:serve": "concurrently --kill-others \"yarn run build functions --watch\" \"firebase serve --only functions\"",
"firebase:shell": "concurrently --kill-others \"yarn run build functions --watch\" \"firebase functions:shell\" --raw",
"firebase:deploy": "firebase deploy",
  • yarn firebase:serve - run functions locally
  • yarn firebase:shell - run functions shell locally
  • yarn firebase:deploy --only functions - deploy functions

Explanation

At the time of writing firebase serve serves functions only from dist directory. To make it work we use concurrently to run build with watch flag, and serve “concurrently”.

Summary

This pretty much covers it. Easy and elegant way to incorporate Firebase Functions into Nx project. Source code for this can be found in here. However it is actively developed so if you want to review THIS version, checkout this commit.

--

--