Express会话不适用于Firebase托管

时间:2018-07-01 00:30:56

标签: javascript firebase express firebase-hosting

当我满足以下条件时,会话将保持不变,并且页面会计算访问次数。

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!");
   }
});

但是,当我删除app.listen(3000, ...)并改为通过CLI中的命令localhostfirebase serve中运行时,会话不会持久化。

我还尝试通过firebase deploy在生产环境上运行,但是再次,会话没有持久化。

我在app.use(session({上尝试了多个选项,并且我相信解决方案可能在那里。

有什么建议吗?

更新

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 }
}));

2 个答案:

答案 0 :(得分:1)

我将建议您使用一些FirestoreStore,而不是使用此FirebaseStore

我注意到您正在使用Express,因此您可能要检查以下用法:

Express

注意:在Express 4中,必须将express-session传递给connect-session-firebase导出函数,以扩展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
  }));

您可能还需要真正考虑该依赖项提供的安全性

  

如果您使用公共可用的Firebase数据库,请设置适当的   规则:

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

您可以详细了解Firebase rulesconnect-session-firebase

答案 1 :(得分:-1)

如果您使用的是Firebase托管,则不妨使用将Express会话与Firebase连接起来的连接器。

您可以尝试使用connect-session-firebase中间件,它将Firebase数据库存储与当前Express会话集成在一起。这样可以解决有关会话持久性的问题。

更新:

如果您使用Firebase托管和云功能,则只能设置名称为__session的cookie。您可能必须使用该名称才能在Firebase托管中保留会话。

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 }
}));

有关更多信息: