83 lines
2.3 KiB
JavaScript
83 lines
2.3 KiB
JavaScript
function parseJsonSafe(value) {
|
|
if (!value) {
|
|
return null;
|
|
}
|
|
if (typeof value === 'object') {
|
|
return value;
|
|
}
|
|
try {
|
|
return JSON.parse(value);
|
|
} catch (_error) {
|
|
return null;
|
|
}
|
|
}
|
|
|
|
function readFormArray(body, key) {
|
|
if (Array.isArray(body[key])) {
|
|
return body[key];
|
|
}
|
|
if (body[key] === undefined) {
|
|
return [];
|
|
}
|
|
return [body[key]];
|
|
}
|
|
|
|
function normalizePageNumber(value) {
|
|
const pageNumber = Math.floor(Number(value) || 1);
|
|
return Math.max(1, pageNumber);
|
|
}
|
|
|
|
async function fetchPagedRows(pool, options) {
|
|
const selectSql = String(options && options.selectSql || '').trim();
|
|
const countSql = String(options && options.countSql || '').trim();
|
|
const params = Array.isArray(options && options.params) ? options.params : [];
|
|
const pageSize = Math.max(1, Number(options && options.pageSize) || 10);
|
|
const currentPage = normalizePageNumber(options && options.page);
|
|
|
|
if (!selectSql || !countSql) {
|
|
throw new Error('fetchPagedRows requires selectSql and countSql.');
|
|
}
|
|
|
|
const [countRows] = await pool.query(countSql, params);
|
|
const totalItems = Number(countRows && countRows[0] && countRows[0].count) || 0;
|
|
const totalPages = Math.max(1, Math.ceil(totalItems / pageSize));
|
|
const safeCurrentPage = Math.min(currentPage, totalPages);
|
|
const offset = (safeCurrentPage - 1) * pageSize;
|
|
const [rows] = await pool.query(`${selectSql} LIMIT ? OFFSET ?`, params.concat([pageSize, offset]));
|
|
|
|
return {
|
|
rows: rows || [],
|
|
totalItems: totalItems,
|
|
totalPages: totalPages,
|
|
currentPage: safeCurrentPage,
|
|
pageSize: pageSize
|
|
};
|
|
}
|
|
|
|
async function fetchDuplicateName(pool, tableName, name, excludeId, columnName) {
|
|
const normalizedName = String(name || '').trim();
|
|
if (!normalizedName) {
|
|
return null;
|
|
}
|
|
|
|
const normalizedColumnName = String(columnName || 'name').trim() || 'name';
|
|
const params = [normalizedName];
|
|
let sql = `SELECT id, \`${normalizedColumnName}\` AS name FROM \`${tableName}\` WHERE LOWER(TRIM(\`${normalizedColumnName}\`)) = LOWER(TRIM(?))`;
|
|
if (excludeId !== undefined && excludeId !== null) {
|
|
sql += ' AND id <> ?';
|
|
params.push(excludeId);
|
|
}
|
|
sql += ' LIMIT 1';
|
|
|
|
const [rows] = await pool.query(sql, params);
|
|
return rows[0] || null;
|
|
}
|
|
|
|
module.exports = {
|
|
parseJsonSafe,
|
|
readFormArray,
|
|
normalizePageNumber,
|
|
fetchPagedRows,
|
|
fetchDuplicateName
|
|
};
|