Protect Firebase database from reading by other site - firebase

My web app is using Firebase as database, and is going to live soon. Everything is awesome, just one thing I'm aware that my public database can be read by another site without any protection.
For example, my database have a public data set is posts and can read via Anonymous login. Of course all posts are public, people can get them all with several technologies such as crawling, but read directly from Firebase database causing me uncomfortable.
I've read some articles and answered question on SO, for example How to prevent other access to my firebase and feel better a bit.
But for client-only application, there is no other solution to protect firebase public data from reading directly ?

Related

How to secure database without authentication?

I am creating an Unity game where I want to have global top 50 score list with usernames. I use Firebase realtime database. There is no need for user to authenticate. I am not that familiar with database security and pretty beginner with this concept. I am using Rest Api from Unity Asset store because it was pretty easy to send and get data from databse.
How can I be sure that every score sent to database is from my app?
Add a dedicated user with password to your database
Somewhere in you app, add those credentials e.g. in a ScriptableObject / in some component
Always use those credentials to authenticate
Note that your app can still be decompiled and thereby cheated.
You can at least make it more difficult by encrypting the data etc.
The only way really around is to have an account and sessioning server to assure a user is locked in with a valid session.
If you don't use Firebase Authentication, you can't restrict who can access your database. Anyone will be able to issues a query, and they can even do it using the Realtime Database REST API. All they have to know is the name of your project.
Even if you do use Firebase Authentication, anyone may still effectively authenticate and access the database outside of your app using other public APIs.
My experience is that you can't stop dedicated "users" from cheating global at high scores. I made a small handfull of trivial games for windows phone with global top 50. Even if your game is unpopular, and you obfuscate your code, and you are on an unpopular platform, and you encrypt your network traffic: somebody is going to jailbreak their phone, decompile your app, and inject their own high score into your game before high scores are sent to the global list. The only way I ever came up with to combat this was to keep track of play sessions -on the server- to make sure their scores were theoretically possible based on how long they were playing.
Disclaimer: I don't know anything about Firebase
From what I can tell, you will need to set up access for Default and Public sections of your configuration to tell the database who can and cannot access your database. Here's their documentation on Get Started with Database Rules.
In general database access, no one should know the details of your connection to a database, so all calls should only ever come from your app.

Embedding a Firebase Storage Video to Wordpress but Hiding the URL

I need Hide the URL of an embedded video to prevent anyone from accessing the video outside of my domain.
What I want to use Firebase Storage for, is to store and stream the videos which ONLY paid users logged into my site can access.
Is there any way I can hide the URL so that people can only access the videos from within my web page in wordpress?
Thanks!
As Doug said in his comment, it is impossible to completely hide a download URL. There are complicated ways to obscure it, but I would recommend you avoid going down that rabbit hole - none are foolproof.
Instead, you should implement your security using Firebase Storage's built-in security rules - the situation you are describing is EXACTLY what this feature is designed to accomplish. You can put a rule in place that only users who have purchased the course (meaning, they have that video's identifier under their account in the database) are granted access... and you can even limit access to your project (see steps in answer #1) to specific domains.
There are a ton of great resources out there for you to reference while learning how the security rules work. First would be the docs I linked earlier, but they also have some pretty good official Firebase Youtube videos on the subject of rules.
If you are talking about having the videos stored in Firebase, hopefully you are planning to use the rest of Firebase's back-end features... because the ONE BIG ISSUE with this suggestion is that it relies on you using Firebase's built-in authentication. If your users are already logging into your site via an established non-Firebase system you've added to your Wordpress site, then I'm afraid this solution won't be so simple. Not impossible, but not as simple. If that's the case, you will need to pass the customer information to Firebase to login to a duplicated customer account, even if the end user doesn't realize they are being logged in to Firebase, and THEN they will have that special auth token that Firebase security uses to identify & grant access with the security rules.

Understanding the Firebase and purpose of google cloud functions

Let's say I'm developing app like Instagram: for iOS, Android and Web. I decided to use Google Firebase as it really seems to simplify the work.
The features user needs in the app are:
Authorization/Registration
Uploading photos
Searching for other people, following them and see their photos
I come from traditional "own-backend" development where I do need to setup a server, create database and finally write the API to let the frontend retrieve the data from the server. That's the reason why it's unclear to me how it all works in Firebase.
So the question is how can I create such app:
Should I create my own API with cloud functions? Or it's ok to work with the database directly from the client-side?
If I work with the database directly why do I need cloud functions? Should I use them?
Sorry for such silly questions, but it is really hard to get from scratch.
The main difference between Firebase and the traditional setup you describe is that with Firebase, as far as the app developer is concerned, the client has direct access to the database, without the need for an intermediate custom API layer. Firebase provides SDKs in various languages that you would typically use to fetch the data you need / commit data updates.
You also have admin SDKs that you can use server-side, but these are meant for you to run some custom business logic - such as analytics, caching in an external service, for exemple - not for you to implement a data fetching API layer.
This has 2 important consequences:
You must define security rules to control who is allowed to read/write at what paths in your database. These security rules are defined at the project level, and rely on the authenticated user (using Firebase Authentication). Typically, if you store the user profile at the path users/$userId, you would define a rule saying that this node can be written to only if the authenticated user has an id of $userId.
You must structure your data in a way that makes it easily readable - without the need for complex database operations such as JOINs that are not supported by Firebase (you do have some limited querying options tough).
These 2 points allow you to skip the 2 main roles of traditional APIs: validating access and fetching/formatting the data.
Cloud functions allow you to react to data changes. Let's say everytime a new user is created, you want to send him a Welcome email: you could define a cloud function sending this email everytime a new node is appended to the users path. They allow you to run the code you would typically run server-side when writes happen, so they can have a very broad range of use-cases: side-effects (such as sending an email), caching data in an external service, caching data within Firebase for easier reads, analytics, etc..
You don't really need a server, you can access the database directly from the client, as long as your users are authenticated and you have defined reasonable security rules on Firebase.
In your use case you could, for example, use cloud functions to create a thumbnail when someone uploads a photo (Firebase Cloud Functions has ImageMagick included for that), or to denormalize your data so your application is faster, or to generate logs. So, basically you can use them whenever you need to do some server side processing when something changes on your database or storage. But I find cloud functions hard to develop and debug, and there are alternatives such as creating a Node application that subscribes to real time changes in your data and processes it. The downside is that you need to host it outside Firebase.
My answer is definitely NOT complete or professional, but here are the reasons why I choose Cloud Functions
Performance
You mentioned that you're writing an instagram-like mobile device app, then I assume that people can comment on others' pictures, as well as view those comments. How would you like to download comments from database and display them on users' devices? I mean, there could be hundreds, maybe thousands of comments on 1 post, you'll need to paginate your results. Why not let the server do all the hard work, free up users' devices and wait for the results? This doesn't seem like a lot better, but let's face it, if your app is incredibly successful, you'll have millions of users, millions of comments that you need to deal with, server will do those hard jobs way better than a mobile phone.
Security
If your project is small, then it's true that you won't worry about performance, but what about security? If you do everything on client side, you're basically allowing every device to connect to your database, meaning that every device can read from/write into your database. Once a malicious user have found out your database url, all he has to do is to
firebase.database().ref(...).remove();
With 1 line of code, you'll lose all your data. Okay, if you say, then I'll just come up with some good security rules like the one below:
This means that for each post, only the owner of that post can make any changes to it or read from it, other people are forbidden to do anything. It's good, but not realistic. People are supposed to be able to comment on the post, that's modifying the post, this rule will not apply to the situation. But again, if you let everybody read/write, it's not safe again. Then, why not just make .read and .write false, like this:
It's 100% safe, because nobody can do anything about anything in your database. Then, you write an API to do all the operations to your database. API limits the operations that can be done to your database. And you have experience in writing APIs, I'm sure you can do something to make your API strong in terms of security, for example, if a user wants to delete a post that he created, in your deletePost API, you're supposed to authenticate the user first. This way, 'nobody' can cause any damage to your database.

What's the risk of defining Firebase Realtime Database rules as public?

Documentation advises not to do so, but what if I make a part of the database publically readable and writeable? What harm could it cause?
Anyone who knows the name of your project could read and write the data in your database at those locations. The name of your project is generally public information to anyone who has a copy of your Android, iOS, or web app.
Obviously, this could cause problem with the data in your app. Also, if your project has billing enabled, you could end up paying for all the storage and bandwidth that could be used by a potential malicious attacker.

Do I need a Storage Controller for all my model classes in the app to use azure file sync?

Background:
Xamrin Forms Client App
Azure backend with Dot Net
Using Azure offline data sync
trying to use Azure offline File Sync
Related SO questions
there have been 2 more questions I asked here which are somewhat related
Getting a 404 while using Azure File Sync
Getting a 500 while using Azure File Sync
Solution
As stated above in the first link, I had to create a storage controller for the User entity to be able to successfully login even though I do not intend to use Files for Users.
As I work further in the app, I am still getting more 404 errors as I can see in fiddler. These are similar calls which are looking to access an API like below
GET /tables/{EntityName}/{Id}/MobileServ‌​iceFiles HTTP/1.1
My Question Now
Do I need a storage controller for every entity I have in my solution? may be every entity that inherits from EntityData?
Is there a way I can selectively tell the system which entities are going to work with files & have storage controllers only for them? Like, may be, marking them with some Attribute?
Reference
I am using this blog post to implement Azure File Sync in my app.
To answer my own query (and not the answer I wanted to hear) YES. We need a Storage controller for all entities, even if they don't have any files to be stored in Storage account. This is a limitation.
Found this info on comments of the original blog I was following (I wish I did it earlier), to quote the author
Donna Malayeri [donnam#MSFT] Chris • 2 months ago
It's a limitation of the current storage SDK that you can't specify which tables have files. See this GitHub issue: https://github.com/Azure/azure...
As a workaround, you have to make your own file sync trigger factory.
Here's a sample: https://github.com/azure-appse...
The reason the SDK calls Get/Delete for files in the storage
controller is because the server manages the mapping from record to
container or blob name. You wouldn't necessarily want to give the
client access to the blob account to access arbitrary files or
containers, for instance. In the case of delete, the server doesn't
even need to give out a SAS token with delete permissions, since it
can just authenticate the user and do the delete itself.

Resources