From c2e13d56f2c284bf161c119877de54d7269afdf7 Mon Sep 17 00:00:00 2001
From: aruhani <163067503+aruhani@users.noreply.github.com>
Date: Mon, 24 Mar 2025 22:43:06 -0600
Subject: [PATCH 01/13] Removing Password Temporarily
---
backend/utils/database.js | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/backend/utils/database.js b/backend/utils/database.js
index 020e67c..adecb39 100644
--- a/backend/utils/database.js
+++ b/backend/utils/database.js
@@ -5,7 +5,7 @@ const pool = mysql.createPool({
host: "localhost",
user: "root",
database: "marketplace",
- password: "12345678",
+ //password: "12345678",
});
//Export a promise for promise-based query
From f7e4b49ac8c5aea86d74abd9e5566046f6b98f57 Mon Sep 17 00:00:00 2001
From: aruhani <163067503+aruhani@users.noreply.github.com>
Date: Sun, 20 Apr 2025 10:42:52 -0600
Subject: [PATCH 02/13] Backend for Transactions
Added in 3 files, for the backend
---
backend/controllers/transaction.js | 153 +++++++++++++++++++++++++++++
backend/index.js | 2 +
backend/routes/transaction.js | 30 ++++++
3 files changed, 185 insertions(+)
create mode 100644 backend/controllers/transaction.js
create mode 100644 backend/routes/transaction.js
diff --git a/backend/controllers/transaction.js b/backend/controllers/transaction.js
new file mode 100644
index 0000000..6072d2f
--- /dev/null
+++ b/backend/controllers/transaction.js
@@ -0,0 +1,153 @@
+// controllers/transaction.js
+
+const db = require("../utils/database");
+
+// Create a new transaction
+exports.createTransaction = async (req, res) => {
+ const { userID, productID, date, paymentStatus } = req.body;
+
+ try {
+ const [result] = await db.execute(
+ `INSERT INTO Transaction (UserID, ProductID, Date, PaymentStatus)
+ VALUES (?, ?, ?, ?)`,
+ [userID, productID, date, paymentStatus]
+ );
+
+ res.json({
+ success: true,
+ message: "Transaction created successfully",
+ transactionID: result.insertId,
+ });
+ } catch (error) {
+ console.error("Error creating transaction:", error);
+ res.status(500).json({ error: "Could not create transaction" });
+ }
+};
+
+// Get all transactions for a given product
+exports.getTransactionsByProduct = async (req, res) => {
+ const { productID } = req.params;
+
+ try {
+ const [transactions] = await db.execute(
+ `SELECT
+ TransactionID,
+ UserID,
+ ProductID,
+ Date,
+ PaymentStatus
+ FROM Transaction
+ WHERE ProductID = ?`,
+ [productID]
+ );
+
+ res.json({
+ success: true,
+ transactions,
+ });
+ } catch (error) {
+ console.error("Error fetching transactions by product:", error);
+ res.status(500).json({ error: "Could not retrieve transactions" });
+ }
+};
+
+// Get all transactions for a given user
+exports.getTransactionsByUser = async (req, res) => {
+ const { userID } = req.body;
+
+ try {
+ const [transactions] = await db.execute(
+ `SELECT
+ TransactionID,
+ UserID,
+ ProductID,
+ Date,
+ PaymentStatus
+ FROM Transaction
+ WHERE UserID = ?`,
+ [userID]
+ );
+
+ res.json({
+ success: true,
+ transactions,
+ });
+ } catch (error) {
+ console.error("Error fetching transactions by user:", error);
+ res.status(500).json({ error: "Could not retrieve transactions" });
+ }
+};
+
+// Get all transactions in the system
+exports.getAllTransactions = async (req, res) => {
+ try {
+ const [transactions] = await db.execute(
+ `SELECT
+ TransactionID,
+ UserID,
+ ProductID,
+ Date,
+ PaymentStatus
+ FROM Transaction`
+ );
+
+ res.json({
+ success: true,
+ transactions,
+ });
+ } catch (error) {
+ console.error("Error fetching all transactions:", error);
+ res.status(500).json({ error: "Could not retrieve transactions" });
+ }
+};
+
+// Update the payment status of a transaction
+exports.updatePaymentStatus = async (req, res) => {
+ const { transactionID, paymentStatus } = req.body;
+
+ try {
+ const [result] = await db.execute(
+ `UPDATE Transaction
+ SET PaymentStatus = ?
+ WHERE TransactionID = ?`,
+ [paymentStatus, transactionID]
+ );
+
+ if (result.affectedRows === 0) {
+ return res.status(404).json({ success: false, message: "Transaction not found" });
+ }
+
+ res.json({
+ success: true,
+ message: "Payment status updated successfully",
+ });
+ } catch (error) {
+ console.error("Error updating payment status:", error);
+ res.status(500).json({ error: "Could not update payment status" });
+ }
+};
+
+// Delete a transaction
+exports.deleteTransaction = async (req, res) => {
+ const { transactionID } = req.body;
+
+ try {
+ const [result] = await db.execute(
+ `DELETE FROM Transaction
+ WHERE TransactionID = ?`,
+ [transactionID]
+ );
+
+ if (result.affectedRows === 0) {
+ return res.status(404).json({ success: false, message: "Transaction not found" });
+ }
+
+ res.json({
+ success: true,
+ message: "Transaction deleted successfully",
+ });
+ } catch (error) {
+ console.error("Error deleting transaction:", error);
+ res.status(500).json({ error: "Could not delete transaction" });
+ }
+};
diff --git a/backend/index.js b/backend/index.js
index 7afa3fe..e3b875f 100644
--- a/backend/index.js
+++ b/backend/index.js
@@ -9,6 +9,7 @@ const searchRouter = require("./routes/search");
const recommendedRouter = require("./routes/recommendation");
const history = require("./routes/history");
const review = require("./routes/review");
+const transactionRouter = require("./routes/transaction");
const { generateEmailTransporter } = require("./utils/mail");
const {
@@ -42,6 +43,7 @@ app.use("/api/search", searchRouter);
app.use("/api/engine", recommendedRouter);
app.use("/api/history", history);
app.use("/api/review", review);
+app.use("/api/transaction", transactionRouter);
// Set up a scheduler to run cleanup every hour
diff --git a/backend/routes/transaction.js b/backend/routes/transaction.js
new file mode 100644
index 0000000..b9ccb75
--- /dev/null
+++ b/backend/routes/transaction.js
@@ -0,0 +1,30 @@
+// routes/transaction.js
+const express = require("express");
+const txCtrl = require("../controllers/transaction"); // <— grab the module
+const router = express.Router();
+
+// logging middleware
+router.use((req, res, next) => {
+ console.log(`Incoming ${req.method} ${req.originalUrl}`);
+ next();
+});
+
+// Create a new transaction
+router.post("/createTransaction", txCtrl.createTransaction);
+
+// Get all transactions for a specific product
+router.get("/getTransactionsByProduct/:productID", txCtrl.getTransactionsByProduct);
+
+// Get all transactions for a specific user
+router.post("/getTransactionsByUser", txCtrl.getTransactionsByUser);
+
+// Get all transactions in the system
+router.get("/getAllTransactions", txCtrl.getAllTransactions);
+
+// Update payment status on a transaction
+router.patch("/updatePaymentStatus", txCtrl.updatePaymentStatus);
+
+// Delete a transaction
+router.delete("/deleteTransaction", txCtrl.deleteTransaction);
+
+module.exports = router;
From 25f2c3d8af8dda75244651a705ce40d82c69d6b8 Mon Sep 17 00:00:00 2001
From: noahnghg <157671712+noahnghg@users.noreply.github.com>
Date: Sun, 20 Apr 2025 21:18:43 -0600
Subject: [PATCH 03/13] adding stuff to the onClick
---
backend/controllers/transaction.js | 3 ++-
backend/utils/database.js | 1 +
backend/utils/helper.js | 2 +-
frontend/src/pages/ProductDetail.jsx | 34 +++++++++++++++++++++++++++-
mysql-code/Schema.sql | 3 ++-
5 files changed, 39 insertions(+), 4 deletions(-)
diff --git a/backend/controllers/transaction.js b/backend/controllers/transaction.js
index 6072d2f..22c17b3 100644
--- a/backend/controllers/transaction.js
+++ b/backend/controllers/transaction.js
@@ -7,10 +7,11 @@ exports.createTransaction = async (req, res) => {
const { userID, productID, date, paymentStatus } = req.body;
try {
+ const formattedDate = new Date(date).toISOString().slice(0, 19).replace("T", " ");
const [result] = await db.execute(
`INSERT INTO Transaction (UserID, ProductID, Date, PaymentStatus)
VALUES (?, ?, ?, ?)`,
- [userID, productID, date, paymentStatus]
+ [userID, productID, formattedDate, paymentStatus]
);
res.json({
diff --git a/backend/utils/database.js b/backend/utils/database.js
index 6e75c3a..4459545 100644
--- a/backend/utils/database.js
+++ b/backend/utils/database.js
@@ -4,6 +4,7 @@ const pool = mysql.createPool({
host: "localhost",
user: "root",
database: "Marketplace",
+ password: "12345678"
});
module.exports = pool.promise();
diff --git a/backend/utils/helper.js b/backend/utils/helper.js
index 406a897..1d39b48 100644
--- a/backend/utils/helper.js
+++ b/backend/utils/helper.js
@@ -18,7 +18,7 @@ async function sendVerificationEmail(email, verificationCode) {
// Clean up expired verification codes (run this periodically)
function cleanupExpiredCodes() {
- db_con.query(
+ db.query(
"DELETE FROM AuthVerification WHERE Date < DATE_SUB(NOW(), INTERVAL 15 MINUTE) AND Authenticated = 0",
(err, result) => {
if (err) {
diff --git a/frontend/src/pages/ProductDetail.jsx b/frontend/src/pages/ProductDetail.jsx
index a5f0d73..4bae56e 100644
--- a/frontend/src/pages/ProductDetail.jsx
+++ b/frontend/src/pages/ProductDetail.jsx
@@ -417,7 +417,39 @@ const ProductDetail = () => {