<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/"
    xmlns:atom="http://www.w3.org/2005/Atom" xmlns:media="http://search.yahoo.com/mrss/" version="2.0">
    <channel>
        
        <title>
            <![CDATA[ #firebase-cloud-functions - freeCodeCamp.org ]]>
        </title>
        <description>
            <![CDATA[ Browse thousands of programming tutorials written by experts. Learn Web Development, Data Science, DevOps, Security, and get developer career advice. ]]>
        </description>
        <link>https://www.freecodecamp.org/news/</link>
        <image>
            <url>https://cdn.freecodecamp.org/universal/favicons/favicon.png</url>
            <title>
                <![CDATA[ #firebase-cloud-functions - freeCodeCamp.org ]]>
            </title>
            <link>https://www.freecodecamp.org/news/</link>
        </image>
        <generator>Eleventy</generator>
        <lastBuildDate>Fri, 26 Jun 2026 17:32:33 +0000</lastBuildDate>
        <atom:link href="https://www.freecodecamp.org/news/tag/firebase-cloud-functions/rss.xml" rel="self" type="application/rss+xml" />
        <ttl>60</ttl>
        
            <item>
                <title>
                    <![CDATA[ Node.js and Cloud Firestore Tutorial – How to Build a Home Inventory System ]]>
                </title>
                <description>
                    <![CDATA[ By Suchandra Datta In this article, you'll practice your JavaScript skills while streamlining your household chores by creating your very own home inventory system.  I've often found that it's hard to keep track common household items that I buy freq... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/nodejs-and-cloud-firestore-tutorial-build-a-home-inventory-system/</link>
                <guid isPermaLink="false">66d852648acc348be2a441d6</guid>
                
                    <category>
                        <![CDATA[ Cloud Computing ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Firebase ]]>
                    </category>
                
                    <category>
                        <![CDATA[ #firebase-cloud-functions ]]>
                    </category>
                
                    <category>
                        <![CDATA[ JavaScript ]]>
                    </category>
                
                    <category>
                        <![CDATA[ node js ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Fri, 30 Apr 2021 16:26:24 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2021/04/home-inventory-system-article.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Suchandra Datta</p>
<p>In this article, you'll practice your JavaScript skills while streamlining your household chores by creating your very own home inventory system. </p>
<p>I've often found that it's hard to keep track common household items that I buy frequently such as food, spices, medicine, and the like. It's annoying at best and frustrating at worst when I uncover a long-forgotten packet of chips from the depths of the cupboard. </p>
<p>Tired of keeping track manually, I decided to make my own home inventory system. This system would allow me to:</p>
<ul>
<li>create records for each item, along with helpful information such as price and quantity</li>
<li>filter items on the basis of different criteria such as price, quantity and expiration date</li>
<li>sort items based on given criteria</li>
<li>delete items no longer in use</li>
<li>edit existing records</li>
</ul>
<p>In this tutorial I'll walk you through the process of how I built this system. Let's get started.</p>
<h2 id="heading-how-to-define-the-database-schema">How to Define the Database Schema</h2>
<p><a target="_blank" href="https://firebase.google.com/docs/firestore">Cloud Firestore</a> is a cloud-hosted, scalable, flexible NoSQL database offered by Firebase. Data is stored in documents, and documents are grouped together into collections, similar to storing pages of information in a file and keeping multiple files together in a drawer. </p>
<p>Firestore offers powerful querying options ranging from simple sorting to adding limits to query results. </p>
<p>For our purposes, we'll define a Collection for a specific category. Each Document will correspond to a product within that category and the contents of a Document will be each field of information along with it's data value. For example: </p>
<pre><code class="lang-python"><span class="hljs-string">"Snacks"</span> : {
    <span class="hljs-string">"Food_Item_1"</span> : { <span class="hljs-string">"Price"</span>:P1, <span class="hljs-string">"Quantity"</span>:Q1, <span class="hljs-string">"ExpiryDate"</span>:D1},
    <span class="hljs-string">"Food_Item_2"</span> : { <span class="hljs-string">"Price"</span>:P2, <span class="hljs-string">"Quantity"</span>:Q2, <span class="hljs-string">"ExpiryDate"</span>:D2},    
    .
    .
    <span class="hljs-string">"Food_Item_N"</span> : { <span class="hljs-string">"Price"</span>:PN, <span class="hljs-string">"Quantity"</span>:QN, <span class="hljs-string">"ExpiryDate"</span>:DN}
}
</code></pre>
<p>Our Collection name would be Snacks, our Document names would be Food_Item_1, Food_Item_2 and so on, and the contents of each document would be price, quantity and expiry date.</p>
<h2 id="heading-how-to-get-input-from-the-user">How to Get Input from the User</h2>
<p>Let's first create a few routes and views and import the required node modules. </p>
<pre><code><span class="hljs-keyword">const</span> express = <span class="hljs-built_in">require</span>(<span class="hljs-string">"express"</span>)
<span class="hljs-keyword">const</span> app = express()
<span class="hljs-comment">//Middleware to parse data in body portion of incoming request, like POST //request</span>
<span class="hljs-keyword">const</span> body_parser = <span class="hljs-built_in">require</span>(<span class="hljs-string">"body-parser"</span>)

objForUrlencoded = body_parser.urlencoded({<span class="hljs-attr">extended</span>:<span class="hljs-literal">false</span>})

app.set(<span class="hljs-string">"view engine"</span>, <span class="hljs-string">"ejs"</span>)
app.use(<span class="hljs-string">"/assets"</span>, express.static(<span class="hljs-string">"assets"</span>))
app.use(objForUrlencoded)

app.get(<span class="hljs-string">"/"</span>, <span class="hljs-function">(<span class="hljs-params">req,res,next</span>)=&gt;</span>{<span class="hljs-comment">//Show the homepage</span>
    res.render(<span class="hljs-string">"homepage"</span>)
})
app.get(<span class="hljs-string">"/save_data.ejs"</span>, <span class="hljs-function">(<span class="hljs-params">req,res,next</span>)=&gt;</span>{<span class="hljs-comment">//Show the form for saving data</span>
    res.render(<span class="hljs-string">"save_data"</span>)
})
app.get(<span class="hljs-string">"/search_data.ejs"</span>, <span class="hljs-function">(<span class="hljs-params">req,res,next</span>)=&gt;</span>{<span class="hljs-comment">//Show the form for searching data</span>
    res.render(<span class="hljs-string">"search_data"</span>)
})

app.listen(<span class="hljs-number">1337</span>, <span class="hljs-function">()=&gt;</span>{ <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"Listening on port 1337"</span>)})
</code></pre><p>Here we define a simple Express app which listens on port 1337 and renders pages as specified by the HTTP method (GET, POST) and URL. We create a simple form for user input. </p>
<p>Keep in mind that each HTML input field must have a name attribute which will later on serve as a key to access the corresponding values of the input field. For example:</p>
<pre><code>&lt;input type=<span class="hljs-string">"text"</span> name=<span class="hljs-string">"productName"</span>&gt;
<span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">br</span>/&gt;</span></span><span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">br</span>/&gt;</span></span>
<span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">label</span> <span class="hljs-attr">for</span>=<span class="hljs-string">"productCategory"</span>&gt;</span>Product Category:<span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span></span>
<span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">select</span> <span class="hljs-attr">name</span>=<span class="hljs-string">"productCategory"</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">option</span> <span class="hljs-attr">value</span>=<span class="hljs-string">"Snacks"</span>&gt;</span>Snacks<span class="hljs-tag">&lt;/<span class="hljs-name">option</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">option</span> <span class="hljs-attr">value</span>=<span class="hljs-string">"Biscuits"</span>&gt;</span>Biscuits<span class="hljs-tag">&lt;/<span class="hljs-name">option</span>&gt;</span>
     <span class="hljs-tag">&lt;<span class="hljs-name">option</span> <span class="hljs-attr">value</span>=<span class="hljs-string">"Spices"</span>&gt;</span>Spices<span class="hljs-tag">&lt;/<span class="hljs-name">option</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">select</span>&gt;</span></span>
<span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">br</span>/&gt;</span></span><span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">br</span>/&gt;</span></span>
<span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">label</span> <span class="hljs-attr">for</span>=<span class="hljs-string">"price"</span>&gt;</span>Price:<span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span></span>
  &lt;input type="number" name="price"&gt;
&lt;br/&gt;&lt;br/&gt;
&lt;label for="quantity"&gt;Quantity:&lt;/label&gt;
  &lt;input type="number" name="quantity"&gt;
</code></pre><p>Later we can access the name of the product as the value of key "productName", the category of the product as the value of the key "productCategory", and so on.</p>
<h2 id="heading-how-to-save-data-to-the-database">How to Save Data to the Database</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/04/image-124.png" alt="Image" width="600" height="400" loading="lazy">
<em>Simple UI of the home inventory system</em></p>
<p>Okay then, now that we've got some data, let's save it to Firestore! This involves setting up a service account, obtaining a secret key, and using that to initialize the Credentials object to connect the database to our app using the Firebase Admin API. </p>
<p>For a more in-depth explanation of the process, you can check out their <a target="_blank" href="https://firebase.google.com/docs/database/admin/start">docs</a>. </p>
<pre><code><span class="hljs-comment">/*Set up Admin API for Firebase*/</span>
<span class="hljs-keyword">const</span> admin = <span class="hljs-built_in">require</span>(<span class="hljs-string">'firebase-admin'</span>);
<span class="hljs-comment">//Define path to secret key generated for service account</span>
<span class="hljs-keyword">const</span> serviceAccount = <span class="hljs-built_in">require</span>(PATH TO KEY);
<span class="hljs-comment">//Initialize the app</span>
admin.initializeApp({
  <span class="hljs-attr">credential</span>: admin.credential.cert(serviceAccount)
});
</code></pre><p>Here, we've used the path to the secret key which is a JSON file. You can do the same by defining environment variables as described <a target="_blank" href="https://firebase.google.com/docs/admin/setup#prerequisites">here</a>. </p>
<p>Next, we save our data to Firestore using the set method as follows:</p>
<pre><code><span class="hljs-keyword">let</span> db = admin.firestore()

<span class="hljs-comment">//Depending on your schema, save data by specifying the collection name, //document name and data contents as follows</span>
<span class="hljs-keyword">await</span> db.collection(key).doc(prod).set(save_to_database[key][prod])
</code></pre><p>Here are a few terms you should be familiar with while navigating the Firestore docs, particularly the <a target="_blank" href="https://firebase.google.com/docs/reference/js/firebase.firestore.CollectionReference">API reference</a>:</p>
<ul>
<li><strong>CollectionReference</strong> – this object is used for adding documents, getting DocumentReferences, and querying documents.</li>
<li><strong>DocumentReference</strong> – this refers to a document location in the database used to read/write/listen to that location.</li>
<li><strong>QuerySnapshot</strong> – an object that contains the results of a query</li>
<li><strong>DocumentSnapshot</strong> – contains data read from a document. You can extract the data using the .data() method.</li>
</ul>
<h2 id="heading-how-to-query-the-data">How to Query the Data</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/04/image-125.png" alt="Image" width="600" height="400" loading="lazy">
<em>Simple UI for searching/filtering the data</em></p>
<p>Once Firestore is packed with data, we can perform all sorts of complex queries on it. </p>
<p>Let's say we want to know how many items we have with the Category "Snacks". Whenever we execute a query, we get a QuerySnapshot which is a list of DocumentSnapshots. </p>
<pre><code><span class="hljs-comment">//Get all docs under the given category</span>
helper_func_get_data = <span class="hljs-keyword">async</span> (category, db) =&gt; {
    <span class="hljs-keyword">const</span> data = <span class="hljs-keyword">await</span> db.collection(category).get()
    <span class="hljs-keyword">if</span>(data.empty)
        {
            <span class="hljs-keyword">return</span> <span class="hljs-number">-1</span>
        }
    <span class="hljs-keyword">else</span> <span class="hljs-keyword">return</span> data

}
</code></pre><p>We can check if the query returned any data at all using the .empty property and iterate over all received documents using the forEach function like this:</p>
<pre><code>data.forEach(<span class="hljs-function">(<span class="hljs-params">doc</span>) =&gt;</span> { Product_Info[doc.id] = doc.data()})

<span class="hljs-comment">//Here data is a QuerySnapshot and Product_Info is a JavaScript object </span>
<span class="hljs-comment">//with document names as keys and their corresponding values. We can pass this </span>
<span class="hljs-comment">//object as an argument in render() method to display the received contents</span>
</code></pre><p>Here's how to figure out the total price of all Snacks:</p>
<pre><code>total_agg = <span class="hljs-number">0</span>
data.forEach(<span class="hljs-function">(<span class="hljs-params">doc</span>) =&gt;</span> { total_agg+=doc.data()[aggregate_over]

<span class="hljs-comment">//aggregate_over is a variable which defines criteria to sum over like price //or quantity</span>
</code></pre><p>To sort all Snacks on the basis of their price, do this:</p>
<pre><code><span class="hljs-keyword">const</span> data = <span class="hljs-keyword">await</span> db.collection(category).orderBy(filter_criteria).get()
</code></pre><p>where filter_criteria = "Price".</p>
<h2 id="heading-how-to-delete-items-from-the-database">How to Delete Items from the Database</h2>
<p>Over time, our household items that we consume daily are depleted and we'll need to delete them from the database to maintain consistency. </p>
<p>Until there's a feasible mechanism to connect the refrigerator to Cloud Firestore, we'll have to manually delete our records for Snacks once we've eaten them.</p>
<pre><code>firebase_delete_data = <span class="hljs-keyword">async</span> (category, response, product_name) =&gt; {
    <span class="hljs-keyword">try</span>
    { 
      <span class="hljs-keyword">let</span> db = admin.firestore()
      <span class="hljs-keyword">await</span> db.collection(category).doc(product_name).delete()
      response.render(<span class="hljs-string">"search_data"</span>)
       }
    <span class="hljs-keyword">catch</span>(err)
    {<span class="hljs-built_in">console</span>.log(err)}
}
</code></pre><h2 id="heading-how-to-update-items-in-the-database">How to Update Items in the Database</h2>
<pre><code>firebase_update_data = <span class="hljs-keyword">async</span> (category, response, reqbody) =&gt; {
    <span class="hljs-keyword">try</span>
    {
        <span class="hljs-keyword">let</span> db = admin.firestore()
        <span class="hljs-keyword">await</span> db.collection(category).doc(reqbody[<span class="hljs-string">"productName"</span>]).update({<span class="hljs-string">"Price"</span>: <span class="hljs-built_in">parseFloat</span>(reqbody[<span class="hljs-string">"price"</span>]), <span class="hljs-string">"Quantity"</span>: <span class="hljs-built_in">parseFloat</span>(reqbody[<span class="hljs-string">"quantity"</span>]), <span class="hljs-string">"ExpiryDate"</span>: reqbody[<span class="hljs-string">"expiryDate"</span>]})
        response.render(<span class="hljs-string">"successpage"</span>)
    }
    <span class="hljs-keyword">catch</span>(err)
    {
        <span class="hljs-built_in">console</span>.log(err)
        response.render(<span class="hljs-string">"failurepage"</span>)
    }
}
</code></pre><p>Another common functionality we'll want to have is to update existing records in the database. </p>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/04/image-126.png" alt="Image" width="600" height="400" loading="lazy">
<em>Simple UI for updating product details</em></p>
<p>Once our functionalities are implemented, we export the functions to use from our Express app like this:</p>
<pre><code><span class="hljs-built_in">module</span>.exports = {
    <span class="hljs-string">"firebase_save_data"</span> : firebase_save_data,
    <span class="hljs-string">"firebase_retrieve_data"</span>: firebase_retrieve_data,
    <span class="hljs-string">"firebase_delete_data"</span>: firebase_delete_data,
    <span class="hljs-string">"firebase_update_data"</span>: firebase_update_data
    }
</code></pre><p>and import the required module as follows:</p>
<pre><code><span class="hljs-keyword">const</span> firebase_functions = <span class="hljs-built_in">require</span>(<span class="hljs-string">"./firebase_CRUD_custom_code/firebase_functions.js"</span>)
</code></pre><p>Then we can use our functions as required. For example, if we want to update any items we can do the following:</p>
<pre><code>app.post(<span class="hljs-string">"/update"</span>, objForUrlencoded, <span class="hljs-function">(<span class="hljs-params">req,res</span>) =&gt;</span> {

    firebase_functions.firebase_update_data(req.body[<span class="hljs-string">"category"</span>], res, req.body)
})
</code></pre><h2 id="heading-wrapping-up">Wrapping up!</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/04/image-127.png" alt="Image" width="600" height="400" loading="lazy"></p>
<p>To wrap up, in this article we learned about the data model of Cloud Firestore, how to save data, the mechanism for retrieving data, how to work with QuerySnapshots, sorting data on different filters, deleting items, and updating items through our Express app. </p>
<p>In this way, we can automate the task of tracking frequently used products in our households. We can also check which products are out of stock and so much more to make our busy lives easier. </p>
<p>I hope you enjoyed reading this article just as much as I enjoyed writing it. Thank you for your time, have a good day and happy coding!</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ How to Add Authentication to React Native in Three Steps Using Firebase ]]>
                </title>
                <description>
                    <![CDATA[ By Said Hayani Authentication allows us to secure our apps, or limit access for non-user members. Authentication can also be used, for example, to limit access to a paid service or specific service.  That's just one example of how authentication can ... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/how-to-add-authentication-to-react-native-in-three-steps-using-firebase/</link>
                <guid isPermaLink="false">66d460d04bc8f441cb6df823</guid>
                
                    <category>
                        <![CDATA[ 100DaysOfCode ]]>
                    </category>
                
                    <category>
                        <![CDATA[ authentication ]]>
                    </category>
                
                    <category>
                        <![CDATA[ coding ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Firebase ]]>
                    </category>
                
                    <category>
                        <![CDATA[ #firebase-cloud-functions ]]>
                    </category>
                
                    <category>
                        <![CDATA[ JavaScript ]]>
                    </category>
                
                    <category>
                        <![CDATA[ learning to code ]]>
                    </category>
                
                    <category>
                        <![CDATA[ programing ]]>
                    </category>
                
                    <category>
                        <![CDATA[ React Native ]]>
                    </category>
                
                    <category>
                        <![CDATA[ tech  ]]>
                    </category>
                
                    <category>
                        <![CDATA[ technology ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Wed, 22 Apr 2020 04:22:18 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2020/04/rn-firebase-auth.png" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Said Hayani</p>
<p>Authentication allows us to secure our apps, or limit access for non-user members. Authentication can also be used, for example, to limit access to a paid service or specific service. </p>
<p>That's just one example of how authentication can be in your app. Today we will add authentication to a React Native app using Firebase.</p>
<h2 id="heading-1-installing-react-native-firebase">1 Installing react-native-firebase</h2>
<p>The first thing we do is install and initialize Firebase inside our app. In React Native we need to use a Firebase Container for React Native. We are going to use <a target="_blank" href="https://github.com/invertase/react-native-firebase">react-native-firebase</a>.</p>
<p>If you are about to start a new React Native app from scratch and you would like to use Firebase, you are lucky - you can install react-native-firebase pre-integrated using the React Native CLI.</p>
<pre><code class="lang-shell">//
npx @react-native-community/cli init --template=@react-native-firebase/template authenticationFirebase
//** source: https://invertase.io/oss/react-native-firebase/quick-start/new-project
</code></pre>
<p>Then just install the pod for iOS by running the following command inside the root directory of your app.</p>
<pre><code class="lang-shell">cd ios &amp;&amp; pod install
</code></pre>
<p>If you are having issues installing a new project with Firebase please refer to <a target="_blank" href="https://invertase.io/oss/react-native-firebase/quick-start/new-project">react-native-firebase docs</a></p>
<h3 id="heading-adding-react-native-firebase-to-an-existing-project">Adding react-native-firebase to an existing project</h3>
<p>Install the <code>react-native-firebase</code> package using yarn or npm</p>
<pre><code class="lang-shell"> yarn add @react-native-firebase/app
</code></pre>
<p>or:</p>
<pre><code class="lang-shell"> npm install @react-native-firebase/app
</code></pre>
<p>Then install pods for iOS.</p>
<p><code>shell cd ios &amp;&amp; pod install</code></p>
<h3 id="heading-running-the-app">Running the app</h3>
<p>For iOS, there are two ways to do it: I personally use Xcode, as it gives me a clear idea if something went wrong and the build failed.
<img src="build-xcode.gif" alt="Xcode" width="600" height="400" loading="lazy"></p>
<p>Always make sure the package is running - hit <code>yarn start</code> to start the app.</p>
<p>The second way to run the app on iOS is running the react-native run-ios command - and that's it.</p>
<h2 id="heading-adding-firebase-credentials">Adding firebase credentials</h2>
<p>This step requires us to create a new project in <a target="_blank" href="https://console.firebase.google.com/">the Firebase console </a>.</p>
<p>After creating a new project on the dashboard page select <strong>add Firebase to iOS app</strong>. This will show you the steps to add credentials to iOS like below.</p>
<p>It consists of a few steps :</p>
<ul>
<li><p>Download the <code>GoogleService-info.plist</code> file and put it inside the iOS folder within your project.
<img src="https://www.freecodecamp.org/news/content/images/2020/04/add-firebase-ios.png" alt="add-firebase-ios" width="600" height="400" loading="lazy"></p>
</li>
<li><p>Initialize Firebase</p>
</li>
</ul>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/04/initialize-firebase.png" alt="initialize-firebase" width="600" height="400" loading="lazy"></p>
<h2 id="heading-for-android">For Android</h2>
<p>Android has a different setup for Firebase. In project settings in the Firebase console select <strong>add Firebase to Android</strong>.
<img src="https://www.freecodecamp.org/news/content/images/2020/04/firebase-to-android.png" alt="firebase-to-android" width="600" height="400" loading="lazy"></p>
<p>You can put any name you like in the app name input - just make sure it conforms to the Firebase requirements. Then click <strong>Register</strong>.</p>
<p>After that, you need to download the <code>google-services.json</code> file and put it within the android/app folder.</p>
<p>Then the next step is to initialize the Android SDK.
<img src="https://www.freecodecamp.org/news/content/images/2020/04/add-android-sdk.png" alt="add-android-sdk" width="600" height="400" loading="lazy"></p>
<p>The last step is to apply the Firebase plugin inside: <code>android/app/build.gradle</code> .</p>
<pre><code class="lang-shell">apply plugin: 'com.google.gms.google-services'
</code></pre>
<p>If you have any issues running the steps above you can always refer to the <a target="_blank" href="https://firebase.google.com/docs">Firebase docs</a> or <a target="_blank" href="https://rnfirebase.io/">react-native-firebase</a> websites.</p>
<p>Now that we are done with the integration, the next step is to implement Firebase functions to create users and sign in in React Native.</p>
<h2 id="heading-adding-signin-login">Adding SignIn, Login</h2>
<p>This phase is simple: just some React and JavaScript code to call Firebase functions. I'm going to create a simple UI for Login and SignUp (this is not necessary for this tutorial so you can skip this step).</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/04/loginComponent.gif" alt="loginComponent" width="600" height="400" loading="lazy"></p>
<blockquote>
<p>I will put the full source code at the end of article *</p>
</blockquote>
<p>We will use the <code>createUserWithEmailAndPassword</code> function to sign up for a new user. I already implemented all the validation on the form - we just need to call this function to create a user.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/04/form-validation.gif" alt="form-validation" width="600" height="400" loading="lazy"></p>
<p>When the user presses the Continue button, <code>__doSignUp</code> will be called and the code looks like this:</p>
<pre><code class="lang-jsx"><span class="hljs-keyword">const</span> __doSignUp = <span class="hljs-function">() =&gt;</span> {
  <span class="hljs-keyword">if</span> (!email) {
    setError(<span class="hljs-string">"Email required *"</span>)
    setValid(<span class="hljs-literal">false</span>)
    <span class="hljs-keyword">return</span>
  } <span class="hljs-keyword">else</span> <span class="hljs-keyword">if</span> (!password &amp;&amp; password.trim() &amp;&amp; password.length &gt; <span class="hljs-number">6</span>) {
    setError(<span class="hljs-string">"Weak password, minimum 5 chars"</span>)
    setValid(<span class="hljs-literal">false</span>)
    <span class="hljs-keyword">return</span>
  } <span class="hljs-keyword">else</span> <span class="hljs-keyword">if</span> (!__isValidEmail(email)) {
    setError(<span class="hljs-string">"Invalid Email"</span>)
    setValid(<span class="hljs-literal">false</span>)
    <span class="hljs-keyword">return</span>
  }

  __doCreateUser(email, password)
}

<span class="hljs-keyword">const</span> __doCreateUser = <span class="hljs-keyword">async</span> (email, password) =&gt; {
  <span class="hljs-keyword">try</span> {
    <span class="hljs-keyword">let</span> response = <span class="hljs-keyword">await</span> auth().createUserWithEmailAndPassword(email, password)
    <span class="hljs-keyword">if</span> (response) {
      <span class="hljs-built_in">console</span>.log(tag, <span class="hljs-string">"?"</span>, response)
    }
  } <span class="hljs-keyword">catch</span> (e) {
    <span class="hljs-built_in">console</span>.error(e.message)
  }
}
</code></pre>
<p>Make sure you installed <code>@react-native-firebase/auth</code>to be able to call <code>auth().createUserWithEmailAndPassword(email, password)</code></p>
<pre><code class="lang-jsx"><span class="hljs-comment">// import auth</span>
<span class="hljs-keyword">import</span> auth <span class="hljs-keyword">from</span> <span class="hljs-string">"@react-native-firebase/auth"</span>
</code></pre>
<p>The function that creates a new user in Firebase looks like this:</p>
<pre><code class="lang-jsx"><span class="hljs-keyword">const</span> __doCreateUser = <span class="hljs-keyword">async</span> (email, password) =&gt;{
    <span class="hljs-keyword">try</span> {
     <span class="hljs-keyword">let</span> response =  <span class="hljs-keyword">await</span> auth().createUserWithEmailAndPassword(email, password);
      <span class="hljs-keyword">if</span>(response){
        <span class="hljs-built_in">console</span>.log(tag,<span class="hljs-string">"?"</span>,response)
      }
    } <span class="hljs-keyword">catch</span> (e) {
      <span class="hljs-built_in">console</span>.error(e.message);
    }
</code></pre>
<p>If the function throws an error, make sure to enable the email / password method in the authentication section in the Firebase console.
<img src="https://www.freecodecamp.org/news/content/images/2020/04/enable-email-auth.png" alt="enable-email-auth" width="600" height="400" loading="lazy"></p>
<p>If everything went well, and the data entered (email, password) is valid, an alert will show up. If you check the Authentication section in the Firebase console you will notice that a new user has been created.
<img src="https://www.freecodecamp.org/news/content/images/2020/04/signUpSuccess.gif" alt="signUpSuccess" width="600" height="400" loading="lazy"></p>
<p>Here is the source code of <code>SignInComponent</code>.</p>
<pre><code class="lang-jsx"><span class="hljs-keyword">const</span> SigInComponent = <span class="hljs-function">() =&gt;</span> {
  <span class="hljs-keyword">const</span> [email, setEmail] = useState(<span class="hljs-string">""</span>)
  <span class="hljs-keyword">const</span> [password, setPassword] = useState(<span class="hljs-string">""</span>)
  <span class="hljs-keyword">const</span> [fetching, setFetching] = useState(<span class="hljs-literal">false</span>)
  <span class="hljs-keyword">const</span> [error, setError] = useState(<span class="hljs-string">""</span>)
  <span class="hljs-keyword">const</span> [isValid, setValid] = useState(<span class="hljs-literal">true</span>)
  <span class="hljs-keyword">const</span> __doSignUp = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-keyword">if</span> (!email) {
      setError(<span class="hljs-string">"Email required *"</span>)
      setValid(<span class="hljs-literal">false</span>)
      <span class="hljs-keyword">return</span>
    } <span class="hljs-keyword">else</span> <span class="hljs-keyword">if</span> (!password &amp;&amp; password.trim() &amp;&amp; password.length &gt; <span class="hljs-number">6</span>) {
      setError(<span class="hljs-string">"Weak password, minimum 5 chars"</span>)
      setValid(<span class="hljs-literal">false</span>)
      <span class="hljs-keyword">return</span>
    } <span class="hljs-keyword">else</span> <span class="hljs-keyword">if</span> (!__isValidEmail(email)) {
      setError(<span class="hljs-string">"Invalid Email"</span>)
      setValid(<span class="hljs-literal">false</span>)
      <span class="hljs-keyword">return</span>
    }

    __doCreateUser(email, password)
  }

  <span class="hljs-keyword">const</span> __doCreateUser = <span class="hljs-keyword">async</span> (email, password) =&gt; {
    <span class="hljs-keyword">try</span> {
      <span class="hljs-keyword">let</span> response = <span class="hljs-keyword">await</span> auth().createUserWithEmailAndPassword(
        email,
        password
      )
      <span class="hljs-keyword">if</span> (response &amp;&amp; response.user) {
        Alert.alert(<span class="hljs-string">"Success ✅"</span>, <span class="hljs-string">"Account created successfully"</span>)
      }
    } <span class="hljs-keyword">catch</span> (e) {
      <span class="hljs-built_in">console</span>.error(e.message)
    }
  }

  <span class="hljs-keyword">return</span> (
    <span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">SafeAreaView</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.containerStyle}</span>&gt;</span>
      <span class="hljs-tag">&lt;<span class="hljs-name">View</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{{</span> <span class="hljs-attr">flex:</span> <span class="hljs-attr">0.2</span> }}&gt;</span>
        {!!fetching &amp;&amp; <span class="hljs-tag">&lt;<span class="hljs-name">ActivityIndicator</span> <span class="hljs-attr">color</span>=<span class="hljs-string">{blue}</span> /&gt;</span>}
      <span class="hljs-tag">&lt;/<span class="hljs-name">View</span>&gt;</span>
      <span class="hljs-tag">&lt;<span class="hljs-name">View</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.headerContainerStyle}</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">Text</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.headerTitleStyle}</span>&gt;</span> Sign Up <span class="hljs-tag">&lt;/<span class="hljs-name">Text</span>&gt;</span>
      <span class="hljs-tag">&lt;/<span class="hljs-name">View</span>&gt;</span>
      <span class="hljs-tag">&lt;<span class="hljs-name">View</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.formContainerStyle}</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">TextInput</span>
          <span class="hljs-attr">label</span>=<span class="hljs-string">{</span>"<span class="hljs-attr">Email</span>"}
          <span class="hljs-attr">autoCapitalize</span>=<span class="hljs-string">{false}</span>
          <span class="hljs-attr">keyboardType</span>=<span class="hljs-string">"email-address"</span>
          <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.textInputStyle}</span>
          <span class="hljs-attr">placeholder</span>=<span class="hljs-string">"Mail address"</span>
          <span class="hljs-attr">onChangeText</span>=<span class="hljs-string">{text</span> =&gt;</span> {
            setError
            setEmail(text)
          }}
          error={isValid}
        /&gt;

        <span class="hljs-tag">&lt;<span class="hljs-name">TextInput</span>
          <span class="hljs-attr">label</span>=<span class="hljs-string">{</span>"<span class="hljs-attr">Password</span>"}
          <span class="hljs-attr">secureTextEntry</span>
          <span class="hljs-attr">autoCapitalize</span>=<span class="hljs-string">{false}</span>
          <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.textInputStyle}</span>
          <span class="hljs-attr">selectionColor</span>=<span class="hljs-string">{blue}</span>
          <span class="hljs-attr">placeholder</span>=<span class="hljs-string">"Password"</span>
          <span class="hljs-attr">error</span>=<span class="hljs-string">{isValid}</span>
          <span class="hljs-attr">onChangeText</span>=<span class="hljs-string">{text</span> =&gt;</span> setPassword(text)}
        /&gt;
      <span class="hljs-tag">&lt;/<span class="hljs-name">View</span>&gt;</span>
      {error ? (
        <span class="hljs-tag">&lt;<span class="hljs-name">View</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.errorLabelContainerStyle}</span>&gt;</span>
          <span class="hljs-tag">&lt;<span class="hljs-name">Text</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.errorTextStyle}</span>&gt;</span>{error}<span class="hljs-tag">&lt;/<span class="hljs-name">Text</span>&gt;</span>
        <span class="hljs-tag">&lt;/<span class="hljs-name">View</span>&gt;</span>
      ) : null}
      <span class="hljs-tag">&lt;<span class="hljs-name">View</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.signInButtonContainerStyle}</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">TouchableHighlight</span>
          <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.signInButtonStyle}</span>
          <span class="hljs-attr">onPress</span>=<span class="hljs-string">{__doSignUp}</span>
          <span class="hljs-attr">underlayColor</span>=<span class="hljs-string">{blue}</span>
        &gt;</span>
          <span class="hljs-tag">&lt;<span class="hljs-name">View</span>
            <span class="hljs-attr">style</span>=<span class="hljs-string">{{</span>
              <span class="hljs-attr">flexDirection:</span> "<span class="hljs-attr">row</span>",
              <span class="hljs-attr">justifyContent:</span> "<span class="hljs-attr">space-around</span>",
            }}
          &gt;</span>
            <span class="hljs-tag">&lt;<span class="hljs-name">Text</span> <span class="hljs-attr">style</span>=<span class="hljs-string">{styles.signInButtonTextStyle}</span>&gt;</span>Continue<span class="hljs-tag">&lt;/<span class="hljs-name">Text</span>&gt;</span>
          <span class="hljs-tag">&lt;/<span class="hljs-name">View</span>&gt;</span>
        <span class="hljs-tag">&lt;/<span class="hljs-name">TouchableHighlight</span>&gt;</span>
      <span class="hljs-tag">&lt;/<span class="hljs-name">View</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">SafeAreaView</span>&gt;</span></span>
  )
}
</code></pre>
<p>For <code>LoginComponent</code> it’s mostly the same the only thing we need to change is we use <code>signInWithEmailAndPassword</code> method instead.</p>
<pre><code class="lang-jsx"><span class="hljs-keyword">const</span> __doSingIn = <span class="hljs-keyword">async</span> (email, password) =&gt; {
  <span class="hljs-keyword">try</span> {
    <span class="hljs-keyword">let</span> response = <span class="hljs-keyword">await</span> auth().signInWithEmailAndPassword(email, password)
    <span class="hljs-keyword">if</span> (response &amp;&amp; response.user) {
      Alert.alert(<span class="hljs-string">"Success ✅"</span>, <span class="hljs-string">"Authenticated successfully"</span>)
    }
  } <span class="hljs-keyword">catch</span> (e) {
    <span class="hljs-built_in">console</span>.error(e.message)
  }
}
</code></pre>
<p>![loginSuccess](loginSuccess.gif</p>
<p>And the authentication has been successfully implemented in our app ??</p>
<p>Just one last thing: if we have to verify if the user is already logged in, we need to display something else instead of the Login or SignIn screens. For example, we can display the Home screen.</p>
<p>We can use a Firebase module to verify a session. It can be imported from the auth module.</p>
<pre><code class="lang-jsx"><span class="hljs-keyword">import</span> auth, { firebase } <span class="hljs-keyword">from</span> <span class="hljs-string">"@react-native-firebase/auth"</span>
</code></pre>
<pre><code class="lang-jsx"> componentDidMount() {
    <span class="hljs-comment">//  this.register("said1292@gmail.com", "123456");</span>
    <span class="hljs-built_in">this</span>.__isTheUserAuthenticated();
  }

  __isTheUserAuthenticated = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-keyword">let</span> user = firebase.auth().currentUser.uid;
    <span class="hljs-keyword">if</span> (user) {
      <span class="hljs-built_in">console</span>.log(tag,  user);
      <span class="hljs-built_in">this</span>.setState({ <span class="hljs-attr">authenticated</span>: <span class="hljs-literal">true</span> });
    } <span class="hljs-keyword">else</span> {
      <span class="hljs-built_in">this</span>.setState({ <span class="hljs-attr">authenticated</span>: <span class="hljs-literal">false</span> });
    }
  };
</code></pre>
<p>And we can change the UI based on if the user is authenticated or not. We can display user info by just using the same method.</p>
<pre><code class="lang-jsx">firebase.auth().currentUser.email <span class="hljs-comment">// said543@gmail.com</span>
</code></pre>
<p>And to logout, you can just call <code>await firebase.auth().signOut()</code>;</p>
<p>I’m sure integrating navigation like <a target="_blank" href="https://reactnavigation.org/">react-navigation </a> would be awesome, but it was not our focus in this article. So feel free to add navigation so you can just navigate based on the user status.</p>
<p>Feel free to check out the full source code ?on <a target="_blank" href="https://github.com/hayanisaid/react-native-authentication-firebase">GitHub</a></p>
<p><em>Thanks for reading</em>.</p>
<p>Originally published on <a target="_blank" href="https://saidhayani.com/How%20to%20Add%20authentication%20to%20React%20Native%20in%20three%20steps%20using%C2%A0Firebase/">saidhayani.com</a></p>
<h3 id="heading-learn-more-about-react-nativehttpssaidhayanicom"><a target="_blank" href="https://saidhayani.com/">Learn more about React native</a>.</h3>
<ul>
<li><a target="_blank" href="https://twitter.com/SaidHYN">Twitter</a></li>
<li><a target="_blank" href="https://github.com/hayanisaid">GitHub</a></li>
<li><a target="_blank" href="https://www.instagram.com/saaed_happy/">Instagram</a></li>
<li><a target="_blank" href="http://eepurl.com/dk9OJL">Join the mail-list</a></li>
</ul>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ Firebase Cloud Functions: the great, the meh, and the ugly ]]>
                </title>
                <description>
                    <![CDATA[ By Pier Bover When I reviewed Firebase last year, I complained that it wasn’t completely serverless. A Node server was still needed for common functionalities such as sending emails or creating thumbnails. Firebase Cloud Functions were announced a fe... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/firebase-cloud-functions-the-great-the-meh-and-the-ugly-c4562c6dc65d/</link>
                <guid isPermaLink="false">66c34a6e93db2451bd441451</guid>
                
                    <category>
                        <![CDATA[ Cloud Computing ]]>
                    </category>
                
                    <category>
                        <![CDATA[ #firebase-cloud-functions ]]>
                    </category>
                
                    <category>
                        <![CDATA[ General Programming ]]>
                    </category>
                
                    <category>
                        <![CDATA[ serverless ]]>
                    </category>
                
                    <category>
                        <![CDATA[ tech  ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Tue, 29 May 2018 18:24:33 +0000</pubDate>
                <media:content url="https://cdn-media-1.freecodecamp.org/images/0*P7XjBh6QtYZ5z7wJ." medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Pier Bover</p>
<p>When <a target="_blank" href="https://medium.freecodecamp.org/firebase-the-great-the-meh-and-the-ugly-a07252fbcf15">I reviewed Firebase</a> last year, I complained that it wasn’t completely serverless. A Node server was still needed for common functionalities such as sending emails or creating thumbnails.</p>
<p>Firebase Cloud Functions were announced a few months later. The service is still in beta, but I’ve been using it happily for a couple of months in production.</p>
<p>Let’s see how it’s doing.</p>
<h3 id="heading-what-are-firebase-cloud-functions">What are Firebase Cloud Functions?</h3>
<p>If you’ve never heard of cloud functions before, the concept is quite straightforward. Deploy concise logic to a server in the form of functions and some diligent elves can be magically invoked from limbo to do a task for you. All of this without caring about infrastructure and paying only for execution resources.</p>
<p>In many cases, this new paradigm can simplify writing, maintaining, and running backend code.</p>
<p>Firebase Cloud Functions in particular are like Lego blocks that you can connect to any Firebase service. For example, a function can be triggered when an image is uploaded to Firebase Storage to create a thumbnail, or maybe clean some user data when a node is deleted in the Realtime Database. Pretty much anything of interest that happens in Firebase can trigger a function.</p>
<p>If that isn’t enough, you can also use HTTP to trigger functions with GET, POST, etc. Check out this amazing video on how to combine Firebase Hosting with Cloud Functions to create a complete Express app:</p>
<h3 id="heading-the-great">The Great</h3>
<h4 id="heading-infrastructure-doesnt-get-any-easier-than-this">Infrastructure doesn’t get any easier than this</h4>
<p>Infrastructure is completely abstracted from you, much like the rest of Firebase. Every time a function is triggered, a new virtual server comes to life, does its job, and returns to limbo. Google Cloud’s magic will keep triggering your functions and scale infrastructure according to workload automatically.</p>
<h4 id="heading-pricing">Pricing</h4>
<p>Cloud functions in general are very cost-effective. It’s difficult to compare pricing of cloud providers, but I can say that based on my experience, Firebase Cloud Functions have been <em>ridiculously</em> cheap. It’s hard to believe Google is making any money out of this.</p>
<h4 id="heading-easy-to-use">Easy to use</h4>
<p>As usual with Firebase and Google, the docs are great and you won’t be making mental acrobatics to <em>get it</em>. There are also <a target="_blank" href="https://github.com/firebase/functions-samples">tons of samples on Github</a> to get you started. Deployment auth is handled by the Firebase CLI, so getting a hello world up and running is literally:</p>
<pre><code>firebase init functionsfirebase deploy
</code></pre><p>I think the simplicity of using Firebase and Google Cloud in general is just awesome, specially compared to the competition.</p>
<h4 id="heading-flexible">Flexible</h4>
<p>Like I wrote before, these functions can be triggered by all sorts of events. I bet you will not run out of ideas on how to integrate them with your Firebase project or even the rest of your stack.</p>
<p>Here are some of problems we’ve solved using Firebase Cloud Functions:</p>
<ul>
<li>Generate PDFs for a online invoicing service using Phantom.js, and sign these invoices with some government service</li>
<li>Connect a Go service with a third party SOAP provider (ugh)</li>
<li>Send emails via HTTP from anywhere in our stack</li>
</ul>
<h3 id="heading-the-meh">The Meh</h3>
<h4 id="heading-cold-starts">Cold starts</h4>
<p>Scalability is great, but run time can fluctuate wildly. A simple hello world function can take 3ms to do its job, or a 100ms.</p>
<pre><code>functions.https.onRequest(<span class="hljs-function">(<span class="hljs-params">request, response</span>) =&gt;</span> {    response.send(“Hello <span class="hljs-keyword">from</span> Firebase!”);});
</code></pre><p><img src="https://cdn-media-1.freecodecamp.org/images/1*7oLzO7vAtNeEChBQrYMpiA.png" alt="Image" width="800" height="712" loading="lazy"></p>
<p>These fluctuations are caused by virtual server boot times. If the virtual server that is running your function is awake, the function will trigger instantly. But if the server has to be brought up from limbo, it will obviously need more time to start working. In the cloud functions lingo, this is referred to as warm and cold starts.</p>
<p>In practice, you can’t rely on consistent response times unless you are caching your data, as described in the previous video, or use hacks to keep your functions warm.</p>
<p>Unfortunately cold starts are an unavoidable aspect of dealing with cloud functions (from any provider). You will have to take that into account when deciding to use a cloud function to solve something.</p>
<h4 id="heading-no-scheduler-cron">No scheduler (cron)</h4>
<p>Cloud functions are perfect for doing low traffic tasks like generating reports or doing periodic backups at 2am, but with Firebase or Google Cloud there is no easy way to trigger your functions based on a schedule.</p>
<p>The <a target="_blank" href="https://github.com/firebase/functions-cron">Firebase team recommends</a> creating an App Engine project to orchestrate these triggers. The service really begs for something like the <a target="_blank" href="https://devcenter.heroku.com/articles/scheduler">Heroku Scheduler</a>.</p>
<h4 id="heading-javascript-only">JavaScript only</h4>
<p>Eh, I’m ok with JavaScript, but both Azure and AWS support many more languages. It’s ironic that Google doesn’t support Go in its cloud function service, but AWS does.</p>
<h4 id="heading-node-6">Node 6</h4>
<p>Again, the competition is doing better. Both AWS Lambda and Azure Functions are already running on Node 8. The biggest drawback here is going back to promises without async/await or having to configure Babel on your project.</p>
<h3 id="heading-the-ugly">The Ugly</h3>
<h4 id="heading-dev-workflow">Dev workflow</h4>
<p>With the exception of <a target="_blank" href="https://firebase.google.com/docs/functions/local-emulator#use_firebase_serve_for_https_functions">HTTP triggered functions</a>, you can’t run your functions locally. Functions triggered by a Firebase service have to be deployed to the cloud.</p>
<p>This has many ugly implications:</p>
<ul>
<li>Little mistakes end up costing a lot of time, since new functions take a couple of minutes to start working.</li>
<li>Deployed functions have no obvious versions. All logs of the same function appear to be from the same version. It’s never clear when the new functions are actually working, so your only choice is to manually trigger the functions and See-What-Happens™.</li>
<li>No rollbacks</li>
</ul>
<h4 id="heading-environments">Environments</h4>
<p>On top of the previous points, managing environments is… complicated.</p>
<p>You can add environment variables to your functions projects using the <a target="_blank" href="https://firebase.google.com/docs/functions/config-env">Firebase CLI</a> but, like other aspects of Firebase, this is a naive approach that doesn’t scale well.</p>
<p>You will need credentials to access pretty much anything outside of the Firebase sandbox. For other Google Cloud services, these credentials come in the form of <code>.json</code> files. Multiply that by every environment (dev, production, staging) and you can end up with a royal mess.</p>
<p>I ended up up manually renaming credential files before deploying, or worse, deploying all credentials and selecting the appropriate one at runtime. Please, let me know in the comments if you’ve found a way around this.</p>
<p>I’d love to see an <em>Environment</em> tab in the Firebase Console where I could easily manage these settings for the whole Firebase project. Switching between environments should be as easy as <code>firebase use production</code>.</p>
<h3 id="heading-conclusion">Conclusion</h3>
<p>Other than some friction during dev phase, my experience with Firebase Cloud Functions has been positive. Once deployed, these things are reliable and require zero maintenance as promised. So yes, Firebase is finally completely serverless. Hurrah!</p>
<p>If you are already using Firebase, it’s really a no brainer. Firebase Cloud Functions are a great complement for your project, even if the service is still in beta.</p>
<p>On the other hand, it’s fair to say the competition has a more mature product. If you are not invested in Firebase or Google Cloud, and are considering using cloud functions in your stack, you should probably be looking into what AWS or Azure have to offer as well.</p>
<p>To be completely honest, I’m a bit concerned that the service is still in beta. It’s been over a year since it was announced and progress feels painfully slow. The competition seems far more committed to its cloud products, even if, according the Diane Greene, CEO for Google’s cloud businesses, Google Cloud is the <a target="_blank" href="https://techcrunch.com/2018/02/01/googles-diane-greene-says-billion-dollar-cloud-revenue-already-puts-them-in-elite-company/">“fastest growing cloud”</a>.</p>
<p>That is all.</p>
<p><strong>Note:</strong> In a previous version of this article I claimed that it wasn’t possible to write tests for non HTTP functions. This is wrong, and <a target="_blank" href="https://firebase.google.com/docs/functions/unit-testing#testing_background_non_http_functions">here are the docs</a> on how to do that.</p>
 ]]>
                </content:encoded>
            </item>
        
    </channel>
</rss>
