AngularJS转Ionic后Passport的isAuthenticated()始终返回false
Hey there! I totally get the frustration of spending a day on an auth issue that works perfectly on web but breaks in Ionic—let's get this sorted out.
The Root Cause
You’re spot-on about the cookie issue. Passport relies on session cookies to track authenticated users. When your AngularJS app runs in a browser, the browser automatically handles sending cookies with every request. But Ionic (especially when wrapped in Cordova) doesn’t do this by default—so after a successful login, the session cookie never gets sent back to your server on subsequent requests, which is why req.isAuthenticated() keeps returning false.
Step 1: Server-Side Configuration (Express/Passport)
First, tweak your Express setup to handle cross-origin credentials and set cookies that work for both web and Ionic:
- CORS Setup: Ensure your CORS middleware allows credentials and includes your Ionic app’s origin. If you’re using the
corsnpm package:
const cors = require('cors'); app.use(cors({ origin: ['http://your-web-app-url', 'http://localhost:8100'], // Add your web app URL and Ionic dev server URL credentials: true // Critical: Lets cookies be sent across origins }));
- Session Configuration: Update your Express session settings to make cookies accessible cross-origin:
const session = require('express-session'); app.use(session({ secret: 'your-secure-secret-key', resave: false, saveUninitialized: false, cookie: { sameSite: process.env.NODE_ENV === 'production' ? 'none' : 'lax', // 'none' for cross-origin, 'lax' for same-origin web secure: process.env.NODE_ENV === 'production', // Use true in production (HTTPS only), false in local dev (HTTP) maxAge: 24 * 60 * 60 * 1000 // 1-day session timeout } }));
sameSite: 'none'tells browsers to send the cookie even for cross-origin requests (required for Ionic).secure: trueensures cookies are only sent over HTTPS—keep thisfalsewhen testing locally with HTTP.
- Verify Passport Serialization: Double-check your
serializeUseranddeserializeUserfunctions are correctly saving/retrieving user data to the session:
passport.serializeUser((user, done) => { done(null, user.id); // Save user ID to the session }); passport.deserializeUser((id, done) => { User.findById(id, (err, user) => { done(err, user); // Fetch full user data from DB using the session ID }); });
Step 2: Client-Side (Ionic/AngularJS) Fix
You need to tell your Ionic app to send cookies with every request. Here’s how to do it for AngularJS 1.6 (matching your original app’s stack):
AngularJS Global Configuration
Add this to your app’s config block to enable credentials for all $http requests:
angular.module('yourAppName') .config(['$httpProvider', function($httpProvider) { // Tell Angular to include cookies with cross-origin requests $httpProvider.defaults.withCredentials = true; }]);
For Ionic 4+ (Using Angular’s HttpClient)
If you’ve upgraded to a newer Ionic version using Angular’s HttpClient, create an interceptor to attach credentials to all requests:
import { Injectable } from '@angular/core'; import { HttpInterceptor, HttpRequest, HttpHandler } from '@angular/common/http'; @Injectable() export class CredentialsInterceptor implements HttpInterceptor { intercept(req: HttpRequest<any>, next: HttpHandler) { // Clone the request and enable credentials const authReq = req.clone({ withCredentials: true }); return next.handle(authReq); } }
Then register the interceptor in your AppModule:
import { HTTP_INTERCEPTORS } from '@angular/common/http'; @NgModule({ providers: [ { provide: HTTP_INTERCEPTORS, useClass: CredentialsInterceptor, multi: true } ] }) export class AppModule { }
Debugging Tips
- Inspect Network Requests: Use Chrome DevTools (for web) or the Ionic DevApp inspector to:
- Confirm the login response includes a
Set-Cookieheader. - Check that subsequent requests (like
/api/login/loggedin) include that cookie in the request headers.
- Confirm the login response includes a
- Local Testing Fixes: If you’re using
ionic serve, try accessing your server via your machine’s local IP (e.g.,http://192.168.x.x:3000) instead oflocalhost—this avoids some cookie-related quirks. - Check HTTPS: In production, make sure both your server and Ionic app are using HTTPS—
secure: truecookies won’t work over HTTP.
Why This Works for Both Web and Ionic
- Web App: Browsers will still handle cookies normally, and
sameSite: 'lax'(or'none'with HTTPS) maintains security. - Ionic App: The
withCredentials: truesetting ensures cookies are sent with every request, and the server’s CORS/session configuration accepts them cross-origin.
Your existing login and loggedin routes don’t need changes—they’ll work once the cookie session is properly maintained between client and server.
内容的提问来源于stack exchange,提问作者Valentin Macé

