From f58d3e3ef4f51be7fb2be1321eeca92c51010b2a Mon Sep 17 00:00:00 2001 From: Kilian Date: Tue, 25 Jun 2024 15:50:22 +0200 Subject: [PATCH 1/4] Add Navigation component Need to fix lib exports first --- ui/src/components/Navigation.tsx | 27 +++++++++++++++++++++++++++ ui/styles/tailwind.css | 22 ++++++++++++++++++++++ 2 files changed, 49 insertions(+) create mode 100644 ui/src/components/Navigation.tsx diff --git a/ui/src/components/Navigation.tsx b/ui/src/components/Navigation.tsx new file mode 100644 index 0000000..93b1ff1 --- /dev/null +++ b/ui/src/components/Navigation.tsx @@ -0,0 +1,27 @@ +import { Box, Icon, Row } from "@uug-ai/ui"; +import React from "react"; + +const Navigation = () => { + return ( + + + + {/* Navigation Main (add new content here) */} + + + + + + + + + + {/* end of Navigation main */} + + + + + ); +}; + +export default Navigation; diff --git a/ui/styles/tailwind.css b/ui/styles/tailwind.css index 54f81be..5ab0b9e 100644 --- a/ui/styles/tailwind.css +++ b/ui/styles/tailwind.css @@ -695,6 +695,10 @@ video { margin-top: auto; } +.mr-2 { + margin-right: 0.5rem; +} + .block { display: block; } @@ -807,6 +811,10 @@ video { height: 100%; } +.h-screen { + height: 100vh; +} + .min-h-screen { min-height: 100vh; } @@ -896,6 +904,10 @@ video { flex-shrink: 1; } +.flex-grow { + flex-grow: 1; +} + .grow { flex-grow: 1; } @@ -1251,6 +1263,11 @@ video { background-color: rgb(229 231 235 / var(--tw-bg-opacity)); } +.bg-slate-100 { + --tw-bg-opacity: 1; + background-color: rgb(241 245 249 / var(--tw-bg-opacity)); +} + .bg-gradient-to-br { background-image: linear-gradient(to bottom right, var(--tw-gradient-stops)); } @@ -1562,6 +1579,11 @@ video { color: rgb(185 28 28 / var(--tw-text-opacity)); } +.text-red-500 { + --tw-text-opacity: 1; + color: rgb(239 68 68 / var(--tw-text-opacity)); +} + .underline { text-decoration-line: underline; } From ebe6ee3aa6eb87bb4b37028ec6a4823739f6c582 Mon Sep 17 00:00:00 2001 From: Kilian Date: Tue, 25 Jun 2024 17:07:47 +0200 Subject: [PATCH 2/4] Add Navigation to dashboard layout --- ui/package.json | 2 +- ui/src/app/dashboard/layout.tsx | 12 ++---- ui/src/components/Navigation.tsx | 10 ++++- ui/styles/tailwind.css | 68 ++++++++++++++++++++++++++++++++ ui/yarn.lock | 14 +++++-- 5 files changed, 91 insertions(+), 15 deletions(-) diff --git a/ui/package.json b/ui/package.json index 9f8c240..266fe3c 100644 --- a/ui/package.json +++ b/ui/package.json @@ -15,7 +15,7 @@ "@hookform/resolvers": "^3.5.0", "@reduxjs/toolkit": "^2.2.5", "@testing-library/jest-dom": "^6.4.6", - "@uug-ai/ui": "1.0.35", + "@uug-ai/ui": "^1.0.36", "autoprefixer": "^10.4.19", "cookies-next": "^4.2.1", "next": "14", diff --git a/ui/src/app/dashboard/layout.tsx b/ui/src/app/dashboard/layout.tsx index 1b5d759..ff91d76 100644 --- a/ui/src/app/dashboard/layout.tsx +++ b/ui/src/app/dashboard/layout.tsx @@ -1,5 +1,6 @@ +import Navigation from "@/components/Navigation"; import SignOutButton from "@/components/SignOutButton"; -import { Row, Stack } from "@/components/ui"; +import { Row, Stack } from "../../components/ui"; import { authOptions } from "@/utils/auth"; import { getServerSession } from "next-auth"; @@ -12,14 +13,7 @@ export default async function DashboardLayout({ return (
- {/* Mock navigation element with session info */} - -
-

NAVIGATION

-
{JSON.stringify(session, null, 2)}
-
- -
+
{children}
diff --git a/ui/src/components/Navigation.tsx b/ui/src/components/Navigation.tsx index 93b1ff1..5d9f103 100644 --- a/ui/src/components/Navigation.tsx +++ b/ui/src/components/Navigation.tsx @@ -1,4 +1,12 @@ -import { Box, Icon, Row } from "@uug-ai/ui"; +import { + Box, + Icon, + Row, + NavigationHeader, + NavItem, + NavigationSocials, + NavigationFooter, +} from "./ui"; import React from "react"; const Navigation = () => { diff --git a/ui/styles/tailwind.css b/ui/styles/tailwind.css index 5ab0b9e..11e692e 100644 --- a/ui/styles/tailwind.css +++ b/ui/styles/tailwind.css @@ -667,6 +667,10 @@ video { top: 1.25rem; } +.top-3 { + top: 0.75rem; +} + .isolate { isolation: isolate; } @@ -699,6 +703,22 @@ video { margin-right: 0.5rem; } +.mb-2 { + margin-bottom: 0.5rem; +} + +.ml-2 { + margin-left: 0.5rem; +} + +.ml-5 { + margin-left: 1.25rem; +} + +.mt-2 { + margin-top: 0.5rem; +} + .block { display: block; } @@ -990,6 +1010,10 @@ video { gap: 0.25rem; } +.gap-2 { + gap: 0.5rem; +} + .space-x-10 > :not([hidden]) ~ :not([hidden]) { --tw-space-x-reverse: 0; margin-right: calc(2.5rem * var(--tw-space-x-reverse)); @@ -1268,6 +1292,11 @@ video { background-color: rgb(241 245 249 / var(--tw-bg-opacity)); } +.bg-slate-500 { + --tw-bg-opacity: 1; + background-color: rgb(100 116 139 / var(--tw-bg-opacity)); +} + .bg-gradient-to-br { background-image: linear-gradient(to bottom right, var(--tw-gradient-stops)); } @@ -1340,6 +1369,10 @@ video { padding: 1rem; } +.p-7 { + padding: 1.75rem; +} + .px-20 { padding-left: 5rem; padding-right: 5rem; @@ -1395,6 +1428,22 @@ video { padding-top: 2rem; } +.pb-4 { + padding-bottom: 1rem; +} + +.pl-5 { + padding-left: 1.25rem; +} + +.pr-10 { + padding-right: 2.5rem; +} + +.pt-5 { + padding-top: 1.25rem; +} + .text-left { text-align: left; } @@ -1451,6 +1500,11 @@ video { line-height: 2.25rem; } +.text-xs { + font-size: 0.75rem; + line-height: 1rem; +} + .font-bold { font-weight: 700; } @@ -1584,6 +1638,16 @@ video { color: rgb(239 68 68 / var(--tw-text-opacity)); } +.text-gray-600 { + --tw-text-opacity: 1; + color: rgb(75 85 99 / var(--tw-text-opacity)); +} + +.text-green-700 { + --tw-text-opacity: 1; + color: rgb(21 128 61 / var(--tw-text-opacity)); +} + .underline { text-decoration-line: underline; } @@ -1816,4 +1880,8 @@ video { .disabled\:border-0:disabled { border-width: 0px; +} + +.group:hover .group-hover\:opacity-100 { + opacity: 1; } \ No newline at end of file diff --git a/ui/yarn.lock b/ui/yarn.lock index fbc2ea4..3b9c0b5 100644 --- a/ui/yarn.lock +++ b/ui/yarn.lock @@ -2877,10 +2877,10 @@ resolved "https://registry.yarnpkg.com/@ungap/structured-clone/-/structured-clone-1.2.0.tgz#756641adb587851b5ccb3e095daf27ae581c8406" integrity sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ== -"@uug-ai/ui@1.0.35": - version "1.0.35" - resolved "https://registry.yarnpkg.com/@uug-ai/ui/-/ui-1.0.35.tgz#3daab5491ac3d3a2d33d9b47af1f3d07b9aec2e8" - integrity sha512-/ZNHGNt1NWsYk1XTKmUlLSsSqelWXuo3UiIOCxwE2DNeTTfvboB8/OpXOCgKYpTKtoay5Zs85g+WyE6rrLFkbg== +"@uug-ai/ui@^1.0.36": + version "1.0.36" + resolved "https://registry.yarnpkg.com/@uug-ai/ui/-/ui-1.0.36.tgz#d52b7d7be7de9183f4f225d46348c77de4792cb7" + integrity sha512-wWm7tCiObTGk6jZYGUohEDozRz3Q6O/w3abw3hlPvb3vckem1n9ODSI8HoAm7Wn9mM7TdZTasNxSFqB9GlvOuQ== dependencies: "@storybook/addon-essentials" "^8.0.9" "@storybook/addon-interactions" "^8.0.9" @@ -2891,6 +2891,7 @@ class-variance-authority "^0.7.0" clsx "^2.0.0" next "^14.2.3" + pigeon-maps "^0.21.6" react "^18" react-dom "^18" react-webcam "^7.2.0" @@ -7336,6 +7337,11 @@ pify@^4.0.1: resolved "https://registry.yarnpkg.com/pify/-/pify-4.0.1.tgz#4b2cd25c50d598735c50292224fd8c6df41e3231" integrity sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g== +pigeon-maps@^0.21.6: + version "0.21.6" + resolved "https://registry.yarnpkg.com/pigeon-maps/-/pigeon-maps-0.21.6.tgz#e9b89e614fa46a94c7e86984cf8e6794a1eccc0e" + integrity sha512-6io58lhpbtVT/DUKDoOqsjeAFW46Nfe+gr4PX/kmD1dyJxfb8WaT4hcgwcmM8dJdkyfibgLHo59Uo2o2/xscaQ== + pirates@^4.0.1, pirates@^4.0.4, pirates@^4.0.6: version "4.0.6" resolved "https://registry.yarnpkg.com/pirates/-/pirates-4.0.6.tgz#3018ae32ecfcff6c29ba2267cbf21166ac1f36b9" From 321a7dacd09901b0e32a566396917f2193f655ef Mon Sep 17 00:00:00 2001 From: Kilian Date: Wed, 26 Jun 2024 11:12:01 +0200 Subject: [PATCH 3/4] Fix Jest tests --- ui/__tests__/SignOut.test.js | 22 ++++++++++++++-------- ui/jest.config.ts | 2 +- ui/jest.setup.ts | 2 ++ ui/src/components/Navigation.tsx | 2 ++ ui/src/components/SignOutButton.tsx | 1 - 5 files changed, 19 insertions(+), 10 deletions(-) create mode 100644 ui/jest.setup.ts diff --git a/ui/__tests__/SignOut.test.js b/ui/__tests__/SignOut.test.js index a5c9daf..2698f2a 100644 --- a/ui/__tests__/SignOut.test.js +++ b/ui/__tests__/SignOut.test.js @@ -1,23 +1,29 @@ -// SignOutButton.test.js (or .test.tsx if using TypeScript) +// __tests__/SignOut.test.js import { render, screen } from "@testing-library/react"; -import "@testing-library/jest-dom"; +import userEvent from "@testing-library/user-event"; import SignOutButton from "../src/components/SignOutButton"; import { signOut } from "next-auth/react"; -// Mock next-auth/react's signOut function +// Mock next-auth/react jest.mock("next-auth/react", () => ({ signOut: jest.fn(), })); describe("SignOutButton", () => { it('renders "Sign out" button', () => { - // Render the SignOutButton component render(); + const signOutButton = screen.getByRole("button", { name: /sign out/i }); + expect(signOutButton).toBeInTheDocument(); + }); + + it("calls signOut when button is clicked", async () => { + render(); + const signOutButton = screen.getByRole("button", { name: /sign out/i }); - // Get the button element - const buttonElement = screen.getByRole("button", { name: /Sign out/i }); + await userEvent.click(signOutButton); - // Check if the button is in the document - expect(buttonElement).toBeInTheDocument(); + expect(signOut).toHaveBeenCalledWith({ + callbackUrl: "/signin", + }); }); }); diff --git a/ui/jest.config.ts b/ui/jest.config.ts index bec0e28..c399615 100644 --- a/ui/jest.config.ts +++ b/ui/jest.config.ts @@ -51,5 +51,5 @@ module.exports = { "/node_modules/", "^.+\\.module\\.(css|sass|scss)$", ], - setupFilesAfterEnv: ["./jest.setup.js"], + setupFilesAfterEnv: ["./jest.setup.ts"], }; diff --git a/ui/jest.setup.ts b/ui/jest.setup.ts new file mode 100644 index 0000000..20d43f5 --- /dev/null +++ b/ui/jest.setup.ts @@ -0,0 +1,2 @@ +import "@testing-library/jest-dom"; +import "next-router-mock/dynamic-routes"; diff --git a/ui/src/components/Navigation.tsx b/ui/src/components/Navigation.tsx index 5d9f103..2b92151 100644 --- a/ui/src/components/Navigation.tsx +++ b/ui/src/components/Navigation.tsx @@ -1,3 +1,4 @@ +import SignOutButton from "./SignOutButton"; import { Box, Icon, @@ -27,6 +28,7 @@ const Navigation = () => { {/* end of Navigation main */} + ); diff --git a/ui/src/components/SignOutButton.tsx b/ui/src/components/SignOutButton.tsx index c29247f..d87c38b 100644 --- a/ui/src/components/SignOutButton.tsx +++ b/ui/src/components/SignOutButton.tsx @@ -1,7 +1,6 @@ "use client"; import { signOut } from "next-auth/react"; -import { useRouter } from "next/navigation"; export default function SignOutButton() { const handleSignOut = () => { From dfb6ed2f1497a3f1fb9d6b8a7b479479d818de27 Mon Sep 17 00:00:00 2001 From: Kilian Date: Wed, 26 Jun 2024 14:45:09 +0200 Subject: [PATCH 4/4] Adjust dashboard layout --- ui/src/app/dashboard/layout.tsx | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/ui/src/app/dashboard/layout.tsx b/ui/src/app/dashboard/layout.tsx index ff91d76..95c7e17 100644 --- a/ui/src/app/dashboard/layout.tsx +++ b/ui/src/app/dashboard/layout.tsx @@ -1,21 +1,15 @@ import Navigation from "@/components/Navigation"; -import SignOutButton from "@/components/SignOutButton"; -import { Row, Stack } from "../../components/ui"; -import { authOptions } from "@/utils/auth"; -import { getServerSession } from "next-auth"; +import { Row } from "@/components/ui"; export default async function DashboardLayout({ - children, // will be a page or nested layout + children, }: { children: React.ReactNode; }) { - const session = await getServerSession(authOptions); return ( -
- - -
{children}
-
-
+ + +
{children}
+
); }