6

I want to export a Firebase object from JavaScript as JSON and download it. For example, this item that is in the patients/ reference. I would like to download it on a .json file with this format:

"-LCZPCkiGCNhFaQ8ckJ-" : {
  "altura" : 165,
  "apellido" : "Salas",
  "extra" : {
    "Jubilado" : "No",
    "Localidad" : "Madrid",
    "Telefono" : "698532147"
  },
  "fechaNacimiento" : "14/10/1961",
  "nombre" : "Paquita",
  "sexo" : "Mujer"
}

I have only been able to download a file stored in Storage but not in Realtime Database

 firebase.storage().ref('grabaciones/').child(grabacion).getDownloadURL().then(function (url) {
  let a = document.createElement("a");
  a.download = grabacion;
  a.href = url;
  document.body.appendChild(a);
  a.click();
}).catch(function (error) {
  // Handle any errors
  console.log(error);
});

Thank you in advance.

Updated code, where the element is obtained as a JSON and is downloaded as a .json. Only works in Firefox:

$scope.exportarJSON = function (paciente) {
        console.log(grabacion);
        firebase.database().ref('pacientes/').child(pacinte).once('value', function (paciente) {
          download(paciente + ".json", JSON.stringify(paciente.val()));
        });
    };



 function download(filename, text) {
    var element = document.createElement('a');
    element.setAttribute('href', 'data:text/json;charset=utf-8,' + encodeURIComponent(text));
    element.setAttribute('download', filename);

    element.style.display = 'none';
    document.body.appendChild(element);

    element.click();

    document.body.removeChild(element);
  }
asierta
  • 307
  • 4
  • 16

3 Answers3

7

Ever piece of data in your Firebase Database has its own unique URL. For example, I quickly imported your sample data into one of my databases, and it now lives on https://stackoverflow.firebaseio.com/50408054/-LCZPCkiGCNhFaQ8ckJ-.

If you go to that URL, you will be prompted to log in. Since you don't have access to my project, you can't see my database console.

But you can access the data as JSON. Since I've granted public read access to the data, you can access it as JSON through this URL: https://stackoverflow.firebaseio.com/50408054/-LCZPCkiGCNhFaQ8ckJ-.json. As you can see, that is the same URL as before, but now with .json added at the end.

This is part of Firebase's REST API, which is fully documented here: https://firebase.google.com/docs/database/rest/start. You should be able to use this REST URL in your download link, as long as the data is publicly readable.

Frank van Puffelen
  • 565,676
  • 79
  • 828
  • 807
  • Thanks for the response, but I need the information not accessible publicly. I have managed to do it following @RenaudTarnec 's strategy, as you can see in the answer, but thanks for the interesting information. – asierta May 19 '18 at 09:07
  • 2
    I believe the link changed to: https://firebase.google.com/docs/database/rest/start – DavidTaubmann Jun 20 '19 at 04:13
3

You can use a Callable Function, as follows:

Cloud Function code (index.js)

const functions = require('firebase-functions');
const admin = require('firebase-admin');

admin.initializeApp();

exports.getJSON = functions.https.onCall((data, context) => {

    return admin.database().ref('yourLocation').once('value')
        .then(function(snapshot) {
            return snapshot.val();
    });

    //Note that yourLocation is hardcoded in this example but could be obtained from 
    //the data parameter, which value comes from the JavaScript call in your web page    

});

Code in a web page, for example:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>

    <script src="https://www.gstatic.com/firebasejs/5.0.3/firebase-app.js"></script>
    <script src="https://www.gstatic.com/firebasejs/5.0.3/firebase-auth.js"></script>
    <script src="https://www.gstatic.com/firebasejs/5.0.3/firebase-functions.js"></script>

</head>
<body>

<script>

    // Initialize Firebase
    var config = {
        apiKey: "....",
        authDomain: "",
        databaseURL: "",
        projectId: ""
    };

    firebase.initializeApp(config);

    var getJSON = firebase.functions().httpsCallable('getJSON');
    getJSON().then(function(result) {
        console.log(JSON.stringify(result.data));
    }).catch(function(error) {
        // Getting the Error details.
        var code = error.code;
        var message = error.message;
        var details = error.details;
        // ...
    });

</script>


</body>
</html>

You will find the doc on Callable Functions here: https://firebase.google.com/docs/functions/callable

Note that you can call this Function from and iOS or Android app as well.

You could do something similar with a simple HTTPS Cloud Function and call it as a REST API endpoint (for example with the Axios library). One of the advantage of using a Callable Function is that "Firebase Authentication and FCM tokens are automatically included in requests" so you can easily restrict the calls to authorized users only.

Renaud Tarnec
  • 79,263
  • 10
  • 95
  • 121
  • Ok, I think I understood the idea. I tried to implement it without resorting to Firebase functions and it seems to work, I have added it to the question I have also added the download function to download the file as a .json, as explained in [this question](https://stackoverflow.com/a/18197341/6304714), but I only get it to work in Firefox. The part of the download would be the one missing in your code. Thanks for your answer – asierta May 18 '18 at 12:04
0

Finally I have managed to do this by obtaining the data from Firebase, and applying JSON.stringify () to that data. Later to download them as a .json file, I created a Blob with the string following the code of this question. Thanks for the answers, they have been inspiring

 $scope.exportarJSON = function (paciente) {
        console.log(grabacion);
        firebase.database().ref('pacientes/').child(pacinte).once('value', function (paciente) {
          download(paciente + ".json", paciente.val());
        });
    };


function download(filename, paciente) {
    let file = JSON.stringify(paciente);
    let blob = new Blob([file], {type: "application/json"});
    let url  = URL.createObjectURL(blob);
    let element = document.createElement('a');
    element.setAttribute('href', url);
    element.setAttribute('download', paciente.nombre + ".json");

    element.style.display = 'none';
    document.body.appendChild(element);

    element.click();

    document.body.removeChild(element);
  }
asierta
  • 307
  • 4
  • 16