Read this before you use Firebase for sensitive data

Tom Colvin
4 min readNov 23, 2021

--

Filing cabinet drawers

Firebase is great. As a back end environment, it’s easy to set up, well secured, and very flexible. We’re big fans of it.

But, we found a worrying result after recently performing a full-on penetration test of a Firebase application for a client. It’s something to be aware of if you are considering Firebase as a back-end for your application.

What’s wrong

Put simply, though Firebase is secure on the server side, its Android SDK (at least) does not treat locally cached data with the same degree of reverence. When it stores data on the device, it does so with no encryption and no protection.

This is problematic because it leaves numerous avenues for a bad guy to get access to that data. For example, through physical access to the device, or by attacking backups.

But most importantly it goes against many, many privacy policies and industry guidelines for safe data storage.

We couldn’t, for example, sign off our test app against OWASP’s security checklist, which is a well-respected major industry standard. And it goes against Google’s own best practices for storing data, too.

Here are some of the specific problems:

Credential tokens stored in plaintext

After running our test app, we noticed the file PersistedInstallation.<ID>.json being saved to the ‘files’ subfolder of the app’s sandbox folder. This contains the following:

Firebase’s plain text storage of sensitive credential data — PersistedInstallation.XXX.json
Firebase’s plain text storage of sensitive credential data — PersistedInstallation.XXX.json

You can see that the ID and refresh tokens are clearly visible in plaintext.

Firestore data stored in plaintext

After interacting with the Firestore database, a file named firestore.%5BDEFAULT%5D.<ID> is added to the ‘databases’ subfolder of the app’s sandbox.

On downloading and analysing, we realised this is a SQLite file.

It contains the following tables:

Schema of the SQLite database created by the Firebase Android SDK
Schema of the SQLite database created by the Firebase Android SDK

…Many of which look like they might contain juicy content!

A particular table of interest is remote_documents which contains the following:

Sensitive data stored plaintext in the SQLite database by Firebase Android SDK
Sensitive data stored plaintext in the SQLite database by Firebase Android SDK

This represents the entire contents of several Firestore documents which have been cached.

Some ways to work around the issue

Obviously, the problem here is caused by the Firebase SDK. But you don’t actually have to use that when building a Firebase project, because there’s a parallel REST API available. In other words you could manually sign in and perform create/read/update/delete actions on the database. And most importantly that allows you to manage the caching your own way — so you can properly encrypt data at rest on the device.

But this isn’t anything like a viable solution. The official Android SDK has benefitted from years of development effort — and no doubt hundreds of millions of dollars spent — in order to get to the stage it’s at. And for all that effort it’s brilliantly well tuned; for example, the way Firestore manages offline working so transparently is exemplary. Trying to reproduce all that functionality even with a relatively large development team just isn’t viable.

A partial mitigation would be to add root detection to your app. That’s software designed to detect if the phone it’s running on has been rooted. Rooted phones bypass the normal Android security controls, including those which prevent apps from reading the internal storage of other apps, and are therefore a large part of the argument for encryption. But root detection algorithms are fallible, as new versions of rooting software try new ways to remain undetected.

It goes without saying that even if the root detection were completely infallible, it would only be a partial mitigation of some of the problems.

So what should you do?

You should be aware of these limitations in the security of Firebase. Apply one or other of the mitigations above, and that will certainly help.

Keep an eye out for Google solving the problem, which they surely must do eventually.

But in the meantime, be aware that Firebase can’t currently pass the most stringent security requirements.

This test was performed against Android Firebase Core v20.0.0, Firestore v24.0.0 and Firebase Auth v21.0.1, which are the latest at the time of writing.

Tom Colvin is CTO of Conseal Security, the mobile app security testing experts; and Apptaura, the mobile app developers.

--

--

Tom Colvin
Tom Colvin

Written by Tom Colvin

The Android guy. Consultant Android developer and CTO of Apptaura, the app dev specialists. Google Developer Expert in Android. All articles 100% me, no AI.

Responses (1)