Firebase Hosting is not compatible with Express session

After setting up my code as shown below, I noticed that sessions are being persisted and the page is able to count the number of visits.

app.set('trust proxy', true)
// The documentation specifies '1' instead of 'true'

app.use(session({
   secret: 'my secret',
   proxy: true,
   resave: false,
   saveUninitialized: true,
   cookie: { secure: false }
}))

app.listen(3000, function(){
   console.log("Server is connected!");
});

app.get("/login", (req, res) => {
   if(req.session.page_views){
       req.session.page_views++;
       res.send("You visited this page " + req.session.page_views + " times");
   } else {
       req.session.page_views = 1;
       res.send("Welcome to this page for the first time!");
   }
});

However, when I removed the app.listen(3000, ...) and opted to run on localhost by executing firebase serve in the CLI, the sessions were no longer persisted.

I also attempted deploying to a production environment using firebase deploy, but unfortunately, the sessions were still not persisted.

I have made several adjustments within the app.use(session({ section and I believe the solution lies within those changes.

Any suggestions?

UPDATE

const express = require('express');
const session = require('express-session');
const FirestoreStore = require('firestore-store')(session);
const bodyParser = require('body-parser');

app.use(cookieParser('My secret'));
app.use(bodyParser.urlencoded({ extended: true }));

app.use(session({
    store: new FirestoreStore({
         database: firebase.firestore()
    }),
    secret: 'My secret',
    resave: true,
    saveUninitialized: true,
    cookie: {maxAge : 60000,
             secure: false,
             httpOnly: false }
}));

Answer №1

Have you considered using FirebaseStore instead of FirestoreStore for your project?

If you're working with Express, here's a guide on how to integrate FirebaseStore:

Express

Note: In Express 4, make sure to pass express-session to connect-session-firebase function to extend express-session.Store:

const express = require('express');
const session = require('express-session');
const FirebaseStore = require('connect-session-firebase')(session);
const firebase = require('firebase-admin');
const ref = firebase.initializeApp({
  credential: firebase.credential.cert('path/to/serviceAccountCredentials.json'),
  databaseURL: 'https://databaseName.firebaseio.com'
});

express()
  .use(session({
    store: new FirebaseStore({
      database: ref.database()
    }),
    secret: 'keyboard cat',
    resave: true,
    saveUninitialized: true
  }));

Remember that considering the security provided by this dependency is crucial:

Make sure to set proper rules if you are using a publicly available Firebase Database:

{
  "rules": {
    ".read": "false",
    ".write": "false",
    "sessions": {
      ".read": "false",
      ".write": "false"
    },
    "some_public_data": {
      ".read": "true",
      ".write": "auth !== null"
    }
  }
}

For further information on Firebase rules and connect-session-firebase, check out Firebase rules and connect-session-firebase

Answer №2

If you're utilizing firebase hosting, it's a good idea to utilize a connector that links your express session with firebase.

You may want to experiment with the connect-session-firebase middleware, which seamlessly integrates the firebase database store with your current express session. This could potentially resolve any issues related to session persistence.

UPDATE:

In case you are using firebase hosting along with cloud functions, keep in mind that only a cookie named __session can be set. Therefore, you will need to use this specific name for persisting sessions in firebase hosting.

app.use(session({
    store: new FirestoreStore({
         database: firebase.firestore()
    }),
    name: '__session',
    secret: 'My secret',
    resave: true,
    saveUninitialized: true,
    cookie: {maxAge : 60000,
             secure: false,
             httpOnly: false }
}));

For more information:

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Encountered an error stating 'Cannot read property 'user' of undefined' while attempting to generate a user document during account creation using Firebase

I'm having trouble adding the user ID to a new collection named 'accounts' during account creation. I keep encountering an error that says 'Cannot read property 'user' of undefined'. Can someone please help me troubleshoo ...

Is there a way to keep the node text in place and prevent overlapping in my D3.js tree?

I'm facing an issue with long text strings in my D3 tree. The nodes move according to the tree structure, but how can I handle excessively long node-text? For instance, if the label "T-ALL" had a longer name, it could overlap with the neighboring nod ...

Using InputAdornment with MUI AutoComplete causes the options list to disappear

I created a custom AutoComplete component with the following structure: <Autocomplete freeSolo size="small" id="filter-locks-autocomplete" options={json_list ? json_list : []} groupBy={(option) => option.lock.building} ...

Issue: Unable to utilize import statement outside a module as per the guidelines of the vue-test-utils official tutorial

I'm struggling to get Vue testing set up with vue-test-utils and jest. I followed the installation guide at https://vue-test-utils.vuejs.org/installation/#semantic-versioning, but can't seem to figure out what's wrong. Here's what I&apo ...

Tips for utilizing the setInterval function in javascript to update the background color of the body

Currently, I am tackling a project for my course and I am seeking to modify the body's background color on my website randomly by leveraging the setInterval technique in my JavaScript file. Any suggestions on how to achieve this task? ...

Grouping geoJSON data on Mapbox / Leaflet

I am currently in the process of setting up a clustered map on mapbox, similar to the example shown here: At the moment, my point data is being extracted from MYSQL and then converted into GeoJson using GeoPHP. You can view the current map setup here. I ...

Is the Angular-fullstack generator production application experiencing issues with serving socket.io correctly?

Having a bit of trouble with two angular-fullstack apps deployed on AWS using the same setup and configuration. It appears that socket.io-client/socket.io.js is not being properly served on one of them, despite both apps having identical settings. There ...

vuejs mounted: Unable to assign a value to an undefined variable

When I try to run the function below upon mounted, I encounter an error: "Cannot set the property 'days' of undefined" Here is my code snippet: function getDays(date) { this.days = (new Date()).getTime() / ...

Implementing pagination in React: A step-by-step guide

I am fetching data from the GitHub API, specifically from here Although I have all the necessary data to display, I want to limit it so that only 20 repositories are shown per page. In addition, I prefer not to use any frameworks or plugins for this task ...

Is the performance of Rails/Haml/Sass lower compared to that of Node/Express/Jade/Stylus?

I've noticed some interesting differences in my development workflow: When using SASS with the --watch flag, I sometimes experience a delay of 1-2 seconds before changes are reflected in the browser. This doesn't happen when using jade/stylus ...

Is there a way to determine the dimensions of a pdf file using javascript and capture a snapshot of it for showcasing on a website?

I'm fairly new to HTML/CSS and haven't delved into javascript yet, but I have a good understanding of reading other people's code. Currently, I'm putting together my portfolio website and would like to include my resume on the page in a ...

Run the curl command using nodejs

curl -i --upload-file ~/Downloads/tree-736885__480.jpg -H 'Authorization: Bearer token' "uploadURL" I have the above curl command that I need to execute in Node.js. How can I trigger this? I attempted to convert it to axios but encoun ...

The instance is referring to "close" as a property or method during render, but it is not defined. Ensure that this property is reactive and properly defined

Upon my initial foray into Vue.js, I encountered a perplexing warning: vue.runtime.esm.js?2b0e:619 [Vue warn]: Property or method "success" is not defined on the instance but referenced during render. Make sure that this property is reactive, e ...

Jquery is not working as expected

I am having trouble implementing a jQuery function to show and hide select components. It doesn't seem to be working correctly. Can someone help me identify the issue? <html> <head> <meta charset='UTF-8' /> <script ...

Implementing AJAX mysqli interaction in PHP following the MVC design pattern

Today I'm encountering yet another AJAX-related error. I am in the process of developing a user registration system using AJAX and PHP, following MVC architecture. Previously, I successfully built a login system without AJAX that functions flawlessl ...

Identifying Mistakes to Address Promise Failures

I encountered unhandled promise rejection errors and attempted to catch them and log them after each .then statement. Unfortunately, I ran into an 'unexpected token' issue when running the code on my server due to the period before .try. Despit ...

Using JQuery to eliminate Javascript code after setting up an event listener, but prior to the listener being activated

Having trouble finding a solution to my question through search. I'm sorry if it has already been asked before. I am attempting to define an event listener and immediately remove the JS code after defining it. The challenge is that I want the removal ...

I am struggling to successfully upload a video in Laravel

In this section, the Ajax functionality is used to add a video URL to the database. The values for the Video title and description are successfully being saved in the database, but there seems to be an issue with retrieving the URL. <div class="m ...

Dividing the functionality of socket.io events into separate modules

I have come across several inquiries discussing this matter, but I couldn't quite figure out how to make it work. Currently, I have an application running on express for API routes and a real-time socket app. My goal is to maintain a clean server.js ...

Get the Zip file content using PushStreamContent JavaScript

I am looking for the correct method to download a PushStreamContent within a Post request. I have already set up the backend request like this: private static HttpClient Client { get; } = new HttpClient(); public HttpResponseMessage Get() { var filenames ...