Home > Enterprise >  How to setup Node to make different domains share cookies?
How to setup Node to make different domains share cookies?

Time:09-18

I have the problem that on production (Apache server/MERN stack) certain cookies are not accessible from the browser with document.cookie.

On localhost, both front-end and back-end are on the same domain, namely localhost, and just use different port numbers. Because they are working on the same domain, they share cookies.

On production, however, front-end and back-end operate on different (sub)domains. As a result, they don't have access to each other's cookies.

How can I make the cookies set by the back-end accessible for the front-end, also on production?

I thought this should be done with CORS, and with httpOnly: false and sameSite: 'none'. But the Node setup below doesn't work. In the browser I'm unable to access from the front-end the cookies set by the back-end.

var cors = require("cors");
const session = require("express-session");
const csurf = require("csurf");
const cookieParser = require("cookie-parser");

var corsOptions = {
    origin: process.env.CORS_ORIGIN_URL.split(","),  // the front-end is included here.
    credentials: true,
    exposedHeaders: ["set-cookie"],
};
app.use(cors(corsOptions));

let sessionSettings = {
    secret: process.env.SESSION_SECRET,
    key: process.env.SESSION_KEY,
    store: sessionStore,
    resave: true,
    saveUninitialized: true,
    cookie: {
        secure: false,
    },
};
app.use(session(sessionSettings));

const protect = csurf({ 
    cookie: true,
    httpOnly: false,
    sameSite: 'none'
});

app.use(
    cookieParser("test", {
        sameSite: 'none',
        httpOnly: false,
        secure: false,
        maxAge: 900000,
    })
);

app.use((req, res, next) => {
    protect(req, res, next);
});

app.use((req, res, next) => {
    if (req.csrfToken) {
        res.cookie(
            "XSRF-TOKEN", 
            req.csrfToken(),
            {
                secure: true, 
                httpOnly: false, 
                sameSite: 'None'
            }
        );
    }
    next();
});

app.use(`${process.env.API_PATH}/csrf`, (req, res) => {
    return res.status(200).json({
        status: true,
        csrfToken: req.csrfToken(),
    });
});

...

CodePudding user response:

Here you need to share the cookie with subdomains and main domain. You can do this by adding a domain field in res.cookie options. Now your main domain and subdomains can access this cookie.

res.cookie(
    "XSRF-TOKEN", 
    req.csrfToken(),
    {
        secure: true, 
        httpOnly: false, 
        sameSite: 'None',
        domain: 'mydomain.com'
    }
);

  • Related