Editing accounts, change root account username, removed token expiration

This commit is contained in:
Mark Cooper 2021-09-05 18:20:29 -05:00
parent e534d015be
commit 1f2afe4d92
13 changed files with 170 additions and 55 deletions

View file

@ -4,7 +4,7 @@ const User = require('./objects/User')
const { isObject } = require('./utils/index')
class ApiController {
constructor(db, scanner, auth, streamManager, rssFeeds, downloadManager, emitter) {
constructor(db, scanner, auth, streamManager, rssFeeds, downloadManager, emitter, clientEmitter) {
this.db = db
this.scanner = scanner
this.auth = auth
@ -12,6 +12,7 @@ class ApiController {
this.rssFeeds = rssFeeds
this.downloadManager = downloadManager
this.emitter = emitter
this.clientEmitter = clientEmitter
this.router = express()
this.init()
@ -34,12 +35,13 @@ class ApiController {
this.router.get('/metadata/:id/:trackIndex', this.getMetadata.bind(this))
this.router.patch('/match/:id', this.match.bind(this))
this.router.get('/users', this.getUsers.bind(this))
this.router.post('/user', this.createUser.bind(this))
this.router.delete('/user/:id', this.deleteUser.bind(this))
this.router.delete('/user/audiobook/:id', this.resetUserAudiobookProgress.bind(this))
this.router.patch('/user/password', this.userChangePassword.bind(this))
this.router.patch('/user/settings', this.userUpdateSettings.bind(this))
this.router.get('/users', this.getUsers.bind(this))
this.router.post('/user', this.createUser.bind(this))
this.router.patch('/user/:id', this.updateUser.bind(this))
this.router.delete('/user/:id', this.deleteUser.bind(this))
this.router.patch('/serverSettings', this.updateServerSettings.bind(this))
@ -273,7 +275,7 @@ class ApiController {
var newUser = new User(account)
var success = await this.db.insertUser(newUser)
if (success) {
this.emitter('user_added', newUser)
this.clientEmitter(req.user.id, 'user_added', newUser)
res.json({
user: newUser.toJSONForBrowser()
})
@ -284,6 +286,36 @@ class ApiController {
}
}
async updateUser(req, res) {
if (req.user.type !== 'root') {
Logger.error('User other than root attempting to update user', req.user)
return res.sendStatus(403)
}
var user = this.db.users.find(u => u.id === req.params.id)
if (!user) {
return res.sendStatus(404)
}
var account = req.body
// Updating password
if (account.password) {
account.pash = await this.auth.hashPass(account.password)
delete account.password
}
var hasUpdated = user.update(account)
if (hasUpdated) {
await this.db.updateEntity('user', user)
}
this.clientEmitter(req.user.id, 'user_updated', user.toJSONForBrowser())
res.json({
success: true,
user: user.toJSONForBrowser()
})
}
async deleteUser(req, res) {
if (req.params.id === 'root') {
return res.sendStatus(500)
@ -304,7 +336,7 @@ class ApiController {
var userJson = user.toJSONForBrowser()
await this.db.removeEntity('user', user.id)
this.emitter('user_removed', userJson)
this.clientEmitter(req.user.id, 'user_removed', userJson)
res.json({
success: true
})

View file

@ -68,7 +68,7 @@ class Auth {
}
generateAccessToken(payload) {
return jwt.sign(payload, process.env.TOKEN_SECRET, { expiresIn: '1800s' });
return jwt.sign(payload, process.env.TOKEN_SECRET);
}
verifyToken(token) {

View file

@ -94,7 +94,7 @@ class Db {
}
insertSettings(settings) {
return this.settingsDb.insert(settings).then((results) => {
return this.settingsDb.insert([settings]).then((results) => {
Logger.debug(`[DB] Inserted ${results.inserted} settings`)
this.settings = this.settings.concat(settings)
}).catch((error) => {

View file

@ -34,7 +34,7 @@ class Server {
this.streamManager = new StreamManager(this.db, this.MetadataPath)
this.rssFeeds = new RssFeeds(this.Port, this.db)
this.downloadManager = new DownloadManager(this.db, this.MetadataPath, this.emitter.bind(this))
this.apiController = new ApiController(this.db, this.scanner, this.auth, this.streamManager, this.rssFeeds, this.downloadManager, this.emitter.bind(this))
this.apiController = new ApiController(this.db, this.scanner, this.auth, this.streamManager, this.rssFeeds, this.downloadManager, this.emitter.bind(this), this.clientEmitter.bind(this))
this.hlsController = new HlsController(this.db, this.scanner, this.auth, this.streamManager, this.emitter.bind(this), this.MetadataPath)
this.server = null
@ -54,11 +54,27 @@ class Server {
return this.db.serverSettings
}
getClientsForUser(userId) {
return Object.values(this.clients).filter(c => c.user && c.user.id === userId)
}
emitter(ev, data) {
// Logger.debug('EMITTER', ev)
this.io.emit(ev, data)
}
clientEmitter(userId, ev, data) {
var clients = this.getClientsForUser(userId)
if (!clients.length) {
return Logger.error(`[Server] clientEmitter - no clients found for user ${userId}`)
}
clients.forEach((client) => {
if (client.socket) {
client.socket.emit(ev, data)
}
})
}
async fileAddedUpdated({ path, fullPath }) { }
async fileRemoved({ path, fullPath }) { }

View file

@ -68,6 +68,22 @@ class User {
this.settings = user.settings || this.getDefaultUserSettings()
}
update(payload) {
var hasUpdates = false
const keysToCheck = ['pash', 'type', 'username', 'isActive']
keysToCheck.forEach((key) => {
if (payload[key] !== undefined) {
if (key === 'isActive' || payload[key]) { // pash, type, username must evaluate to true (cannot be null or empty)
if (payload[key] !== this[key]) {
hasUpdates = true
this[key] = payload[key]
}
}
}
})
return hasUpdates
}
updateAudiobookProgress(stream) {
if (!this.audiobooks) this.audiobooks = {}
if (!this.audiobooks[stream.audiobookId]) {