From edf5647ea158b06ee5ce0ebd6ccd8ea367d16c94 Mon Sep 17 00:00:00 2001 From: spandanjadhav Date: Wed, 6 Dec 2023 13:41:04 -0600 Subject: [PATCH 1/2] styling changes to login page --- frontend/src/app/page.tsx | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/frontend/src/app/page.tsx b/frontend/src/app/page.tsx index bcc0a85..426009f 100644 --- a/frontend/src/app/page.tsx +++ b/frontend/src/app/page.tsx @@ -76,8 +76,8 @@ const AuthPage: React.FC = () => { return (
-
- credit wise photo +
+ credit wise photo

Sign In

@@ -148,13 +148,14 @@ const AuthPage: React.FC = () => { Forgot Username or Password? -
- Set Up Online Access -
+ + Set Up Online Access +
); }; -export default AuthPage; \ No newline at end of file +export default AuthPage; + From feb01564b76455771fb1d272927c4061e9172f97 Mon Sep 17 00:00:00 2001 From: spandanjadhav Date: Wed, 6 Dec 2023 14:07:43 -0600 Subject: [PATCH 2/2] more styling changes for login --- frontend/next.config.js | 8 +- frontend/postcss.config.js | 12 +- frontend/src/app/budgets/budgetstable.tsx | 414 +++++++++--------- frontend/src/app/components/Card.tsx | 44 +- frontend/src/app/components/Header.tsx | 104 ++--- .../src/app/components/SubscriptionModal.tsx | 254 +++++------ frontend/src/app/components/TableDropdown.tsx | 100 ++--- frontend/src/app/components/Transactions.tsx | 216 ++++----- frontend/src/app/deposits/page.tsx | 58 +-- frontend/src/app/layout.tsx | 54 +-- frontend/src/app/page.tsx | 326 +++++++------- frontend/src/app/payments/layout.tsx | 78 ++-- frontend/src/app/payments/page.tsx | 36 +- .../src/app/payments/subscriptions/page.tsx | 202 ++++----- frontend/src/app/statements/page.tsx | 20 +- frontend/src/app/types/Transaction.ts | 22 +- frontend/tailwind.config.ts | 40 +- 17 files changed, 997 insertions(+), 991 deletions(-) diff --git a/frontend/next.config.js b/frontend/next.config.js index 767719f..ab026d0 100644 --- a/frontend/next.config.js +++ b/frontend/next.config.js @@ -1,4 +1,4 @@ -/** @type {import('next').NextConfig} */ -const nextConfig = {} - -module.exports = nextConfig +/** @type {import('next').NextConfig} */ +const nextConfig = {} + +module.exports = nextConfig diff --git a/frontend/postcss.config.js b/frontend/postcss.config.js index 33ad091..a03e681 100644 --- a/frontend/postcss.config.js +++ b/frontend/postcss.config.js @@ -1,6 +1,6 @@ -module.exports = { - plugins: { - tailwindcss: {}, - autoprefixer: {}, - }, -} +module.exports = { + plugins: { + tailwindcss: {}, + autoprefixer: {}, + }, +} diff --git a/frontend/src/app/budgets/budgetstable.tsx b/frontend/src/app/budgets/budgetstable.tsx index c97029b..c08d3e8 100644 --- a/frontend/src/app/budgets/budgetstable.tsx +++ b/frontend/src/app/budgets/budgetstable.tsx @@ -1,207 +1,207 @@ -'use client' - -import React from 'react'; -import { useState, useEffect } from "react"; -import { FaEdit, FaTrash, FaCheck, FaTimes } from 'react-icons/fa'; - -interface IBudgetItem { - id: number; - category: string, - assigned: string, - spent: string, - available: string, -} - -const BudgetTable: React.FC = () => { - const [budgets, setBudgets] = useState([]); - const [editingId, setEditingId] = useState(null); - -const mapBudgetToTableCell = (budget: any) => { - return { - id: budget.id, - category: budget.category_name || '', - assigned: `$${(budget.budget_amount || 0).toFixed(2)}`, - spent: `$${(budget.amount_spent || 0).toFixed(2)}`, - available: `$${((budget.budget_amount - budget.amount_spent) || 0).toFixed(2)}`, - }; -}; - - - useEffect(() => { - fetch(`http://localhost/budget`).then((res) => res.json()).then((data) => data.map(mapBudgetToTableCell)).then((budget) => { - setBudgets(budget); - }).catch((error) => console.error('Error fetching data:', error));; - }, []); - - useEffect(() => { - console.log(budgets); - }, [budgets]); - - const handleEditChange = (id: number, field: string, value: string) => { - setBudgets((prevBudgets) => - prevBudgets.map((budget) => - budget.id === id ? { ...budget, [field]: value } : budget - ) - ); - }; - - - const editItem = (budgetId: number) => { - setEditingId(budgetId) - } - - const saveItem = (id: number) => { - const editedBudget = budgets.find((budget) => budget.id === id); - - if (!editedBudget) { - console.error('Budget not found'); - return; - } - - const { category, assigned, spent, available } = editedBudget; - - fetch(`http://localhost/budget/${id}`, { - method: 'PUT', - headers: { - 'Content-Type': 'application/json', - }, - body: JSON.stringify({ - start_date: "2023-11-12", - category_name: category, - budget_amount: parseFloat(assigned.replace('$', '')), - amount_spent: parseFloat(spent.replace('$', '')), - }), - }) - .then((res) => res.json()) - .then((updatedBudget) => { - console.log('API Response:', updatedBudget); - setEditingId(null); - - setBudgets((prevBudgets) => - prevBudgets.map((budget) => - budget.id === id ? mapBudgetToTableCell(updatedBudget) : budget - ) - ); - }) - .catch((error) => console.error('Error updating item:', error)); - }; - - const deleteItem = (id: number) => { - // console.log(`Deleted item with ID: ${id}`); - - fetch(`http://localhost/budget/${id}`, { - method: 'DELETE' - }) - .then(() => { - setBudgets((prevBudgets) => prevBudgets.filter((budget) => budget.id !== id)); - }) - .catch((error) => console.error('Error deleting item:', error)); - } - - const addItem = () => { - const newBudgetItem = { - start_date: "2023-11-12", - category_name: "New Budget", - budget_amount: 0, - amount_spent: 0, - }; - - fetch(`http://localhost/budget`, { - method: 'POST', - headers: { - 'Content-Type': 'application/json', - }, - body: JSON.stringify(newBudgetItem), - }) - .then((res) => res.json()) - .then((addedBudget) => { - - setBudgets((prevBudgets) => [...prevBudgets, mapBudgetToTableCell(addedBudget)]); - setEditingId(addedBudget.id); - }) - .catch((error) => console.error('Error adding item:', error)); - }; - - - return ( -
- - - - - - - - {/* */} - - - - - - {budgets.map((budget) => ( - - - - - - - - ))} - - -
CategoryAssignedSpentAvailableEnableActions
- {editingId === budget.id ? ( - handleEditChange(budget.id, 'category', e.target.value)} - className="rounded p-1 border border-blue-500" - /> - ) : ( - budget.category - )} - - {editingId === budget.id ? ( - handleEditChange(budget.id, 'assigned', e.target.value)} - className="rounded p-1 border border-blue-500" - /> - ) : ( - `${budget.assigned}` - )} - - {budget.spent} - - {budget.available} - - {editingId === budget.id ? ( - <> - saveItem(budget.id)} style={{ cursor: 'pointer' }}> - - - setEditingId(null)} style={{ cursor: 'pointer' }}> - - - - ) : ( -
- editItem(budget.id)} /> - deleteItem(budget.id)} /> -
- )} -
-
- -
-
- ); -} - - -export default BudgetTable; - +'use client' + +import React from 'react'; +import { useState, useEffect } from "react"; +import { FaEdit, FaTrash, FaCheck, FaTimes } from 'react-icons/fa'; + +interface IBudgetItem { + id: number; + category: string, + assigned: string, + spent: string, + available: string, +} + +const BudgetTable: React.FC = () => { + const [budgets, setBudgets] = useState([]); + const [editingId, setEditingId] = useState(null); + +const mapBudgetToTableCell = (budget: any) => { + return { + id: budget.id, + category: budget.category_name || '', + assigned: `$${(budget.budget_amount || 0).toFixed(2)}`, + spent: `$${(budget.amount_spent || 0).toFixed(2)}`, + available: `$${((budget.budget_amount - budget.amount_spent) || 0).toFixed(2)}`, + }; +}; + + + useEffect(() => { + fetch(`http://localhost/budget`).then((res) => res.json()).then((data) => data.map(mapBudgetToTableCell)).then((budget) => { + setBudgets(budget); + }).catch((error) => console.error('Error fetching data:', error));; + }, []); + + useEffect(() => { + console.log(budgets); + }, [budgets]); + + const handleEditChange = (id: number, field: string, value: string) => { + setBudgets((prevBudgets) => + prevBudgets.map((budget) => + budget.id === id ? { ...budget, [field]: value } : budget + ) + ); + }; + + + const editItem = (budgetId: number) => { + setEditingId(budgetId) + } + + const saveItem = (id: number) => { + const editedBudget = budgets.find((budget) => budget.id === id); + + if (!editedBudget) { + console.error('Budget not found'); + return; + } + + const { category, assigned, spent, available } = editedBudget; + + fetch(`http://localhost/budget/${id}`, { + method: 'PUT', + headers: { + 'Content-Type': 'application/json', + }, + body: JSON.stringify({ + start_date: "2023-11-12", + category_name: category, + budget_amount: parseFloat(assigned.replace('$', '')), + amount_spent: parseFloat(spent.replace('$', '')), + }), + }) + .then((res) => res.json()) + .then((updatedBudget) => { + console.log('API Response:', updatedBudget); + setEditingId(null); + + setBudgets((prevBudgets) => + prevBudgets.map((budget) => + budget.id === id ? mapBudgetToTableCell(updatedBudget) : budget + ) + ); + }) + .catch((error) => console.error('Error updating item:', error)); + }; + + const deleteItem = (id: number) => { + // console.log(`Deleted item with ID: ${id}`); + + fetch(`http://localhost/budget/${id}`, { + method: 'DELETE' + }) + .then(() => { + setBudgets((prevBudgets) => prevBudgets.filter((budget) => budget.id !== id)); + }) + .catch((error) => console.error('Error deleting item:', error)); + } + + const addItem = () => { + const newBudgetItem = { + start_date: "2023-11-12", + category_name: "New Budget", + budget_amount: 0, + amount_spent: 0, + }; + + fetch(`http://localhost/budget`, { + method: 'POST', + headers: { + 'Content-Type': 'application/json', + }, + body: JSON.stringify(newBudgetItem), + }) + .then((res) => res.json()) + .then((addedBudget) => { + + setBudgets((prevBudgets) => [...prevBudgets, mapBudgetToTableCell(addedBudget)]); + setEditingId(addedBudget.id); + }) + .catch((error) => console.error('Error adding item:', error)); + }; + + + return ( +
+ + + + + + + + {/* */} + + + + + + {budgets.map((budget) => ( + + + + + + + + ))} + + +
CategoryAssignedSpentAvailableEnableActions
+ {editingId === budget.id ? ( + handleEditChange(budget.id, 'category', e.target.value)} + className="rounded p-1 border border-blue-500" + /> + ) : ( + budget.category + )} + + {editingId === budget.id ? ( + handleEditChange(budget.id, 'assigned', e.target.value)} + className="rounded p-1 border border-blue-500" + /> + ) : ( + `${budget.assigned}` + )} + + {budget.spent} + + {budget.available} + + {editingId === budget.id ? ( + <> + saveItem(budget.id)} style={{ cursor: 'pointer' }}> + + + setEditingId(null)} style={{ cursor: 'pointer' }}> + + + + ) : ( +
+ editItem(budget.id)} /> + deleteItem(budget.id)} /> +
+ )} +
+
+ +
+
+ ); +} + + +export default BudgetTable; + diff --git a/frontend/src/app/components/Card.tsx b/frontend/src/app/components/Card.tsx index acec4e8..5a86535 100644 --- a/frontend/src/app/components/Card.tsx +++ b/frontend/src/app/components/Card.tsx @@ -1,23 +1,23 @@ -interface ICardProps { - title: string, - line1: string, - line2: string, - buttonText: string -} - -const Card = (props: ICardProps) => { - return <> -
-
-
{props.title}
-

{props.line1}

-
-

{props.line2}

-
- -
-
- -} - +interface ICardProps { + title: string, + line1: string, + line2: string, + buttonText: string +} + +const Card = (props: ICardProps) => { + return <> +
+
+
{props.title}
+

{props.line1}

+
+

{props.line2}

+
+ +
+
+ +} + export default Card; \ No newline at end of file diff --git a/frontend/src/app/components/Header.tsx b/frontend/src/app/components/Header.tsx index 36a6347..7beb5ec 100644 --- a/frontend/src/app/components/Header.tsx +++ b/frontend/src/app/components/Header.tsx @@ -1,52 +1,54 @@ -'use client' - -import { useState, useEffect } from "react"; -import styles from "./Header.module.css"; -import { usePathname } from "next/navigation"; -import Link from "next/link"; -import logo from "../icons/Capital-One-Logo.png" -import Image from "next/image"; - -const Header = () => { - - const pathName = usePathname(); - // List of pages where the header should be hidden - const pagesWithoutHeader = ['/', '/enrollment']; - - // Check if the current pathname is in the list of pages without header - const shouldHideHeader = pagesWithoutHeader.includes(pathName); - - // If the header should be hidden, return null - if (shouldHideHeader) { - return null; - } - - const headerItems = [ - { name: "Home", link: "/home" }, - { name: "Transfers & Payments", link: "/payments" }, - { name: "Budget & Planning", link: "/budgets" }, - ]; - - - return
-
- - Capital One Logo - -
- -
    - {headerItems.map((item, index) => ( -
  • - -
    - {item.name} -
    - -
  • - ))} -
-
-} - +'use client' + +import { useState, useEffect } from "react"; +import styles from "./Header.module.css"; +import { usePathname } from "next/navigation"; +import Link from "next/link"; +import logo from "../icons/Capital-One-Logo.png" +import Image from "next/image"; + +const Header = () => { + + const pathName = usePathname(); + // List of pages where the header should be hidden + const pagesWithoutHeader = ['/', '/enrollment']; + + // Check if the current pathname is in the list of pages without header + const shouldHideHeader = pagesWithoutHeader.includes(pathName); + + // If the header should be hidden, return null + if (shouldHideHeader) { + return null; + } + + const headerItems = [ + { name: "Home", link: "/home" }, + { name: "Transfers & Payments", link: "/payments" }, + { name: "Budget & Planning", link: "/budgets" }, + ]; + + + return ( +
+
+ + Capital One Logo + +
+ +
    + {headerItems.map((item, index) => ( +
  • + +
    + {item.name} +
    + +
  • + ))} +
+
+ ); +} + export default Header; \ No newline at end of file diff --git a/frontend/src/app/components/SubscriptionModal.tsx b/frontend/src/app/components/SubscriptionModal.tsx index 91f43d2..a812f4b 100644 --- a/frontend/src/app/components/SubscriptionModal.tsx +++ b/frontend/src/app/components/SubscriptionModal.tsx @@ -1,128 +1,128 @@ -import { useEffect, useState } from "react"; -import { ITransaction } from "../types/Transaction" - -interface ISubscriptionModal { - transaction: ITransaction | null, - showModal: boolean, - setModal: any, - setTransaction: any -} - -const SubscriptionModal = (props: ISubscriptionModal) => { - const [description, setDescription] = useState(""); - - function closeModal() { - props.setModal(false); - } - - function addSubscription() { - fetch(`http://3.128.31.44/subscription`, { - method: "POST", - headers: { - "Content-Type": "application/json", - }, - body: JSON.stringify({ - "icon_path": "", - "routine": "Monthly", - "description": "", - "subscription_name": `${props.transaction?.name}`, - "price": `${props.transaction?.amount}` - }) - }).then((res) => res.json()).then((data) => { - fetch(`http://3.128.31.44/transaction/${props.transaction?.id}`, { - method: "PUT", - headers: { - "Content-Type": "application/json", - }, - body: JSON.stringify({ - "isSubscription": true, - "budget_id": props.transaction?.budgetId, - "subscription_id": data.id - }) - }).then((res) => res.json()).then(() => { - props.setTransaction(null); - }); - }); - - closeModal(); - } - - function removeSubscription() { - fetch(`http://3.128.31.44/subscription`).then((res) => res.json()).then((subs) => { - subs.map((sub: any) => { - sub.transactions.map((transaction: ITransaction) => { - if (transaction.id === props.transaction?.id) { - fetch(`http://3.128.31.44/subscription/${sub.id}`, { - method: "DELETE" - }).then((res) => res.json()).then(() => { - props.setTransaction(null); - }) - } - }) - }); - }) - - closeModal(); - } - - if (!props.transaction?.subscription) { - return ( - - ); - } - - else { - return ( - - ); - } -} - +import { useEffect, useState } from "react"; +import { ITransaction } from "../types/Transaction" + +interface ISubscriptionModal { + transaction: ITransaction | null, + showModal: boolean, + setModal: any, + setTransaction: any +} + +const SubscriptionModal = (props: ISubscriptionModal) => { + const [description, setDescription] = useState(""); + + function closeModal() { + props.setModal(false); + } + + function addSubscription() { + fetch(`http://3.128.31.44/subscription`, { + method: "POST", + headers: { + "Content-Type": "application/json", + }, + body: JSON.stringify({ + "icon_path": "", + "routine": "Monthly", + "description": "", + "subscription_name": `${props.transaction?.name}`, + "price": `${props.transaction?.amount}` + }) + }).then((res) => res.json()).then((data) => { + fetch(`http://3.128.31.44/transaction/${props.transaction?.id}`, { + method: "PUT", + headers: { + "Content-Type": "application/json", + }, + body: JSON.stringify({ + "isSubscription": true, + "budget_id": props.transaction?.budgetId, + "subscription_id": data.id + }) + }).then((res) => res.json()).then(() => { + props.setTransaction(null); + }); + }); + + closeModal(); + } + + function removeSubscription() { + fetch(`http://3.128.31.44/subscription`).then((res) => res.json()).then((subs) => { + subs.map((sub: any) => { + sub.transactions.map((transaction: ITransaction) => { + if (transaction.id === props.transaction?.id) { + fetch(`http://3.128.31.44/subscription/${sub.id}`, { + method: "DELETE" + }).then((res) => res.json()).then(() => { + props.setTransaction(null); + }) + } + }) + }); + }) + + closeModal(); + } + + if (!props.transaction?.subscription) { + return ( + + ); + } + + else { + return ( + + ); + } +} + export default SubscriptionModal; \ No newline at end of file diff --git a/frontend/src/app/components/TableDropdown.tsx b/frontend/src/app/components/TableDropdown.tsx index e98c55c..4051fbc 100644 --- a/frontend/src/app/components/TableDropdown.tsx +++ b/frontend/src/app/components/TableDropdown.tsx @@ -1,51 +1,51 @@ -import { useEffect, useState } from "react"; -import { ITransaction } from "../types/Transaction"; - -interface ITableDropdownProps { - transaction: ITransaction, - budgets: any[], - changeBudget: any -} - -const TableDropdown = (props: ITableDropdownProps) => { - const [hidden, setHidden] = useState(true); - - function toggle() { - setHidden(!hidden); - } - - function changeBudget(budget: string) { - props.changeBudget(budget, props.transaction); - toggle(); - } - - return <> -
-
- -
- - { - !hidden ? <> -
-
- { - props.budgets.map((budget) => { - return changeBudget(budget)} className="text-gray-700 block px-4 py-2 text-sm cursor-pointer hover:bg-slate-100" tabIndex={-1}>{ budget.category_name }; - }) - } -
-
- : <> - } - -
- -} - +import { useEffect, useState } from "react"; +import { ITransaction } from "../types/Transaction"; + +interface ITableDropdownProps { + transaction: ITransaction, + budgets: any[], + changeBudget: any +} + +const TableDropdown = (props: ITableDropdownProps) => { + const [hidden, setHidden] = useState(true); + + function toggle() { + setHidden(!hidden); + } + + function changeBudget(budget: string) { + props.changeBudget(budget, props.transaction); + toggle(); + } + + return <> +
+
+ +
+ + { + !hidden ? <> +
+
+ { + props.budgets.map((budget) => { + return changeBudget(budget)} className="text-gray-700 block px-4 py-2 text-sm cursor-pointer hover:bg-slate-100" tabIndex={-1}>{ budget.category_name }; + }) + } +
+
+ : <> + } + +
+ +} + export default TableDropdown; \ No newline at end of file diff --git a/frontend/src/app/components/Transactions.tsx b/frontend/src/app/components/Transactions.tsx index 0a52dc5..b0f1e7c 100644 --- a/frontend/src/app/components/Transactions.tsx +++ b/frontend/src/app/components/Transactions.tsx @@ -1,109 +1,109 @@ -import { useEffect, useState } from "react"; -import TableDropdown from "./TableDropdown"; -import { ITransaction } from "../types/Transaction"; -import SubscriptionModal from "./SubscriptionModal"; - -const Transactions = () => { - - const [budgets, setBudgets] = useState([]); - - const [transactions, setTransactions] = useState([]); - - const [showModal, setModal] = useState(false); - - const [currentTransaction, setCurrentTransaction] = useState(null); - - const [refersh, setRefresh] = useState(0); - - function mapTransactionToTableCell(transaction: any) { - return { - date: transaction.date, - name: transaction.alias, - amount: `${transaction.amount}`, - id: transaction.id, - subscription: transaction.isSubscription, - budget: transaction.budget.category_name - } - } - - function openModal(transaction: ITransaction) { - setCurrentTransaction(transaction); - setModal(true); - } - - function changeBudget(budget: any, transaction: ITransaction) { - fetch(`http://3.128.31.44/transaction/${transaction.id}`, { - method: "PUT", - headers: { - "Content-Type": "application/json", - }, - body: JSON.stringify({ - "isSubscription": transaction.subscription, - "budget_id": budget.category_name === "N/A" ? -1 : budgets[budgets.indexOf(budget)].id, - "subscription_id": transaction.subscriptionId - }) - }).then((res) => res.json()).then(() => { - setRefresh((refresh) => refresh + 1); - }) - } - - useEffect(() => { - fetch(`http://3.128.31.44/transaction`).then((res) => res.json()).then((data) => data.map(mapTransactionToTableCell)).then((transactions) => { - setTransactions(transactions); - }); - }, [currentTransaction, refersh]); - - useEffect(() => { - fetch(`http://3.128.31.44/budget`).then((res) => res.json()).then((budgets) => { - const newBudgets: any[] = []; - - budgets.map((budget: any) => { - newBudgets.push(budget); - }); - - setBudgets([{ category_name: "N/A" }, ...newBudgets]); - }); - }, []); - - return <> - - - - - - - - - - - - - - { - transactions.map((transaction, key) => { - return - { Object.entries(transaction).map(([key, value]) => { - if (key === "budget") { - return - } - - if (key === "subscription") { - return - } - - return - }) } - - }) - } - -
DATENAMEAMOUNTIDSUBSCRIPTIONBUDGET
- - - openModal(transaction)} type="checkbox" checked={value} onChange={() => {}} /> -

Subscribe

-
{ value }
- ; -} - +import { useEffect, useState } from "react"; +import TableDropdown from "./TableDropdown"; +import { ITransaction } from "../types/Transaction"; +import SubscriptionModal from "./SubscriptionModal"; + +const Transactions = () => { + + const [budgets, setBudgets] = useState([]); + + const [transactions, setTransactions] = useState([]); + + const [showModal, setModal] = useState(false); + + const [currentTransaction, setCurrentTransaction] = useState(null); + + const [refersh, setRefresh] = useState(0); + + function mapTransactionToTableCell(transaction: any) { + return { + date: transaction.date, + name: transaction.alias, + amount: `${transaction.amount}`, + id: transaction.id, + subscription: transaction.isSubscription, + budget: transaction.budget.category_name + } + } + + function openModal(transaction: ITransaction) { + setCurrentTransaction(transaction); + setModal(true); + } + + function changeBudget(budget: any, transaction: ITransaction) { + fetch(`http://3.128.31.44/transaction/${transaction.id}`, { + method: "PUT", + headers: { + "Content-Type": "application/json", + }, + body: JSON.stringify({ + "isSubscription": transaction.subscription, + "budget_id": budget.category_name === "N/A" ? -1 : budgets[budgets.indexOf(budget)].id, + "subscription_id": transaction.subscriptionId + }) + }).then((res) => res.json()).then(() => { + setRefresh((refresh) => refresh + 1); + }) + } + + useEffect(() => { + fetch(`http://3.128.31.44/transaction`).then((res) => res.json()).then((data) => data.map(mapTransactionToTableCell)).then((transactions) => { + setTransactions(transactions); + }); + }, [currentTransaction, refersh]); + + useEffect(() => { + fetch(`http://3.128.31.44/budget`).then((res) => res.json()).then((budgets) => { + const newBudgets: any[] = []; + + budgets.map((budget: any) => { + newBudgets.push(budget); + }); + + setBudgets([{ category_name: "N/A" }, ...newBudgets]); + }); + }, []); + + return <> + + + + + + + + + + + + + + { + transactions.map((transaction, key) => { + return + { Object.entries(transaction).map(([key, value]) => { + if (key === "budget") { + return + } + + if (key === "subscription") { + return + } + + return + }) } + + }) + } + +
DATENAMEAMOUNTIDSUBSCRIPTIONBUDGET
+ + + openModal(transaction)} type="checkbox" checked={value} onChange={() => {}} /> +

Subscribe

+
{ value }
+ ; +} + export default Transactions; \ No newline at end of file diff --git a/frontend/src/app/deposits/page.tsx b/frontend/src/app/deposits/page.tsx index c55d25b..d02291f 100644 --- a/frontend/src/app/deposits/page.tsx +++ b/frontend/src/app/deposits/page.tsx @@ -1,30 +1,30 @@ -'use client' -import React from 'react' -import Card from "../components/Card"; -import Transactions from '../components/Transactions'; - -const Deposits: React.FC = () => { - return ( -
-
- - - -
- -
-
-

Recent Transactions

-

Previous Billing

-

Financial Summary

-

Custom Date Range

-

Subscription Management

-
- - -
-
- ) -} - +'use client' +import React from 'react' +import Card from "../components/Card"; +import Transactions from '../components/Transactions'; + +const Deposits: React.FC = () => { + return ( +
+
+ + + +
+ +
+
+

Recent Transactions

+

Previous Billing

+

Financial Summary

+

Custom Date Range

+

Subscription Management

+
+ + +
+
+ ) +} + export default Deposits \ No newline at end of file diff --git a/frontend/src/app/layout.tsx b/frontend/src/app/layout.tsx index 8538090..1224a81 100644 --- a/frontend/src/app/layout.tsx +++ b/frontend/src/app/layout.tsx @@ -1,27 +1,27 @@ -import './globals.css' -import type { Metadata } from 'next' -import { Inter } from 'next/font/google' -import dynamic from 'next/dynamic' -import Header from './components/Header' - -const inter = Inter({ subsets: ['latin'] }) - -export const metadata: Metadata = { - title: 'Capital Two App', - description: 'Generated by create next app', -} - -export default function RootLayout({ - children, -}: { - children: React.ReactNode -}) { - return ( - - -
- {children} - - - ) -} +import './globals.css' +import type { Metadata } from 'next' +import { Inter } from 'next/font/google' +import dynamic from 'next/dynamic' +import Header from './components/Header' + +const inter = Inter({ subsets: ['latin'] }) + +export const metadata: Metadata = { + title: 'Capital Two App', + description: 'Generated by create next app', +} + +export default function RootLayout({ + children, +}: { + children: React.ReactNode +}) { + return ( + + +
+ {children} + + + ) +} diff --git a/frontend/src/app/page.tsx b/frontend/src/app/page.tsx index 426009f..0852273 100644 --- a/frontend/src/app/page.tsx +++ b/frontend/src/app/page.tsx @@ -1,161 +1,165 @@ -'use client' - -import React, { useState } from 'react'; -import { useRouter } from 'next/navigation' -import Image from 'next/image'; -import SignUpPic from './icons/SignUp-Pic.png'; -import Link from 'next/link'; -import { usePathname } from 'next/navigation'; -import styles from './auth/auth.module.css'; - -const AuthPage: React.FC = () => { - const pathName = usePathname(); - const router = useRouter(); - - const [username, setUsername] = useState(''); - const [password, setPassword] = useState(''); - const [rememberMe, setRememberMe] = useState(false); - const [showPassword, setShowPassword] = useState(false); - const [usernameError, setUsernameError] = useState(''); - const [passwordError, setPasswordError] = useState(''); - - const handleRememberMeChange = () => { - setRememberMe(!rememberMe); - }; - - const handleShowPasswordToggle = () => { - setShowPassword(!showPassword); - }; - - const handleSignInClick = () => { - if (username.trim() === '') { - setUsernameError('This field is required'); - } else { - setUsernameError(''); - } - - if (password.trim() === '') { - setPasswordError('This field is required'); - } else { - setPasswordError(''); - } - router.push('/home'); - }; - - const inputStyle: React.CSSProperties = { - width: '100%', - padding: '12px', - fontSize: '14px', - border: `1px solid ${usernameError ? 'red' : '#ccc'}`, - boxSizing: 'border-box', - borderRadius: '5px', - marginBottom: '20px', - }; - - const buttonStyle: React.CSSProperties = { - backgroundColor: '#0070f3', - color: '#fff', - padding: '15px', - fontSize: '18px', - border: 'none', - borderRadius: '20px', - cursor: 'pointer', - marginBottom: '20px', - marginRight:'30px', - }; - - const linkStyle: React.CSSProperties = { - color: '#0070f3', - textDecoration: 'underline', - cursor: 'pointer', - marginTop: '25px', - marginBottom: '10px', - display: 'block', - }; - - - return ( -
-
- credit wise photo -
-
-

Sign In

-
- - { - setUsername(e.target.value); - setUsernameError(''); - }} - /> - {usernameError && {usernameError}} -
-
- -
- { - setPassword(e.target.value); - setPasswordError(''); - }} - /> - {passwordError && {passwordError}} -
- {showPassword ? '🙈' : '👁️'} -
-
-
- -
- - -
- - console.log('Forgot Username or Password clicked')}> - Forgot Username or Password? - - - - Set Up Online Access - - -
-
- ); -}; - -export default AuthPage; - +'use client' + +import React, { useState } from 'react'; +import { useRouter } from 'next/navigation' +import Image from 'next/image'; +import SignUpPic from './icons/SignUp-Pic.png'; +import Link from 'next/link'; +import { usePathname } from 'next/navigation'; +import styles from './auth/auth.module.css'; + +const AuthPage: React.FC = () => { + const pathName = usePathname(); + const router = useRouter(); + + const [username, setUsername] = useState(''); + const [password, setPassword] = useState(''); + const [rememberMe, setRememberMe] = useState(false); + const [showPassword, setShowPassword] = useState(false); + const [usernameError, setUsernameError] = useState(''); + const [passwordError, setPasswordError] = useState(''); + + const handleRememberMeChange = () => { + setRememberMe(!rememberMe); + }; + + const handleShowPasswordToggle = () => { + setShowPassword(!showPassword); + }; + + const handleSignInClick = () => { + if (username.trim() === '') { + setUsernameError('This field is required'); + } else { + setUsernameError(''); + } + + if (password.trim() === '') { + setPasswordError('This field is required'); + } else { + setPasswordError(''); + } + router.push('/home'); + }; + + const inputStyle: React.CSSProperties = { + width: '100%', + padding: '12px', + fontSize: '14px', + border: `1px solid ${usernameError ? 'red' : '#ccc'}`, + boxSizing: 'border-box', + borderRadius: '5px', + marginBottom: '20px', + }; + + const buttonStyle: React.CSSProperties = { + backgroundColor: '#0070f3', + color: '#fff', + padding: '15px', + fontSize: '18px', + border: 'none', + borderRadius: '20px', + cursor: 'pointer', + marginBottom: '20px', + marginRight:'30px', + }; + + const linkStyle: React.CSSProperties = { + color: '#0070f3', + fontSize: '20px', + textDecoration: 'underline', + cursor: 'pointer', + marginTop: '25px', + marginBottom: '10px', + display: 'block', + }; + + + return ( +
+
+ credit wise photo +
+
+

Sign In

+
+ + { + setUsername(e.target.value); + setUsernameError(''); + }} + /> + {usernameError && {usernameError}} +
+
+ +
+ { + setPassword(e.target.value); + setPasswordError(''); + }} + /> + {passwordError && {passwordError}} +
+ {showPassword ? '🙈' : '👁️'} +
+
+
+ +
+ + +
+ + console.log('Forgot Username or Password clicked')}> + Forgot Username or Password? + + + + Set Up Online Access + + +
+
+ ); +}; + +export default AuthPage; + diff --git a/frontend/src/app/payments/layout.tsx b/frontend/src/app/payments/layout.tsx index 041d147..4da82b7 100644 --- a/frontend/src/app/payments/layout.tsx +++ b/frontend/src/app/payments/layout.tsx @@ -1,40 +1,40 @@ -"use client"; - -import React from "react"; -import { usePathname } from "next/navigation"; -import Card from "../components/Card"; -import styles from "./layout.module.css"; - -export default function PaymentsLayout({ children }: { children: React.ReactNode }) { - const pathName = usePathname(); - - const navItems = [ - { name: "Recent Transactions", link: "/payments" }, - { name: "Previous Billing", link: "" }, - { name: "Financial Summary", link: "" }, - { name: "Custom Date Range", link: "" }, - { name: "Subscription Management", link: "/payments/subscriptions" }, - ]; - - return
-
-
- -
- { - navItems.map((navItem) => { - const isSelected = pathName === navItem.link; - - return {navItem.name} - }) - } -
-
- { children } -
- -
-
- -
+"use client"; + +import React from "react"; +import { usePathname } from "next/navigation"; +import Card from "../components/Card"; +import styles from "./layout.module.css"; + +export default function PaymentsLayout({ children }: { children: React.ReactNode }) { + const pathName = usePathname(); + + const navItems = [ + { name: "Recent Transactions", link: "/payments" }, + { name: "Previous Billing", link: "" }, + { name: "Financial Summary", link: "" }, + { name: "Custom Date Range", link: "" }, + { name: "Subscription Management", link: "/payments/subscriptions" }, + ]; + + return
+
+
+ +
+ { + navItems.map((navItem) => { + const isSelected = pathName === navItem.link; + + return {navItem.name} + }) + } +
+
+ { children } +
+ +
+
+ +
} \ No newline at end of file diff --git a/frontend/src/app/payments/page.tsx b/frontend/src/app/payments/page.tsx index 2decf01..0fac6fc 100644 --- a/frontend/src/app/payments/page.tsx +++ b/frontend/src/app/payments/page.tsx @@ -1,19 +1,19 @@ -'use client' -import React from 'react' -import Card from "../components/Card"; -import Transactions from '../components/Transactions'; - -const Payments: React.FC = () => { - return ( -
-
- - - -
- -
- ); -}; - +'use client' +import React from 'react' +import Card from "../components/Card"; +import Transactions from '../components/Transactions'; + +const Payments: React.FC = () => { + return ( +
+
+ + + +
+ +
+ ); +}; + export default Payments; \ No newline at end of file diff --git a/frontend/src/app/payments/subscriptions/page.tsx b/frontend/src/app/payments/subscriptions/page.tsx index f6a72cd..8743dce 100644 --- a/frontend/src/app/payments/subscriptions/page.tsx +++ b/frontend/src/app/payments/subscriptions/page.tsx @@ -1,101 +1,101 @@ -import React from 'react'; -import CustomCard from './CustomCard'; - -const SubscriptionsPage: React.FC = () => { - const card0 = { - title: 'Subscription Total', - price: '$65.05', - subTitle: 'Calculated to today', - subPlan: '', - showLogo: false, - customHeightCard0: true, - customWidthCard0: true, - }; - - const card1 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: '09/15-10/14', - subPlan: 'Monthly', - comingUp: 'Coming Up', - showLogo: false, - customHeightCard1: true, - customWidthCard1: true, - }; - - const card2 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: 'Student Premium Plan', - subPlan: 'Monthly', - }; - - const card3 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: 'Student Premium Plan', - subPlan: 'Monthly', - }; - - const card4 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: 'Student Premium Plan', - subPlan: 'Monthly', - }; - - const card5 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: 'Student Premium Plan', - subPlan: 'Monthly', - }; - - const card6 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: 'Student Premium Plan', - subPlan: 'Monthly', - }; - - const card7 = { - title: 'YouTube Premium', - price: '$10.00', - subTitle: 'Student Premium Plan', - subPlan: 'Monthly', - }; - - return ( -
-
-
-
-
-
-
- -
-
- -
-

Subscription Management

- -
-
- - - -
-
- - - -
-
-
- ); -}; - -export default SubscriptionsPage; +import React from 'react'; +import CustomCard from './CustomCard'; + +const SubscriptionsPage: React.FC = () => { + const card0 = { + title: 'Subscription Total', + price: '$65.05', + subTitle: 'Calculated to today', + subPlan: '', + showLogo: false, + customHeightCard0: true, + customWidthCard0: true, + }; + + const card1 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: '09/15-10/14', + subPlan: 'Monthly', + comingUp: 'Coming Up', + showLogo: false, + customHeightCard1: true, + customWidthCard1: true, + }; + + const card2 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: 'Student Premium Plan', + subPlan: 'Monthly', + }; + + const card3 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: 'Student Premium Plan', + subPlan: 'Monthly', + }; + + const card4 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: 'Student Premium Plan', + subPlan: 'Monthly', + }; + + const card5 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: 'Student Premium Plan', + subPlan: 'Monthly', + }; + + const card6 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: 'Student Premium Plan', + subPlan: 'Monthly', + }; + + const card7 = { + title: 'YouTube Premium', + price: '$10.00', + subTitle: 'Student Premium Plan', + subPlan: 'Monthly', + }; + + return ( +
+
+
+
+
+
+
+ +
+
+ +
+

Subscription Management

+ +
+
+ + + +
+
+ + + +
+
+
+ ); +}; + +export default SubscriptionsPage; diff --git a/frontend/src/app/statements/page.tsx b/frontend/src/app/statements/page.tsx index 2f95420..a7180bd 100644 --- a/frontend/src/app/statements/page.tsx +++ b/frontend/src/app/statements/page.tsx @@ -1,10 +1,10 @@ -'use client' -import React from 'react' - -const Statements: React.FC = () => { - return ( -

Statements

- ) -} - -export default Statements +'use client' +import React from 'react' + +const Statements: React.FC = () => { + return ( +

Statements

+ ) +} + +export default Statements diff --git a/frontend/src/app/types/Transaction.ts b/frontend/src/app/types/Transaction.ts index 162ba9f..e491c4f 100644 --- a/frontend/src/app/types/Transaction.ts +++ b/frontend/src/app/types/Transaction.ts @@ -1,12 +1,12 @@ -export interface ITransaction { - date: string, - name: string, - amount: number, - ID: number, - subscription: Boolean, - category: string, - budget: string, - id?: number, - budgetId: number, - subscriptionId: number +export interface ITransaction { + date: string, + name: string, + amount: number, + ID: number, + subscription: Boolean, + category: string, + budget: string, + id?: number, + budgetId: number, + subscriptionId: number } \ No newline at end of file diff --git a/frontend/tailwind.config.ts b/frontend/tailwind.config.ts index 1af3b8f..3556d14 100644 --- a/frontend/tailwind.config.ts +++ b/frontend/tailwind.config.ts @@ -1,20 +1,20 @@ -import type { Config } from 'tailwindcss' - -const config: Config = { - content: [ - './src/pages/**/*.{js,ts,jsx,tsx,mdx}', - './src/components/**/*.{js,ts,jsx,tsx,mdx}', - './src/app/**/*.{js,ts,jsx,tsx,mdx}', - ], - theme: { - extend: { - backgroundImage: { - 'gradient-radial': 'radial-gradient(var(--tw-gradient-stops))', - 'gradient-conic': - 'conic-gradient(from 180deg at 50% 50%, var(--tw-gradient-stops))', - }, - }, - }, - plugins: [], -} -export default config +import type { Config } from 'tailwindcss' + +const config: Config = { + content: [ + './src/pages/**/*.{js,ts,jsx,tsx,mdx}', + './src/components/**/*.{js,ts,jsx,tsx,mdx}', + './src/app/**/*.{js,ts,jsx,tsx,mdx}', + ], + theme: { + extend: { + backgroundImage: { + 'gradient-radial': 'radial-gradient(var(--tw-gradient-stops))', + 'gradient-conic': + 'conic-gradient(from 180deg at 50% 50%, var(--tw-gradient-stops))', + }, + }, + }, + plugins: [], +} +export default config