Skip to content

Commit

Permalink
feat: [WD-12912] Add Application layout components (#874)
Browse files Browse the repository at this point in the history
## Done

- Implementation of Application Layout Components across:
- Navigation, Root, Statusbar, BaseLayout, CustomLayout, and Layout

## QA

1. Run the LXD-UI:
- On the demo server via the link posted by @webteam-app below. This is
only available for PRs created by collaborators of the repo. Ask
@mas-who or @edlerd for access.
- With a local copy of this branch, [build and run as described in the
docs](../CONTRIBUTING.md#setting-up-for-development).
2. Perform the following QA steps:
- [List the steps to QA the new feature(s) or prove that a bug has been
resolved]

## Screenshots
  • Loading branch information
Kxiru authored Sep 3, 2024
2 parents 51240de + 99079c3 commit 6f834dd
Show file tree
Hide file tree
Showing 6 changed files with 81 additions and 100 deletions.
10 changes: 3 additions & 7 deletions src/Root.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { FC } from "react";
import Navigation from "components/Navigation";
import { QueuedNotification } from "@canonical/react-components";
import { Application, QueuedNotification } from "@canonical/react-components";
import { QueryClient, QueryClientProvider } from "@tanstack/react-query";
import { AuthProvider } from "context/auth";
import { EventQueueProvider } from "context/eventQueue";
Expand Down Expand Up @@ -32,18 +32,14 @@ const Root: FC = () => {
<InstanceLoadingProvider>
<OperationsProvider>
<EventQueueProvider>
<div
id="l-application"
className="l-application"
role="presentation"
>
<Application id="l-application">
<Navigation />
<ErrorBoundary fallback={ErrorPage}>
<App />
<Events />
<StatusBar />
</ErrorBoundary>
</div>
</Application>
</EventQueueProvider>
</OperationsProvider>
</InstanceLoadingProvider>
Expand Down
23 changes: 11 additions & 12 deletions src/components/BaseLayout.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { FC, ReactNode } from "react";
import classnames from "classnames";
import { AppMain, Panel } from "@canonical/react-components";

interface Props {
title: string | ReactNode;
Expand All @@ -17,17 +17,16 @@ const BaseLayout: FC<Props> = ({
contentClassName,
}: Props) => {
return (
<main className={classnames("l-main", mainClassName)}>
<div className="p-panel">
<div className="p-panel__header">
<h1 className="p-panel__title">{title}</h1>
{controls && <div className="p-panel__controls">{controls}</div>}
</div>
<div className={classnames("p-panel__content", contentClassName)}>
{children}
</div>
</div>
</main>
<AppMain className={mainClassName}>
<Panel
title={title}
controls={controls}
wrapContent
contentClassName={contentClassName}
>
{children}
</Panel>
</AppMain>
);
};

Expand Down
15 changes: 6 additions & 9 deletions src/components/CustomLayout.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { FC, ReactNode } from "react";
import classnames from "classnames";
import { AppMain, Panel } from "@canonical/react-components";

interface Props {
header?: ReactNode;
Expand All @@ -15,14 +15,11 @@ const CustomLayout: FC<Props> = ({
contentClassName,
}: Props) => {
return (
<main className={classnames("l-main", mainClassName)}>
<div className="p-panel">
{header}
<div className={classnames("p-panel__content", contentClassName)}>
{children}
</div>
</div>
</main>
<AppMain className={mainClassName}>
<Panel contentClassName={contentClassName} header={header}>
{children}
</Panel>
</AppMain>
);
};

Expand Down
107 changes: 48 additions & 59 deletions src/components/Navigation.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { FC, MouseEvent, useEffect, useState } from "react";
import { Button, Icon } from "@canonical/react-components";
import { Button, Icon, SideNavigationItem } from "@canonical/react-components";
import { useAuth } from "context/auth";
import classnames from "classnames";
import Logo from "./Logo";
Expand Down Expand Up @@ -187,7 +187,7 @@ const Navigation: FC = () => {
activeProject={projectName}
/>
</li>
<li className="p-side-navigation__item">
<SideNavigationItem>
<NavLink
to={`/ui/project/${projectName}/instances`}
title={`Instances (${projectName})`}
Expand All @@ -199,8 +199,8 @@ const Navigation: FC = () => {
/>{" "}
Instances
</NavLink>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<NavLink
to={`/ui/project/${projectName}/profiles`}
title={`Profiles (${projectName})`}
Expand All @@ -212,8 +212,9 @@ const Navigation: FC = () => {
/>{" "}
Profiles
</NavLink>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>

<SideNavigationItem>
<NavLink
to={`/ui/project/${projectName}/networks`}
title={`Networks (${projectName})`}
Expand All @@ -225,8 +226,8 @@ const Navigation: FC = () => {
/>{" "}
Networks
</NavLink>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<NavAccordion
baseUrl={`/ui/project/${projectName}/storage`}
title={`Storage (${projectName})`}
Expand All @@ -236,8 +237,7 @@ const Navigation: FC = () => {
open={openNavMenus.includes("storage")}
>
{[
<li
className="p-side-navigation__item"
<SideNavigationItem
key={`/ui/project/${projectName}/storage/pools`}
>
<NavLink
Expand All @@ -248,9 +248,8 @@ const Navigation: FC = () => {
>
Pools
</NavLink>
</li>,
<li
className="p-side-navigation__item"
</SideNavigationItem>,
<SideNavigationItem
key={`/ui/project/${projectName}/storage/volumes`}
>
<NavLink
Expand All @@ -261,11 +260,10 @@ const Navigation: FC = () => {
>
Volumes
</NavLink>
</li>,
</SideNavigationItem>,
...(hasCustomVolumeIso
? [
<li
className="p-side-navigation__item"
<SideNavigationItem
key={`/ui/project/${projectName}/storage/custom-isos`}
>
<NavLink
Expand All @@ -276,13 +274,13 @@ const Navigation: FC = () => {
>
Custom ISOs
</NavLink>
</li>,
</SideNavigationItem>,
]
: []),
]}
</NavAccordion>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<NavLink
to={`/ui/project/${projectName}/images`}
title={`Images (${projectName})`}
Expand All @@ -294,8 +292,8 @@ const Navigation: FC = () => {
/>{" "}
Images
</NavLink>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<NavLink
to={`/ui/project/${projectName}/configuration`}
title={`Configuration (${projectName})`}
Expand All @@ -307,9 +305,9 @@ const Navigation: FC = () => {
/>{" "}
Configuration
</NavLink>
</li>
</SideNavigationItem>
<hr className="is-dark navigation-hr" />
<li className="p-side-navigation__item">
<SideNavigationItem>
<NavLink
to="/ui/cluster"
title="Cluster"
Expand All @@ -321,8 +319,8 @@ const Navigation: FC = () => {
/>{" "}
Cluster
</NavLink>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<NavLink
to={`/ui/operations`}
title={`Operations (${projectName})`}
Expand All @@ -334,9 +332,9 @@ const Navigation: FC = () => {
/>{" "}
Operations
</NavLink>
</li>
</SideNavigationItem>
{!isRestricted && (
<li className="p-side-navigation__item">
<SideNavigationItem>
<NavLink
to="/ui/warnings"
title="Warnings"
Expand All @@ -348,10 +346,10 @@ const Navigation: FC = () => {
/>{" "}
Warnings
</NavLink>
</li>
</SideNavigationItem>
)}
{enablePermissions && (
<li className="p-side-navigation__item">
<SideNavigationItem>
<NavAccordion
baseUrl="/ui/permissions"
title={`Permissions`}
Expand All @@ -361,10 +359,7 @@ const Navigation: FC = () => {
open={openNavMenus.includes("permissions")}
>
{[
<li
className="p-side-navigation__item"
key="/ui/permissions/identities"
>
<SideNavigationItem key="/ui/permissions/identities">
<NavLink
to="/ui/permissions/identities"
title="Identities"
Expand All @@ -374,11 +369,8 @@ const Navigation: FC = () => {
>
Identities
</NavLink>
</li>,
<li
className="p-side-navigation__item"
key="/ui/permissions/groups"
>
</SideNavigationItem>,
<SideNavigationItem key="/ui/permissions/groups">
<NavLink
to="/ui/permissions/groups"
title="LXD groups"
Expand All @@ -387,11 +379,8 @@ const Navigation: FC = () => {
>
Groups
</NavLink>
</li>,
<li
className="p-side-navigation__item"
key="/ui/permissions/idp-groups"
>
</SideNavigationItem>,
<SideNavigationItem key="/ui/permissions/idp-groups">
<NavLink
to="/ui/permissions/idp-groups"
title="Identity provider groups"
Expand All @@ -400,12 +389,12 @@ const Navigation: FC = () => {
>
IDP groups
</NavLink>
</li>,
</SideNavigationItem>,
]}
</NavAccordion>
</li>
</SideNavigationItem>
)}
<li className="p-side-navigation__item">
<SideNavigationItem>
<NavLink
to="/ui/settings"
title="Settings"
Expand All @@ -417,12 +406,12 @@ const Navigation: FC = () => {
/>{" "}
Settings
</NavLink>
</li>
</SideNavigationItem>
</>
)}
{!isAuthenticated && (
<>
<li className="p-side-navigation__item">
<SideNavigationItem>
<NavLink
to="/ui/login"
title="Login"
Expand All @@ -434,7 +423,7 @@ const Navigation: FC = () => {
/>
Login
</NavLink>
</li>
</SideNavigationItem>
</>
)}
</ul>
Expand All @@ -450,7 +439,7 @@ const Navigation: FC = () => {
>
<hr className="is-dark navigation-hr" />
{isAuthenticated && (
<li className="p-side-navigation__item">
<SideNavigationItem>
<div
className="p-side-navigation__link"
title={`${loggedInUserName} (${loggedInUserID})`}
Expand All @@ -470,9 +459,9 @@ const Navigation: FC = () => {
)}
<div className="u-truncate">{loggedInUserName}</div>
</div>
</li>
</SideNavigationItem>
)}
<li className="p-side-navigation__item">
<SideNavigationItem>
<a
className="p-side-navigation__link"
href={docBaseLink}
Expand All @@ -486,8 +475,8 @@ const Navigation: FC = () => {
/>
Documentation
</a>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<a
className="p-side-navigation__link"
href="https://discourse.ubuntu.com/c/lxd/126"
Expand All @@ -501,8 +490,8 @@ const Navigation: FC = () => {
/>
Discussion
</a>
</li>
<li className="p-side-navigation__item">
</SideNavigationItem>
<SideNavigationItem>
<a
className="p-side-navigation__link"
href="https://github.com/canonical/lxd-ui/issues/new"
Expand All @@ -516,9 +505,9 @@ const Navigation: FC = () => {
/>
Report a bug
</a>
</li>
</SideNavigationItem>
{isOidc && (
<li className="p-side-navigation__item">
<SideNavigationItem>
<a
className="p-side-navigation__link"
title="Log out"
Expand All @@ -533,7 +522,7 @@ const Navigation: FC = () => {
/>
Log out
</a>
</li>
</SideNavigationItem>
)}
</ul>
<div
Expand Down
Loading

0 comments on commit 6f834dd

Please sign in to comment.