mirror of
				https://github.com/Unleash/unleash.git
				synced 2025-10-27 11:02:16 +01:00 
			
		
		
		
	Add support for req.logout with passport version 0.6.0 and onwards (#2041)
				
					
				
			Handle logout based on passport version
This commit is contained in:
		
							parent
							
								
									ee6ec888a7
								
							
						
					
					
						commit
						3a0113d16a
					
				@ -115,6 +115,42 @@ test('should call destroy on session', async () => {
 | 
			
		||||
    expect(fakeSession.destroy.mock.calls.length).toBe(1);
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
test('should handle req.logout with callback function', async () => {
 | 
			
		||||
    // passport >=0.6.0
 | 
			
		||||
    const baseUriPath = '';
 | 
			
		||||
    const logoutFunction = jest.fn((cb: (err?: any) => void) => cb());
 | 
			
		||||
    const app = express();
 | 
			
		||||
    const config = createTestConfig({ server: { baseUriPath } });
 | 
			
		||||
    app.use((req: IAuthRequest, res, next) => {
 | 
			
		||||
        req.logout = logoutFunction;
 | 
			
		||||
        next();
 | 
			
		||||
    });
 | 
			
		||||
    app.use('/logout', new LogoutController(config).router);
 | 
			
		||||
    const request = supertest(app);
 | 
			
		||||
    await request.get(`${baseUriPath}/logout`);
 | 
			
		||||
 | 
			
		||||
    expect(logoutFunction).toHaveBeenCalledTimes(1);
 | 
			
		||||
    expect(logoutFunction).toHaveBeenCalledWith(expect.anything());
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
test('should handle req.logout without callback function', async () => {
 | 
			
		||||
    // passport <0.6.0
 | 
			
		||||
    const baseUriPath = '';
 | 
			
		||||
    const logoutFunction = jest.fn();
 | 
			
		||||
    const app = express();
 | 
			
		||||
    const config = createTestConfig({ server: { baseUriPath } });
 | 
			
		||||
    app.use((req: IAuthRequest, res, next) => {
 | 
			
		||||
        req.logout = logoutFunction;
 | 
			
		||||
        next();
 | 
			
		||||
    });
 | 
			
		||||
    app.use('/logout', new LogoutController(config).router);
 | 
			
		||||
    const request = supertest(app);
 | 
			
		||||
    await request.get(`${baseUriPath}/logout`);
 | 
			
		||||
 | 
			
		||||
    expect(logoutFunction).toHaveBeenCalledTimes(1);
 | 
			
		||||
    expect(logoutFunction).toHaveBeenCalledWith();
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
test('should redirect to alternative logoutUrl', async () => {
 | 
			
		||||
    const fakeSession = {
 | 
			
		||||
        destroy: jest.fn(),
 | 
			
		||||
 | 
			
		||||
@ -1,4 +1,5 @@
 | 
			
		||||
import { Response } from 'express';
 | 
			
		||||
import { promisify } from 'util';
 | 
			
		||||
import { IUnleashConfig } from '../types/option';
 | 
			
		||||
import Controller from './controller';
 | 
			
		||||
import { IAuthRequest } from './unleash-types';
 | 
			
		||||
@ -25,14 +26,23 @@ class LogoutController extends Controller {
 | 
			
		||||
                res.redirect(req.session.logoutUrl);
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            req.session.destroy();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (req.logout) {
 | 
			
		||||
            req.logout();
 | 
			
		||||
            if (this.isReqLogoutWithoutCallback(req.logout)) {
 | 
			
		||||
                // passport < 0.6.0
 | 
			
		||||
                req.logout();
 | 
			
		||||
            } else {
 | 
			
		||||
                // for passport >= 0.6.0, a callback function is expected as first argument.
 | 
			
		||||
                // to reuse controller error handling, function is turned into a promise
 | 
			
		||||
                const logoutAsyncFn = promisify(req.logout).bind(req);
 | 
			
		||||
                await logoutAsyncFn();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (req.session) {
 | 
			
		||||
            req.session.destroy();
 | 
			
		||||
        }
 | 
			
		||||
        res.clearCookie(this.cookieName);
 | 
			
		||||
 | 
			
		||||
        if (this.clearSiteDataOnLogout) {
 | 
			
		||||
@ -41,6 +51,12 @@ class LogoutController extends Controller {
 | 
			
		||||
 | 
			
		||||
        res.redirect(`${this.baseUri}/`);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private isReqLogoutWithoutCallback(
 | 
			
		||||
        logout: IAuthRequest['logout'],
 | 
			
		||||
    ): logout is () => void {
 | 
			
		||||
        return logout.length === 0;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export default LogoutController;
 | 
			
		||||
 | 
			
		||||
@ -8,7 +8,7 @@ export interface IAuthRequest<
 | 
			
		||||
    ReqQuery = any,
 | 
			
		||||
> extends Request<PARAM, ResBody, ReqBody, ReqQuery> {
 | 
			
		||||
    user: User;
 | 
			
		||||
    logout: () => void;
 | 
			
		||||
    logout: (() => void) | ((callback: (err?: any) => void) => void);
 | 
			
		||||
    session: any;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user