diff --git a/.github/workflows/deploy-preview.yml b/.github/workflows/deploy-preview.yml
index bede01947..af79d964e 100644
--- a/.github/workflows/deploy-preview.yml
+++ b/.github/workflows/deploy-preview.yml
@@ -46,5 +46,5 @@ jobs:
uses: thollander/actions-comment-pull-request@v2
with:
message: |
- Vercel Preview URL :rocket: : ${{ steps.deploy.outputs.preview_url }}
+ Vercel Preview URL :rocket: : ${{ steps.deploy.outputs.preview_url }}/auth/login
Neon branch :elephant: : https://console.neon.tech/app/projects/${{ secrets.NEON_PROJECT_ID }}/branches/${{ steps.create_branch.outputs.branch_id }}
diff --git a/.github/workflows/format.yml b/.github/workflows/format.yml
index d1d7c6691..b69fec308 100644
--- a/.github/workflows/format.yml
+++ b/.github/workflows/format.yml
@@ -1,13 +1,12 @@
-name: Check Formatting
+name: Lint and Formatting Check
on:
- workflow_dispatch:
- pull_request:
+ push:
paths-ignore:
- 'validator/**'
jobs:
- eslint:
+ main:
name: Run ESLint + Prettier
runs-on: ubuntu-latest
diff --git a/.gitignore b/.gitignore
index 46a3785b0..743a1c8eb 100644
--- a/.gitignore
+++ b/.gitignore
@@ -49,6 +49,7 @@ yarn-error.log*
# See docs/ide-config.md for more information.
.idea
.vs/
+.vscode
.editorconfig
prisma/generated
diff --git a/.vscode/workspace.code-workspace b/.vscode/workspace.code-workspace
deleted file mode 100644
index c48d9735e..000000000
--- a/.vscode/workspace.code-workspace
+++ /dev/null
@@ -1,14 +0,0 @@
-{
- "folders": [
- { "path": "../", "name": "root" },
- {
- "path": "../validator",
- "name": "validator"
- }
- ],
- "settings": {
- "files.exclude": {
- "validator/": true
- }
- }
-}
diff --git a/CODEOWNERS b/CODEOWNERS
index dc4e5cddc..2a34331ac 100644
--- a/CODEOWNERS
+++ b/CODEOWNERS
@@ -1,6 +1,6 @@
# Request lead for file changes in root and workflows.
-/* @akevinge
-/.github/**/* @akevinge
+/* @UTDNebula/pr-reviewers
+/.github/**/* @UTDNebula/pr-reviewers
# Request Planner PR Reviewers team for changes in to the following root directories.
/.vscode/ @UTDNebula/pr-reviewers
diff --git a/cypress.config.ts b/cypress.config.ts
index f3fb7ca89..ed4c8bff3 100644
--- a/cypress.config.ts
+++ b/cypress.config.ts
@@ -23,7 +23,7 @@ export default defineConfig({
viewportHeight: 1080,
viewportWidth: 1920,
baseUrl: 'http://localhost:3000',
- setupNodeEvents(on, config) {
+ setupNodeEvents(on) {
on('after:run', async () => {
await prisma.$disconnect();
});
diff --git a/next.config.js b/next.config.js
index 6adf34c14..069934cf5 100644
--- a/next.config.js
+++ b/next.config.js
@@ -40,11 +40,12 @@ module.exports = async (phase) => {
transform: '@mui/icons-material/{{member}}',
},
},
- rewrites: async () => {
+ redirects: async () => {
return [
{
source: '/',
- destination: '/index.html',
+ destination: 'https://www.utdnebula.com/projects/planner',
+ permanent: true,
},
];
},
diff --git a/package-lock.json b/package-lock.json
index 6262874d3..b86b1742d 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -84,7 +84,6 @@
"eslint-plugin-react": "^7.23.2",
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-storybook": "^0.6.15",
- "husky": "^8.0.0",
"jest": "^29.6.1",
"node-fetch": "^3.3.2",
"postcss": "^8.4.31",
@@ -16785,21 +16784,6 @@
"node": ">=10.17.0"
}
},
- "node_modules/husky": {
- "version": "8.0.3",
- "resolved": "https://registry.npmjs.org/husky/-/husky-8.0.3.tgz",
- "integrity": "sha512-+dQSyqPh4x1hlO1swXBiNb2HzTDN1I2IGLQx1GrBuiqFJfoMrnZWwVmatvSiO+Iz8fBUnf+lekwNo4c2LlXItg==",
- "dev": true,
- "bin": {
- "husky": "lib/bin.js"
- },
- "engines": {
- "node": ">=14"
- },
- "funding": {
- "url": "https://github.com/sponsors/typicode"
- }
- },
"node_modules/hyphen": {
"version": "1.6.4",
"license": "ISC"
diff --git a/package.json b/package.json
index e7deadd1e..f2fd72a0c 100644
--- a/package.json
+++ b/package.json
@@ -18,19 +18,12 @@
"cypress:open": "NODE_ENV=test start-server-and-test dev http://localhost:3000 \"cypress open --browser chrome --e2e\"",
"cypress:run": "NODE_ENV=test start-server-and-test start http://127.0.0.1:3000 \"cypress run --browser chrome --config video=false --e2e\"",
"test": "NODE_OPTIONS=--experimental-vm-modules jest",
- "prepare": "husky install",
"storybook": "storybook dev -p 6006",
"build-storybook": "storybook build"
},
"prisma": {
"seed": "ts-node --transpile-only --compiler-options {\"module\":\"CommonJS\"} prisma/seed.ts"
},
- "lint-staged": {
- "**/*.{js,jsx,ts,tsx,json}": [
- "npx prettier --write",
- "npx eslint --fix"
- ]
- },
"dependencies": {
"@dnd-kit/core": "^6.0.6",
"@mui/icons-material": "^5.3.1",
@@ -108,7 +101,6 @@
"eslint-plugin-react": "^7.23.2",
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-storybook": "^0.6.15",
- "husky": "^8.0.0",
"jest": "^29.6.1",
"node-fetch": "^3.3.2",
"postcss": "^8.4.31",
diff --git a/public/demo.gif b/public/demo.gif
deleted file mode 100644
index 19787953b..000000000
Binary files a/public/demo.gif and /dev/null differ
diff --git a/public/graduation.jpg b/public/graduation.jpg
deleted file mode 100644
index 1b7445f1a..000000000
Binary files a/public/graduation.jpg and /dev/null differ
diff --git a/public/icons8-gold-medal-100.png b/public/icons8-gold-medal-100.png
deleted file mode 100644
index 24f605e70..000000000
Binary files a/public/icons8-gold-medal-100.png and /dev/null differ
diff --git a/public/icons8-lightning-bolt-100.png b/public/icons8-lightning-bolt-100.png
deleted file mode 100644
index 2e6e3716b..000000000
Binary files a/public/icons8-lightning-bolt-100.png and /dev/null differ
diff --git a/public/icons8-mail-96.png b/public/icons8-mail-96.png
deleted file mode 100644
index e143899e7..000000000
Binary files a/public/icons8-mail-96.png and /dev/null differ
diff --git a/public/icons8-menu-rounded-100.png b/public/icons8-menu-rounded-100.png
deleted file mode 100644
index a77a3af16..000000000
Binary files a/public/icons8-menu-rounded-100.png and /dev/null differ
diff --git a/public/icons8-pen-100.png b/public/icons8-pen-100.png
deleted file mode 100644
index f049d0cd7..000000000
Binary files a/public/icons8-pen-100.png and /dev/null differ
diff --git a/public/icons8-stopwatch-100.png b/public/icons8-stopwatch-100.png
deleted file mode 100644
index b851819e4..000000000
Binary files a/public/icons8-stopwatch-100.png and /dev/null differ
diff --git a/public/icons8-test-tube-100.png b/public/icons8-test-tube-100.png
deleted file mode 100644
index 98ad714a0..000000000
Binary files a/public/icons8-test-tube-100.png and /dev/null differ
diff --git a/public/icons8-upload-64.png b/public/icons8-upload-64.png
deleted file mode 100644
index 53763fa1c..000000000
Binary files a/public/icons8-upload-64.png and /dev/null differ
diff --git a/public/index.css b/public/index.css
deleted file mode 100644
index 41e016284..000000000
--- a/public/index.css
+++ /dev/null
@@ -1,563 +0,0 @@
-:root {
- --light-gray: #ddd;
- --gray: #999;
-}
-
-@font-face {
- font-family: "Inter";
- src: url("./Inter-VariableFont_slnt,wght.ttf");
-}
-
-html, body {
- min-height: 100vh;
- scroll-behavior: smooth;
-}
-
-body {
- display: flex;
- flex-direction: column;
- font-family: "Inter", sans-serif;
- margin: 0;
- overflow-x: hidden;
-}
-
-/*
- Components
- */
-
-a {
- text-decoration: none;
-}
-
-.button {
- border: 2px solid var(--light-gray);
- border-radius: 1.5em;
- padding: .6rem 1.1rem;
- transition: background-color .3s;
-}
-
-.button:hover {
- background-color: var(--light-gray);
-}
-
-/*
- Header
- */
-
-header {
- display: flex;
- justify-content: space-between;
- padding: 2rem 10vw;
- z-index: 1;
-}
-
-header ul {
- list-style-type: none;
- margin: 0;
- padding: 0;
-}
-
-header li {
- display: inline-block;
- margin: 0.75rem 1rem;
-}
-
-header a {
- color: var(--gray);
- transition: color .2s;
-}
-
-header a:hover {
- color: #333;
-}
-
-/*
- Login button
- */
-
-.login {
- background-color: #6266F9;
- border-color: #6266F9;
- color: #fff !important;
-}
-
-.login:hover {
- background-color: #474bb6;
- color: #fff;
-}
-
-/*
- Footer
- */
-
-footer {
- display: flex;
- flex-direction: column;
- align-items: center;
- padding: 1rem 0;
-}
-
-footer img {
- margin-bottom: .5rem;
-}
-
-footer p {
- color: var(--gray);
- font-size: .75rem;
-}
-
-hr {
- width: 80%;
- background-color: var(--light-gray);
- border: none;
- height: 1px;
-}
-
-/*
- Middle stuff
- */
-
-main {
- flex-grow: 1;
-}
-
-/*
- First slide
- */
-
-#intro {
- display: flex;
- min-height: calc(120vh - 6rem);
- align-items: center;
- overflow: hidden;
- position: relative;
-}
-
-#intro > div, #plan > div {
- flex-grow: 1;
- display: flex;
- flex-direction: column;
- align-items: flex-start;
- padding: 0 5vw 0 10vw;
-}
-
-#intro > div {
- position: absolute;
- top: 30vh;
-}
-
-#intro h1 {
- font-size: 3rem;
- margin: 0;
- max-width: 30vw;
-}
-
-#intro h2 {
- color: var(--gray);
- font-size: 1rem;
- margin: 0;
- text-transform: uppercase;
-}
-
-#intro h3 {
- color: var(--gray);
- font-weight: normal;
- font-size: 1rem;
- max-width: 30vw;
-}
-
-#intro img, #plan img {
- box-shadow: rgba(100, 100, 111, 0.2) 0px 7px 29px 0px;
- border-radius: 20px 0 0 20px;
-}
-
-#intro img {
- position: absolute;
- left: 42%;
- top: 10%;
- z-index: 0;
- max-height: 90vh;
-}
-
-button {
- appearance: none;
- background: none;
- border: none;
- outline: none;
- font-weight: bold;
- font-size: 1.1rem;
- margin: 1rem 0;
-}
-
-.buttons a {
- color: #000;
-}
-
-#menu {
- display: none;
-}
-
-#menu img {
- border-radius: 50%;
- height: 1.5rem;
- padding: .75rem;
- position: absolute;
- top: 1.5rem;
- right: calc(10vw - .75rem);
- transition: background-color .2s;
-}
-
-#menu img:hover {
- background-color: var(--light-gray);
-}
-
-@media screen and (max-width: 1200px) {
- /*
- Vertically align the image
- */
- #intro {
- flex-direction: column;
- }
-
- #intro h1 {
- font-size: 2.5rem;
- max-width: 400px;
- }
-
- #intro h3 {
- max-width: 400px;
- }
-
- #intro > div {
- position: static;
- padding: 10vh 10vw;
- }
-
- #intro img {
- position: static;
- max-width: 90vw;
- border-radius: 20px;
- margin-bottom: 2rem;
- }
-}
-
-@media screen and (max-width: 900px) {
- header ul {
- display: none;
- }
-
- #menu {
- display: block;
- }
-}
-
-@media screen and (max-width: 650px) {
- /*
- Detach the image
- */
- #intro > div {
- flex-grow: 0;
- }
-
- #intro img {
- width: 150vw;
- }
-}
-
-/*
- Second slide
- */
-
-section:nth-child(odd) {
- background-color: #f4f5f6;
-}
-
-#features, #team, #contact, #plan {
- display: flex;
- flex-direction: column;
- align-items: center;
- justify-content: center;
- min-height: calc(100vh - 4rem);
- padding: 2rem 0;
- text-align: center;
-}
-
-#features h2, #team h2, #contact h2, #plan h2 {
- font-size: 3rem;
- margin: 0;
-}
-
-#features h3 {
- color: var(--gray);
- font-weight: normal;
- width: 30%;
-}
-
-.features {
- display: grid;
- grid-template-columns: repeat(3, 1fr);
- gap: 10vw;
- padding: 15vh 10vw;
-}
-
-.feature {
- align-items: center;
- display: flex;
- flex-direction: column;
-}
-
-.feature div {
- background-color: #eee;
- border-radius: 100%;
-}
-
-.feature img {
- height: 4rem;
- padding: .5rem .6rem;
-}
-
-.feature p {
- color: var(--gray);
- margin: 0;
- line-height: 1.5rem;
-}
-
-@media screen and (max-width: 1200px) {
- #features h2, #team h2, #contact h2, #plan h2 {
- font-size: 2.5rem !important;
- text-align: center !important;
- }
-
- #features h3 {
- width: 300px;
- font-size: 1rem;
- }
-
- .features {
- grid-template-columns: 1fr;
- padding: 5vh 0;
- }
-
- .feature p {
- font-size: .9rem;
- max-width: 300px;
- }
-}
-
-/*
- Third slide
- */
-
-#team ul {
- list-style-type: none;
- margin: 0;
- padding: 0;
-}
-
-#team li {
- display: inline-block;
- font-size: .9rem;
- padding: .5rem;
- margin: 5vh 0;
-}
-
-#team li.login {
- border-radius: 1.5em;
- padding: .5rem 1rem;
-}
-
-#team h2 {
- margin: 2rem;
-}
-
-.selectedTeam {
- background-color: #3772ff;
- border-color: #3772ff;
- color: white !important;
- border-radius: 1.5em;
- padding: .5rem 1rem;
-}
-
-.team {
- display: grid;
- grid-template-columns: repeat(3, 1fr);
- width: 90%;
- margin-top: 3vh;
-}
-
-.member img {
- height: 200px;
- border-radius: 10px;
- transition: box-shadow .2s;
-}
-
-.member img:hover {
- box-shadow: rgba(0, 0, 0, 0.19) 0px 10px 20px, rgba(0, 0, 0, 0.23) 0px 6px 6px;
-}
-
-.member h4 {
- margin: 1rem 0 0 0;
-}
-
-.member h5 {
- color: var(--gray);
- margin: 1rem 0;
-}
-
-@media screen and (max-width: 1200px) {
- .team {
- width: 100%;
- display: flex;
- overflow-x: scroll;
- }
-
- .member:first-child {
- margin-left: 25vw;
- }
-
- .member:last-child {
- margin-right: 25vw;
- }
-
- .member {
- margin: 0 5vw;
- }
-}
-
-/*
- Plan slide
- */
-
-#plan {
- flex-direction: row;
- justify-content: space-between;
-}
-
-#plan img {
- max-height: 90vh;
- transform: translateY(10vh);
-}
-
-#plan h2 {
- font-size: 4rem;
- text-align: left;
- max-width: 600px;
- margin-bottom: 2rem;
-}
-
-@media screen and (max-width: 1200px) {
- #plan {
- flex-direction: column;
- justify-content: center;
- min-height: 50vh;
- }
-
- #plan > div {
- align-items: center;
- flex-grow: 0;
- margin-bottom: 2rem;
- }
-
- #plan img {
- display: none;
- }
-}
-
-/*
- Contact slide
- */
-
-#contact form {
- background-color: #fff;
- border-radius: 20px;
- box-shadow: rgba(0, 0, 0, 0.1) 0px 20px 25px -5px, rgba(0, 0, 0, 0.04) 0px 10px 10px -5px;
- display: flex;
- margin: 3rem;
- text-align: left;
-}
-
-#contact img {
- height: 2rem;
-}
-
-#contact h3 {
- color: var(--gray);
- font-weight: normal;
-}
-
-#contact p {
- margin: 0;
-}
-
-#contact form > div:first-child {
- margin: 10vh 10vw;
-}
-
-#contact form > div:last-child {
- margin: 10vh 10vw 10vh 0;
-}
-
-#contact hr {
- display: none;
-}
-
-.inputField {
- display: flex;
- flex-direction: column;
-}
-
-.inputField label {
- color: var(--gray);
- font-weight: bold;
- font-size: .8rem;
- text-transform: uppercase;
- margin: .5rem 0;
-}
-
-.inputField input, .inputField textarea {
- background-color: #eee;
- border: none;
- border-radius: 20px;
- font-family: "Inter", sans-serif;
- font-size: .9rem;
- padding: 1rem;
- resize: none;
- width: 300px;
- transition: background-color .3s;
-}
-
-.inputField input:focus, .inputField textarea:focus {
- outline: none;
- background-color: #ddd;
-}
-
-@media screen and (max-width: 800px) {
- #contact form {
- flex-direction: column;
- }
-
- #contact form > div:first-child {
- margin: 2rem 10vw;
- }
-
- #contact hr {
- display: block;
- width: calc(100% - 20vw);
- }
-
- #contact form > div:last-child {
- margin: 2rem 10vw;
- }
-
- #contact .button {
- margin: 1rem 0 0 0;
- }
-
- .inputField {
- margin-bottom: 1rem;
- }
-
- .inputField input, .inputField textarea {
- width: 50vw;
- }
-}
diff --git a/public/index.html b/public/index.html
deleted file mode 100644
index a890f6150..000000000
--- a/public/index.html
+++ /dev/null
@@ -1,224 +0,0 @@
-
-
-
-
-
- Nebula Planner
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
Navigate your degree with ease
-
Launch Your Degree Plan with Nebula Planner
-
Blast off your academic journey to the moon with Nebula Labs Planner - the ultimate tool for customizing your four-year degree.
-
-
-
-
-
- Features
-
- Say goodbye to the stress and hassle of degree planning and hello to a smooth, organized path towards graduation with Nebula Planner.
-
-
-
-
-
-
-
Spreadsheet where?
-
- Bye-bye clunky spreadsheets, hello easy-peasy degree planning with simple click-and-drag action. You're welcome!
-
-
-
-
-
-
-
Slay your progress!
-
- Not sure where you are in your degree plan? That's ok. Tracking your degree plan is now a piece of cake with our degree tracker. No cap.
-
-
-
-
-
-
-
Save Time
-
- Nebula Planner streamlines academic planning, enabling you to map out your course requirements, track your progress, and adjust your plan as needed so you can focus on what you do best.
-
-
-
- Get Started
-
-
- Meet the team
-
-
-
-
Caleb Lim
-
Project Lead
-
-
-
-
Aanos Mahmood
-
Design Lead
-
-
-
-
Stephanie Li
-
Product Lead
-
-
-
-
Hilary Nguyen
-
Designer, Product team
-
-
-
-
Aravindan Kasiraman
-
Developer
-
-
-
-
Jason Antwi-Appah
-
Developer
-
-
-
-
Kevin Ge
-
Developer
-
-
-
-
JC Garza
-
Developer
-
-
-
-
Saidarsh Tukkadi
-
Developer
-
-
-
-
Lokesh Yerneni
-
Developer
-
-
-
-
Peyton Barre
-
Developer
-
-
-
-
-
-
-
Explore the Possibilities with Nebula Planner!
-
Get Started
-
-
-
-
-
-
-
-
-
diff --git a/public/mockup.png b/public/mockup.png
deleted file mode 100644
index d302e6338..000000000
Binary files a/public/mockup.png and /dev/null differ
diff --git a/public/person.png b/public/person.png
deleted file mode 100644
index ca906fa3b..000000000
Binary files a/public/person.png and /dev/null differ
diff --git a/public/planner_logo.svg b/public/planner_logo.svg
deleted file mode 100644
index b08977ee6..000000000
--- a/public/planner_logo.svg
+++ /dev/null
@@ -1 +0,0 @@
-
\ No newline at end of file
diff --git a/public/team/Aanos.jpeg b/public/team/Aanos.jpeg
deleted file mode 100644
index 76180dfd3..000000000
Binary files a/public/team/Aanos.jpeg and /dev/null differ
diff --git a/public/team/Aravindan.jpeg b/public/team/Aravindan.jpeg
deleted file mode 100644
index c849ba684..000000000
Binary files a/public/team/Aravindan.jpeg and /dev/null differ
diff --git a/public/team/Caleb.jpeg b/public/team/Caleb.jpeg
deleted file mode 100644
index b3875c2c5..000000000
Binary files a/public/team/Caleb.jpeg and /dev/null differ
diff --git a/public/team/JCGarza.jpeg b/public/team/JCGarza.jpeg
deleted file mode 100644
index e2223a7ab..000000000
Binary files a/public/team/JCGarza.jpeg and /dev/null differ
diff --git a/public/team/Jason.jpeg b/public/team/Jason.jpeg
deleted file mode 100644
index 2f21b439f..000000000
Binary files a/public/team/Jason.jpeg and /dev/null differ
diff --git a/public/team/Kevin.jpeg b/public/team/Kevin.jpeg
deleted file mode 100644
index 002c85eb8..000000000
Binary files a/public/team/Kevin.jpeg and /dev/null differ
diff --git a/public/team/Loki.jpeg b/public/team/Loki.jpeg
deleted file mode 100644
index d6b100acb..000000000
Binary files a/public/team/Loki.jpeg and /dev/null differ
diff --git a/public/team/Peyton.jpg b/public/team/Peyton.jpg
deleted file mode 100644
index 724b1c38b..000000000
Binary files a/public/team/Peyton.jpg and /dev/null differ
diff --git a/public/team/Saidarsh.jpeg b/public/team/Saidarsh.jpeg
deleted file mode 100644
index dadafcdb1..000000000
Binary files a/public/team/Saidarsh.jpeg and /dev/null differ
diff --git a/public/team/Solomon (1).jpeg b/public/team/Solomon (1).jpeg
deleted file mode 100644
index e143477ec..000000000
Binary files a/public/team/Solomon (1).jpeg and /dev/null differ
diff --git a/public/team/hilary.jpeg b/public/team/hilary.jpeg
deleted file mode 100644
index f93a6186e..000000000
Binary files a/public/team/hilary.jpeg and /dev/null differ
diff --git a/public/team/stephanie.jpg b/public/team/stephanie.jpg
deleted file mode 100644
index be567362c..000000000
Binary files a/public/team/stephanie.jpg and /dev/null differ
diff --git a/src/components/AutoCompleteMajor.tsx b/src/components/AutoCompleteMajor.tsx
index cac1016d9..a12211033 100644
--- a/src/components/AutoCompleteMajor.tsx
+++ b/src/components/AutoCompleteMajor.tsx
@@ -1,24 +1,20 @@
import Autocomplete from '@mui/material/Autocomplete';
import Popper from '@mui/material/Popper';
import TextField from '@mui/material/TextField';
-import { FC, useCallback, useRef } from 'react';
+import React, { ComponentPropsWithoutRef, FC, useCallback, useRef } from 'react';
-interface AutoCompleteMajorProps extends React.ComponentPropsWithoutRef<'div'> {
- onValueChange: (value: string) => void;
+interface AutoCompleteMajorProps extends ComponentPropsWithoutRef<'div'> {
+ onValueChange?: (value: string) => void;
onInputChange: (query: string) => void;
options: string[];
- autoFocus?: boolean;
placeholder?: string;
- defaultValue?: string;
}
-const AutoCompleteMajor: FC> = ({
+const AutoCompleteMajor: FC> = ({
onValueChange,
onInputChange,
options,
- autoFocus,
placeholder = 'Major',
- defaultValue = '',
...props
}) => {
const containerRef = useRef(null);
@@ -51,7 +47,7 @@ const AutoCompleteMajor: FC onValueChange(value ?? '')}
+ onChange={(_, value) => typeof onValueChange !== 'undefined' && onValueChange(value ?? '')}
onInputChange={(_, query) => {
onInputChange(query);
}}
diff --git a/src/components/Button.tsx b/src/components/Button.tsx
index 70f1b6471..7ea75729c 100644
--- a/src/components/Button.tsx
+++ b/src/components/Button.tsx
@@ -1,4 +1,4 @@
-import React, { Children, FC } from 'react';
+import React, { Children, ComponentPropsWithoutRef, FC } from 'react';
import Spinner from './Spinner';
@@ -25,7 +25,7 @@ const fontClasses = {
default: 'text-sm font-medium',
};
-export interface ButtonProps extends React.ComponentPropsWithoutRef<'button'> {
+export interface ButtonProps extends ComponentPropsWithoutRef<'button'> {
color?: keyof typeof colorClasses;
size?: keyof typeof sizeClasses;
width?: keyof typeof widthClasses;
diff --git a/src/components/common/ErrorMessage.tsx b/src/components/common/ErrorMessage.tsx
index ddd730154..25e38ad52 100644
--- a/src/components/common/ErrorMessage.tsx
+++ b/src/components/common/ErrorMessage.tsx
@@ -15,7 +15,7 @@ const errorMessageStyle = {
left: '35%',
} as React.CSSProperties;
-export default function ErrorMessage(error: any) {
+export default function ErrorMessage(error: string) {
return (
Something went wrong - {error}!
diff --git a/src/components/common/WarningMessageModal.tsx b/src/components/common/WarningMessageModal.tsx
deleted file mode 100644
index 7e2dce7e6..000000000
--- a/src/components/common/WarningMessageModal.tsx
+++ /dev/null
@@ -1,30 +0,0 @@
-import CloseIcon from '@mui/icons-material/Close';
-import WarningIcon from '@mui/icons-material/Warning';
-import React from 'react';
-
-export interface WarningMessageModalProps {
- setWarning: (open: boolean) => void;
- message: string;
-}
-
-export default function WarningMessageModal(props: WarningMessageModalProps) {
- const { setWarning, message } = props;
- const [expand, setExpand] = React.useState(false);
-
- return (
-
- {expand ? (
-
-
{message}
-
setWarning(false)}>
-
-
-
- ) : (
-
setExpand(true)}>
-
-
- )}
-
- );
-}
diff --git a/src/components/home/Home.tsx b/src/components/home/Home.tsx
index 984b4267e..767c6c3a8 100644
--- a/src/components/home/Home.tsx
+++ b/src/components/home/Home.tsx
@@ -1,7 +1,7 @@
import * as DropdownMenu from '@radix-ui/react-dropdown-menu';
import { Steps } from 'intro.js-react';
import { useRouter } from 'next/router';
-import React, { useState } from 'react';
+import React, { useEffect, useState } from 'react';
import ChevronIcon from '@/icons/ChevronIcon';
import PlusIcon from '@/icons/PlusIcon';
@@ -34,7 +34,7 @@ export default function PlansPage(): JSX.Element {
const router = useRouter();
const [showHomeOnboardingModal, setShowHomeOnboardingModal] = useState(false);
- React.useEffect(() => {
+ useEffect(() => {
setShowHomeOnboardingModal((userData && !userData.seenHomeOnboardingModal) ?? false);
if (!isLoading && userData && !userData.onboardingComplete) {
router.push('/app/onboarding');
diff --git a/src/components/home/Profile.tsx b/src/components/home/Profile.tsx
index e1efd0132..dfae8b552 100644
--- a/src/components/home/Profile.tsx
+++ b/src/components/home/Profile.tsx
@@ -7,7 +7,7 @@ import InputLabel from '@mui/material/InputLabel';
import MenuItem from '@mui/material/MenuItem';
import Select, { SelectChangeEvent } from '@mui/material/Select';
import { signOut } from 'next-auth/react';
-import { useEffect, useMemo, useState } from 'react';
+import React, { useEffect, useMemo, useState } from 'react';
import { toast } from 'react-toastify';
import { trpc } from '@/utils/trpc';
diff --git a/src/components/home/Sidebar.tsx b/src/components/home/Sidebar.tsx
index b3c4cd1bd..d144d5538 100644
--- a/src/components/home/Sidebar.tsx
+++ b/src/components/home/Sidebar.tsx
@@ -4,8 +4,6 @@ import { signOut } from 'next-auth/react';
import { useEffect, useMemo, useState } from 'react';
import ChevronIcon from '@/icons/ChevronIcon';
-import ContactIcon from '@/icons/ContactIcon';
-import FeedbackIcon from '@/icons/FeedbackIcon';
import GlobalIcon from '@/icons/GlobalIcon';
import HomeIcon from '@/icons/HomeIcon';
import LogoIcon from '@/icons/LogoIcon';
@@ -37,17 +35,7 @@ export default function Sidebar({ isMobile }: { isMobile: boolean }): JSX.Elemen
Icon: ProfileIcon,
},
{
- url: 'https://discord.gg/K5B727vEnV',
- label: 'Contact Support',
- Icon: ContactIcon,
- },
- {
- url: 'https://airtable.com/shrFg9MPi9BGguwPU',
- label: 'Feedback Form',
- Icon: FeedbackIcon,
- },
- {
- url: 'https://discord.gg/anrh9B2Z3w',
+ url: 'https://discord.utdnebula.com/',
label: 'Join Our Discord',
Icon: GlobalIcon,
},
diff --git a/src/components/onboarding/AutoCompleteSearchBarOnboarding.tsx b/src/components/onboarding/AutoCompleteSearchBarOnboarding.tsx
deleted file mode 100644
index 783c725c6..000000000
--- a/src/components/onboarding/AutoCompleteSearchBarOnboarding.tsx
+++ /dev/null
@@ -1,94 +0,0 @@
-import SearchIcon from '@mui/icons-material/Search';
-import { IconButton } from '@mui/material';
-import Autocomplete from '@mui/material/Autocomplete';
-import Popper from '@mui/material/Popper';
-import TextField from '@mui/material/TextField';
-import { FC, useCallback, useRef } from 'react';
-
-interface SearchBarProps extends React.ComponentPropsWithoutRef<'div'> {
- onValueChange: (value: string) => void;
- onInputChange: (query: string) => void;
- options: string[];
- autoFocus?: boolean;
- placeholder?: string;
- defaultValue?: string;
-}
-
-const SearchBar: FC> = ({
- onValueChange,
- onInputChange,
- options,
- autoFocus,
- placeholder = 'Course Code',
- defaultValue = '',
- ...props
-}) => {
- const containerRef = useRef(null);
-
- const CustomPopper = useCallback(
- (props) => {
- if (!containerRef.current) {
- return
;
- }
- const { width } = containerRef.current.getBoundingClientRect();
- return (
-
- );
- },
- [containerRef],
- );
-
- return (
-
-
-
onValueChange(value ?? '')}
- onInputChange={(_, query) => onInputChange(query)}
- options={options}
- fullWidth
- PopperComponent={CustomPopper}
- renderInput={(params) => {
- return (
-
- );
- }}
- />
-
-
-
-
-
-
- );
-};
-
-export default SearchBar;
diff --git a/src/components/onboarding/DropdownSelectOnboarding.tsx b/src/components/onboarding/DropdownSelectOnboarding.tsx
deleted file mode 100644
index 98e67b97f..000000000
--- a/src/components/onboarding/DropdownSelectOnboarding.tsx
+++ /dev/null
@@ -1,72 +0,0 @@
-import KeyboardArrowDownIcon from '@mui/icons-material/KeyboardArrowDown';
-import MenuItem from '@mui/material/MenuItem';
-import Select from '@mui/material/Select';
-import React, { useRef, useState } from 'react';
-
-interface DropdownSelectProps {
- id?: string;
- value: T;
- values: T[];
- onChange: (arg: T) => void;
- getValue: (v: T) => T;
- getDisplayedValue: (v: T) => string;
-}
-
-const DropdownSelect = ({
- id,
- value,
- values,
- onChange,
- getValue,
- getDisplayedValue,
-}: DropdownSelectProps) => {
- const [anchorEl, setAnchorEl] = useState(null);
- const anchorRef = useRef(null);
-
- return (
- setAnchorEl(anchorEl ? null : anchorRef.current)}
- >
-
onChange(e.target.value as T)}
- className="border-[#EDEFF7 h-9 w-full rounded-[10px] border-[2px] text-sm shadow-none"
- open={Boolean(anchorEl)}
- onClose={() => setAnchorEl(null)}
- sx={{
- '& .MuiOutlinedInput-notchedOutline': {
- border: 'none',
- },
- }}
- MenuProps={{
- anchorEl,
- onClose: () => setAnchorEl(null),
- open: Boolean(anchorEl),
- }}
- IconComponent={() => (
-
-
-
- )}
- >
- {values.map((v, i) => (
-
- {getDisplayedValue(v)}
-
- ))}
-
-
-
-
- );
-};
-
-export default DropdownSelect;
diff --git a/src/components/onboarding/welcome.tsx b/src/components/onboarding/welcome.tsx
index cd89fc75c..11c4a1d27 100644
--- a/src/components/onboarding/welcome.tsx
+++ b/src/components/onboarding/welcome.tsx
@@ -1,6 +1,6 @@
import { MenuItem, Select, SelectChangeEvent } from '@mui/material';
import Link from 'next/link';
-import React from 'react';
+import React, { useEffect } from 'react';
import AutoCompleteMajor from '@/components/AutoCompleteMajor';
import EmojiIcons from '@/icons/EmojiIcon';
@@ -18,16 +18,10 @@ export type WelcomeTypes = {
export type WelcomeData = {
handleChange: (updatedFields: Partial) => void;
data: WelcomeTypes;
- semesterOptions: { startSemesters: SemesterCode[]; endSemesters: SemesterCode[] };
handleValidate: (value: boolean) => void;
};
-export default function Welcome({
- handleChange,
- data,
- handleValidate,
- semesterOptions,
-}: WelcomeData): JSX.Element {
+export default function Welcome({ handleChange, data, handleValidate }: WelcomeData): JSX.Element {
const { name, startSemester, endSemester }: WelcomeTypes = data;
const setName = (event: SelectChangeEvent) => {
@@ -42,7 +36,6 @@ export default function Welcome({
handleChange({ endSemester: sem });
};
- const [major, setMajor] = React.useState('');
const { majors, err } = useMajors();
const { results, updateQuery } = useSearch({
@@ -105,11 +98,11 @@ export default function Welcome({
handleValidate(isValid);
};
- React.useEffect(() => {
+ useEffect(() => {
checkValidate();
}, [data]);
- React.useEffect(() => {
+ useEffect(() => {
window.scrollTo(0, 0);
}, []);
@@ -117,7 +110,7 @@ export default function Welcome({
return (
<>
Oops, we ran into an error! Please let us know on our{' '}
-
+
discord
{' '}
to get it fixed as soon as possible.
@@ -155,7 +148,6 @@ export default function Welcome({
setMajor(value)}
onInputChange={(query: string) => updateQuery(query)}
options={results.map((major: { filMajor: string }) => major.filMajor)}
autoFocus
diff --git a/src/components/planner/CourseInfoHoverCard.tsx b/src/components/planner/CourseInfoHoverCard.tsx
index a4ea2a9c8..abafbd0ac 100644
--- a/src/components/planner/CourseInfoHoverCard.tsx
+++ b/src/components/planner/CourseInfoHoverCard.tsx
@@ -70,7 +70,7 @@ const CourseDescription = ({ description }: { description: string }) => {
/>{' '}
{
+ onClick={() => {
setShowMore(!showMore);
}}
>
diff --git a/src/components/planner/DegreePlanPDF/AcademicYearTable.tsx b/src/components/planner/DegreePlanPDF/AcademicYearTable.tsx
index 54359dee2..ef9b15d75 100644
--- a/src/components/planner/DegreePlanPDF/AcademicYearTable.tsx
+++ b/src/components/planner/DegreePlanPDF/AcademicYearTable.tsx
@@ -106,7 +106,18 @@ const AcademicTableHeaders = ({ elements }: { elements: string[] }) => {
);
};
-const AcademicTableRow = ({ elements }: { elements: any }) => {
+const AcademicTableRow = ({
+ elements,
+}: {
+ elements: (
+ | null
+ | number
+ | {
+ code: string;
+ title: string;
+ }
+ )[];
+}) => {
return (
{
>
- {elements[0] && elements[0].code}
+ {typeof elements[0] === 'object' &&
+ elements[0] !== null &&
+ 'code' in elements[0] &&
+ elements[0].code}
- {elements[0] && elements[0].title}
+ {typeof elements[0] === 'object' &&
+ elements[0] !== null &&
+ 'title' in elements[0] &&
+ elements[0].title}
{
- {elements[2] && elements[2].code}
+ {typeof elements[2] === 'object' &&
+ elements[2] !== null &&
+ 'code' in elements[2] &&
+ elements[2].code}
- {elements[2] && elements[2].title}
+ {typeof elements[2] === 'object' &&
+ elements[2] !== null &&
+ 'title' in elements[2] &&
+ elements[2].title}
{
- {elements[4] && elements[4].code}
+ {typeof elements[4] === 'object' &&
+ elements[4] !== null &&
+ 'code' in elements[4] &&
+ elements[4].code}
- {elements[4] && elements[4].title}
+ {typeof elements[4] === 'object' &&
+ elements[4] !== null &&
+ 'title' in elements[4] &&
+ elements[4].title}
Oops, we ran into an error! Please let us know on our{' '}
-
+
discord
{' '}
to get it fixed as soon as possible.
diff --git a/src/components/planner/SemesterContext.tsx b/src/components/planner/SemesterContext.tsx
index d3f370b9f..2fe70841a 100644
--- a/src/components/planner/SemesterContext.tsx
+++ b/src/components/planner/SemesterContext.tsx
@@ -184,7 +184,7 @@ export const SemestersContextProvider: FC = ({
const [selectedCourseIds, setSelectedCourseIds] = useState>(new Set());
- const [undoStack, dispatchUndo] = useReducer<
+ const [, dispatchUndo] = useReducer<
(state: UndoStackReducerState, action: UndoStackReducerAction) => UndoStackReducerState
>(
(state, action) => {
@@ -207,12 +207,6 @@ export const SemestersContextProvider: FC = ({
dispatchUndo({ type: 'popUndoStack' });
};
- useEffect(() => {
- if (undoStack.current) {
- undoStack.current();
- }
- }, [undoStack.current]);
-
const handleSelectCourses = (courseIds: string[]) => {
setSelectedCourseIds((existingCourseIds) => {
const newSet = new Set(existingCourseIds);
diff --git a/src/components/planner/Sidebar/Accordion.tsx b/src/components/planner/Sidebar/Accordion.tsx
index 49cd2c910..3cd6a0ead 100644
--- a/src/components/planner/Sidebar/Accordion.tsx
+++ b/src/components/planner/Sidebar/Accordion.tsx
@@ -1,4 +1,4 @@
-import React from 'react';
+import React, { useState } from 'react';
import ChevronIcon from '@/icons/ChevronIcon';
export default function Accordion({
@@ -12,7 +12,7 @@ export default function Accordion({
filled?: boolean;
startOpen?: boolean;
}) {
- const [open, setOpen] = React.useState(startOpen);
+ const [open, setOpen] = useState(startOpen);
function toggleAccordion() {
setOpen(!open);
}
diff --git a/src/components/planner/Sidebar/DraggableCourseList.tsx b/src/components/planner/Sidebar/DraggableCourseList.tsx
index a74fb33e9..e0f75a14b 100644
--- a/src/components/planner/Sidebar/DraggableCourseList.tsx
+++ b/src/components/planner/Sidebar/DraggableCourseList.tsx
@@ -1,5 +1,5 @@
import { UniqueIdentifier } from '@dnd-kit/core';
-import React from 'react';
+import React, { memo } from 'react';
import DraggableSidebarCourseItem from './SidebarCourseItem';
import { DraggableCourse } from '../types';
@@ -24,4 +24,4 @@ function DraggableCourseList({ courses, getDragId }: DraggableCourseListProps) {
);
}
-export default React.memo(DraggableCourseList);
+export default memo(DraggableCourseList);
diff --git a/src/components/planner/Sidebar/RecursiveRequirement.tsx b/src/components/planner/Sidebar/RecursiveRequirement.tsx
index 799415bd2..ec57d089a 100644
--- a/src/components/planner/Sidebar/RecursiveRequirement.tsx
+++ b/src/components/planner/Sidebar/RecursiveRequirement.tsx
@@ -133,7 +133,7 @@ export function RecursiveRequirement({
filled={req.filled}
>
<>
- {req.prefix_groups.map((req2, idx) => (
+ {req.prefix_groups.map((req2) => (
void;
carousel: boolean;
}) {
return (
diff --git a/src/components/planner/Sidebar/RequirementsContainer.tsx b/src/components/planner/Sidebar/RequirementsContainer.tsx
index b7593fce4..c69d0aafc 100644
--- a/src/components/planner/Sidebar/RequirementsContainer.tsx
+++ b/src/components/planner/Sidebar/RequirementsContainer.tsx
@@ -275,18 +275,12 @@ export default function RequirementsContainer({
*/
const [carousel, setCarousel] = useState(false);
- // Note: this logic hides overflow during sliding animation
- const [overflow, setOverflow] = useState(false);
-
function toggleCarousel() {
- setOverflow(true);
setCarousel(!carousel);
}
return (
{
+interface SearchBarProps extends ComponentPropsWithoutRef<'div'> {
updateQuery: (query: string) => void;
placeholder: string;
}
diff --git a/src/components/planner/Sidebar/Sidebar.tsx b/src/components/planner/Sidebar/Sidebar.tsx
index 6a29f2bb4..d78177d9d 100644
--- a/src/components/planner/Sidebar/Sidebar.tsx
+++ b/src/components/planner/Sidebar/Sidebar.tsx
@@ -228,7 +228,7 @@ function CourseSelectorContainer({
@@ -238,7 +238,7 @@ function CourseSelectorContainer({
It seems like your major is no longer supported! Contact us to have it added.
-
+
REPORT ERROR
diff --git a/src/components/planner/Sidebar/SidebarCourseItem.tsx b/src/components/planner/Sidebar/SidebarCourseItem.tsx
index 6843cdcff..bfb03cb47 100644
--- a/src/components/planner/Sidebar/SidebarCourseItem.tsx
+++ b/src/components/planner/Sidebar/SidebarCourseItem.tsx
@@ -2,7 +2,14 @@ import { UniqueIdentifier, useDraggable } from '@dnd-kit/core';
import { CSS } from '@dnd-kit/utilities';
import CheckIcon from '@mui/icons-material/Check';
import DragIndicatorIcon from '@mui/icons-material/DragIndicator';
-import React, { ComponentPropsWithoutRef, forwardRef, useState, useRef, useEffect } from 'react';
+import React, {
+ ComponentPropsWithoutRef,
+ forwardRef,
+ memo,
+ useState,
+ useRef,
+ useEffect,
+} from 'react';
import { getSemesterHourFromCourseCode } from '@/utils/utilFunctions';
@@ -17,7 +24,7 @@ interface SidebarCourseItemProps extends ComponentPropsWithoutRef<'div'> {
}
/** UI Implementation of sidebar course */
/* eslint-disable react/prop-types */
-export const SidebarCourseItem = React.memo(
+export const SidebarCourseItem = memo(
forwardRef
(function SidebarCourseItem(
{ course, isDragging, ...props },
ref,
diff --git a/src/components/planner/Tiles/SemesterCourseItem.tsx b/src/components/planner/Tiles/SemesterCourseItem.tsx
index dee3eb7c8..196eb9966 100644
--- a/src/components/planner/Tiles/SemesterCourseItem.tsx
+++ b/src/components/planner/Tiles/SemesterCourseItem.tsx
@@ -1,6 +1,6 @@
import { UniqueIdentifier, useDraggable } from '@dnd-kit/core';
import DragIndicatorIcon from '@mui/icons-material/DragIndicator';
-import React, { ComponentPropsWithoutRef, FC, forwardRef, useState, useRef } from 'react';
+import React, { ComponentPropsWithoutRef, FC, forwardRef, memo, useState, useRef } from 'react';
import Skeleton from 'react-loading-skeleton';
import Checkbox from '@/components/Checkbox';
@@ -36,7 +36,7 @@ export interface SemesterCourseItemProps extends ComponentPropsWithoutRef<'div'>
/** UI implementation of a semester course */
/* eslint-disable react/prop-types */
-export const MemoizedSemesterCourseItem = React.memo(
+export const MemoizedSemesterCourseItem = memo(
forwardRef(function SemesterCourseItem(
{
course,
@@ -287,4 +287,4 @@ const DraggableSemesterCourseItem: FC = ({
);
};
-export default React.memo(DraggableSemesterCourseItem);
+export default memo(DraggableSemesterCourseItem);
diff --git a/src/components/planner/Tiles/SemesterTile.tsx b/src/components/planner/Tiles/SemesterTile.tsx
index 823278f22..88a54438b 100644
--- a/src/components/planner/Tiles/SemesterTile.tsx
+++ b/src/components/planner/Tiles/SemesterTile.tsx
@@ -1,5 +1,5 @@
import { UniqueIdentifier, useDroppable } from '@dnd-kit/core';
-import React, { FC, forwardRef, useState, useRef, useImperativeHandle } from 'react';
+import React, { FC, forwardRef, memo, useState, useRef, useImperativeHandle } from 'react';
import ChevronIcon from '@/icons/ChevronIcon';
import LockIcon from '@/icons/LockIcon';
@@ -23,7 +23,7 @@ export interface SemesterTileProps {
* Strictly UI implementation of a semester tile
*/
/* eslint-disable react/prop-types */
-export const MemoizedSemesterTile = React.memo(
+export const MemoizedSemesterTile = memo(
forwardRef(function SemesterTile(
{ semester, getDragId },
outerRef,
@@ -223,4 +223,4 @@ const DroppableSemesterTile: FC = ({
);
};
-export default React.memo(DroppableSemesterTile);
+export default memo(DroppableSemesterTile);
diff --git a/src/components/planner/Toolbar/EditablePlanTitle.tsx b/src/components/planner/Toolbar/EditablePlanTitle.tsx
index 490180581..03a10fe2e 100644
--- a/src/components/planner/Toolbar/EditablePlanTitle.tsx
+++ b/src/components/planner/Toolbar/EditablePlanTitle.tsx
@@ -1,4 +1,4 @@
-import React from 'react';
+import React, { useState } from 'react';
import { toast } from 'react-toastify';
import PencilIcon from '@/icons/PencilIcon';
@@ -11,8 +11,8 @@ export default function EditableMajorTitle({
initialTitle: string;
planId: string;
}) {
- const [title, setTitle] = React.useState(initialTitle);
- const [editTitle, setEditTitle] = React.useState(false);
+ const [title, setTitle] = useState(initialTitle);
+ const [editTitle, setEditTitle] = useState(false);
const updatePlanName = trpc.plan.updatePlanTitle.useMutation();
diff --git a/src/components/planner/Toolbar/Toolbar.tsx b/src/components/planner/Toolbar/Toolbar.tsx
index 279478e96..38cacffc3 100644
--- a/src/components/planner/Toolbar/Toolbar.tsx
+++ b/src/components/planner/Toolbar/Toolbar.tsx
@@ -49,7 +49,7 @@ const Toolbar: FC = ({
const { data: coursesData } = q;
- const [{ loading, error, url }, update] = usePDF({
+ const [{ error, url }, update] = usePDF({
document: (
{
dataSet: T[];
- keys: any;
+ keys: string[];
threshold?: number;
}
diff --git a/src/components/search/search.ts b/src/components/search/search.ts
index 57d2395c8..3e8b14176 100644
--- a/src/components/search/search.ts
+++ b/src/components/search/search.ts
@@ -1,4 +1,4 @@
-import React from 'react';
+import { useEffect, useState } from 'react';
interface SearchParams {
getData: () => Promise;
@@ -23,14 +23,14 @@ const useSearch = ({
filterFn,
constraints = [0, 20],
}: SearchParams): SearchReturn => {
- const [results, setResults] = React.useState([]);
- const [err, setErr] = React.useState();
+ const [results, setResults] = useState([]);
+ const [err, setErr] = useState();
const getResults = () => {
return results;
};
- React.useEffect(() => updateQuery(initialQuery), []);
+ useEffect(() => updateQuery(initialQuery), []);
// TODO: Insert logc for filtering w/ chips
// TODO: Update filtering code to deal with data from Nebula API
diff --git a/src/components/template/CustomPlan.tsx b/src/components/template/CustomPlan.tsx
index 4002e96f3..c27e4fe1d 100644
--- a/src/components/template/CustomPlan.tsx
+++ b/src/components/template/CustomPlan.tsx
@@ -290,7 +290,6 @@ export default function CustomPlan({ onDismiss }: { onDismiss: () => void }) {
onValueChange={(value) => setMajor(value)}
onInputChange={(query: string) => updateQuery(query)}
options={results.map((major: { filMajor: string }) => major.filMajor)}
- autoFocus
>
@@ -433,7 +432,7 @@ export default function CustomPlan({ onDismiss }: { onDismiss: () => void }) {
return (
<>
Oops, we ran into an error! Please let us know on our{' '}
-
+
discord
{' '}
to get it fixed as soon as possible.
diff --git a/src/components/template/NewPlan.tsx b/src/components/template/NewPlan.tsx
index 9f1f56b96..537d569c5 100644
--- a/src/components/template/NewPlan.tsx
+++ b/src/components/template/NewPlan.tsx
@@ -14,7 +14,7 @@ export default function CustomPlan({ onDismiss }: { onDismiss: () => void }) {
const [major, setMajor] = useState(null);
const [planNameError, setPlanNameError] = useState(false);
const [majorError, setMajorError] = useState(false);
- const { majors, err } = useMajors();
+ const { majors } = useMajors();
const setErrors = () => {
setPlanNameError(name === '');
setMajorError(major === null);
@@ -106,7 +106,6 @@ export default function CustomPlan({ onDismiss }: { onDismiss: () => void }) {
onValueChange={(value) => setMajor(value)}
onInputChange={(query: string) => updateQuery(query)}
options={results.map((major: { filMajor: string }) => major.filMajor)}
- autoFocus
>
diff --git a/src/components/template/TemplateView.tsx b/src/components/template/TemplateView.tsx
index b9880a44e..c5f1470fd 100644
--- a/src/components/template/TemplateView.tsx
+++ b/src/components/template/TemplateView.tsx
@@ -1,6 +1,5 @@
import router from 'next/router';
-import { useState } from 'react'; //nprogress module
-import React from 'react';
+import React, { useEffect, useState } from 'react'; //nprogress module
import AutoCompleteMajor from '@/components/AutoCompleteMajor';
import { trpc } from '@/utils/trpc';
@@ -45,7 +44,7 @@ export default function TemplateView({ onDismiss }: { onDismiss: () => void }) {
constraints: [0, 100],
});
- React.useEffect(() => {
+ useEffect(() => {
updateQuery('');
}, [isLoading]);
@@ -130,7 +129,6 @@ export default function TemplateView({ onDismiss }: { onDismiss: () => void }) {
onValueChange={(value) => setMajor(value)}
onInputChange={(query: string) => updateQuery(query)}
options={results.map((major: { filMajor: string }) => major.filMajor)}
- autoFocus
>
diff --git a/src/icons/ContactIcon.tsx b/src/icons/ContactIcon.tsx
deleted file mode 100644
index d8ac2e19d..000000000
--- a/src/icons/ContactIcon.tsx
+++ /dev/null
@@ -1,17 +0,0 @@
-import { FC, SVGProps } from 'react';
-
-const ContactIcon: FC> = (props) => {
- return (
-
-
-
- );
-};
-
-export default ContactIcon;
diff --git a/src/icons/DuplicateIcon.tsx b/src/icons/DuplicateIcon.tsx
index 72b6ed999..fae2ab75a 100644
--- a/src/icons/DuplicateIcon.tsx
+++ b/src/icons/DuplicateIcon.tsx
@@ -2,7 +2,14 @@ import { FC, SVGProps } from 'react';
const DuplicateIcon: FC> = (props) => {
return (
-
+
> = (props) => {
- return (
-
-
-
- );
-};
-
-export default FeedbackIcon;
diff --git a/src/icons/FilterIcon.tsx b/src/icons/FilterIcon.tsx
index b948a7456..83cc86d66 100644
--- a/src/icons/FilterIcon.tsx
+++ b/src/icons/FilterIcon.tsx
@@ -2,7 +2,14 @@ import { FC, SVGProps } from 'react';
const FilterIcon: FC> = (props) => {
return (
-
+
> = (props) => {
return (
-
+
): JSX.Element {
return (
-
+
> = (props) => {
fill="inherit"
xmlns="http://www.w3.org/2000/svg"
xmlnsXlink="http://www.w3.org/1999/xlink"
+ {...props}
>
diff --git a/src/icons/LogoutIcon.tsx b/src/icons/LogoutIcon.tsx
index e4625d5f9..278f89ca5 100644
--- a/src/icons/LogoutIcon.tsx
+++ b/src/icons/LogoutIcon.tsx
@@ -2,7 +2,14 @@ import { SVGProps } from 'react';
export default function LogoutIcon(props: SVGProps): JSX.Element {
return (
-
+
): JSX.Element {
return (
-
+
): JSX.Element {
return (
-
+
): JSX.Element {
return (
-
+
(initialOnboardingData);
- const [isModifyLoading, setIsModifyLoading] = React.useState(false);
+ const [isModifyLoading, setIsModifyLoading] = useState(false);
const handleOnboardingDataUpdate = (updatedFields: Partial) => {
setOnboardingData({ ...onboardingData, ...updatedFields });
@@ -69,8 +69,6 @@ export default function OnboardingPage() {
const [page, setPage] = useState(0);
const [validate, setValidate] = useState([true, true, true]);
- const [validNextPage, setValidNextPage] = useState(false);
-
const router = useRouter();
const validateForm = (value: boolean) => {
@@ -100,7 +98,6 @@ export default function OnboardingPage() {
key={0}
handleChange={handleOnboardingDataUpdate as (updatedFields: Partial) => void}
data={{ name, startSemester, endSemester }}
- semesterOptions={{ startSemesters, endSemesters }}
handleValidate={validateForm}
/>,
];
@@ -112,9 +109,7 @@ export default function OnboardingPage() {
}
};
- useEffect(() => {
- setValidNextPage(validate[page]);
- });
+ const validNextPage = validate[page];
// TODO: Find better way to structure this glorified form.
return (
diff --git a/src/pages/auth/login.tsx b/src/pages/auth/login.tsx
index b03e94ef9..19b4c17c7 100644
--- a/src/pages/auth/login.tsx
+++ b/src/pages/auth/login.tsx
@@ -42,7 +42,7 @@ export function AuthPage(props: {
const inputRef = useRef(null);
// Fetch courses here and put in cache
- const q = trpc.courses.publicGetAllCourses.useQuery(undefined, {
+ trpc.courses.publicGetAllCourses.useQuery(undefined, {
staleTime: Infinity,
cacheTime: Infinity,
refetchOnWindowFocus: false,
diff --git a/src/server/trpc/router/plan.ts b/src/server/trpc/router/plan.ts
index 18279d88c..3371bb180 100644
--- a/src/server/trpc/router/plan.ts
+++ b/src/server/trpc/router/plan.ts
@@ -527,7 +527,8 @@ export const planRouter = router({
const bypasses = [...degreeRequirements.bypasses, requirement];
- const updatedDegreeRequirements = await ctx.prisma.degreeRequirements.update({
+ //update degree plan requirements
+ await ctx.prisma.degreeRequirements.update({
where: {
plan: { userId: ctx.session.user.id },
id: degreeRequirements.id,
diff --git a/src/utils/useTaskQueue.ts b/src/utils/useTaskQueue.ts
index f337de2a5..52c4bf7da 100644
--- a/src/utils/useTaskQueue.ts
+++ b/src/utils/useTaskQueue.ts
@@ -1,4 +1,4 @@
-import React from 'react';
+import { useEffect, useRef } from 'react';
export type Task = {
func: (args: T) => Promise;
@@ -15,9 +15,9 @@ export function useTaskQueue(params: { shouldProcess: boolean }): {
isProcessing: boolean;
addTask: (task: Task) => void;
} {
- const queue = React.useRef({ isProcessing: false, tasks: [] });
+ const queue = useRef({ isProcessing: false, tasks: [] });
- React.useEffect(() => {
+ useEffect(() => {
if (!params.shouldProcess || queue.current.tasks.length === 0) return;
if (queue.current.isProcessing) return;
diff --git a/vercel-build-ignore.sh b/vercel-build-ignore.sh
index 7965f5664..a56a24062 100644
--- a/vercel-build-ignore.sh
+++ b/vercel-build-ignore.sh
@@ -1,3 +1,4 @@
+# This cancels Vercel builds until manually started to avoid too many Neon branhces
echo "VERCEL_GIT_COMMIT_REF: $VERCEL_GIT_COMMIT_REF"
if [[ "$VERCEL_GIT_COMMIT_REF" == "develop" || "$VERCEL_GIT_COMMIT_REF" == "main" ]] ; then