Mobile and web applications usually require a back-end server. Web applications require a web server to deliver content. Applications also need to store user profiles and media such as images and videos. Communication between the application and the server is often done using an API, which is usually REST.
Applications are coded in a range of languages. An iOS application is written in Swift or Objective-C. Android applications are written in Java or Kotlin. Web applications are written in HTML, CSS, JavaScript, and often complex frameworks such as Angular or React. Front-end developers need to know the relevant languages and their associated development tools.
Back-end servers are written in a range of languages including Go, Java, PHP, and Python. Each of these languages has its own suite of libraries to facilitate writing complex applications.
Most developers consider themselves front-end or back-end developers. Full-stack developers who are proficient in both roles are relatively rare.
Running and maintaining a back-end server has its own challenges. Servers need to be built, updated, and backed up. Servers also need to be secured to prevent accidental or malicious data loss or access to sensitive data. In addition, servers need to have hostnames and IP addresses assigned so that they can be connected to.
What Is Firebase?
Firebase started out as a mobile messaging architecture which was acquired by Google. It has since evolved to be a suite of more than 25 components that interoperate with the Google Cloud Platform.
Firebase consists of software development kits (SDKs), which allow mobile and web developers to access cloud functionality simply, securely, and reliably. They automatically compensate for poor network connectivity. There is a Firebase web console for enabling, administering, and securing components. There are also command line tools and REST APIs for more in-depth usage.
Some Firebase components are better known than others. There are few dependencies between components, which allows for incremental adoption of functionality. Firebase authentication and analytics are the most widely used.
Firebase has evolved to become a platform that allows mobile and web front-end developers to develop complete applications without the need for back-end servers. Recent enhancements have greatly facilitated serverless solutions which provide a viable, scalable, cost-effective alternative to Cloud Virtual Machine server solutions.
Firebase Pricing and Billing Plans
The basic Firebase billing plan, called Spark, is free. There are limits to cloud resource usage, but they are quite generous. It is possible to run a reasonable sized application without incurring any charges.
A website with up to 1GB content and transfers of less than 10GB/month can be hosted under the Spark plan. Firestore allows up to 1GB of data and network traffic of up to 10GB/month. Cloud storage limits are up to 5GB of data and downloads of up to 1GB/day.
If the application needs more resources, a paid billing plan such as pay as you go is required. The Spark plan free limits still apply. Billable charges are quite low. The pricing can be found at the Firebase pricing page.
Virtual machines run in the cloud incur charges while they are running, even if they are not being used. Firebase serverless solutions scale to zero. This means that resources are effectively only running when in use and do not incur charges when not in use. This is ideal for applications for seasonal businesses such as holiday rentals or periodic events such as concerts. There would be a lot of activity followed by months of inactivity.
How to Set Up Firebase
An email account is required for authentication. A Google mail account is preferred. They can be created at https://mail.google.com.
A Google Cloud Platform (GCP) account is also required. A free trial is available here. This gives you $300 credit, which is available for a year. A credit card is required as proof of identity. Google may charge $1 and then refund it. The credit card will be debited monthly if billing is enabled and billable resources are used. There are also Google provider companies who act as intermediates for billing. You pay the provider for cloud usage, and they pay Google. They have their own billing plans and may offer a free trial.
It is important to monitor the billing section of the cloud console frequently to monitor usage. It is easy to keep resources such as storage active when not required, which can incur considerable costs over time.
Firebase projects are also GCP projects. You can create a GCP project and import it into Firebase, or create a Firebase project, which will also create a GCP project. The Firebase console is here.
A different setup is required for different types of applications. The main ones are Android, iOS, and web applications. The setup instructions can be found in the official Firebase Guides.
The Firebase Command Line Interface (CLI) tools are required for some operations. These require that Node.js
and the npm
tool are installed. If running on macOS or Linux, the npm
command will need to be run with sudo
.
sudo npm install -g firebase-tools
Authentication and Authorization
Firebase authentication is perhaps the most widely used Firebase component. Users can select one or more of a number of authentication mechanisms. These are email address and password, telephone numbers, and federated identity providers Google, Facebook, Twitter, and GitHub. Any number of authentication mechanisms can be enabled.
The Firebase UI prompts the user for the mechanism to use:
Firebase provides user interfaces for authentication that can be invoked from a few lines of code on the client side. There are also APIs for doing authentication manually. On successful authentication, an identity token is generated which can be used for back-end validation.
The APIs allow administration users to manage users programmatically. Operations include:
- Creating, updating, and deleting users
- Look up users by search criteria such as email address or telephone number
- Access information such as account creation date and last log-in date and time
- Validate email addresses and telephone numbers without having to use the existing workflows
Most mobile and web applications want large numbers of users to sign into their applications. For example, anyone with a Google Mail account can authenticate themselves to any application that allows Google authentication. A form of authorization is required to restrict access to the application to certain users. This can be easily done by storing associations between email addresses and access roles in data storage. On successful authentication, the email address is looked up in data storage. If the user exists with the correct roles, then access is granted; otherwise, the user is force logged out.
Firebase Hosting
Firebase hosting allows static web content, which includes JavaScript, to be hosted in the cloud without the need for a web server. The content is cached at the edges of a global Content Delivery Network (CDN). This allows fast access to the content from anywhere in the world.
One or more websites can be hosted by adding them to the Hosting section of a Firebase project in the Firebase Console. Content is delivered over SSL and given two URLs of the form, https://site-name.web.app and https://site-name.firebaseapp.com, where site-name
is either the project name or a user-specified site name.
It is very easy to have the site hosted from your own domain name provided you can change the DNS records for the domain. You add your domain name to a site on the Firebase Console. You will then be given a DNS TXT record, which you have to add to your domain’s DNS to prove to Google that you own the domain. Once the TXT record is visible, you can obtain DNS A records for the site. An SSL certificate is automatically provisioned for the site. Once the certificate has been provisioned, the site is available globally. It can, in principle, take several hours for DNS updates and certificate provisioning. In practice, the process can be completed in 20 minutes.
To add content to hosting, first of all, create a directory for the site and cd
into it from the command line. Next, log in to Firebase and initialize the project directory.
firebase login
firebase init
You will be prompted to select a project and which client services are required. Services can always be added later and don’t have to be selected at this stage.
Create a file called firebase.json
, which defines the website root directory and the files to exclude. You will also need a .gitignore
file to exclude files from version control.
{
"hosting": {
"public": "public",
"ignore": [
"firebase.json",
"**/.*",
"**/node_modules/**"
]
}
}
Then, copy the static content into the public directory. Finally, deploy the site into the cloud.
firebase deploy
To change the web content, simply change the content files and issue the deploy command. Each deployment appears as a version on the Firebase Console. You can roll back to a previous version with a single click.
Firebase Hosting can also rewrite URIs to files, Cloud Functions, and Cloud Run. This greatly simplifies things as it is not necessary to assign a domain to these services. The rewrites are defined by adding a rewrites section to the hosting section of firebase.json. The hosting deployment will fail if the service does not exist.
{
"hosting": {
"public": "public",
"rewrites": [
{
"source": "/xxx",
"destination": "/profile.html"
},
{
"source": "/yyy",
"function": "profile"
},
{
"source": "/api{,/**}",
"run": {
"serviceId": "cloud-api",
"region": "europe-west1"
}
}
]
}
}
Data Storage
Firebase provides client APIs for accessing cloud-based data storage. There are three types of storage:
- Realtime Database
- Cloud Firestore
- Cloud Storage
This allows mobile and web clients to store and retrieve data without the need for a server.
Realtime Database
Realtime Database is a cloud-hosted NoSQL database. Data in the Realtime Database is automatically synchronized in real time to all connected devices. It works cross platform to Android, iOS, and web. The data is stored as a JSON tree structure. Security rules can be set to control read and write access to the data.
Each device keeps a local copy of the database. This means that the data is available when not connected to the network. On reconnect, the local and cloud-based copies of the data are synchronized.
The data is read by applications using a listener. A listener listens on a node in the JSON tree. Whenever the data is changed on the console or by another user, the listener callback is called with the new data value. Realtime Database also supports queries. Each query returns a node and all of its child nodes.
The security rules by default allow no access to the data. Rules can be added globally or to individual nodes of the JSON object. Security rules control read and write access to data and can perform validation.
Realtime Database is best suited to small pieces of data that do not require a deeply nested data structure. The free limit is 1GB of data.
Cloud Firestore
Cloud Firestore is seen as the replacement for the Realtime Database. It extends the functionality of Realtime Database. Data is not in a JSON tree but a hierarchical collection of documents. Each document consists of a set of key-value pairs and optional sub-documents. Queries allow more complex filtering and sorting and only return complete documents. Queries do not return sub-documents.
Cloud Firestore will soon replace Cloud Datastore. It can be run in Datastore mode or in native mode. All Datastore applications will be automatically migrated to Cloud Firestore.
Cloud Firestore is best suited to relatively small pieces of data. It can have a deeply nested data structure. The free limit is 1GB of data.
Cloud Storage
Cloud Storage is for storing files such as images and video clips. Mobile and web clients can use Firebase to upload and download files directly to and from the cloud without the need for a back-end server. The free limit is 5GB of data.
Cloud Functions
Cloud Functions are an important technology for creating serverless applications. A cloud function can be written in JavaScript, TypeScript, Python, or Go, which is deployed directly into the Google cloud. A function is triggered by an HTTP request or by an event in the cloud such as writing to Cloud Storage.
A Cloud Function can only handle one request at a time, but the cloud automatically scales the function by replicating it. A Cloud Function written in Python uses the Flask library to handle HTTP requests. The function takes a request object as a parameter and returns the response body.
A simple Python Cloud Function requires a working directory, and the entry point goes in the file main.py
.
def simple_cloud_function(request):
return "It worked"
Dependencies are managed by pip and go into a file called requirements.txt
.
Flask==1.0.2
A function is deployed using the gcloud
command line tool. It specifies the function name, the language, and the trigger.
gcloud functions deploy simple_cloud_function --runtime python37 \
--trigger-http
The URL for the function is displayed on deployment and can be found by running the describe command.
gcloud functions describe simple_cloud_function
Url: https://europe-west1-project-id.cloudfunctions.net/simplecloud_function
Cloud Functions can call Google Cloud and Firebase APIs to provide back-end functionality. They provide logging information about execution startup and execution time. Additional logging can easily be added. The logs can be viewed in the Stackdriver Logging UI and via the gcloud
command line tool.
gcloud functions logs read simple_cloud_function
Functions can be viewed and deleted in the Google Cloud Console.
Cloud Functions are best used for operations that occur relatively infrequently. An example use is to create a thumbnail when an image is uploaded to Cloud Storage. The free limit is 125,000 invocations per month.
Cloud Run
Cloud Run is recently added functionality that greatly facilitates serverless applications. It enables Docker containers to be run in the cloud without having to do complex infrastructure setup. It can run in managed mode, which uses the Knative runtime, which is built on Kubernetes. It can also run on Anthos, which is also built on Kubernetes but allows containers to be run across clouds and even on your own data center. There is no need to set up and manage a Kubernetes cluster as it is all done automatically.
Any application that can be built into Docker images can be managed by Cloud Run. It automatically scales the number of containers based on demand. It also scales down to zero when the service is not being used. Unused services incur no charges.
The Docker containers need to run a web server if they are to respond to HTTP requests. Python service will use Flask. The entry point will be in app.py
.
from flask import Flask, request
app = Flask(__name__)
@app.route(’/api/profile’)
def profile():
page = ’’’
Page content
’’’
return page
The application needs a Dockerfile
to create the image.
FROM python
ENV APP_HOME /app
WORKDIR $APP_HOME
COPY . .
ENV PORT 8080
RUN pip install Flask gunicorn firebase-admin
CMD exec gunicorn --bind :$PORT --workers 1 --threads 8 app:app
Cloud Run containers are deployed directly into the cloud.
gcloud run deploy --image=image_name --platform=managed \
--region=europe-west1 --allow-unauthenticated
If the service name, platform, region, or whether to allow unauthenticated are not defined in the project configuration or supplied on the command line, they will be prompted for. Once deployment is complete, the service URL will be displayed. The URL can also be obtained using the gcloud command.
gcloud run services list
SERVICE REGION URL LAST DEPLOYED BY LAST DEPLOYED AT
cloud-api europe-west1 https://cloud-api-h42ifbxkyq-ew.a.run.app myemail@gmail.com 2020-02-05T10:53:30.006Z
The URL contains a random number that is difficult to manage. This is where Firebase Hosting rewrite rules become most useful.
Services can be viewed and deleted in the Google Cloud Console.
Cloud Run is ideally suited for hosting a REST API. The monthly free limits are 180,000 CPU seconds, 360,000 GB seconds of memory, 2 million requests, and 1GB network egress. The free network egress limit only applies if the service is deployed in a North America region.
Authentication
By default, Cloud Functions and Cloud Run containers are public and can be accessed by anybody on the internet. Using IAM rules in the Cloud Console, the services can be restricted to project members, Google Groups, and individual email addresses.
If restrictions are in place, unauthorized access is forbidden. To enable access, an identity token has to be added to the request headers. The identity token can be obtained using the gcloud command or during the Firebase authentication process.
gcloud auth print-identity-token
An Authorization header is required.
Authorization: Bearer id-token
Summary
Google Cloud Platform and Firebase provide a range of products that greatly facilitate the development of mobile and web applications. The need for a back-end server can be completely eliminated by allowing clients to access cloud functionality directly or by deploying back-end code into the cloud using Cloud Functions or Cloud Run.
Existing applications can be migrated to serverless incrementally. In fact, the way the technology is evolving could mean that traditional virtual machine-based server solutions will no longer be necessary.