state on mfa set

This commit is contained in:
peintnermax
2024-04-23 11:26:34 +02:00
parent 827af38220
commit 430d87c1a1
2 changed files with 61 additions and 33 deletions

View File

@@ -4,6 +4,7 @@ import { AuthenticationMethodType, LoginSettings } from "@zitadel/server";
import Link from "next/link"; import Link from "next/link";
import { BadgeState, StateBadge } from "./StateBadge"; import { BadgeState, StateBadge } from "./StateBadge";
import clsx from "clsx"; import clsx from "clsx";
import { CheckIcon } from "@heroicons/react/24/outline";
type Props = { type Props = {
loginName?: string; loginName?: string;
@@ -24,8 +25,8 @@ export default function ChooseSecondFactorToSetup({
}: Props) { }: Props) {
const cardClasses = (alreadyAdded: boolean) => const cardClasses = (alreadyAdded: boolean) =>
clsx( clsx(
"bg-background-light-400 dark:bg-background-dark-400 group block space-y-1.5 rounded-md px-5 py-3 border border-divider-light dark:border-divider-dark transition-all ", "relative bg-background-light-400 dark:bg-background-dark-400 group block space-y-1.5 rounded-md px-5 py-3 border border-divider-light dark:border-divider-dark transition-all ",
alreadyAdded ? "opacity-50" : "hover:shadow-lg hover:dark:bg-white/10" alreadyAdded ? "" : "hover:shadow-lg hover:dark:bg-white/10"
); );
const TOTP = (alreadyAdded: boolean) => { const TOTP = (alreadyAdded: boolean) => {
@@ -34,7 +35,12 @@ export default function ChooseSecondFactorToSetup({
href={userMethods.includes(4) ? "" : "/otp/time-based/set"} href={userMethods.includes(4) ? "" : "/otp/time-based/set"}
className={cardClasses(alreadyAdded)} className={cardClasses(alreadyAdded)}
> >
<div className="font-medium flex items-center"> <div
className={clsx(
"font-medium flex items-center",
alreadyAdded ? "opacity-50" : ""
)}
>
<svg <svg
className="h-9 w-9 transform -translate-x-[2px] mr-4" className="h-9 w-9 transform -translate-x-[2px] mr-4"
version="1.1" version="1.1"
@@ -77,13 +83,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
/> />
</svg>{" "} </svg>{" "}
<span>Authenticator App</span> <span>Authenticator App</span>
</div>
{alreadyAdded && ( {alreadyAdded && (
<> <>
<span className="flex-1"></span>
<Setup /> <Setup />
</> </>
)} )}
</div>
</Link> </Link>
); );
}; };
@@ -91,7 +96,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
const U2F = (alreadyAdded: boolean) => { const U2F = (alreadyAdded: boolean) => {
return ( return (
<Link href="/u2f/set" className={cardClasses(alreadyAdded)}> <Link href="/u2f/set" className={cardClasses(alreadyAdded)}>
<div className="font-medium flex items-center"> <div
className={clsx(
"font-medium flex items-center",
alreadyAdded ? "" : ""
)}
>
<svg <svg
xmlns="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg"
fill="none" fill="none"
@@ -107,13 +117,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
/> />
</svg> </svg>
<span>Universal Second Factor</span> <span>Universal Second Factor</span>
</div>
{alreadyAdded && ( {alreadyAdded && (
<> <>
<span className="flex-1"></span>
<Setup /> <Setup />
</> </>
)} )}
</div>
</Link> </Link>
); );
}; };
@@ -121,7 +130,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
const EMAIL = (alreadyAdded: boolean) => { const EMAIL = (alreadyAdded: boolean) => {
return ( return (
<Link href="/otp/email/set" className={cardClasses(alreadyAdded)}> <Link href="/otp/email/set" className={cardClasses(alreadyAdded)}>
<div className="font-medium flex items-center"> <div
className={clsx(
"font-medium flex items-center",
alreadyAdded ? "" : ""
)}
>
<svg <svg
className="w-8 h-8 mr-4" className="w-8 h-8 mr-4"
xmlns="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg"
@@ -138,13 +152,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
</svg> </svg>
<span>Code via Email</span> <span>Code via Email</span>
</div>
{alreadyAdded && ( {alreadyAdded && (
<> <>
<span className="flex-1"></span>
<Setup /> <Setup />
</> </>
)} )}
</div>
</Link> </Link>
); );
}; };
@@ -152,7 +165,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
const SMS = (alreadyAdded: boolean) => { const SMS = (alreadyAdded: boolean) => {
return ( return (
<Link href="/otp/sms/set" className={cardClasses(alreadyAdded)}> <Link href="/otp/sms/set" className={cardClasses(alreadyAdded)}>
<div className="font-medium flex items-center"> <div
className={clsx(
"font-medium flex items-center",
alreadyAdded ? "" : ""
)}
>
<svg <svg
className="w-8 h-8 mr-4" className="w-8 h-8 mr-4"
xmlns="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg"
@@ -168,13 +186,12 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
/> />
</svg> </svg>
<span>Code via SMS</span> <span>Code via SMS</span>
</div>
{alreadyAdded && ( {alreadyAdded && (
<> <>
<span className="flex-1"></span>
<Setup /> <Setup />
</> </>
)} )}
</div>
</Link> </Link>
); );
}; };
@@ -196,5 +213,11 @@ C72,238.87917,85.87916,225,102.99997,225H248z"
} }
function Setup() { function Setup() {
return <StateBadge state={BadgeState.Success}>Setup</StateBadge>; return (
<div className="transform absolute right-2 top-0">
<StateBadge evenPadding={true} state={BadgeState.Success}>
<CheckIcon className="w-4 h-4" />
</StateBadge>
</div>
);
} }

View File

@@ -11,9 +11,10 @@ export enum BadgeState {
export type StateBadgeProps = { export type StateBadgeProps = {
state: BadgeState; state: BadgeState;
children: ReactNode; children: ReactNode;
evenPadding?: boolean;
}; };
const getBadgeClasses = (state: BadgeState) => const getBadgeClasses = (state: BadgeState, evenPadding: boolean) =>
clsx({ clsx({
"w-fit border-box h-18.5px flex flex-row items-center whitespace-nowrap tracking-wider leading-4 items-center justify-center px-2 py-2px text-12px rounded-full shadow-sm": "w-fit border-box h-18.5px flex flex-row items-center whitespace-nowrap tracking-wider leading-4 items-center justify-center px-2 py-2px text-12px rounded-full shadow-sm":
true, true,
@@ -25,11 +26,15 @@ const getBadgeClasses = (state: BadgeState) =>
state === BadgeState.Error, state === BadgeState.Error,
"bg-state-alert-light-background text-state-alert-light-color dark:bg-state-alert-dark-background dark:text-state-alert-dark-color": "bg-state-alert-light-background text-state-alert-light-color dark:bg-state-alert-dark-background dark:text-state-alert-dark-color":
state === BadgeState.Alert, state === BadgeState.Alert,
"p-[2px]": evenPadding,
}); });
export function StateBadge({ export function StateBadge({
state = BadgeState.Success, state = BadgeState.Success,
evenPadding = false,
children, children,
}: StateBadgeProps) { }: StateBadgeProps) {
return <span className={`${getBadgeClasses(state)}`}>{children}</span>; return (
<span className={`${getBadgeClasses(state, evenPadding)}`}>{children}</span>
);
} }