cash-report-system/backend/routes/stores.js
2025-07-24 01:34:56 +02:00

141 lines
4.1 KiB
JavaScript

// GET / - list all stores (any authenticated user)
const express = require("express");
const { body, param, validationResult } = require("express-validator");
const { db } = require("../database/init");
const verifyToken = require("../middleware/auth");
const router = express.Router();
// GET /api/stores - list stores user has access to (admin: all)
router.get("/", verifyToken, (req, res) => {
if (req.user.role === "admin") {
// Admin: show all stores
db.all(
"SELECT id, name, address, isActive, createdAt, updatedAt FROM stores",
[],
(err, rows) => {
if (err) return res.status(500).json({ error: "Database error" });
res.json({ stores: rows });
}
);
} else {
// Non-admin: only stores user has access to
db.all(
`SELECT s.id, s.name, s.address, s.isActive, s.createdAt, s.updatedAt
FROM stores s
INNER JOIN user_store_access usa ON usa.storeId = s.id
WHERE usa.userId = ?`,
[req.user.userId],
(err, rows) => {
if (err) return res.status(500).json({ error: "Database error" });
res.json({ stores: rows });
}
);
}
});
// POST /api/stores - admin only, create store
router.post(
"/",
verifyToken,
[
body("name")
.isString()
.isLength({ min: 2 })
.withMessage("Store name required"),
body("address").optional().isString(),
],
(req, res) => {
if (req.user.role !== "admin")
return res.status(403).json({ error: "Admin only" });
const errors = validationResult(req);
if (!errors.isEmpty())
return res.status(400).json({ errors: errors.array() });
db.run(
"INSERT INTO stores (name, address) VALUES (?, ?)",
[req.body.name, req.body.address || null],
function (err) {
if (err) {
if (err.message && err.message.includes("UNIQUE constraint failed")) {
return res.status(409).json({ error: "Store already exists" });
}
return res.status(500).json({ error: "Database error" });
}
res.status(201).json({ id: this.lastID });
}
);
}
);
// PUT /api/stores/:id - admin only, edit store (name, address, isActive)
router.put(
"/:id",
verifyToken,
[
param("id").isInt(),
body("name").optional().isString().isLength({ min: 2 }),
body("address").optional().isString(),
body("isActive").optional().isBoolean(),
],
(req, res) => {
if (req.user.role !== "admin")
return res.status(403).json({ error: "Admin only" });
const errors = validationResult(req);
if (!errors.isEmpty())
return res.status(400).json({ errors: errors.array() });
const storeId = req.params.id;
const { name, address, isActive } = req.body;
const fields = [];
const values = [];
if (name !== undefined) {
fields.push("name = ?");
values.push(name);
}
if (address !== undefined) {
fields.push("address = ?");
values.push(address);
}
if (isActive !== undefined) {
fields.push("isActive = ?");
values.push(isActive ? 1 : 0);
}
if (fields.length === 0)
return res.status(400).json({ error: "No data to update" });
values.push(storeId);
db.run(
`UPDATE stores SET ${fields.join(
", "
)}, updatedAt = CURRENT_TIMESTAMP WHERE id = ?`,
values,
function (err) {
if (err) {
if (err.message && err.message.includes("UNIQUE constraint failed")) {
return res.status(409).json({ error: "Store name already exists" });
}
return res.status(500).json({ error: "Database error" });
}
res.json({ updated: this.changes });
}
);
}
);
// DELETE /api/stores/:id - admin only
router.delete("/:id", verifyToken, [param("id").isInt()], (req, res) => {
if (req.user.role !== "admin")
return res.status(403).json({ error: "Admin only" });
db.run("DELETE FROM stores WHERE id = ?", [req.params.id], function (err) {
if (err) return res.status(500).json({ error: "Database error" });
res.json({ deleted: this.changes });
});
});
module.exports = router;