Firebase cloud functions in Ionic 4 - Complete guide
Tags: ionic, firebase, cloud, functions
Published: 2019-09-23 10:18:18

<main role="main"><article class=" u-minHeight100vhOffset65 u-overflowHidden postArticle postArticle--full is-withAccentColors" lang="en"><div class="postArticle-content js-postField js-notesSource editable" id="editor_6" g_editable="true" role="textbox" contenteditable="true" data-default-value="Title
Tell your story…" spellcheck="false"><section name="41aa" class="section section--body section--first section--last"><div class="section-divider"><hr class="section-divider"></div><div class="section-content"><div class="section-inner sectionLayout--insetColumn"><p name="6d05" class="graf graf--p graf-after--figure">This post will take you through the basics of Firebase cloud functions&#8202;—&#8202;How to create, deploy and use the cloud functions. Also, we’ll have a look into the cloud function dashboard in Firebase to understand the capabilities.</p><h3 name="45d4" class="graf graf--h3 graf-after--p">What is Firebase&nbsp;?</h3><p name="0089" class="graf graf--p graf-after--h3">If you don’t know much about Firebase&nbsp;… you need to catch up with latest tech news. Firebase is the hot stuff in market today to create quick mobile app back-ends, with a ton of built-in and ready-to-integrate features.</p><p name="17b0" class="graf graf--p graf-after--p">The most used feature of Firebase is as a back-end. It does not require any back-end setup or configuration from developer’s end. Along with this back-end, you get a ready-to-use database as well. Some of the other popular features are</p><ul class="postList"><li name="4785" class="graf graf--li graf-after--p">Push notifications</li><li name="320b" class="graf graf--li graf-after--li"><strong class="markup--strong markup--li-strong">Cloud functions</strong></li><li name="952e" class="graf graf--li graf-after--li is-selected">Analytics</li><li name="90e4" class="graf graf--li graf-after--li">Ad-mob</li><li name="f6b2" class="graf graf--li graf-after--li">Crashlytics</li><li name="c424" class="graf graf--li graf-after--li">In-app messages</li><li name="a560" class="graf graf--li graf-after--li">Remote config</li><li name="c5ce" class="graf graf--li graf-after--li">Social logins</li><li name="432a" class="graf graf--li graf-after--li">…… and more</li></ul><p name="23c6" class="graf graf--p graf-after--li">That being said, I’m sure you are very much interested in learning all of it. You can check out our Firebase social logins with <a href="https://enappd.com/blog/facebook-login-in-ionic-4-apps-using-firebase/25"  class="markup--anchor markup--p-anchor" rel="noopener"    target="_blank"><strong class="markup--strong markup--p-strong">Facebook</strong></a> and <a href="https://enappd.com/blog/twitter-login-in-ionic-4-apps-using-firebase/24"  class="markup--anchor markup--p-anchor" rel="noopener"    target="_blank"><strong class="markup--strong markup--p-strong">Twitter</strong></a> blogs on our <a href="http://enappd.com/blog"  class="markup--anchor markup--p-anchor" rel="noopener"    target="_blank">site</a>, along with free starters ( 👻 woohoo&nbsp;! )</p><h3 name="2d11" class="graf graf--h3 graf-after--p">What are (Firebase) Cloud Functions?</h3><p name="e838" class="graf graf--p graf-after--h3">When you use a ready-to-integrate back-end (BaaS) in your mobile or web-app, you are basically not setting up any back-end on your own. So essentially all the functions / services are written beforehand for you. These functions and services are created based on the most used features by users. e.g.</p><ul class="postList"><li name="7f58" class="graf graf--li graf-after--p">Authentications</li><li name="5836" class="graf graf--li graf-after--li">Database operations&#8202;—&#8202;Read, Write, Update, Delete</li><li name="d544" class="graf graf--li graf-after--li">In some cases&#8202;—&#8202;Filtering, pagination, geo-queries etc.</li></ul><p name="a7e1" class="graf graf--p graf-after--li"><strong class="markup--strong markup--p-strong">But what if you want a custom function or query for your app&nbsp;? </strong>Because you didn’t create the back-end, you cannot write a custom function, right&nbsp;? Not really 😏. <strong class="markup--strong markup--p-strong">Cloud functions</strong> come to your rescue. These are basically simple functions you can write and deploy on the BaaS platform, and these functions will be executed as if they are a part of the platform. (of course, you need to take care of the syntax, requests, responses etc. )</p><p name="d27a" class="graf graf--p graf-after--p">For example, you are a Grocery shopping app. With a BaaS like Firebase, you can Read, Write, Update and Delete the data. But for a certain feature, you need to show the user their monthly expense on the app. Now, Firebase does give you options to query the data by fields like Date etc. But combining data from different tables can be tricky with single or even a complex query. In such a case, you write a function which queries all relevant tables, prepare the data as you want, and sends back to your app in smallest possible data format.</p><p name="bc80" class="graf graf--p graf-after--p">Overall, you can divide the Firebase cloud functions advantages as follows</p><ol class="postList"><li name="e7ec" class="graf graf--li graf-after--p">You can create custom functions to do complex queries e.g. queries combining multiple tables, date and geolocation calculations</li><li name="77a5" class="graf graf--li graf-after--li">Calling a cloud function is as easy as calling a REST API</li><li name="6c8a" class="graf graf--li graf-after--li">Complex calculations in the back-end are faster than on front-end e.g. finding matches in a dating app</li><li name="2bff" class="graf graf--li graf-after--li">Cron-jobs can directly run cloud functions on a scheduled basis, doing regular calculations for the database</li><li name="15c8" class="graf graf--li graf-after--li">Creating, updating and deploying Firebase cloud functions is as easy as changing code in your IDE and committing code to Git.</li><li name="e997" class="graf graf--li graf-after--li">Get rid of managing servers&#8202;—&#8202;Firebase takes care of everything</li><li name="8e5d" class="graf graf--li graf-after--li">You can test the cloud function on local environment as well</li></ol><h3 name="1c24" class="graf graf--h3 graf-after--li">What is Ionic&nbsp;4?</h3><p name="eaae" class="graf graf--p graf-after--h3">You probably already know about Ionic, but I’m putting it here just for the sake of beginners. <strong class="markup--strong markup--p-strong">Ionic</strong> is a complete open-source SDK for hybrid mobile app development. Ionic provides tools and services for developing hybrid mobile apps using Web technologies like CSS, HTML5, and Sass. Apps can be built with these Web technologies and then distributed through native app stores to be installed on devices.</p><p name="de54" class="graf graf--p graf-after--p">In other words&#8202;—&#8202;If you create native apps in Android, you code in Java. If you create native apps in iOS, you code in Obj-C or Swift. Both of these are powerful, but complex languages. With Cordova (and Ionic) you can write a single piece of code for your app that can run on both iOS and Android (and windows!), that too with the simplicity of HTML, CSS, and JS.</p><h3 name="473b" class="graf graf--h3 graf-after--p">Post Structure</h3><p name="43a3" class="graf graf--p graf-after--h3">We will go step-by-step to understand the basics of integrating Firebase cloud functions in an Ionic 4 app. We’ll follow these steps</p><ol class="postList"><li name="6810" class="graf graf--li graf-after--p">Create a basic Ionic 4 app</li><li name="3788" class="graf graf--li graf-after--li">Create a Firebase project</li><li name="6a82" class="graf graf--li graf-after--li">Setup Firebase functions and write your first function</li><li name="a8af" class="graf graf--li graf-after--li">Deploy Firebase function and test from your app</li><li name="15cd" class="graf graf--li graf-after--li">Firebase cloud function dashboard and capabilities</li><li name="ba94" class="graf graf--li graf-after--li">Write a complex cloud function and fetch result in the app</li></ol><p name="25fe" class="graf graf--p graf-after--li">Let’s jump right in</p><h3 name="8730" class="graf graf--h3 graf-after--p">1. Create a basic Ionic 4&nbsp;app</h3><blockquote name="793e" class="graf graf--blockquote graf-after--h3">I have covered this topic in detail in <a href="https://enappd.com/blog/how-to-create-an-ionic-4-app-for-beginners/13/"  class="markup--anchor markup--blockquote-anchor" rel="noopener"    target="_blank">this blog</a>.</blockquote><p name="178b" class="graf graf--p graf-after--blockquote">Creating an Ionic 4 app is as simple as running a single command from command prompt / terminal.</p><p name="ac57" class="graf graf--p graf-after--p">In short, the steps you need to take here are</p><ul class="postList"><li name="1e8a" class="graf graf--li graf-after--p">Make sure you have node installed in the system (V10.0.0 at the time of this blog post)</li><li name="1ae0" class="graf graf--li graf-after--li">Install ionic cli using npm</li><li name="508a" class="graf graf--li graf-after--li">Create an Ionic app using <code class="markup--code markup--li-code">ionic start</code></li></ul><p name="afc5" class="graf graf--p graf-after--li">You can create a <code class="markup--code markup--p-code">sidemenu</code> starter for the sake of this tutorial. On running <code class="markup--code markup--p-code">ionic start</code>&nbsp;, node modules will be installed. Once the installation is done, run your app on browser using</p><pre name="f473" class="graf graf--pre graf-after--p">$ ionic serve</pre><p name="5a2e" class="graf graf--p graf-after--pre">At this moment, your app should look like this</p><figure tabindex="0" contenteditable="false" name="12d3" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 393px; max-height: 684px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 174%;"></div><img class="graf-image" data-image-id="1*dKG8G3khINpIzOyC48LN9Q.png" data-width="393" data-height="684" src="https://cdn-images-1.medium.com/max/800/1*dKG8G3khINpIzOyC48LN9Q.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Homepage for Sidemenu starter in Ionic&nbsp;4</figcaption></figure><h3 name="7270" class="graf graf--h3 graf-after--figure">2. Create a Firebase project and connect to your&nbsp;app</h3><p name="2ae0" class="graf graf--p graf-after--h3">Firebase is a Google product (now), so you need to create a “Firebase project” to connect it to your app and keep all related services at one place. You can create a large number of FREE projects in Firebase.</p><blockquote name="e361" class="graf graf--blockquote graf-after--p">I have covered Ionic 4 Firebase integration in detail in <a href="https://enappd.com/blog/how-to-integrate-firebase-in-ionic-4-apps/23/"  class="markup--anchor markup--blockquote-anchor" rel="noopener"    target="_blank">this blog</a></blockquote><p name="a61b" class="graf graf--p graf-after--blockquote"><strong class="markup--strong markup--p-strong">Please note&#8202;—&#8202;Firebase functions can run without attaching Firebase in the app (as REST APIs). You need to copy the Firebase configuration and install angularfire 2 plugin only if you want to attach Firebase database or other functionalities in your app.</strong></p><h4 name="34fe" class="graf graf--h4 graf-after--p">Creating Firebase&nbsp;project</h4><p name="9f05" class="graf graf--p graf-after--h4">Go to console.firebase.google.com and create a new project. Your dashboard will look like this when you have a number of firebase projects</p><figure tabindex="0" contenteditable="false" name="fc38" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 388px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 55.400000000000006%;"></div><img class="graf-image" data-image-id="1*teoLcvS1IcAUTc7Derns3g.png" data-width="1387" data-height="768" src="https://cdn-images-1.medium.com/max/800/1*teoLcvS1IcAUTc7Derns3g.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase dashboard with a number of&nbsp;projects</figcaption></figure><h4 name="48d2" class="graf graf--h4 graf-after--figure">Copy Firebase configuration</h4><p name="33b6" class="graf graf--p graf-after--h4">Open your project by clicking it, and in the dashboard, select <strong class="markup--strong markup--p-strong">“Add Firebase to your web app”. </strong>Follow the procedure and you will get your project’s configuration. Copy the configuration, this will be used to connect your app with Firebase.</p><figure tabindex="0" contenteditable="false" name="45e7" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 480px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 68.60000000000001%;"></div><img class="graf-image" data-image-id="1*OwHD8bA8yqjk6DP_h9u-cQ.png" data-width="800" data-height="549" src="https://cdn-images-1.medium.com/max/800/1*OwHD8bA8yqjk6DP_h9u-cQ.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Copy Firebase project configuration</figcaption></figure><h4 name="44b2" class="graf graf--h4 graf-after--figure">Integrate Firebase in your Ionic&nbsp;app</h4><p name="1470" class="graf graf--p graf-after--h4">Back in your Ionic app, install <a href="https://github.com/angular/angularfire2/"  class="markup--anchor markup--p-anchor" rel="noopener"    target="_blank">Angularfire2</a> plugin. AngularFire is The official library for Firebase and Angular.</p><p name="93e6" class="graf graf--p graf-after--p">To install the plugin, run the following command from your terminal</p><pre name="d745" class="graf graf--pre graf-after--p">$ npm install firebase angularfire2</pre><p name="1ddc" class="graf graf--p graf-after--pre">Paste your Firebase config in <strong class="markup--strong markup--p-strong">environment</strong> file of your Ionic app project. The environment file should be in the project root.</p><figure tabindex="0" contenteditable="false" name="91a1" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 223px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 31.900000000000002%;"></div><img class="graf-image" data-image-id="1*8B3y4-396WnPZG9GHQyypQ.png" data-width="800" data-height="255" src="https://cdn-images-1.medium.com/max/800/1*8B3y4-396WnPZG9GHQyypQ.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Paste your Firebase configuration in environment file</figcaption></figure><p name="124b" class="graf graf--p graf-after--figure">After this, you will need to import angularFire2 and firebase in your <code class="markup--code markup--p-code">app.module.ts</code> and then you can implement CRUD and other functionalities in the app.</p><h3 name="a09b" class="graf graf--h3 graf-after--p">3. Setup Firebase functions and write your first&nbsp;function</h3><p name="bad7" class="graf graf--p graf-after--h3">Firebase functions can be used once we setup <code class="markup--code markup--p-code">firebase-tools</code> in the system. Install it globally with npm using</p><pre name="62b4" class="graf graf--pre graf-after--p">$ npm install firebase-tools -g</pre><h4 name="9871" class="graf graf--h4 graf-after--pre">Login to&nbsp;Firebase</h4><p name="f3b4" class="graf graf--p graf-after--h4">Before using Firebase functions, you need to login to your Firebase account using CLI (yeah&nbsp;! 🤷&zwj;♂). Run</p><pre name="35c4" class="graf graf--pre graf-after--p">$ firebase login</pre><p name="afaa" class="graf graf--p graf-after--pre">and it will open the Google login card in your browser. Login to your account and the CLI will receive the authentication info (pretty cool, right&nbsp;? )</p><figure tabindex="0" contenteditable="false" name="0e23" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 211px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 30.099999999999998%;"></div><img class="graf-image" data-image-id="1*48emnlyYA9mu9W4-66LUmg.png" data-width="1079" data-height="325" src="https://cdn-images-1.medium.com/max/800/1*48emnlyYA9mu9W4-66LUmg.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase login in CLI using browser&#8202;—&#8202;successful&nbsp;!</figcaption></figure><p name="f494" class="graf graf--p graf-after--figure">Your CLI will look like this</p><figure tabindex="0" contenteditable="false" name="9dc2" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 142px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 20.3%;"></div><img class="graf-image" data-image-id="1*mIgJ3ubtnhjfvRPgRyf6OA.png" data-width="969" data-height="197" src="https://cdn-images-1.medium.com/max/800/1*mIgJ3ubtnhjfvRPgRyf6OA.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Logging in Firebase using&nbsp;CLI</figcaption></figure><h4 name="50d0" class="graf graf--h4 graf-after--figure">Connect Firebase to your&nbsp;project</h4><p name="f853" class="graf graf--p graf-after--h4">Once you are logged in, you need to define which Firebase project you want to connect to your Ionic 4 app (because you can have more than one in your Firebase console. I have 30+ 😃&nbsp;! ). Run</p><pre name="5263" class="graf graf--pre graf-after--p">$ firebase init</pre><p name="1bea" class="graf graf--p graf-after--pre">This will first ask you to choose the project, then choose <code class="markup--code markup--p-code">functions</code> option from the choices. (Don’t worry about other options, I’ll post more blogs on them soon). Follow the instructions and setup all dependencies of Firebase functions</p><figure tabindex="0" contenteditable="false" name="3449" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 383px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 54.6%;"></div><img class="graf-image" data-image-id="1*1NfBWo9pc2SWfrJ-lIISHQ.png" data-width="968" data-height="529" src="https://cdn-images-1.medium.com/max/800/1*1NfBWo9pc2SWfrJ-lIISHQ.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Choose Functions options in `Firebase init`</figcaption></figure><blockquote name="8ee7" class="graf graf--blockquote graf-after--figure">Note&#8202;—&#8202;Sometimes linting creates errors during deployment. If you face this issue, try re-running <code class="markup--code markup--blockquote-code"><em class="markup--em markup--blockquote-em">firebase init</em></code> and don’t select linting option when asked</blockquote><p name="6b3d" class="graf graf--p graf-after--blockquote">As we discussed earlier&nbsp;, with <strong class="markup--strong markup--p-strong">Firebase Functions, </strong>you can essentially write back-end (node.js) functions, test them locally with <code class="markup--code markup--p-code">firebase serve</code> and can then deploy these to your Firebase project, so it can be connected to your app / website.</p><p name="72a6" class="graf graf--p graf-after--p">Once you have Firebase project connected, you will see a <code class="markup--code markup--p-code">functions</code> folder in your project root, as shown below</p><figure tabindex="0" contenteditable="false" name="bdb9" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 295px; max-height: 501px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 169.79999999999998%;"></div><img class="graf-image" data-image-id="1*q-KcVAn51NmNPhtcTRlcpQ.png" data-width="295" data-height="501" src="https://cdn-images-1.medium.com/max/800/1*q-KcVAn51NmNPhtcTRlcpQ.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase functions folder in project&nbsp;root</figcaption></figure><h4 name="7dd6" class="graf graf--h4 graf-after--figure">Create a firebase function to say “Hello&nbsp;World”</h4><p name="3e40" class="graf graf--p graf-after--h4">Open <code class="markup--code markup--p-code">functions/src/index.ts</code> (or&nbsp;.js, depending on what you chose in previous step). This is the file that will contain functions to be executed by Firebase. Firebase creates a URL for each of these functions when deployed, so you can call these functions like a REST API</p><figure tabindex="0" contenteditable="false" name="d2f5" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 151px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 21.6%;"></div><img class="graf-image" data-image-id="1*hQ2bqGMJ-oOGLNRoweBm7A.png" data-width="952" data-height="206" src="https://cdn-images-1.medium.com/max/800/1*hQ2bqGMJ-oOGLNRoweBm7A.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Default index.ts in Firebase functions folder</figcaption></figure><p name="8c9c" class="graf graf--p graf-after--figure">By default, Firebase gives you a <code class="markup--code markup--p-code">helloWorld</code> function, uncomment it and you can use it as is. Let’s understand what is happening here (if you haven’t used node.js ever)</p><ul class="postList"><li name="95c3" class="graf graf--li graf-after--p"><strong class="markup--strong markup--li-strong">export </strong>exports the function as a individual entity. You can have as many functions as you want in this file itself</li><li name="bd17" class="graf graf--li graf-after--li"><strong class="markup--strong markup--li-strong">request</strong> is the request you send from front-end, similar to a REST API. It is relevant for POST requests</li><li name="02dc" class="graf graf--li graf-after--li"><strong class="markup--strong markup--li-strong">response</strong> is the response Firebase cloud function will send back to your app</li></ul><p name="4343" class="graf graf--p graf-after--li">In this sample case, the function is simple sending back a <strong class="markup--strong markup--p-strong">“hello from Firebase” </strong>(irrespective of request i.e. this is a GET type request). Change the response as you like&nbsp;!</p><p name="44cb" class="graf graf--p graf-after--p">Congratulations, you just wrote your first Firebase cloud function.</p><h4 name="ca08" class="graf graf--h4 graf-after--p">⭐️️⭐️️️ Extra&nbsp;: Adding CORS to Firebase function to run locally⭐️️⭐️️️</h4><p name="9afc" class="graf graf--p graf-after--h4">When developing an Ionic 4 app, you’ll do most of your development in browser. So it makes sense to get the Firebase function response in serve as well. By default, Firebase does not allow response to localhost urls. To avoid this, we will have to add <strong class="markup--strong markup--p-strong">CORS </strong>middleware in the Firebase function. If you want to test simply in your phone, <strong class="markup--strong markup--p-strong">CORS</strong> middleware is not required.</p><p name="63fa" class="graf graf--p graf-after--p">Don’t worry, it is very simple.</p><ol class="postList"><li name="4fec" class="graf graf--li graf-after--p">Add CORS dependency in your <code class="markup--code markup--li-code">functions/package.json</code></li></ol><figure tabindex="0" contenteditable="false" name="01ed" class="graf graf--figure graf-after--li"><div class="aspectRatioPlaceholder is-locked" style="max-width: 430px; max-height: 322px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 74.9%;"></div><img class="graf-image" data-image-id="1*Aejc6ZLx5ydL3VMxVaNEug.png" data-width="430" data-height="322" src="https://cdn-images-1.medium.com/max/800/1*Aejc6ZLx5ydL3VMxVaNEug.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Add CORS in dependency</figcaption></figure><p name="4d87" class="graf graf--p graf-after--figure">2. Move in <code class="markup--code markup--p-code">functions</code> folder, and run <code class="markup--code markup--p-code">npm install</code> again to install the new dependency</p><p name="5f4d" class="graf graf--p graf-after--p">3. Import CORS in Firebase functions file, and modify the response code as follows</p><figure tabindex="0" contenteditable="false" name="b3b0" class="graf graf--figure graf--iframe graf-after--p"><div class="aspectRatioPlaceholder is-locked"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 35.699999999999996%;"></div><div class="iframeContainer">{% gist https://gist.github.com/enappd/203d4eaf32e49cbda51cd9a51eca1db0.js %}</div></div><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for embed (optional)">Add CORS in Firebase function response</figcaption></figure><p name="f9d6" class="graf graf--p graf-after--figure">Now, you can run the Firebase function in your <code class="markup--code markup--p-code">ionic serve</code> as well&nbsp;!</p><h3 name="670c" class="graf graf--h3 graf-after--p">4. Deploy Firebase function and test from your&nbsp;app</h3><p name="a3c3" class="graf graf--p graf-after--h3">Now that the function is ready, we will deploy it to Firebase. This way we can use it in the app directly (similar to a REST API)</p><h4 name="6656" class="graf graf--h4 graf-after--p">Deploy Firebase&nbsp;function</h4><p name="59e4" class="graf graf--p graf-after--h4">To deploy the firebase function, in your root folder itself, run</p><pre name="09c6" class="graf graf--pre graf-after--p">$ firebase deploy --only functions</pre><p name="3b2b" class="graf graf--p graf-after--pre">This will make sure you are only deploying <code class="markup--code markup--p-code">functions</code> to Firebase. This is especially useful when you have multiple things attached to Firebase, and you have made changes in only one of them.</p><p name="dcaf" class="graf graf--p graf-after--p">Deployment will look like this in the CLI</p><figure tabindex="0" contenteditable="false" name="8eaf" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 261px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 37.3%;"></div><img class="graf-image" data-image-id="1*IUoawFsbnmMl8bphgmNmYQ.png" data-width="731" data-height="273" src="https://cdn-images-1.medium.com/max/800/1*IUoawFsbnmMl8bphgmNmYQ.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase functions deployment</figcaption></figure><p name="1697" class="graf graf--p graf-after--figure">Notice in the <strong class="markup--strong markup--p-strong">function URL</strong>, it provides you the URL to call the cloud function. <code class="markup--code markup--p-code"><a href="https://us-central1-full-firebase-ionic4.cloudfunctions.net/helloWorld"  class="markup--anchor markup--p-anchor" rel="nofollow noopener noopener" target="_blank">https://us-central1-full-firebase-ionic4.cloudfunctions.net/helloWorld</a></code></p><h4 name="deee" class="graf graf--h4 graf-after--p">Run Firebase function in local environment</h4><p name="67f1" class="graf graf--p graf-after--h4">If you don’t want to deploy everytime you make a change in your Firebase function, you can serve the functions locally and use the local function URL for testing.</p><p name="deb9" class="graf graf--p graf-after--p">Run</p><pre name="3903" class="graf graf--pre graf-after--p">$ firebase serve</pre><p name="5fdb" class="graf graf--p graf-after--pre">This will serve the functions locally, and provide you a local URL of each of the function. Replace the function web URL with local URL and you’ll be able to access the function in your app.</p><h4 name="909e" class="graf graf--h4 graf-after--p">Calling the cloud functions from Ionic 4&nbsp;app</h4><p name="ef57" class="graf graf--p graf-after--h4">I modified the app to have a button with which we can call the cloud function. Right below the button, we will receive the response from Firebase cloud function.</p><figure tabindex="0" contenteditable="false" name="adbe" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 378px; max-height: 670px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 177.2%;"></div><img class="graf-image" data-image-id="1*v5ejYlrUzF7_fPjY836nQA.png" data-width="378" data-height="670" src="https://cdn-images-1.medium.com/max/800/1*v5ejYlrUzF7_fPjY836nQA.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Modify the homepage to call Firebase function with a simple&nbsp;button</figcaption></figure><p name="5271" class="graf graf--p graf-after--figure">To enable our app to make HTTP requests, we import <code class="markup--code markup--p-code">HttpClient</code> in our <code class="markup--code markup--p-code">app.module.ts</code></p><figure tabindex="0" contenteditable="false" name="e5f8" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 345px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 49.3%;"></div><img class="graf-image" data-image-id="1*JVCCvddH6hLlGFuBVz5D1Q.png" data-width="958" data-height="472" src="https://cdn-images-1.medium.com/max/800/1*JVCCvddH6hLlGFuBVz5D1Q.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Import HttpCient in app.module.ts</figcaption></figure><p name="13bc" class="graf graf--p graf-after--figure">and in our <code class="markup--code markup--p-code">home.page.ts</code> page</p><pre name="b3ae" class="graf graf--pre graf-after--p">import { HttpClient } from "@angular/common/http";</pre><pre name="a225" class="graf graf--pre graf-after--pre">...</pre><pre name="52ef" class="graf graf--pre graf-after--pre">constructor(private http: HttpClient){}</pre><p name="615a" class="graf graf--p graf-after--pre">Now, on the click of our button, we’ll call the cloud function, and receive the response. The <code class="markup--code markup--p-code">home.page.ts</code> looks like following</p><figure tabindex="0" contenteditable="false" name="c8b9" class="graf graf--figure graf--iframe graf-after--p is-defaultValue"><div class="aspectRatioPlaceholder is-locked"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 35.699999999999996%;"></div><div class="iframeContainer">{% gist https://gist.github.com/enappd/4cb23785ca40e97ecd9d7e56823dd090.js %}</div></div></figure><p name="26cc" class="graf graf--p graf-after--figure">Just for reference, the <code class="markup--code markup--p-code">home.page.html</code> looks like following</p><figure tabindex="0" contenteditable="false" name="48db" class="graf graf--figure graf--iframe graf-after--p is-defaultValue"><div class="aspectRatioPlaceholder is-locked"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 35.699999999999996%;"></div><div class="iframeContainer">{% gist https://gist.github.com/enappd/84feaf60d25754f4b2f683a77557aa81.js %}</div></div></figure><p name="d252" class="graf graf--p graf-after--figure">Now, hit the button, and you’ll receive a response from Firebase function&nbsp;!</p><figure tabindex="0" contenteditable="false" name="251d" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 350px; max-height: 607px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 173.4%;"></div><img class="graf-image" data-image-id="1*2q41mIAy1JO-z5WBkAOQww.gif" data-width="350" data-height="607" src="https://cdn-images-1.medium.com/max/800/1*2q41mIAy1JO-z5WBkAOQww.gif"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase function works&nbsp;!!</figcaption></figure><p name="0394" class="graf graf--p graf-after--figure">🎊 Voila&nbsp;! Your first Firebase cloud function is working like a charm&nbsp;!</p><figure tabindex="0" contenteditable="false" name="ff2d" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 500px; max-height: 346px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 69.19999999999999%;"></div><img class="graf-image" data-image-id="1*Mex0N4L-8V9SkAxgxC25Pg.gif" data-width="500" data-height="346" src="https://cdn-images-1.medium.com/max/800/1*Mex0N4L-8V9SkAxgxC25Pg.gif"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Oh yeah&nbsp;!</figcaption></figure><p name="612b" class="graf graf--p graf-after--figure"><strong class="markup--strong markup--p-strong">Little troubleshooting tip</strong></p><p name="1199" class="graf graf--p graf-after--p">If you face pre-deploy linting error during deployment, go to your <code class="markup--code markup--p-code">firebase.json</code> file and remove the pre-deploy script calls from JSON.</p><figure tabindex="0" contenteditable="false" name="62c5" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 468px; max-height: 185px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 39.5%;"></div><img class="graf-image" data-image-id="1*4MU6u813i2c_Zs7_aqEjBA.png" data-width="468" data-height="185" src="https://cdn-images-1.medium.com/max/800/1*4MU6u813i2c_Zs7_aqEjBA.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Remove the pre-deploy scripts if you face pre-deploy errors</figcaption></figure><h3 name="bbfc" class="graf graf--h3 graf-after--figure">5. Firebase cloud function dashboard</h3><p name="ade7" class="graf graf--p graf-after--h3">Till now, we were doing everything in the CLI or front-end code. It becomes challenging to maintain a large number of cloud functions, and their executions or errors with CLI alone. Firebase has provided a very good solution for this.</p><p name="b2b0" class="graf graf--p graf-after--p">In Firebase console, you can actually check all the functions deployed, their executions and if they faced any errors.</p><h4 name="e384" class="graf graf--h4 graf-after--p">List of deployed functions</h4><figure tabindex="0" contenteditable="false" name="8619" class="graf graf--figure graf-after--h4"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 340px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 48.5%;"></div><img class="graf-image" data-image-id="1*0pK6uZyBPTXp9jSG6VSA4g.png" data-width="1387" data-height="673" src="https://cdn-images-1.medium.com/max/800/1*0pK6uZyBPTXp9jSG6VSA4g.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">List of functions deployed in&nbsp;Firebase</figcaption></figure><p name="cef0" class="graf graf--p graf-after--figure">You can see the functions deployed in the <strong class="markup--strong markup--p-strong">Functions </strong>tab of Firebase console.</p><h4 name="e79a" class="graf graf--h4 graf-after--p">Execution log</h4><p name="1ebb" class="graf graf--p graf-after--h4">You can also check the execution of each / all function(s) in Firebase console&#8202;—&#8202;Logs tab</p><figure tabindex="0" contenteditable="false" name="99b4" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 332px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 47.4%;"></div><img class="graf-image" data-image-id="1*67l51RvOMGuzk7A_Pxv5rQ.png" data-width="1387" data-height="658" src="https://cdn-images-1.medium.com/max/800/1*67l51RvOMGuzk7A_Pxv5rQ.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Check firebase function&nbsp;logs</figcaption></figure><p name="9940" class="graf graf--p graf-after--figure">The logs show general comments of errors returned by the function. This is especially useful if you want to track any error happening in your functions.</p><h4 name="eb79" class="graf graf--h4 graf-after--p">Functions’ health</h4><p name="5052" class="graf graf--p graf-after--h4">If you have a large number of functions, and huge amount of executions, then a list of logs won’t suffice. You can check an overview of errors in the <strong class="markup--strong markup--p-strong">Health</strong> tab</p><figure tabindex="0" contenteditable="false" name="4b32" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 652px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 93.10000000000001%;"></div><img class="graf-image" data-image-id="1*6K5OWwrW7Xa9xiIhFHL3Fg.png" data-width="1600" data-height="1490" src="https://cdn-images-1.medium.com/max/800/1*6K5OWwrW7Xa9xiIhFHL3Fg.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase console showing health of function execution</figcaption></figure><h4 name="045b" class="graf graf--h4 graf-after--figure">Usage log</h4><p name="b80d" class="graf graf--p graf-after--h4">To track how many functions you execute in a time period (to check against your billing plan) you can use the <strong class="markup--strong markup--p-strong">Usage </strong>tab</p><figure tabindex="0" contenteditable="false" name="eeb5" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 341px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 48.699999999999996%;"></div><img class="graf-image" data-image-id="1*_DouTzzFlWk3Xr3Y38MZnA.png" data-width="1386" data-height="675" src="https://cdn-images-1.medium.com/max/800/1*_DouTzzFlWk3Xr3Y38MZnA.png"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Firebase function usage&nbsp;log</figcaption></figure><p name="e8d4" class="graf graf--p graf-after--figure">This way, Firebase provides a good number of visual and logging tools to make your life easy when dealing with cloud functions.</p><h3 name="40a2" class="graf graf--h3 graf-after--p">6. Write a cloud function with complex&nbsp;query</h3><p name="d1c3" class="graf graf--p graf-after--h3">For the first example, we simply responded with a “Hello from Firebase”. But that is not sufficient for most of the apps. Apps often need to query the database in various ways and need the final result as a response.</p><p name="87f1" class="graf graf--p graf-after--p">I am putting out a similar example here. The example is implemented with FireStore DB. This is a sample example for finding a driver in a <a href="https://store.enappd.com/product/taxi-booking-complete-platform/"  class="markup--anchor markup--p-anchor" rel="noopener"    target="_blank"><strong class="markup--strong markup--p-strong">Taxi Booking Platform</strong></a><strong class="markup--strong markup--p-strong">. </strong>The logic isn’t as complex as that of Uber etc. but queries a couple of DB tables, and then updates certain documents in the DB as well, before sending a response to the app. Let’s have a look.</p><figure tabindex="0" contenteditable="false" name="5cea" class="graf graf--figure graf--iframe graf-after--p is-defaultValue"><div class="aspectRatioPlaceholder is-locked"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 35.699999999999996%;"></div><div class="iframeContainer">{% gist https://gist.github.com/enappd/52754a4afaa13b2d937371be37dda4c8.js %}</div></div></figure><p name="99ba" class="graf graf--p graf-after--figure">Let us understand what is happening here</p><ul class="postList"><li name="a8a0" class="graf graf--li graf-after--p">As we did before, we imported certain dependencies. Additionally, <code class="markup--code markup--li-code">firebase-admin</code> is also imported, which is required to allow Firebase function to access your Firebase project’s DB (yes, there is no direct connection 😺)</li><li name="9dfc" class="graf graf--li graf-after--li">Same as before, we implemented <strong class="markup--strong markup--li-strong">CORS</strong> for localhost usage</li><li name="fa09" class="graf graf--li graf-after--li">Since there is a <code class="markup--code markup--li-code">request</code> object coming in, this is a POST request.</li><li name="9bfa" class="graf graf--li graf-after--li">In the first step, the <code class="markup--code markup--li-code">req.body</code> is read, and stored in a variable</li><li name="a5c1" class="graf graf--li graf-after--li">Then, <code class="markup--code markup--li-code">drivers</code> collection is read in the DB, and a driver matching the email <code class="markup--code markup--li-code">driver@enappd.com</code> is filtered. In a production app, this will be the place where the app’s “driver finding logic” will go.</li><li name="792e" class="graf graf--li graf-after--li">Once the driver is found, the customer’s record is updated with <code class="markup--code markup--li-code">origin</code> and <code class="markup--code markup--li-code">destination</code> storing customer’s coordinates.</li><li name="adbb" class="graf graf--li graf-after--li">Once the customer is updated, the driver record is also updated, marking him unavailable, and saving user_id in driver’s record</li><li name="fff1" class="graf graf--li graf-after--li">Once all this process is done, the response is sent to the app. The response contains the information of the driver selected. This information will be used in the app to show the customer which driver is arriving for the ride.</li></ul><p name="f65d" class="graf graf--p graf-after--li">This was a simple example of how Firebase cloud function can perform complex queries in your DB, and return the result to your app quickly. If all this was done on front-end, the response time would be much larger because of the multiple DB query hits.</p><h3 name="b31f" class="graf graf--h3 graf-after--p">Conclusion</h3><p name="1d61" class="graf graf--p graf-after--h3">In this post, we learned how to create, integrate, deploy and test simple Firebase functions. We also saw the Firebase console capabilities related to functions. We had a look at how complex queries can be performed with Firebase functions, citing an example from a <a href="https://store.enappd.com/product/taxi-booking-complete-platform/"  class="markup--anchor markup--p-anchor" rel="noopener"    target="_blank"><strong class="markup--strong markup--p-strong">Taxi Booking Platform</strong></a><strong class="markup--strong markup--p-strong">. </strong>Firebase functions are an amazing tool to enable your app do much more than simple DB querying, or making complex queries from front-end.</p><p name="ca16" class="graf graf--p graf-after--p"><strong class="markup--strong markup--p-strong">Stay tuned for more Ionic blogs!</strong></p><h3 name="ec59" class="graf graf--h3 graf-after--p">Next Steps</h3><p name="178a" class="graf graf--p graf-after--h3">Now that you have learned the implementation of Firebase functions in Ionic 4, you can also try</p><ul class="postList"><li name="9f48" class="graf graf--li graf-after--p"><a href="https://enappd.com/blog/ionic-4-paypal-payment-integration-for-apps-and-pwa/16"  class="markup--anchor markup--li-anchor" rel="nofollow noopener noopener noopener"    target="_blank">Ionic 4 PayPal payment integration&#8202;—&#8202;for Apps and PWA</a></li><li name="aa95" class="graf graf--li graf-after--li"><a href="https://enappd.com/blog/ionic-4-stripe-payment-integration-with-firebase-for-apps-and-pwa/17"  class="markup--anchor markup--li-anchor" rel="nofollow noopener noopener noopener"    target="_blank">Ionic 4 Stripe payment integration&#8202;—&#8202;for Apps and PWA</a></li><li name="fc67" class="graf graf--li graf-after--li"><a href="https://enappd.com/blog/how-to-integrate-apple-pay-in-ionic-4-apps/21"  class="markup--anchor markup--li-anchor" rel="nofollow noopener noopener noopener"    target="_blank">Ionic 4 Apple Pay integration</a></li><li name="b1fc" class="graf graf--li graf-after--li"><a href="https://enappd.com/blog/twitter-login-in-ionic-4-apps-using-firebase/24"  class="markup--anchor markup--li-anchor" rel="noopener"    target="_blank">Twitter login in Ionic 4 with Firebase</a></li><li name="57fe" class="graf graf--li graf-after--li"><a href="https://enappd.com/blog/facebook-login-in-ionic-4-apps-using-firebase/25"  class="markup--anchor markup--li-anchor" rel="noopener"    target="_blank">Facebook login in Ionic 4 with Firebase</a></li><li name="97f4" class="graf graf--li graf-after--li"><a href="https://medium.com/enappd/using-geolocation-and-beacon-plugins-in-ionic-4-754b41304007"  class="markup--anchor markup--li-anchor"    target="_blank">Geolocation</a> in Ionic 4</li><li name="34a6" class="graf graf--li graf-after--li"><a href="https://medium.com/enappd/qr-code-scanning-and-optical-character-recognition-ocr-in-ionic-4-95fd46be91dd"  class="markup--anchor markup--li-anchor"    target="_blank">QR Code and scanners</a> in Ionic 4 and</li><li name="de81" class="graf graf--li graf-after--li"><a href="https://medium.com/enappd/how-to-translate-in-ionic-4-globalization-internationalization-and-localization-31ec5807a8bc"  class="markup--anchor markup--li-anchor"    target="_blank">Translations in Ionic 4</a></li></ul><p name="2930" class="graf graf--p graf-after--li">If you need a base to start your next Ionic 4 app, you can make your next awesome app using <a href="https://store.enappd.com/product/ionic-4-full-app/"  class="markup--anchor markup--p-anchor" rel="noopener nofollow noopener noopener nofollow noopener noopener nofollow noopener noopener noopener"    target="_blank">Ionic 4 Full App</a></p><figure tabindex="0" contenteditable="false" name="89dc" class="graf graf--figure graf-after--p"><div class="aspectRatioPlaceholder is-locked" style="max-width: 700px; max-height: 442px;"><div class="aspectRatioPlaceholder-fill" style="padding-bottom: 63.2%;"></div><img class="graf-image" data-image-id="1*2BzL8TesnBHuazHr3VA4SQ.jpeg" data-width="760" data-height="480" src="https://cdn-images-1.medium.com/max/800/1*2BzL8TesnBHuazHr3VA4SQ.jpeg"><div class="crosshair u-ignoreBlock"></div></div><br/><figcaption class="imageCaption" contenteditable="true" data-default-value="Type caption for image (optional)">Use Ionic 4 Full app for your next awesome&nbsp;app</figcaption></figure><h3 name="1b1c" class="graf graf--h3 graf-after--figure">References</h3><ul class="postList"><li name="bb4a" class="graf graf--li graf-after--h3 graf--trailing"><a href="https://ionicframework.com/docs"  class="markup--anchor markup--li-anchor" rel="noopener nofollow noopener noopener nofollow noopener noopener nofollow noopener noopener noopener"    target="_blank">Ionic documentation</a></li></ul></div></div></section></div></article></main>