Files
Server/services/authService.js
T
azures04 22542243f6 Add auth, JWT tokens, and bootstrap startup
Introduce bootstrap entrypoint and prestartup to ping DB and generate/manage RSA keypair. Add security module for key IO. Implement JWT-based access and refresh tokens (tokensService) with refresh_tokens table and repo. Add auth, provider and user services, and refresh-token management. Update repositories (users, credentials, providers, servers) with SQL fixes and new helper methods. Move DDL execution to bootstrap (remove from server). Update package.json main and add dependencies (bcryptjs, jsonwebtoken). Update .env.example and .gitignore accordingly.
2026-09-02 01:55:58 +02:00

83 lines
2.9 KiB
JavaScript

const bcrypt = require("bcryptjs")
const usersRepo = require("../repositories/usersRepo")
const tokensService = require("./tokensService")
const identitiesRepo = require("../repositories/identitiesRepo")
const credentialsRepo = require("../repositories/credentialsRepo")
const { DefaultError } = require("../errors/errors")
async function registerLocal({ identifier, password, profile = { displayName, avatarURL } }) {
try {
const user = await usersRepo.create(identifier, process.env.SERVER_UUID, null, profile.displayName, profile.avatarURL)
const hashedPassword = await bcrypt.hash(password, Number(process.env.BCRYPT_SALT))
const credentials = await credentialsRepo.create(user.id, hashedPassword)
if (Array.isArray(credentials)) {
throw new DefaultError(500, "Internal Server Error", "UserRegistration")
}
return user
} catch (error) {
throw error
}
}
async function validatePassword({ password, passwordHash }) {
try {
await bcrypt.compare(password, passwordHash)
} catch (error) {
throw new DefaultError(401, "Bad credentials", "Wrong password")
}
}
async function loginLocal({ identifier, password }) {
try {
const user = await usersRepo.findByIdentifier(identifier)
const credentials = await credentialsRepo.findByUserId(user.id)
await validatePassword({ password: password, passwordHash: credentials.passwordHash })
const accessToken = await tokensService.signToken(user)
const refreshToken = await tokensService.signRefreshToken(user.id)
return { user, tokens: { accessToken, refreshToken } }
} catch (error) {
console.log(error)
throw new DefaultError(500, "Internal Server Error", error.toString())
}
}
async function refreshAccessToken({ userId, refreshToken }) {
try {
await tokensService.verifyRefreshToken(refreshToken)
await tokensService.revokeRefreshToken(refreshToken)
const user = await usersRepo.findById(userId)
const newAccessToken = await tokensService.signToken(user)
const newRefreshToken = await tokensService.signRefreshToken(userId)
return { accessToken: newAccessToken, refreshToken: newRefreshToken }
} catch (error) {
throw error
}
}
async function changePassword({ userId, password, newPassword }) {
try {
const credentials = await credentialsRepo.findByUserId(userId)
await validatePassword({ password, passwordHash: credentials.passwordHash })
await credentialsRepo.updatePassword(userId, newPassword)
return true
} catch (error) {
throw error
}
}
async function resetPassword({ userId, newPassword }) {
try {
await credentialsRepo.updatePassword(userId, newPassword)
return true
} catch (error) {
throw error
}
}
module.exports = {
loginLocal,
resetPassword,
registerLocal,
changePassword,
refreshAccessToken
}