From c5ce8369d366391cdffb2b064a83ad7fad6f10a8 Mon Sep 17 00:00:00 2001 From: Fran McDade Date: Wed, 13 Nov 2024 15:44:56 +1000 Subject: [PATCH] feat: add optional version information to footer (#258) --- .../Tooltip/components/Title/constants.ts | 5 ++ .../Tooltip/components/Title/title.tsx | 53 +++++++++++++++++++ .../Tooltip/components/Title/utils.ts | 31 +++++++++++ .../components/VersionInfo/constants.ts | 30 +++++++++++ .../Footer/components/VersionInfo/types.ts | 14 +++++ .../Footer/components/VersionInfo/utils.ts | 32 +++++++++++ .../VersionInfo/versionInfo.styles.ts | 10 ++++ .../components/VersionInfo/versionInfo.tsx | 31 +++++++++++ .../Layout/components/Footer/footer.tsx | 7 ++- .../components/Dialog/dialog.styles.ts | 5 ++ .../ViewSupport/viewSupport.styles.ts | 5 ++ src/config/entities.ts | 1 + src/styles/common/mui/chip.ts | 36 +++++++++++++ src/theme/common/components.ts | 16 ++++++ 14 files changed, 274 insertions(+), 2 deletions(-) create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/constants.ts create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/title.tsx create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/utils.ts create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/constants.ts create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/types.ts create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/utils.ts create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/versionInfo.styles.ts create mode 100644 src/components/Layout/components/Footer/components/VersionInfo/versionInfo.tsx create mode 100644 src/styles/common/mui/chip.ts diff --git a/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/constants.ts b/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/constants.ts new file mode 100644 index 00000000..ae237dc6 --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/constants.ts @@ -0,0 +1,5 @@ +import { LinkOwnProps } from "@mui/material"; + +export const LINK_PROPS: Partial = { + color: "inherit", +}; diff --git a/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/title.tsx b/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/title.tsx new file mode 100644 index 00000000..b8a28482 --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/title.tsx @@ -0,0 +1,53 @@ +import { Typography } from "@mui/material"; +import React from "react"; +import { useConfig } from "../../../../../../../../../../hooks/useConfig"; +import { TEXT_BODY_SMALL_400_2_LINES } from "../../../../../../../../../../theme/common/typography"; +import { Link } from "../../../../../../../../../Links/components/Link/link"; +import { VersionInfoProps } from "../../../../types"; +import { getGitHash, getVersion } from "../../../../utils"; +import { LINK_PROPS } from "./constants"; +import { getCommitUrl, getReleaseUrl } from "./utils"; + +export const Title = ({ + versionInfo, +}: Pick): JSX.Element | null => { + const { + config: { gitHubUrl }, + } = useConfig(); + if (!versionInfo) return null; + const { buildDate, catalog, gitHash, version } = versionInfo; + return ( + + {buildDate && ( +
+ Build Date: + {buildDate} +
+ )} +
+ Version: + +
+ {gitHash && ( +
+ Git Commit: + +
+ )} + {catalog && ( +
+ Catalog: + {catalog} +
+ )} +
+ ); +}; diff --git a/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/utils.ts b/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/utils.ts new file mode 100644 index 00000000..93eafaeb --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/components/Tooltip/components/Title/utils.ts @@ -0,0 +1,31 @@ +import { VersionInfo } from "../../../../types"; + +/** + * Returns GitHub commit URL for the given git hash. + * @param gitHubRepoUrl - GitHub repository URL. + * @param versionInfo - Version info. + * @returns GitHub commit URL. + */ +export function getCommitUrl( + gitHubRepoUrl?: string, + versionInfo?: VersionInfo +): string { + if (!gitHubRepoUrl || !versionInfo) return ""; + if (!versionInfo.gitHash) return ""; + return `${gitHubRepoUrl}/commit/${versionInfo.gitHash}`; +} + +/** + * Returns GitHub release URL for the given release version. + * @param gitHubRepoUrl - GitHub repository URL. + * @param versionInfo - Version info. + * @returns GitHub release URL. + */ +export function getReleaseUrl( + gitHubRepoUrl?: string, + versionInfo?: VersionInfo +): string { + if (!gitHubRepoUrl || !versionInfo) return ""; + if (!versionInfo.version) return ""; + return `${gitHubRepoUrl}/releases/tag/${versionInfo.version}`; +} diff --git a/src/components/Layout/components/Footer/components/VersionInfo/constants.ts b/src/components/Layout/components/Footer/components/VersionInfo/constants.ts new file mode 100644 index 00000000..8e4711db --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/constants.ts @@ -0,0 +1,30 @@ +import { ChipProps, TooltipProps } from "@mui/material"; +import { CHIP_PROPS as MUI_CHIP_PROPS } from "../../../../../../styles/common/mui/chip"; + +export const CHIP_PROPS: Partial = { + color: MUI_CHIP_PROPS.COLOR.DEFAULT, + size: MUI_CHIP_PROPS.SIZE.SMALL, +}; + +export const TOOLTIP_PROPS: Partial = { + arrow: true, + slotProps: { + popper: { + modifiers: [ + { + name: "offset", + options: { + offset: [0, -4], + }, + }, + { + name: "preventOverflow", + options: { padding: 8 }, + }, + ], + }, + tooltip: { + sx: { maxWidth: "none" }, + }, + }, +}; diff --git a/src/components/Layout/components/Footer/components/VersionInfo/types.ts b/src/components/Layout/components/Footer/components/VersionInfo/types.ts new file mode 100644 index 00000000..197c9cec --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/types.ts @@ -0,0 +1,14 @@ +import { ChipProps, TooltipProps } from "@mui/material"; + +export interface VersionInfo { + buildDate?: string; + catalog?: string; + gitHash?: string; + version?: string; +} + +export interface VersionInfoProps { + chipProps?: Partial; + tooltipProps?: Partial; + versionInfo?: VersionInfo; +} diff --git a/src/components/Layout/components/Footer/components/VersionInfo/utils.ts b/src/components/Layout/components/Footer/components/VersionInfo/utils.ts new file mode 100644 index 00000000..748a17f5 --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/utils.ts @@ -0,0 +1,32 @@ +import { VersionInfo } from "./types"; + +/** + * Returns displayable shortened version of Git hash. + * @param gitHash - Git hash. + * @returns displayable shortened version of Git hash. + */ +export function getGitHash(gitHash?: string): string | undefined { + return gitHash?.substring(0, 7); +} + +/** + * Returns Chip label based on version info. + * @param versionInfo - Version info. + * @returns Chip label. + */ +export function getLabel(versionInfo?: VersionInfo): string | undefined { + if (!versionInfo) return; + const { catalog, gitHash, version } = versionInfo; + return [getVersion(version), getGitHash(gitHash), catalog] + .filter(Boolean) + .join("-"); +} + +/** + * Returns displayable version, or "Unversioned" if version is not provided. + * @param version - Version info. + * @returns Version. + */ +export function getVersion(version?: string): string { + return version || "Unversioned"; +} diff --git a/src/components/Layout/components/Footer/components/VersionInfo/versionInfo.styles.ts b/src/components/Layout/components/Footer/components/VersionInfo/versionInfo.styles.ts new file mode 100644 index 00000000..9ead85bf --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/versionInfo.styles.ts @@ -0,0 +1,10 @@ +import styled from "@emotion/styled"; +import { Chip } from "@mui/material"; +import { inkLight } from "../../../../../../styles/common/mixins/colors"; + +export const StyledChip = styled(Chip)` + border-radius: 4px; + .MuiChip-label { + color: ${inkLight}; + } +`; diff --git a/src/components/Layout/components/Footer/components/VersionInfo/versionInfo.tsx b/src/components/Layout/components/Footer/components/VersionInfo/versionInfo.tsx new file mode 100644 index 00000000..b1ebcd63 --- /dev/null +++ b/src/components/Layout/components/Footer/components/VersionInfo/versionInfo.tsx @@ -0,0 +1,31 @@ +import { Tooltip } from "@mui/material"; +import React from "react"; +import { BaseComponentProps } from "../../../../../types"; +import { Title } from "./components/Tooltip/components/Title/title"; +import { CHIP_PROPS, TOOLTIP_PROPS } from "./constants"; +import { VersionInfoProps } from "./types"; + +import { getLabel } from "./utils"; +import { StyledChip } from "./versionInfo.styles"; + +export const VersionInfo = ({ + chipProps, + className, + tooltipProps, + versionInfo, +}: BaseComponentProps & VersionInfoProps): JSX.Element | null => { + return ( + } + {...tooltipProps} + > + + + ); +}; diff --git a/src/components/Layout/components/Footer/footer.tsx b/src/components/Layout/components/Footer/footer.tsx index b7ca1d1d..6071e5ca 100644 --- a/src/components/Layout/components/Footer/footer.tsx +++ b/src/components/Layout/components/Footer/footer.tsx @@ -6,10 +6,11 @@ import { NavLinkItem } from "../Header/components/Content/components/Navigation/ import { AppBar, Link, Links, Socials } from "./footer.styles"; export interface FooterProps { - Branding: ReactNode; + Branding?: ReactNode; className?: string; navLinks?: NavLinkItem[]; socials?: Social[]; + versionInfo?: ReactNode; } export const Footer = ({ @@ -17,6 +18,7 @@ export const Footer = ({ className, navLinks, socials, + versionInfo, }: FooterProps): JSX.Element => { return ( {Branding} - {(navLinks || socials) && ( + {(navLinks || socials || versionInfo) && ( {navLinks && navLinks.map(({ label, target = ANCHOR_TARGET.SELF, url }, i) => ( @@ -39,6 +41,7 @@ export const Footer = ({ /> ))} {socials && } + {versionInfo} )} diff --git a/src/components/Support/components/SupportRequest/components/Dialog/dialog.styles.ts b/src/components/Support/components/SupportRequest/components/Dialog/dialog.styles.ts index 035723c2..974db5a5 100644 --- a/src/components/Support/components/SupportRequest/components/Dialog/dialog.styles.ts +++ b/src/components/Support/components/SupportRequest/components/Dialog/dialog.styles.ts @@ -1,5 +1,6 @@ import styled from "@emotion/styled"; import { Fab as MFab, Popover as MPopover } from "@mui/material"; +import { mediaTabletUp } from "../../../../../../styles/common/mixins/breakpoints"; import { smokeMain } from "../../../../../../styles/common/mixins/colors"; import { shadows02 } from "../../../../../../styles/common/mixins/shadows"; import { tabletUp } from "../../../../../../theme/common/breakpoints"; @@ -15,6 +16,10 @@ export const Fab = styled(MFab)` position: fixed; right: 16px; z-index: ${({ open }) => (open ? 1350 : 1050)}; // Above backdrop component. + + ${mediaTabletUp} { + bottom: 72px; + } `; export const Popover = styled(MPopover)` diff --git a/src/components/Support/components/ViewSupport/viewSupport.styles.ts b/src/components/Support/components/ViewSupport/viewSupport.styles.ts index 142bc589..8360c3c7 100644 --- a/src/components/Support/components/ViewSupport/viewSupport.styles.ts +++ b/src/components/Support/components/ViewSupport/viewSupport.styles.ts @@ -1,4 +1,5 @@ import styled from "@emotion/styled"; +import { mediaTabletUp } from "../../../../styles/common/mixins/breakpoints"; import { primaryDark, primaryMain, @@ -27,4 +28,8 @@ export const Fab = styled("a")` &:hover { background-color: ${primaryDark}; } + + ${mediaTabletUp} { + bottom: 72px; + } `; diff --git a/src/config/entities.ts b/src/config/entities.ts index 0f55d952..b7e29fa0 100644 --- a/src/config/entities.ts +++ b/src/config/entities.ts @@ -360,6 +360,7 @@ export interface SiteConfig { explorerTitle: HeroTitle; export?: ExportConfig; exportToTerraUrl?: string; // TODO(cc) revist location; possibly nest inside "export"? + gitHubUrl?: string; layout: { floating?: FloatingConfig; footer: FooterProps; diff --git a/src/styles/common/mui/chip.ts b/src/styles/common/mui/chip.ts new file mode 100644 index 00000000..acfbe27e --- /dev/null +++ b/src/styles/common/mui/chip.ts @@ -0,0 +1,36 @@ +import { ChipProps } from "@mui/material"; + +type ChipPropsOptions = { + COLOR: typeof COLOR; + SIZE: typeof SIZE; + VARIANT: typeof VARIANT; +}; + +const COLOR: Record = { + DEFAULT: "default", + ERROR: "error", + INFO: "info", + PRIMARY: "primary", + SECONDARY: "secondary", + SUCCESS: "success", + WARNING: "warning", +}; + +const SIZE: Record = { + MEDIUM: "medium", + SMALL: "small", +}; + +const VARIANT: Record = { + FILLED: "filled", + FILTER_TAG: "filterTag", + N_TAG: "ntag", + OUTLINED: "outlined", + STATUS: "status", +}; + +export const CHIP_PROPS: ChipPropsOptions = { + COLOR, + SIZE, + VARIANT, +}; diff --git a/src/theme/common/components.ts b/src/theme/common/components.ts index 5ff62cdc..2a1e2f9f 100644 --- a/src/theme/common/components.ts +++ b/src/theme/common/components.ts @@ -1,5 +1,6 @@ import { Components, Theme } from "@mui/material"; import { DropDownIcon } from "../../components/common/Form/components/Select/components/DropDownIcon/dropDownIcon"; +import { CHIP_PROPS } from "../../styles/common/mui/chip"; import { desktopUp, mobileUp, tabletUp } from "./breakpoints"; import { alpha32, @@ -417,8 +418,23 @@ export const MuiChip = (theme: Theme): Components["MuiChip"] => { color: "inherit", margin: "0 -2px 0 0", }, + label: { + ...theme.typography[TEXT_BODY_SMALL_400], + }, }, variants: [ + { + props: { size: CHIP_PROPS.SIZE.SMALL }, + style: { + height: 20, + }, + }, + { + props: { size: CHIP_PROPS.SIZE.MEDIUM }, + style: { + height: 24, + }, + }, { props: { color: "default" }, style: {