ostroner 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (112) hide show
  1. package/bin/create-project.js +57 -0
  2. package/package.json +23 -0
  3. package/templates/stock-chain/backend/.env +9 -0
  4. package/templates/stock-chain/backend/.eslintrc.js +6 -0
  5. package/templates/stock-chain/backend/.prettierrc +14 -0
  6. package/templates/stock-chain/backend/README.md +1 -0
  7. package/templates/stock-chain/backend/package-lock.json +1666 -0
  8. package/templates/stock-chain/backend/package.json +21 -0
  9. package/templates/stock-chain/backend/src/app.js +59 -0
  10. package/templates/stock-chain/backend/src/config/db.js +29 -0
  11. package/templates/stock-chain/backend/src/controllers/auth.js +31 -0
  12. package/templates/stock-chain/backend/src/controllers/bookingcontroller.js +65 -0
  13. package/templates/stock-chain/backend/src/controllers/buscontroller.js +59 -0
  14. package/templates/stock-chain/backend/src/controllers/deliverycontroller.js +35 -0
  15. package/templates/stock-chain/backend/src/controllers/schedulecontroller.js +85 -0
  16. package/templates/stock-chain/backend/src/controllers/shipmentcontroller.js +35 -0
  17. package/templates/stock-chain/backend/src/controllers/suppliercontroller.js +35 -0
  18. package/templates/stock-chain/backend/src/controllers/usercontroller.js +59 -0
  19. package/templates/stock-chain/backend/src/middleware/auth.js +11 -0
  20. package/templates/stock-chain/backend/src/middleware/errorHandler.js +7 -0
  21. package/templates/stock-chain/backend/src/models/delivery.js +20 -0
  22. package/templates/stock-chain/backend/src/models/index.js +6 -0
  23. package/templates/stock-chain/backend/src/models/shipment.js +20 -0
  24. package/templates/stock-chain/backend/src/models/supplier.js +17 -0
  25. package/templates/stock-chain/backend/src/models/user.js +15 -0
  26. package/templates/stock-chain/backend/src/routes/authroute.js +11 -0
  27. package/templates/stock-chain/backend/src/routes/bookingroute.js +18 -0
  28. package/templates/stock-chain/backend/src/routes/busroute.js +18 -0
  29. package/templates/stock-chain/backend/src/routes/deliveriesroute.js +18 -0
  30. package/templates/stock-chain/backend/src/routes/scheduleroute.js +18 -0
  31. package/templates/stock-chain/backend/src/routes/shipmentsroute.js +18 -0
  32. package/templates/stock-chain/backend/src/routes/suppliersroute.js +18 -0
  33. package/templates/stock-chain/backend/src/routes/userroute.js +18 -0
  34. package/templates/stock-chain/frontend/.env +1 -0
  35. package/templates/stock-chain/frontend/README.md +16 -0
  36. package/templates/stock-chain/frontend/eslint.config.js +21 -0
  37. package/templates/stock-chain/frontend/index.html +13 -0
  38. package/templates/stock-chain/frontend/package-lock.json +3131 -0
  39. package/templates/stock-chain/frontend/package.json +33 -0
  40. package/templates/stock-chain/frontend/public/favicon.svg +1 -0
  41. package/templates/stock-chain/frontend/public/icons.svg +24 -0
  42. package/templates/stock-chain/frontend/src/App.jsx +55 -0
  43. package/templates/stock-chain/frontend/src/assets/hero.png +0 -0
  44. package/templates/stock-chain/frontend/src/assets/react.svg +1 -0
  45. package/templates/stock-chain/frontend/src/assets/vite.svg +1 -0
  46. package/templates/stock-chain/frontend/src/components/Button.jsx +15 -0
  47. package/templates/stock-chain/frontend/src/components/Input.jsx +25 -0
  48. package/templates/stock-chain/frontend/src/context/AuthContext.jsx +59 -0
  49. package/templates/stock-chain/frontend/src/index.css +7 -0
  50. package/templates/stock-chain/frontend/src/main.jsx +18 -0
  51. package/templates/stock-chain/frontend/src/pages/AppLayout.jsx +125 -0
  52. package/templates/stock-chain/frontend/src/pages/Login.jsx +78 -0
  53. package/templates/stock-chain/frontend/src/pages/ManagerDeliveries.jsx +113 -0
  54. package/templates/stock-chain/frontend/src/pages/ManagerShipments.jsx +113 -0
  55. package/templates/stock-chain/frontend/src/pages/ManagerSuppliers.jsx +122 -0
  56. package/templates/stock-chain/frontend/src/pages/Register.jsx +60 -0
  57. package/templates/stock-chain/frontend/src/services/api.js +8 -0
  58. package/templates/stock-chain/frontend/src/services/authService.js +11 -0
  59. package/templates/stock-chain/frontend/vite.config.js +8 -0
  60. package/templates/y-bus/backend/.env +9 -0
  61. package/templates/y-bus/backend/.eslintrc.js +6 -0
  62. package/templates/y-bus/backend/.prettierrc +14 -0
  63. package/templates/y-bus/backend/README.md +1 -0
  64. package/templates/y-bus/backend/package-lock.json +1666 -0
  65. package/templates/y-bus/backend/package.json +21 -0
  66. package/templates/y-bus/backend/src/app.js +44 -0
  67. package/templates/y-bus/backend/src/config/db.js +29 -0
  68. package/templates/y-bus/backend/src/controllers/auth.js +23 -0
  69. package/templates/y-bus/backend/src/controllers/bookingcontroller.js +65 -0
  70. package/templates/y-bus/backend/src/controllers/buscontroller.js +59 -0
  71. package/templates/y-bus/backend/src/controllers/schedulecontroller.js +85 -0
  72. package/templates/y-bus/backend/src/controllers/usercontroller.js +59 -0
  73. package/templates/y-bus/backend/src/middleware/auth.js +11 -0
  74. package/templates/y-bus/backend/src/middleware/errorHandler.js +7 -0
  75. package/templates/y-bus/backend/src/models/booking.js +27 -0
  76. package/templates/y-bus/backend/src/models/bus.js +16 -0
  77. package/templates/y-bus/backend/src/models/index.js +15 -0
  78. package/templates/y-bus/backend/src/models/schedule.js +25 -0
  79. package/templates/y-bus/backend/src/models/user.js +20 -0
  80. package/templates/y-bus/backend/src/routes/bookingroute.js +18 -0
  81. package/templates/y-bus/backend/src/routes/busroute.js +18 -0
  82. package/templates/y-bus/backend/src/routes/scheduleroute.js +18 -0
  83. package/templates/y-bus/backend/src/routes/userroute.js +18 -0
  84. package/templates/y-bus/frontend/.env +1 -0
  85. package/templates/y-bus/frontend/README.md +16 -0
  86. package/templates/y-bus/frontend/eslint.config.js +21 -0
  87. package/templates/y-bus/frontend/index.html +13 -0
  88. package/templates/y-bus/frontend/package-lock.json +3131 -0
  89. package/templates/y-bus/frontend/package.json +33 -0
  90. package/templates/y-bus/frontend/public/favicon.svg +1 -0
  91. package/templates/y-bus/frontend/public/icons.svg +24 -0
  92. package/templates/y-bus/frontend/src/App.jsx +108 -0
  93. package/templates/y-bus/frontend/src/assets/hero.png +0 -0
  94. package/templates/y-bus/frontend/src/assets/react.svg +1 -0
  95. package/templates/y-bus/frontend/src/assets/vite.svg +1 -0
  96. package/templates/y-bus/frontend/src/components/Button.jsx +15 -0
  97. package/templates/y-bus/frontend/src/components/Input.jsx +25 -0
  98. package/templates/y-bus/frontend/src/context/AuthContext.jsx +59 -0
  99. package/templates/y-bus/frontend/src/index.css +7 -0
  100. package/templates/y-bus/frontend/src/main.jsx +18 -0
  101. package/templates/y-bus/frontend/src/pages/AppLayout.jsx +135 -0
  102. package/templates/y-bus/frontend/src/pages/CustomerTrips.jsx +101 -0
  103. package/templates/y-bus/frontend/src/pages/Login.jsx +81 -0
  104. package/templates/y-bus/frontend/src/pages/ManagerBuses.jsx +140 -0
  105. package/templates/y-bus/frontend/src/pages/ManagerDashboard.jsx +108 -0
  106. package/templates/y-bus/frontend/src/pages/ManagerReport.jsx +89 -0
  107. package/templates/y-bus/frontend/src/pages/ManagerSchedules.jsx +233 -0
  108. package/templates/y-bus/frontend/src/pages/MyBookings.jsx +78 -0
  109. package/templates/y-bus/frontend/src/pages/Register.jsx +67 -0
  110. package/templates/y-bus/frontend/src/services/api.js +8 -0
  111. package/templates/y-bus/frontend/src/services/authService.js +33 -0
  112. package/templates/y-bus/frontend/vite.config.js +8 -0
@@ -0,0 +1,21 @@
1
+ {
2
+ "name": "backend-project",
3
+ "version": "1.0.0",
4
+ "main": "src/app.js",
5
+ "type": "module",
6
+ "scripts": {
7
+ "dev": "nodemon src/app.js"
8
+ },
9
+ "devDependencies": {
10
+ "nodemon": "^3.1.14"
11
+ },
12
+ "dependencies": {
13
+ "bcryptjs": "^3.0.3",
14
+ "cors": "^2.8.6",
15
+ "dotenv": "^17.4.2",
16
+ "express": "^5.2.1",
17
+ "jsonwebtoken": "^9.0.3",
18
+ "mysql2": "^3.22.4",
19
+ "sequelize": "^6.37.8"
20
+ }
21
+ }
@@ -0,0 +1,59 @@
1
+ import express from "express";
2
+ import cors from "cors";
3
+ import { connectDB, sequelize } from "./config/db.js";
4
+ import "./models/index.js";
5
+ import authRoutes from "./routes/authroute.js";
6
+ import suppliersRoutes from "./routes/suppliersroute.js";
7
+ import shipmentsRoutes from "./routes/shipmentsroute.js";
8
+ import deliveriesRoutes from "./routes/deliveriesroute.js";
9
+
10
+ const app = express();
11
+
12
+ // Allow multiple Vite dev servers (and custom list via CLIENT_URL env var)
13
+ // CLIENT_URL can be a comma-separated list, e.g. "http://localhost:5173,http://localhost:5174"
14
+ const allowedOrigins = (process.env.CLIENT_URL
15
+ ? process.env.CLIENT_URL.split(",")
16
+ : [
17
+ "http://localhost:5173",
18
+ "http://localhost:5174",
19
+ "http://localhost:5175",
20
+ "http://localhost:5176",
21
+ ]
22
+ ).map((s) => s.trim()).filter(Boolean);
23
+
24
+ app.use(
25
+ cors({
26
+ origin: function (origin, callback) {
27
+ // allow non-browser tools (no origin)
28
+ if (!origin) return callback(null, true);
29
+ if (allowedOrigins.includes(origin)) return callback(null, true);
30
+ return callback(new Error("Not allowed by CORS"));
31
+ },
32
+ credentials: true,
33
+ })
34
+ );
35
+ app.use(express.json());
36
+
37
+ app.use("/api/auth", authRoutes);
38
+ app.use("/api/suppliers", suppliersRoutes);
39
+ app.use("/api/shipments", shipmentsRoutes);
40
+ app.use("/api/deliveries", deliveriesRoutes);
41
+
42
+ app.get("/", (req, res) => {
43
+ res.json({
44
+ message: "API Running"
45
+ });
46
+ });
47
+
48
+ const PORT = process.env.PORT || 5000;
49
+
50
+ const startServer = async () => {
51
+ await connectDB();
52
+ await sequelize.sync({ alter: true });
53
+
54
+ app.listen(PORT, () => {
55
+ console.log(`Server running on ${PORT}`);
56
+ });
57
+ };
58
+
59
+ startServer();
@@ -0,0 +1,29 @@
1
+ import dotenv from "dotenv";
2
+ import { Sequelize } from "sequelize";
3
+
4
+ dotenv.config();
5
+
6
+ const sequelize = new Sequelize(
7
+ "supplier_chain",
8
+ process.env.DB_USER,
9
+ process.env.DB_PASSWORD,
10
+ {
11
+ host: process.env.DB_HOST,
12
+ port: Number(process.env.DB_PORT) || 3306,
13
+ dialect: "mysql",
14
+ logging: false,
15
+ }
16
+ );
17
+
18
+ const connectDB = async () => {
19
+ try {
20
+ await sequelize.authenticate();
21
+ console.log("Database connected successfully");
22
+ } catch (error) {
23
+ console.error("Database connection failed:", error.message);
24
+ throw error;
25
+ }
26
+ };
27
+
28
+ export { sequelize, connectDB };
29
+ export default sequelize;
@@ -0,0 +1,31 @@
1
+ import bcrypt from "bcryptjs";
2
+ import { User } from "../models/index.js";
3
+
4
+ export async function register(req, res) {
5
+ const { username, password } = req.body;
6
+ if (!username || !password) return res.status(400).json({ success: false, message: "username and password required" });
7
+ const exists = await User.findOne({ where: { username } });
8
+ if (exists) return res.status(409).json({ success: false, message: "Username already taken" });
9
+ const hashed = await bcrypt.hash(password, 10);
10
+ const user = await User.create({ username, password: hashed });
11
+ res.status(201).json({ success: true, data: { userid: user.userid, username: user.username } });
12
+ }
13
+
14
+ export async function login(req, res) {
15
+ const { username, password } = req.body;
16
+ if (!username || !password) return res.status(400).json({ success: false, message: "username and password required" });
17
+ const user = await User.findOne({ where: { username } });
18
+ if (!user) return res.status(401).json({ success: false, message: "Invalid username or password" });
19
+ const ok = await bcrypt.compare(password, user.password);
20
+ if (!ok) return res.status(401).json({ success: false, message: "Invalid username or password" });
21
+ res.json({ success: true, data: { userid: user.userid, username: user.username } });
22
+ }
23
+
24
+ export function me(req, res) {
25
+ // frontend stores user locally; keep this endpoint for compatibility
26
+ res.json({ success: true, data: null });
27
+ }
28
+
29
+ export function logout(req, res) {
30
+ res.json({ success: true, message: "Logged out" });
31
+ }
@@ -0,0 +1,65 @@
1
+ import { Booking } from "../models/booking.js";
2
+ import { Schedule } from "../models/schedule.js";
3
+ import { User } from "../models/user.js";
4
+
5
+ export const createBooking = async (req, res) => {
6
+ try {
7
+ const booking = await Booking.create(req.body);
8
+ return res.status(201).json({ success: true, data: booking });
9
+ } catch (error) {
10
+ return res.status(400).json({ success: false, message: error.message });
11
+ }
12
+ };
13
+
14
+ export const getAllBookings = async (req, res) => {
15
+ try {
16
+ const bookings = await Booking.findAll({
17
+ include: [{ model: Schedule }, { model: User }],
18
+ });
19
+ return res.json({ success: true, data: bookings });
20
+ } catch (error) {
21
+ return res.status(500).json({ success: false, message: error.message });
22
+ }
23
+ };
24
+
25
+ export const getBookingById = async (req, res) => {
26
+ try {
27
+ const booking = await Booking.findByPk(req.params.id, {
28
+ include: [{ model: Schedule }, { model: User }],
29
+ });
30
+ if (!booking) {
31
+ return res.status(404).json({ success: false, message: "Booking not found" });
32
+ }
33
+ return res.json({ success: true, data: booking });
34
+ } catch (error) {
35
+ return res.status(500).json({ success: false, message: error.message });
36
+ }
37
+ };
38
+
39
+ export const updateBooking = async (req, res) => {
40
+ try {
41
+ const booking = await Booking.findByPk(req.params.id);
42
+ if (!booking) {
43
+ return res.status(404).json({ success: false, message: "Booking not found" });
44
+ }
45
+
46
+ await booking.update(req.body);
47
+ return res.json({ success: true, data: booking });
48
+ } catch (error) {
49
+ return res.status(400).json({ success: false, message: error.message });
50
+ }
51
+ };
52
+
53
+ export const deleteBooking = async (req, res) => {
54
+ try {
55
+ const booking = await Booking.findByPk(req.params.id);
56
+ if (!booking) {
57
+ return res.status(404).json({ success: false, message: "Booking not found" });
58
+ }
59
+
60
+ await booking.destroy();
61
+ return res.json({ success: true, message: "Booking deleted successfully" });
62
+ } catch (error) {
63
+ return res.status(500).json({ success: false, message: error.message });
64
+ }
65
+ };
@@ -0,0 +1,59 @@
1
+ import { Bus } from "../models/bus.js";
2
+
3
+ export const createBus = async (req, res) => {
4
+ try {
5
+ const bus = await Bus.create(req.body);
6
+ return res.status(201).json({ success: true, data: bus });
7
+ } catch (error) {
8
+ return res.status(400).json({ success: false, message: error.message });
9
+ }
10
+ };
11
+
12
+ export const getAllBuses = async (req, res) => {
13
+ try {
14
+ const buses = await Bus.findAll();
15
+ return res.json({ success: true, data: buses });
16
+ } catch (error) {
17
+ return res.status(500).json({ success: false, message: error.message });
18
+ }
19
+ };
20
+
21
+ export const getBusById = async (req, res) => {
22
+ try {
23
+ const bus = await Bus.findByPk(req.params.id);
24
+ if (!bus) {
25
+ return res.status(404).json({ success: false, message: "Bus not found" });
26
+ }
27
+ return res.json({ success: true, data: bus });
28
+ } catch (error) {
29
+ return res.status(500).json({ success: false, message: error.message });
30
+ }
31
+ };
32
+
33
+ export const updateBus = async (req, res) => {
34
+ try {
35
+ const bus = await Bus.findByPk(req.params.id);
36
+ if (!bus) {
37
+ return res.status(404).json({ success: false, message: "Bus not found" });
38
+ }
39
+
40
+ await bus.update(req.body);
41
+ return res.json({ success: true, data: bus });
42
+ } catch (error) {
43
+ return res.status(400).json({ success: false, message: error.message });
44
+ }
45
+ };
46
+
47
+ export const deleteBus = async (req, res) => {
48
+ try {
49
+ const bus = await Bus.findByPk(req.params.id);
50
+ if (!bus) {
51
+ return res.status(404).json({ success: false, message: "Bus not found" });
52
+ }
53
+
54
+ await bus.destroy();
55
+ return res.json({ success: true, message: "Bus deleted successfully" });
56
+ } catch (error) {
57
+ return res.status(500).json({ success: false, message: error.message });
58
+ }
59
+ };
@@ -0,0 +1,35 @@
1
+ import { Delivery } from "../models/index.js";
2
+
3
+ export async function getAllDeliveries(req, res) {
4
+ const items = await Delivery.findAll();
5
+ res.json({ success: true, data: items });
6
+ }
7
+
8
+ export async function getDeliveryById(req, res) {
9
+ const { id } = req.params;
10
+ const item = await Delivery.findByPk(id);
11
+ if (!item) return res.status(404).json({ success: false, message: "Delivery not found" });
12
+ res.json({ success: true, data: item });
13
+ }
14
+
15
+ export async function createDelivery(req, res) {
16
+ const payload = req.body;
17
+ const item = await Delivery.create(payload);
18
+ res.status(201).json({ success: true, data: item });
19
+ }
20
+
21
+ export async function updateDelivery(req, res) {
22
+ const { id } = req.params;
23
+ const item = await Delivery.findByPk(id);
24
+ if (!item) return res.status(404).json({ success: false, message: "Delivery not found" });
25
+ await item.update(req.body);
26
+ res.json({ success: true, data: item });
27
+ }
28
+
29
+ export async function deleteDelivery(req, res) {
30
+ const { id } = req.params;
31
+ const item = await Delivery.findByPk(id);
32
+ if (!item) return res.status(404).json({ success: false, message: "Delivery not found" });
33
+ await item.destroy();
34
+ res.json({ success: true, message: "Delivery deleted" });
35
+ }
@@ -0,0 +1,85 @@
1
+ import { Schedule } from "../models/schedule.js";
2
+ import { Bus } from "../models/bus.js";
3
+ import { Booking } from "../models/booking.js";
4
+
5
+ export const createSchedule = async (req, res) => {
6
+ try {
7
+ const schedule = await Schedule.create(req.body);
8
+ return res.status(201).json({ success: true, data: schedule });
9
+ } catch (error) {
10
+ return res.status(400).json({ success: false, message: error.message });
11
+ }
12
+ };
13
+
14
+ export const getAllSchedules = async (req, res) => {
15
+ try {
16
+ const where = {};
17
+ if (req.query.status) {
18
+ where.schedulestatus = req.query.status;
19
+ }
20
+ const availableOnly = req.query.available === "true";
21
+
22
+ const schedules = await Schedule.findAll({
23
+ where,
24
+ include: [
25
+ { model: Bus },
26
+ ...(availableOnly ? [{ model: Booking, attributes: ["bookingid"] }] : []),
27
+ ],
28
+ order: [["departuretime", "ASC"]],
29
+ });
30
+
31
+ if (!availableOnly) {
32
+ return res.json({ success: true, data: schedules });
33
+ }
34
+
35
+ const availableSchedules = schedules.filter((schedule) => {
36
+ const totalSeats = Number(schedule.Bus?.totalseats || 0);
37
+ const bookedSeats = Array.isArray(schedule.Bookings) ? schedule.Bookings.length : 0;
38
+ return totalSeats > 0 && bookedSeats < totalSeats;
39
+ });
40
+
41
+ return res.json({ success: true, data: availableSchedules });
42
+ } catch (error) {
43
+ return res.status(500).json({ success: false, message: error.message });
44
+ }
45
+ };
46
+
47
+ export const getScheduleById = async (req, res) => {
48
+ try {
49
+ const schedule = await Schedule.findByPk(req.params.id, { include: [{ model: Bus }] });
50
+ if (!schedule) {
51
+ return res.status(404).json({ success: false, message: "Schedule not found" });
52
+ }
53
+ return res.json({ success: true, data: schedule });
54
+ } catch (error) {
55
+ return res.status(500).json({ success: false, message: error.message });
56
+ }
57
+ };
58
+
59
+ export const updateSchedule = async (req, res) => {
60
+ try {
61
+ const schedule = await Schedule.findByPk(req.params.id);
62
+ if (!schedule) {
63
+ return res.status(404).json({ success: false, message: "Schedule not found" });
64
+ }
65
+
66
+ await schedule.update(req.body);
67
+ return res.json({ success: true, data: schedule });
68
+ } catch (error) {
69
+ return res.status(400).json({ success: false, message: error.message });
70
+ }
71
+ };
72
+
73
+ export const deleteSchedule = async (req, res) => {
74
+ try {
75
+ const schedule = await Schedule.findByPk(req.params.id);
76
+ if (!schedule) {
77
+ return res.status(404).json({ success: false, message: "Schedule not found" });
78
+ }
79
+
80
+ await schedule.destroy();
81
+ return res.json({ success: true, message: "Schedule deleted successfully" });
82
+ } catch (error) {
83
+ return res.status(500).json({ success: false, message: error.message });
84
+ }
85
+ };
@@ -0,0 +1,35 @@
1
+ import { Shipment } from "../models/index.js";
2
+
3
+ export async function getAllShipments(req, res) {
4
+ const items = await Shipment.findAll();
5
+ res.json({ success: true, data: items });
6
+ }
7
+
8
+ export async function getShipmentById(req, res) {
9
+ const { id } = req.params;
10
+ const item = await Shipment.findByPk(id);
11
+ if (!item) return res.status(404).json({ success: false, message: "Shipment not found" });
12
+ res.json({ success: true, data: item });
13
+ }
14
+
15
+ export async function createShipment(req, res) {
16
+ const payload = req.body;
17
+ const item = await Shipment.create(payload);
18
+ res.status(201).json({ success: true, data: item });
19
+ }
20
+
21
+ export async function updateShipment(req, res) {
22
+ const { id } = req.params;
23
+ const item = await Shipment.findByPk(id);
24
+ if (!item) return res.status(404).json({ success: false, message: "Shipment not found" });
25
+ await item.update(req.body);
26
+ res.json({ success: true, data: item });
27
+ }
28
+
29
+ export async function deleteShipment(req, res) {
30
+ const { id } = req.params;
31
+ const item = await Shipment.findByPk(id);
32
+ if (!item) return res.status(404).json({ success: false, message: "Shipment not found" });
33
+ await item.destroy();
34
+ res.json({ success: true, message: "Shipment deleted" });
35
+ }
@@ -0,0 +1,35 @@
1
+ import { Supplier } from "../models/index.js";
2
+
3
+ export async function getAllSuppliers(req, res) {
4
+ const suppliers = await Supplier.findAll();
5
+ res.json({ success: true, data: suppliers });
6
+ }
7
+
8
+ export async function getSupplierById(req, res) {
9
+ const { id } = req.params;
10
+ const supplier = await Supplier.findByPk(id);
11
+ if (!supplier) return res.status(404).json({ success: false, message: "Supplier not found" });
12
+ res.json({ success: true, data: supplier });
13
+ }
14
+
15
+ export async function createSupplier(req, res) {
16
+ const payload = req.body;
17
+ const supplier = await Supplier.create(payload);
18
+ res.status(201).json({ success: true, data: supplier });
19
+ }
20
+
21
+ export async function updateSupplier(req, res) {
22
+ const { id } = req.params;
23
+ const supplier = await Supplier.findByPk(id);
24
+ if (!supplier) return res.status(404).json({ success: false, message: "Supplier not found" });
25
+ await supplier.update(req.body);
26
+ res.json({ success: true, data: supplier });
27
+ }
28
+
29
+ export async function deleteSupplier(req, res) {
30
+ const { id } = req.params;
31
+ const supplier = await Supplier.findByPk(id);
32
+ if (!supplier) return res.status(404).json({ success: false, message: "Supplier not found" });
33
+ await supplier.destroy();
34
+ res.json({ success: true, message: "Supplier deleted" });
35
+ }
@@ -0,0 +1,59 @@
1
+ import { User } from "../models/user.js";
2
+
3
+ export const createUser = async (req, res) => {
4
+ try {
5
+ const user = await User.create(req.body);
6
+ return res.status(201).json({ success: true, data: user });
7
+ } catch (error) {
8
+ return res.status(400).json({ success: false, message: error.message });
9
+ }
10
+ };
11
+
12
+ export const getAllUsers = async (req, res) => {
13
+ try {
14
+ const users = await User.findAll();
15
+ return res.json({ success: true, data: users });
16
+ } catch (error) {
17
+ return res.status(500).json({ success: false, message: error.message });
18
+ }
19
+ };
20
+
21
+ export const getUserById = async (req, res) => {
22
+ try {
23
+ const user = await User.findByPk(req.params.id);
24
+ if (!user) {
25
+ return res.status(404).json({ success: false, message: "User not found" });
26
+ }
27
+ return res.json({ success: true, data: user });
28
+ } catch (error) {
29
+ return res.status(500).json({ success: false, message: error.message });
30
+ }
31
+ };
32
+
33
+ export const updateUser = async (req, res) => {
34
+ try {
35
+ const user = await User.findByPk(req.params.id);
36
+ if (!user) {
37
+ return res.status(404).json({ success: false, message: "User not found" });
38
+ }
39
+
40
+ await user.update(req.body);
41
+ return res.json({ success: true, data: user });
42
+ } catch (error) {
43
+ return res.status(400).json({ success: false, message: error.message });
44
+ }
45
+ };
46
+
47
+ export const deleteUser = async (req, res) => {
48
+ try {
49
+ const user = await User.findByPk(req.params.id);
50
+ if (!user) {
51
+ return res.status(404).json({ success: false, message: "User not found" });
52
+ }
53
+
54
+ await user.destroy();
55
+ return res.json({ success: true, message: "User deleted successfully" });
56
+ } catch (error) {
57
+ return res.status(500).json({ success: false, message: error.message });
58
+ }
59
+ };
@@ -0,0 +1,11 @@
1
+ export function requireAuth(req, res, next) {
2
+ if (!req.session.user) return res.status(401).json({ success: false, message: 'Unauthorized. Please login.' });
3
+ next();
4
+ }
5
+ export function requireRole(...roles) {
6
+ return (req, res, next) => {
7
+ if (!req.session.user) return res.status(401).json({ success: false, message: 'Unauthorized. Please login.' });
8
+ if (!roles.includes(req.session.user.userrole)) return res.status(403).json({ success: false, message: 'Forbidden.' });
9
+ next();
10
+ };
11
+ }
@@ -0,0 +1,7 @@
1
+ export function notFound(req, res) { res.status(404).json({ success: false, message: `Route not found: ${req.originalUrl}` }); }
2
+ export function errorHandler(err, req, res, next) {
3
+ console.error(err);
4
+ if (err?.issues) return res.status(400).json({ success: false, message: 'Validation error', errors: err.issues });
5
+ if (err?.code === 'ER_DUP_ENTRY') return res.status(409).json({ success: false, message: 'Duplicate record. Seat may already be booked or plate number exists.' });
6
+ res.status(500).json({ success: false, message: 'Internal server error' });
7
+ }
@@ -0,0 +1,20 @@
1
+ import { DataTypes } from "sequelize";
2
+ import sequelize from "../config/db.js";
3
+
4
+ export const Delivery = sequelize.define(
5
+ "Delivery",
6
+ {
7
+ deliveryCode: { type: DataTypes.STRING(50), primaryKey: true },
8
+ deliveryDate: { type: DataTypes.DATE, allowNull: false },
9
+ quantityDelivered: { type: DataTypes.INTEGER, allowNull: false },
10
+ deliveryStatus: {
11
+ type: DataTypes.ENUM("pending", "completed", "failed"),
12
+ allowNull: false,
13
+ defaultValue: "pending",
14
+ },
15
+ created_at: { type: DataTypes.DATE, defaultValue: DataTypes.NOW },
16
+ },
17
+ { tableName: "deliveries", timestamps: false }
18
+ );
19
+
20
+ export default Delivery;
@@ -0,0 +1,6 @@
1
+ import { Supplier } from "./supplier.js";
2
+ import { Shipment } from "./shipment.js";
3
+ import { Delivery } from "./delivery.js";
4
+ import { User } from "./user.js";
5
+
6
+ export { Supplier, Shipment, Delivery, User };
@@ -0,0 +1,20 @@
1
+ import { DataTypes } from "sequelize";
2
+ import sequelize from "../config/db.js";
3
+
4
+ export const Shipment = sequelize.define(
5
+ "Shipment",
6
+ {
7
+ shipmentNumber: { type: DataTypes.STRING(50), primaryKey: true },
8
+ shipmentDate: { type: DataTypes.DATE, allowNull: false },
9
+ shipmentStatus: {
10
+ type: DataTypes.ENUM("pending", "in_transit", "delivered", "cancelled"),
11
+ allowNull: false,
12
+ defaultValue: "pending",
13
+ },
14
+ destination: { type: DataTypes.STRING(150), allowNull: false },
15
+ created_at: { type: DataTypes.DATE, defaultValue: DataTypes.NOW },
16
+ },
17
+ { tableName: "shipments", timestamps: false }
18
+ );
19
+
20
+ export default Shipment;
@@ -0,0 +1,17 @@
1
+ import { DataTypes } from "sequelize";
2
+ import sequelize from "../config/db.js";
3
+
4
+ export const Supplier = sequelize.define(
5
+ "Supplier",
6
+ {
7
+ supplierCode: { type: DataTypes.STRING(50), primaryKey: true },
8
+ supplierName: { type: DataTypes.STRING(150), allowNull: false },
9
+ telephone: { type: DataTypes.STRING(50), allowNull: true },
10
+ address: { type: DataTypes.STRING(255), allowNull: true },
11
+ email: { type: DataTypes.STRING(150), allowNull: true, validate: { isEmail: true } },
12
+ created_at: { type: DataTypes.DATE, defaultValue: DataTypes.NOW },
13
+ },
14
+ { tableName: "suppliers", timestamps: false }
15
+ );
16
+
17
+ export default Supplier;
@@ -0,0 +1,15 @@
1
+ import { DataTypes } from "sequelize";
2
+ import sequelize from "../config/db.js";
3
+
4
+ export const User = sequelize.define(
5
+ "User",
6
+ {
7
+ userid: { type: DataTypes.INTEGER, autoIncrement: true, primaryKey: true },
8
+ username: { type: DataTypes.STRING(100), allowNull: false, unique: true },
9
+ password: { type: DataTypes.STRING(255), allowNull: false },
10
+ created_at: { type: DataTypes.DATE, defaultValue: DataTypes.NOW },
11
+ },
12
+ { tableName: "users", timestamps: false }
13
+ );
14
+
15
+ export default User;
@@ -0,0 +1,11 @@
1
+ import { Router } from "express";
2
+ import { register, login, me, logout } from "../controllers/auth.js";
3
+
4
+ const router = Router();
5
+
6
+ router.post("/register", register);
7
+ router.post("/login", login);
8
+ router.get("/me", me);
9
+ router.post("/logout", logout);
10
+
11
+ export default router;
@@ -0,0 +1,18 @@
1
+ import { Router } from "express";
2
+ import {
3
+ createBooking,
4
+ deleteBooking,
5
+ getAllBookings,
6
+ getBookingById,
7
+ updateBooking,
8
+ } from "../controllers/bookingcontroller.js";
9
+
10
+ const router = Router();
11
+
12
+ router.get("/", getAllBookings);
13
+ router.get("/:id", getBookingById);
14
+ router.post("/", createBooking);
15
+ router.put("/:id", updateBooking);
16
+ router.delete("/:id", deleteBooking);
17
+
18
+ export default router;
@@ -0,0 +1,18 @@
1
+ import { Router } from "express";
2
+ import {
3
+ createBus,
4
+ deleteBus,
5
+ getAllBuses,
6
+ getBusById,
7
+ updateBus,
8
+ } from "../controllers/buscontroller.js";
9
+
10
+ const router = Router();
11
+
12
+ router.get("/", getAllBuses);
13
+ router.get("/:id", getBusById);
14
+ router.post("/", createBus);
15
+ router.put("/:id", updateBus);
16
+ router.delete("/:id", deleteBus);
17
+
18
+ export default router;