feat(xo-server/api): close connection when session expires (#4071)
See xoa-support#1389
This commit is contained in:
parent
9f6fc785bc
commit
851bcf9816
@ -5,8 +5,16 @@ import { getUserPublicProperties } from '../utils'
|
||||
// ===================================================================
|
||||
|
||||
export async function signIn(credentials) {
|
||||
const user = await this.authenticateUser(credentials)
|
||||
this.session.set('user_id', user.id)
|
||||
const { session } = this
|
||||
|
||||
const { user, expiration } = await this.authenticateUser(credentials)
|
||||
session.set('user_id', user.id)
|
||||
|
||||
if (expiration === undefined) {
|
||||
session.unset('expiration')
|
||||
} else {
|
||||
session.set('expiration', expiration)
|
||||
}
|
||||
|
||||
return getUserPublicProperties(user)
|
||||
}
|
||||
|
@ -251,7 +251,7 @@ async function setUpPassport(express, xo, { authentication: authCfg }) {
|
||||
xo.registerPassportStrategy(
|
||||
new LocalStrategy(async (username, password, done) => {
|
||||
try {
|
||||
const user = await xo.authenticateUser({ username, password })
|
||||
const { user } = await xo.authenticateUser({ username, password })
|
||||
done(null, user)
|
||||
} catch (error) {
|
||||
done(null, false, { message: error.message })
|
||||
@ -518,6 +518,11 @@ const setUpApi = (webServer, xo, config) => {
|
||||
|
||||
// Connect the WebSocket to the JSON-RPC server.
|
||||
socket.on('message', message => {
|
||||
const expiration = connection.get('expiration', undefined)
|
||||
if (expiration !== undefined && expiration < Date.now()) {
|
||||
return void connection.close()
|
||||
}
|
||||
|
||||
jsonRpc.write(message)
|
||||
})
|
||||
|
||||
@ -565,7 +570,7 @@ const setUpConsoleProxy = (webServer, xo) => {
|
||||
{
|
||||
const { token } = parseCookies(req.headers.cookie)
|
||||
|
||||
const user = await xo.authenticateUser({ token })
|
||||
const { user } = await xo.authenticateUser({ token })
|
||||
if (!(await xo.hasPermissions(user.id, [[id, 'operate']]))) {
|
||||
throw invalidCredentials()
|
||||
}
|
||||
|
@ -37,7 +37,7 @@ export default class {
|
||||
|
||||
const user = await xo.getUserByName(username, true)
|
||||
if (user && (await xo.checkUserPassword(user.id, password))) {
|
||||
return user.id
|
||||
return { userId: user.id }
|
||||
}
|
||||
})
|
||||
|
||||
@ -48,7 +48,8 @@ export default class {
|
||||
}
|
||||
|
||||
try {
|
||||
return (await xo.getAuthenticationToken(tokenId)).user_id
|
||||
const token = await xo.getAuthenticationToken(tokenId)
|
||||
return { expiration: token.expiration, userId: token.user_id }
|
||||
} catch (error) {}
|
||||
})
|
||||
|
||||
@ -88,6 +89,10 @@ export default class {
|
||||
// A provider can return:
|
||||
// - `undefined`/`null` if the user could not be authenticated
|
||||
// - the identifier of the authenticated user
|
||||
// - an object containing:
|
||||
// - `userId`
|
||||
// - optionally `expiration` to indicate when the session is no longer
|
||||
// valid
|
||||
// - an object with a property `username` containing the name
|
||||
// of the authenticated user
|
||||
const result = await provider(credentials)
|
||||
@ -97,9 +102,20 @@ export default class {
|
||||
continue
|
||||
}
|
||||
|
||||
return result.username
|
||||
? await this._xo.registerUser(undefined, result.username)
|
||||
: await this._xo.getUser(result)
|
||||
if (typeof result === 'string') {
|
||||
return {
|
||||
user: await this._getUser(result),
|
||||
}
|
||||
}
|
||||
|
||||
const { userId, username, expiration } = result
|
||||
|
||||
return {
|
||||
user: await (userId !== undefined
|
||||
? this._xo.getUser(userId)
|
||||
: this._xo.registerUser(undefined, username)),
|
||||
expiration,
|
||||
}
|
||||
} catch (error) {
|
||||
// DEPRECATED: Authentication providers may just throw `null`
|
||||
// to indicate they could not authenticate the user without
|
||||
@ -109,7 +125,9 @@ export default class {
|
||||
}
|
||||
}
|
||||
|
||||
async authenticateUser(credentials) {
|
||||
async authenticateUser(
|
||||
credentials
|
||||
): Promise<{| user: Object, expiration?: number |}> {
|
||||
// don't even attempt to authenticate with empty password
|
||||
const { password } = credentials
|
||||
if (password === '') {
|
||||
|
Loading…
Reference in New Issue
Block a user