Integrate config tables into existing scripts, add new config tables and settings pages

This commit is contained in:
2025-01-12 15:40:27 -05:00
parent b815062525
commit 8172323954
13 changed files with 1671 additions and 126 deletions

View File

@@ -267,12 +267,27 @@ router.get('/trending-products', async (req, res) => {
router.get('/inventory-metrics', async (req, res) => {
const pool = req.app.locals.pool;
try {
// Get global configuration values
const [configs] = await pool.query(`
SELECT
st.low_stock_threshold,
tc.calculation_period_days as turnover_period
FROM stock_thresholds st
CROSS JOIN turnover_config tc
WHERE st.id = 1 AND tc.id = 1
`);
const config = configs[0] || {
low_stock_threshold: 5,
turnover_period: 30
};
// Get stock levels by category
const [stockLevels] = await pool.query(`
SELECT
c.name as category,
SUM(CASE WHEN stock_quantity > 5 THEN 1 ELSE 0 END) as inStock,
SUM(CASE WHEN stock_quantity > 0 AND stock_quantity <= 5 THEN 1 ELSE 0 END) as lowStock,
SUM(CASE WHEN stock_quantity > ? THEN 1 ELSE 0 END) as inStock,
SUM(CASE WHEN stock_quantity > 0 AND stock_quantity <= ? THEN 1 ELSE 0 END) as lowStock,
SUM(CASE WHEN stock_quantity = 0 THEN 1 ELSE 0 END) as outOfStock
FROM products p
JOIN product_categories pc ON p.product_id = pc.product_id
@@ -280,7 +295,7 @@ router.get('/inventory-metrics', async (req, res) => {
WHERE visible = true
GROUP BY c.name
ORDER BY c.name ASC
`);
`, [config.low_stock_threshold, config.low_stock_threshold]);
// Get top vendors with product counts and average stock
const [topVendors] = await pool.query(`
@@ -298,7 +313,6 @@ router.get('/inventory-metrics', async (req, res) => {
`);
// Calculate stock turnover rate by category
// Turnover = Units sold in last 30 days / Average inventory level
const [stockTurnover] = await pool.query(`
WITH CategorySales AS (
SELECT
@@ -309,7 +323,7 @@ router.get('/inventory-metrics', async (req, res) => {
JOIN product_categories pc ON p.product_id = pc.product_id
JOIN categories c ON pc.category_id = c.id
WHERE o.canceled = false
AND DATE(o.date) >= DATE_SUB(CURDATE(), INTERVAL 30 DAY)
AND DATE(o.date) >= DATE_SUB(CURDATE(), INTERVAL ? DAY)
GROUP BY c.name
),
CategoryStock AS (
@@ -331,25 +345,9 @@ router.get('/inventory-metrics', async (req, res) => {
FROM CategorySales cs
JOIN CategoryStock cst ON cs.category = cst.category
ORDER BY rate DESC
`);
`, [config.turnover_period]);
res.json({
stockLevels: stockLevels.map(row => ({
...row,
inStock: parseInt(row.inStock || 0),
lowStock: parseInt(row.lowStock || 0),
outOfStock: parseInt(row.outOfStock || 0)
})),
topVendors: topVendors.map(row => ({
vendor: row.vendor,
productCount: parseInt(row.productCount || 0),
averageStockLevel: parseFloat(row.averageStockLevel || 0)
})),
stockTurnover: stockTurnover.map(row => ({
category: row.category,
rate: parseFloat(row.rate || 0)
}))
});
res.json({ stockLevels, topVendors, stockTurnover });
} catch (error) {
console.error('Error fetching inventory metrics:', error);
res.status(500).json({ error: 'Failed to fetch inventory metrics' });