mirror of
				https://github.com/advplyr/audiobookshelf.git
				synced 2025-10-27 11:18:14 +01:00 
			
		
		
		
	Add in-memory user cache
This commit is contained in:
		
							parent
							
								
									2e970cbb39
								
							
						
					
					
						commit
						a382482173
					
				@ -990,28 +990,18 @@ class Auth {
 | 
			
		||||
        })
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    Database.userModel
 | 
			
		||||
      .update(
 | 
			
		||||
        {
 | 
			
		||||
          pash: pw
 | 
			
		||||
        },
 | 
			
		||||
        {
 | 
			
		||||
          where: { id: matchingUser.id }
 | 
			
		||||
        }
 | 
			
		||||
      )
 | 
			
		||||
      .then(() => {
 | 
			
		||||
        Logger.info(`[Auth] User "${matchingUser.username}" changed password`)
 | 
			
		||||
        res.json({
 | 
			
		||||
          success: true
 | 
			
		||||
        })
 | 
			
		||||
    try {
 | 
			
		||||
      await matchingUser.update({ pash: pw })
 | 
			
		||||
      Logger.info(`[Auth] User "${matchingUser.username}" changed password`)
 | 
			
		||||
      res.json({
 | 
			
		||||
        success: true
 | 
			
		||||
      })
 | 
			
		||||
      .catch((error) => {
 | 
			
		||||
        Logger.error(`[Auth] User "${matchingUser.username}" failed to change password`, error)
 | 
			
		||||
        res.json({
 | 
			
		||||
          error: 'Unknown error'
 | 
			
		||||
        })
 | 
			
		||||
    } catch (error) {
 | 
			
		||||
      Logger.error(`[Auth] User "${matchingUser.username}" failed to change password`, error)
 | 
			
		||||
      res.json({
 | 
			
		||||
        error: 'Unknown error'
 | 
			
		||||
      })
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -3,6 +3,53 @@ const sequelize = require('sequelize')
 | 
			
		||||
const Logger = require('../Logger')
 | 
			
		||||
const SocketAuthority = require('../SocketAuthority')
 | 
			
		||||
const { isNullOrNaN } = require('../utils')
 | 
			
		||||
const { LRUCache } = require('lru-cache')
 | 
			
		||||
 | 
			
		||||
class UserCache {
 | 
			
		||||
  constructor() {
 | 
			
		||||
    this.cache = new LRUCache({ max: 100 })
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  getById(id) {
 | 
			
		||||
    const user = this.cache.get(id)
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  getByEmail(email) {
 | 
			
		||||
    const user = this.cache.find((u) => u.email === email)
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  getByUsername(username) {
 | 
			
		||||
    const user = this.cache.find((u) => u.username === username)
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  getByOldId(oldUserId) {
 | 
			
		||||
    const user = this.cache.find((u) => u.extraData?.oldUserId === oldUserId)
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  getByOpenIDSub(sub) {
 | 
			
		||||
    const user = this.cache.find((u) => u.extraData?.authOpenIDSub === sub)
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  set(user) {
 | 
			
		||||
    user.fromCache = true
 | 
			
		||||
    this.cache.set(user.id, user)
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  delete(userId) {
 | 
			
		||||
    this.cache.delete(userId)
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  maybeInvalidate(user) {
 | 
			
		||||
    if (!user.fromCache) this.delete(user.id)
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const userCache = new UserCache()
 | 
			
		||||
 | 
			
		||||
const { DataTypes, Model } = sequelize
 | 
			
		||||
 | 
			
		||||
@ -206,7 +253,11 @@ class User extends Model {
 | 
			
		||||
   */
 | 
			
		||||
  static async getUserByUsername(username) {
 | 
			
		||||
    if (!username) return null
 | 
			
		||||
    return this.findOne({
 | 
			
		||||
 | 
			
		||||
    const cachedUser = userCache.getByUsername(username)
 | 
			
		||||
    if (cachedUser) return cachedUser
 | 
			
		||||
 | 
			
		||||
    const user = await this.findOne({
 | 
			
		||||
      where: {
 | 
			
		||||
        username: {
 | 
			
		||||
          [sequelize.Op.like]: username
 | 
			
		||||
@ -214,6 +265,10 @@ class User extends Model {
 | 
			
		||||
      },
 | 
			
		||||
      include: this.sequelize.models.mediaProgress
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    if (user) userCache.set(user)
 | 
			
		||||
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /**
 | 
			
		||||
@ -223,7 +278,11 @@ class User extends Model {
 | 
			
		||||
   */
 | 
			
		||||
  static async getUserByEmail(email) {
 | 
			
		||||
    if (!email) return null
 | 
			
		||||
    return this.findOne({
 | 
			
		||||
 | 
			
		||||
    const cachedUser = userCache.getByEmail(email)
 | 
			
		||||
    if (cachedUser) return cachedUser
 | 
			
		||||
 | 
			
		||||
    const user = await this.findOne({
 | 
			
		||||
      where: {
 | 
			
		||||
        email: {
 | 
			
		||||
          [sequelize.Op.like]: email
 | 
			
		||||
@ -231,6 +290,10 @@ class User extends Model {
 | 
			
		||||
      },
 | 
			
		||||
      include: this.sequelize.models.mediaProgress
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    if (user) userCache.set(user)
 | 
			
		||||
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /**
 | 
			
		||||
@ -240,9 +303,17 @@ class User extends Model {
 | 
			
		||||
   */
 | 
			
		||||
  static async getUserById(userId) {
 | 
			
		||||
    if (!userId) return null
 | 
			
		||||
    return this.findByPk(userId, {
 | 
			
		||||
 | 
			
		||||
    const cachedUser = userCache.getById(userId)
 | 
			
		||||
    if (cachedUser) return cachedUser
 | 
			
		||||
 | 
			
		||||
    const user = await this.findByPk(userId, {
 | 
			
		||||
      include: this.sequelize.models.mediaProgress
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    if (user) userCache.set(user)
 | 
			
		||||
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /**
 | 
			
		||||
@ -254,12 +325,19 @@ class User extends Model {
 | 
			
		||||
   */
 | 
			
		||||
  static async getUserByIdOrOldId(userId) {
 | 
			
		||||
    if (!userId) return null
 | 
			
		||||
    return this.findOne({
 | 
			
		||||
    const cachedUser = userCache.getById(userId) || userCache.getByOldId(userId)
 | 
			
		||||
    if (cachedUser) return cachedUser
 | 
			
		||||
 | 
			
		||||
    const user = await this.findOne({
 | 
			
		||||
      where: {
 | 
			
		||||
        [sequelize.Op.or]: [{ id: userId }, { 'extraData.oldUserId': userId }]
 | 
			
		||||
      },
 | 
			
		||||
      include: this.sequelize.models.mediaProgress
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    if (user) userCache.set(user)
 | 
			
		||||
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /**
 | 
			
		||||
@ -269,10 +347,18 @@ class User extends Model {
 | 
			
		||||
   */
 | 
			
		||||
  static async getUserByOpenIDSub(sub) {
 | 
			
		||||
    if (!sub) return null
 | 
			
		||||
    return this.findOne({
 | 
			
		||||
 | 
			
		||||
    const cachedUser = userCache.getByOpenIDSub(sub)
 | 
			
		||||
    if (cachedUser) return cachedUser
 | 
			
		||||
 | 
			
		||||
    const user = await this.findOne({
 | 
			
		||||
      where: sequelize.where(sequelize.literal(`extraData->>"authOpenIDSub"`), sub),
 | 
			
		||||
      include: this.sequelize.models.mediaProgress
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    if (user) userCache.set(user)
 | 
			
		||||
 | 
			
		||||
    return user
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /**
 | 
			
		||||
@ -623,6 +709,7 @@ class User extends Model {
 | 
			
		||||
      mediaProgress = await this.sequelize.models.mediaProgress.create(newMediaProgressPayload)
 | 
			
		||||
      this.mediaProgresses.push(mediaProgress)
 | 
			
		||||
    }
 | 
			
		||||
    userCache.maybeInvalidate(this)
 | 
			
		||||
    return {
 | 
			
		||||
      mediaProgress
 | 
			
		||||
    }
 | 
			
		||||
@ -804,6 +891,21 @@ class User extends Model {
 | 
			
		||||
 | 
			
		||||
    return hasUpdates
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  async update(values, options) {
 | 
			
		||||
    userCache.maybeInvalidate(this)
 | 
			
		||||
    return await super.update(values, options)
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  async save(options) {
 | 
			
		||||
    userCache.maybeInvalidate(this)
 | 
			
		||||
    return await super.save(options)
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  async destroy(options) {
 | 
			
		||||
    userCache.delete(this.id)
 | 
			
		||||
    await super.destroy(options)
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
module.exports = User
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user