generated from azures04/Base-REST-API
Add MariaDB integration and repositories
Introduce DB support and repos: add modules/database.js (connection pool + runDDL) and SQL DDL files (data/ddl/*) for servers, users, providers, identities and credentials. Add repository layers: users, servers, providers, identities, credentials. Update server.js to run DDL at startup. Update .env.example with DB settings and bump dependencies in package.json/package-lock.json (add mariadb, bump dotenv/helmet/path-to-regexp/zod and dev tool upgrades). Error handling and logging included for DDL and repo operations.
This commit is contained in:
@@ -0,0 +1,49 @@
|
||||
const { pool } = require("../modules/database")
|
||||
const { DefaultError } = require("../errors/errors")
|
||||
|
||||
async function findByUserId(userId) {
|
||||
try {
|
||||
const sql = "SELECT* FROM credentials WHERE userId = ?"
|
||||
const rows = await pool.query(sql, [userId])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function create(userId, hashedPassword) {
|
||||
try {
|
||||
const sql = "INSERT INTO credentials (userId, hashedPassword) VALUES (?, ?)"
|
||||
const rows = await pool.query(sql, [userId, hashedPassword])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function updatePassword(userId, hashedPassword) {
|
||||
try {
|
||||
const sql = "UPDATE credentials SET hashedPassword = ? WHERE userId = ?"
|
||||
const rows = await pool.query(sql, [hashedPassword, userId])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function remove(id) {
|
||||
try {
|
||||
const sql = "DELETE FROM credentials WHERE userId = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
create,
|
||||
remove,
|
||||
findByUserId,
|
||||
updatePassword,
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
const { pool } = require("../modules/database")
|
||||
const { DefaultError } = require("../errors/errors")
|
||||
|
||||
async function findByUserId(userId) {
|
||||
try {
|
||||
const sql = "SELECT* FROM identities WHERE userId = ?"
|
||||
const rows = await pool.query(sql, [userId])
|
||||
return rows || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function findByProviderAndSubject(providerId, providerUserId) {
|
||||
try {
|
||||
const sql = "SELECT* FROM identities WHERE providerId = ? AND providerUserId = ?"
|
||||
const rows = await pool.query(sql, [providerId, providerUserId])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function create(userId, providerId, providerUserId) {
|
||||
try {
|
||||
const sql = "INSERT INTO identities (userId, providerId, providerUserId) VALUES (?, ?, ?)"
|
||||
const rows = await pool.query(sql, [userId, providerId, providerUserId])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function remove(id) {
|
||||
try {
|
||||
const sql = "DELETE FROM identities WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
create,
|
||||
remove,
|
||||
findByUserId,
|
||||
findByProviderAndSubject
|
||||
}
|
||||
@@ -0,0 +1,105 @@
|
||||
const { pool } = require("../modules/database")
|
||||
const { DefaultError } = require("../errors/errors")
|
||||
|
||||
async function findById(id) {
|
||||
try {
|
||||
const sql = "SELECT* FROM providers WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function findByName(id) {
|
||||
try {
|
||||
const sql = "SELECT* FROM providers WHERE name = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function listEnabled() {
|
||||
try {
|
||||
const sql = "SELECT* FROM providers WHERE isEnabled = ?"
|
||||
const rows = await pool.query(sql, [true])
|
||||
return rows || []
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function setEnabled(id, isEnabled) {
|
||||
try {
|
||||
const sql = "UPDATE providers SET isEnabled = ? WHERE id = ?"
|
||||
const rows = await pool.query(sql, [isEnabled, id])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function create(name, issuerLogo, issuerURL) {
|
||||
try {
|
||||
const sql = "INSERT INTO providers (name, issuerLogo, issuerURL) VALUES (?, ?, ?)"
|
||||
const rows = await pool.query(sql, [name, issuerLogo, issuerURL])
|
||||
return rows[0]
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function updateProvider(id, name, issuerLogo, issuerURL) {
|
||||
try {
|
||||
const fields = []
|
||||
const params = { id }
|
||||
|
||||
if (name !== undefined) {
|
||||
fields.push('`name` = :name')
|
||||
params.name = name
|
||||
}
|
||||
|
||||
if (issuerLogo !== undefined) {
|
||||
fields.push('`issuerLogo` = :issuerLogo')
|
||||
params.issuerLogo = issuerLogo
|
||||
}
|
||||
|
||||
if (issuerURL !== undefined) {
|
||||
fields.push('`issuerURL` = :issuerURL')
|
||||
params.issuerURL = issuerURL
|
||||
}
|
||||
|
||||
if (fields.length === 0) {
|
||||
return findById(id)
|
||||
}
|
||||
|
||||
const sql = `UPDATE providers SET ${fields.join(', ')} WHERE id = :id`
|
||||
await pool.query(sql, params)
|
||||
|
||||
return findById(id)
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function remove(id) {
|
||||
try {
|
||||
const sql = "DELETE FROM providers WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
remove,
|
||||
create,
|
||||
findById,
|
||||
findByName,
|
||||
setEnabled,
|
||||
listEnabled,
|
||||
updateProvider,
|
||||
}
|
||||
@@ -0,0 +1,78 @@
|
||||
const { pool } = require("../modules/database")
|
||||
const { DefaultError } = require("../errors/errors")
|
||||
|
||||
async function findById(id) {
|
||||
try {
|
||||
const sql = "SELECT* FROM servers WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function findByUrl(url) {
|
||||
try {
|
||||
const sql = "SELECT* FROM servers WHERE url = ?"
|
||||
const rows = await pool.query(sql, [url])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function create(url, publicKey) {
|
||||
try {
|
||||
const sql = "INSERT INTO servers (serverUrl, publicKey) VALUES (?, ?)"
|
||||
const rows = await pool.query(sql, [url, publicKey])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function remove(id) {
|
||||
try {
|
||||
const sql = "DELETE FROM servers WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function updateServer(id, serverUrl, publicKey) {
|
||||
try {
|
||||
const fields = []
|
||||
const params = { id }
|
||||
|
||||
if (serverUrl !== undefined) {
|
||||
fields.push('`serverUrl` = :serverUrl')
|
||||
params.serverUrl = serverUrl
|
||||
}
|
||||
|
||||
if (publicKey !== undefined) {
|
||||
fields.push('`publicKey` = :publicKey')
|
||||
params.publicKey = publicKey
|
||||
}
|
||||
|
||||
if (fields.length === 0) {
|
||||
return findById(id)
|
||||
}
|
||||
|
||||
const sql = `UPDATE servers SET ${fields.join(', ')} WHERE id = :id`
|
||||
await pool.query(sql, params)
|
||||
|
||||
return findById(id)
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
create,
|
||||
remove,
|
||||
findById,
|
||||
findByUrl,
|
||||
updateServer
|
||||
}
|
||||
@@ -0,0 +1,90 @@
|
||||
const { pool } = require("../modules/database")
|
||||
const { DefaultError } = require("../errors/errors")
|
||||
|
||||
async function findById(id) {
|
||||
try {
|
||||
const sql = "SELECT* FROM servers WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function create(serverId, remoteId = null, displayName, avatarUrl) {
|
||||
try {
|
||||
const sql = "INSERT INTO users (serverId, remoteId, displayName, avatarUrl) VALUES (?, ?, ?, ?)"
|
||||
const rows = await pool.query(sql, [serverId, remoteId, displayName, avatarUrl])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function remove(id) {
|
||||
try {
|
||||
const sql = "DELETE FROM users WHERE id = ?"
|
||||
const rows = await pool.query(sql, [id])
|
||||
return rows.affectedRows > 0
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function isLocal(id) {
|
||||
const sql = "SELECT (remoteId IS NULL) AS isLocal FROM users WHERE id = ?"
|
||||
const rows = await db.query(sql, [id])
|
||||
|
||||
if (rows.length === 0) {
|
||||
throw new DefaultError(404, `User ${id} not found`)
|
||||
}
|
||||
|
||||
return Boolean(rows[0].isLocal)
|
||||
}
|
||||
|
||||
async function updateProfile(id, displayName, avatarUrl) {
|
||||
try {
|
||||
const fields = []
|
||||
const params = { id }
|
||||
|
||||
if (displayName !== undefined) {
|
||||
fields.push('`displayName` = :displayName')
|
||||
params.displayName = displayName
|
||||
}
|
||||
|
||||
if (avatarUrl !== undefined) {
|
||||
fields.push('`avatarUrl` = :avatarUrl')
|
||||
params.avatarUrl = avatarUrl
|
||||
}
|
||||
|
||||
if (fields.length === 0) {
|
||||
return findById(id)
|
||||
}
|
||||
|
||||
const sql = `UPDATE users SET ${fields.join(', ')} WHERE id = :id`
|
||||
await pool.query(sql, params)
|
||||
|
||||
return findById(id)
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
async function findByServerAndRemoteId(serverId, remoteId) {
|
||||
try {
|
||||
const sql = "SELECT * FROM users WHERE serverId = ? AND remoteId = ?"
|
||||
const rows = await pool.query(sql, [serverId, remoteId])
|
||||
return rows[0] || null
|
||||
} catch (error) {
|
||||
throw new DefaultError(500, "Internal Server Error", error)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
create,
|
||||
remove,
|
||||
isLocal,
|
||||
findById,
|
||||
updateProfile,
|
||||
findByServerAndRemoteId
|
||||
}
|
||||
Reference in New Issue
Block a user