Session Cookies (connect.sid) Not Set in Browser on Vercel Deployment

#Session Cookies (connect.sid) Not Set in Browser on Vercel Deployment

1. Bug Description

Title:
Session Cookies (connect.sid) Not Set in Browser on Vercel Deployment

Summary:
The session functionality of my application works correctly in my local development environment. However, when deployed to Vercel, the session cookie (connect.sid) is not set in the browser, despite proper configuration of express-session, connect-mongo, and CORS. This issue prevents session persistence and user authentication.


2. Steps to Reproduce

  1. Deploy the application on Vercel.
  2. Use the /api/auth/login endpoint with valid user credentials:
    • Request URL: https://your-vercel-url/api/auth/login
    • Method: POST
    • Payload:
      {
        "email": "user@example.com",
        "password": "password123"
      }
      
  3. Inspect the network response and headers in the browser developer tools or Postman.

3. Expected Behavior

The server should send a Set-Cookie header in the response containing the connect.sid session cookie.


4. Observed Behavior

  • The Set-Cookie header is missing in the server response.
  • No session cookie (connect.sid) is set in the browser.

5. Supporting Evidence

Request Details (from browser or Postman):

Request URL:
https://your-vercel-url/api/auth/login

Response Headers:

access-control-allow-credentials: true
access-control-allow-origin: https://your-client-url
cache-control: public, max-age=0, must-revalidate
content-type: application/json; charset=utf-8
strict-transport-security: max-age=63072000; includeSubDomains; preload
vary: Origin
x-powered-by: Express

Response Body:

{
  "message": "Logged in successfully"
}

Missing Header:
The Set-Cookie header is absent.

MongoDB Session Collection:

Sessions are being successfully stored in the MongoDB database, as confirmed in the sessions collection.

Local Environment:

When tested locally:

  • The Set-Cookie header is present.
  • Sessions are persisted, and authentication works as expected.

6. Relevant Code

Session Configuration (index.js):

const session = require('express-session');
const MongoStore = require('connect-mongo');

app.use(
  session({
    secret: process.env.SESSION_SECRET || 'secret',
    resave: false,
    saveUninitialized: false,
    store: MongoStore.create({
      mongoUrl: process.env.MONGO_URI,
      ttl: 14 * 24 * 60 * 60, // 14 days
    }),
    cookie: {
      secure: true, // HTTPS-only
      httpOnly: true, // Accessible only by the server
      sameSite: 'None', // Cross-site cookie support
    },
  })
);

CORS Configuration:

const cors = require('cors');
app.use(
  cors({
    origin: 'https://your-client-url',
    credentials: true, // Allows sending cookies
  })
);

Login Endpoint (authController.js):

exports.loginUser = async (req, res) => {
  const { email, password } = req.body;

  try {
    let user = await User.findOne({ email });
    if (!user) {
      return res.status(400).json({ msg: 'User not found' });
    }

    const isMatch = await bcrypt.compare(password, user.password);
    if (!isMatch) {
      return res.status(400).json({ msg: 'Invalid credentials' });
    }

    req.session.user = {
      id: user._id,
      name: user.name,
      email: user.email,
    };

    req.session.save((err) => {
      if (err) {
        console.error('Session save error:', err);
        return res.status(500).json({ message: 'Failed to save session' });
      }

      res.status(200).json({ message: 'Logged in successfully' });
    });
  } catch (err) {
    console.error(err.message);
    res.status(500).send('Server error');
  }
};

Check Session Endpoint:

exports.checkSession = (req, res) => {
  if (req.session && req.session.user) {
    return res.json({ isAuthenticated: true, user: req.session.user });
  } else {
    return res.status(401).json({ isAuthenticated: false });
  }
};

7. Environment Details

Local Environment:

  • Node.js version: 16.x
  • MongoDB: Local instance
  • Operating System: Windows 10

Production Environment (Vercel):

  • Node.js version: 16.x
  • MongoDB: Hosted on MongoDB Atlas
  • Vercel Build Settings: Default configuration
  • Domain: https://your-vercel-url

8. Questions/Issues

  1. Is there a known issue with Set-Cookie behavior in Vercel when using express-session?
  2. Are there any Vercel-specific configurations required for session persistence with cookies?
  3. Why does the session functionality work locally but not on Vercel?

9. Additional Debugging Steps Taken

  • Verified MongoDB session storage; sessions are saved correctly.
  • Checked for Set-Cookie headers in the response; missing in production.
  • Ensured CORS and session configurations align with Vercel requirements.

We are happy to recommend some debugging steps for your application:

  1. Use browser developer tools to inspect the cookies and see if they’re being set at all.
  2. Check your server logs for any error messages related to session or cookie handling.
  3. Temporarily log the session data on both client and server sides to see where the discrepancy occurs.

Also I would recommend checking out our write up and using Express with Vercel as there are a few things to consider: Using Express.js with Vercel

All the debugging steps that you have mention, I have already completed. And checked everything else.
I found nothing.
please check the code if I’m missing something.

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.