Search code examples
javascriptfirebaseauthenticationfirebase-authenticationgoogle-workspace

how to get user information other than user name with Firebase Authentification


I'm an English teacher in Japan. I'm developing a web app using Firebase Hosting

My students have Google account because we use Gsuite for Education, so I decided to get students' data with Firebase Auth.

function signIn(){
  var provider = new firebase.auth.GoogleAuthProvider();
  firebase.auth().signInWithPopup(provider);
}
function saveMessage() {
  // Add a new message entry to the Firebase database.
  firebase.firestore().collection('messages').add({
      name: firebase.auth().currentUser.displayName,
      text: messageInputElement.value,
      timestamp: firebase.firestore.FieldValue.serverTimestamp()
  })

In saveMessage function I get user's name with firebase.auth().currentUser.displayName

Is it possible to get more user information? For example, I want User's school name, class number and student number. I read Firebase Auth document. https://firebase.google.com/docs/reference/js/firebase.User#providerdata This seems to be good. However I couldn't understand how to use it.

Could you tell me how to get user information other than user name with Firebase Auth?


This is index.html

<!doctype html>
<html lang="ja">
   <head>
      <title>音読アプリ アドバンス</title>
   </head>

   <body>
      <input id="sign-in" type="submit" value="SignIn">
      <br>
      <textarea id="text"></textarea>
      <br>
      <input id="download" type="submit" value="download">
      <div id='player'></div>

      <!-- Import and configure the Firebase SDK -->
      <!-- These scripts are made available when the app is served or deployed on Firebase Hosting -->
      <script src="/__/firebase/7.14.3/firebase-app.js"></script>
      <script src="/__/firebase/7.14.3/firebase-auth.js"></script>
      <script src="/__/firebase/7.14.3/firebase-storage.js"></script>
      <script src="/__/firebase/7.14.3/firebase-messaging.js"></script>
      <script src="/__/firebase/7.14.3/firebase-firestore.js"></script>
      <script src="/__/firebase/7.14.3/firebase-performance.js"></script>
      <script src="/__/firebase/7.14.3/firebase-functions.js"></script>
      <script src="/__/firebase/init.js"></script>

      <script src="scripts/main.js"></script>
   </body>
</html>

This is main.js (client-side)

'use strict';
function signIn(){
  var provider = new firebase.auth.GoogleAuthProvider();
  firebase.auth().signInWithPopup(provider);
}
function saveMessage() {
  // Add a new message entry to the Firebase database.
  firebase.firestore().collection('messages').add({
      name: firebase.auth().currentUser.displayName,
      text: messageInputElement.value,
      timestamp: firebase.firestore.FieldValue.serverTimestamp()
  })
      .then(docRef => {

          this.firestoreDocListener = docRef.onSnapshot(doc => {
              if (doc.exists && doc.data().hasOwnProperty('fileName')) {
                  console.log(doc.data().fileName);
                  // Use doc.data().fileName the way you need!
                  // Create a reference from a Google Cloud Storage URI
                  var storage = firebase.storage();
                  var pathReference = storage.ref(doc.data().fileName)
                  pathReference.getDownloadURL().then(function(url) {
                    console.log(url);
                    const audio = document.createElement('AUDIO');
                    audio.controls = true;
                    audio.src = url;
                    const player = document.getElementById('player');
                    player.appendChild(audio);
                  }).catch(function(error) {
                    // A full list of error codes is available at
                    // https://firebase.google.com/docs/storage/web/handle-errors
                    switch (error.code) {
                      case 'storage/object-not-found':
                        console.log('storage/object-not-found')
                        break;

                      case 'storage/unauthorized':
                        console.log('storage/unauthorized')
                        break;

                      case 'storage/canceled':
                        console.log('storage/canceled')
                        break;

                      case 'storage/unknown':
                        console.log('storage/unknown')
                        break;
                    }  
                  });

              }
          });

      })
      .catch(function (error) {
          console.error('Error writing new message to Firebase Database', error);
      });
}

// Checks that the Firebase SDK has been correctly setup and configured.
function checkSetup() {
  if (!window.firebase || !(firebase.app instanceof Function) || !firebase.app().options) {
    window.alert('You have not configured and imported the Firebase SDK. ' +
        'Make sure you go through the codelab setup instructions and make ' +
        'sure you are running the codelab using `firebase serve`');
  }
}

// Checks that Firebase has been imported.
checkSetup();

// Shortcuts to DOM Elements.
var messageInputElement = document.getElementById('text');
var submitButtonElement = document.getElementById('download');
var signInButtonElement =document.getElementById('sign-in');


// Saves message on form submit.
submitButtonElement.addEventListener('click', saveMessage);
signInButtonElement.addEventListener('click', signIn);

This is index.js (server-side cloud functions)

const functions = require('firebase-functions');
var admin = require("firebase-admin");
admin.initializeApp();
const textToSpeech = require('@google-cloud/text-to-speech');
require('date-utils');

exports.myFunction = functions.firestore
    .document('messages/{id}')
    .onCreate(async (snap) => {   // See the async here

        try {    //See the "global" try/catch

            const client = new textToSpeech.TextToSpeechClient();

            // The text to synthesize
            const newValue = snap.data();
            const text = newValue.text;

            // Construct the request
            const request = {
                input: { text: text },
                // Select the language and SSML voice gender (optional)
                voice: { languageCode: 'en-US', ssmlGender: 'NEUTRAL' },
                // select the type of audio encoding
                audioConfig: { audioEncoding: 'MP3' },
            };


            var bucket = admin.storage().bucket('adv********.appspot.com');
            var dt = new Date();
            var formatted = dt.toFormat('YYYYMMDDHH24MISS');
            var file = bucket.file('audio/' + formatted + '.mp3');
            // Create the file metadata
            var metadata = {
                contentType: 'audio/mpeg'
            };

            // Performs the text-to-speech request
            const [response] = await client.synthesizeSpeech(request);
            await file.save(response.audioContent, metadata);
            console.log("File written to Firebase Storage.");

            await snap.ref.update({ fileName: 'audio/' + formatted + '.mp3' });

            return null;

        } catch (error) {
            console.error(error);
        }

    });

Solution

  • You will need to create a custom form on your front end that gathers that data and save those details after creating of the user, possibly in a function like so:

    function writeUserData(userId, name, fav_color, best_friend, best_hero) {
      firebase.database().ref('users/' + userId).set({
        name: name,
        fav_color: fav_color,
        best_friend : best_friend,
        best_hero: best_hero
      });
    }
    

    You then typically would structure your database like so:

    "users": {
        "$userID": {
            "name": "John",
            "fav_color": "chartruese",
            "best_friend": "James",
            "best_hero": "spiderman"
        }
    }
    

    Just a note, You usually would post this data after the user is authenticated, that way you can add a firebase rule to make sure that only that user can post and read that data.