Skip to main content
Version: 3.1.x

Firebase

Honeycomb comes with methods and configurations to deploy tasks with Firebase. These tools make it possible to reach a wider audience by hosting your task online.

Setting up Firebase

info

Members of Brown University should submit a support ticket to have their Firebase project created. Members of other institutions should check to see if their university has access to Google Cloud.

Otherwise, a personal Firebase account can be created for free. Please follow the firebase documentation for creating a new project.

Adding Products

First we'll configure Firebase Hosting and Cloud Firestore on your project.

  1. Log in to Firebase with your Google account on the Firebase console.

  2. Navigate to your project from the console

  3. Register a new web app to your project (Register your app)

    note

    We recommend giving your web app the same name as your task's repository

  4. Add Firestore Database to your project (Create a Cloud Firestore database)

    note

    Chose production mode for the starting mode and the default "Cloud Firestore Location"

The Firebase project is now fully set up! Now we'll connect your task to that project from your computer.

Installing the Command Line Interface

The Firebase CLI can be installed with the node package manager just like the rest of Honeycomb's dependencies. Be sure to log in with same account you used when logging into the console!

Install the Firebase CLI
npm install -g firebase-tools
Login to Firebase
firebase login

A "command not found" error usually indicates firebase-tools has not been installed correctly

Connecting Your Firebase Project

  1. Change the default project name of your task in .firebaserc
.firebaserc
{
"projects": {
"default": "<your project name>"
}
}
  1. Copy the web app credentials from the Firebase console to the corresponding variables in .env.firebase

    1. Return to your project on the Firebase console.

    2. Navigate to your project setting

      Firebase project settings
    3. Scroll down and copy the auto-generated values from the Firebase console to the corresponding variables in the .env.firebase file in the env folder of your Honeycomb task repo

      Firebase web credentials

      env/.env.firebase
      REACT_APP_FIREBASE="true"
      REACT_APP_apiKey=
      REACT_APP_authDomain=
      REACT_APP_projectId=
      REACT_APP_storageBucket=
      REACT_APP_messagingSenderId=
      REACT_APP_appId=

      Additional variables may be present in the console, they do not need to be copied.

  2. Deploy the default Firestore security rules

Deploy Firestore rules
firebase deploy --only firestore:rules

Your task is now connected to an initialized Firebase project!

Registering Studies

caution

This step must be followed exactly. See Security Rules for more information.

  1. Navigate to your Firestore Database in the console.
  2. Click "Start collection"
  3. Enter registered_studies for the collection id and click "next"
  4. Enter the id of your study for the document id
  5. Add a field named registered_participants with the type "array"
  6. Add the id of each study participant as a string inside the array
Create a study

The study should like this when you're finished:

Example study

Additional studies must be created inside the registered_studies collection

Developing With Firebase

Two terminal windows must be used while developing for Firebase. Instructions splitting terminals in VSCode can be found here.

Run Honeycomb with Firebase Enabled
npm run dev:firebase
Start the Firebase Emulators
npm run firebase:emulators:start

Honeycomb is now running in the browser and connected to data on an emulated instance of Firestore. That data can be viewed at http://localhost:4000/firestore.

info

Honeycomb populates the Firestore emulators with the study s1 and participant p1.

Deploying on Firebase

Firebase deployments are handled automatically following Continuous Integration Continuous Development practices using GitHub Actions. Here we will connect create custom actions that are connected to the task's Firebase project.

Execute the following command to begin initializing Firebase hosting via GitHub actions. Be sure to follow the instructions below as the prompts appear.

Initialize Firebase hosting via Github actions
firebase init hosting:github
  1. The window should log you in automatically. If not, follow the prompts to log in with the same account you used in the console.
  2. <username>/<repository name> refers to the name of your repository in Github. Be sure it's typed correctly!
  3. Enter y for the prompt "Set up the workflow to run a build script before every deploy?"
  4. Enter npm install && npm run build:firebase for the prompt "What script should be run before every deploy?"
  5. Enter y to overwrite the current workflow file
  6. Enter y for the prompt "Set up automatic deployment to your site's live channel when a PR is merged?"
  7. Enter main for the prompt "What is the name of the GitHub branch associated with your site's live channel?"
  8. Enter y to overwrite the current workflow file

Firebase will update the files firebase-hosting-pull-request.yml and firebase-hosting-merge.yml inside the .github/workflows/ directory. Ensure the correct run script is present in both files.

Github actions created by firebase

Downloading Data

Honeycomb ships with a script for downloading data from Firebase onto a computer. A local service account must be created in order to use it.

Setting up a Service Account

Service accounts are accounts that are not attached to a human user. They authorize access to a Firebase project without someone physically logging in online. We use a service account to give the download script access to the Firestore database automatically.

  1. Return to the project settings your project on the Firebase console.

    Firebase project settings
  2. Click on the "Service accounts" tab

  3. Near the bottom, click "Generate new Private key" and "Generate Key"

  4. Rename the key firebase-service-account.json and move it to the root directory of your task. Be sure the file looks grayed out and is not picked up by git!

danger

A service account has total administrative access to ts Firebase project. The file and keys inside should never be shared and never committed to GitHub.

Using the Download Script

Honeycomb comes with a download script. It will programmatically access Firestore to download the experiment data you choose

Script Usage
npm run firebase:download -- <studyID> <participantID> [sessionNumber] [outputRoot]
  • studyID: The ID of a given study
  • participantID: The ID of a given participant on the studyID study
  • sessionNumber: Optional number to select which session to download, defaults to the most recent session
  • outputRoot: Optional path to the folder where data should be saved, defaults to the current folder

Running the script without sessionNumber list all of the available sessions. For example:

Found 3 sessions:
0: 2022-07-26T22:04:55.544Z
1: 2022-07-27T14:16:36.301Z
2: 2022-07-27T19:56:26.229Z

sessionNumber

Adding a sessionNumber will download that sessions data:

Download data for session 2022-07-26T22:04:55.544Z
npm run firebase:download -- <studyID> <participantID> 0 [outputRoot]

outputRoot

Session data is stored in the current directory by default. The folders and file name are chosen to avoid naming collisions: ./participant_responses/<studyID>/<participantID>/<sessionID>.json

Adding an outputRoot will download that data in a custom location:

Download data for session 2022-07-26T22:04:55.544Z at /path/to/my/data
npm run firebase:download -- <studyID> <participantID> 0 /path/to/my/data

This will result in data saved to /path/to/my/data/participant_responses/<studyID>/<participantID>/<sessionID>.json

Further Reading

The Firebase Documentation details its Emulator Suite in much greater detail.

Security Rules

Honeycomb uses security rules to authenticate participants and studies for each task. By default participants must be registered to each study in order to complete the task.

Firestore rules are defined in the firestore.rules file in the home directory. Note the highlighted lines:

firestore.rules
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
match /participant_responses/{studyID}/participants/{participantID} {
allow create, read:
if participantID in get(/databases/$(database)/documents/registered_studies/$(studyID)).data.registered_participants;
// ...
}
}
}

Lines 3 and 4 indicate that Honeycomb attempts to connect to a document at /databases/{database}/documents/participant_responses/{studyID}/participants/{participantID} where studyID is a given study and participantID is a given participant within that study.

Line 6 defines our rule - it must pass for Honeycomb to connect to the document. participantID must be found in an array called registered_participants inside of a document at /databases/{database}/documents/registered_studies/{studyID}.

Line 5 indicates how Honeycomb can interact with that document. Note that Honeycomb cannot update or delete data! You must manually make these changes from the Firestore console.

danger

Firestore rules must define every match pattern in your project. Attempting to connect anywhere other than /participant_responses/{studyID}/participants/{participantID} will be automatically denied even if you add other collections to your database. This is why firestore.rules contains additional nested rules - these should be left alone.