refactor(web): finding 5 — replace match(boolean) with ternary + ActionButton wrapper

Three auth-settings components (password, two-factor, social-provider) each
duplicated an identical m.div hover/tap wrapper for both branches of
match(boolean). Extracted one ActionButton wrapper and replaced match with
a plain ternary; removed ts-pattern imports.

Claude-Session: https://claude.ai/code/session_012Bnvt1MghwHj4qQRxuQUGa
This commit is contained in:
Amruth Pillai
2026-07-04 21:47:22 +02:00
parent 22398a502b
commit 02538836a9
3 changed files with 86 additions and 90 deletions
@@ -3,11 +3,24 @@ import { PasswordIcon, PencilSimpleLineIcon } from "@phosphor-icons/react";
import { Link, useNavigate } from "@tanstack/react-router";
import { m } from "motion/react";
import { useCallback } from "react";
import { match } from "ts-pattern";
import { Button } from "@reactive-resume/ui/components/button";
import { useDialogStore } from "@/dialogs/store";
import { useAuthAccounts } from "./hooks";
// ponytail: m.div wrapper is identical for both branches — extracted, match(boolean) removed
function ActionButton({ children }: { children: React.ReactNode }) {
return (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
{children}
</m.div>
);
}
export function PasswordSection() {
const navigate = useNavigate();
const { openDialog } = useDialogStore();
@@ -35,39 +48,24 @@ export function PasswordSection() {
<Trans>Password</Trans>
</h2>
{match(hasPassword)
.with(true, () => (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
<Button variant="outline" onClick={handleUpdatePassword}>
<PencilSimpleLineIcon />
<Trans>Update Password</Trans>
</Button>
</m.div>
))
.with(false, () => (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
<Button
variant="outline"
nativeButton={false}
render={
<Link to="/auth/forgot-password">
<Trans>Set Password</Trans>
</Link>
}
/>
</m.div>
))
.exhaustive()}
<ActionButton>
{hasPassword ? (
<Button variant="outline" onClick={handleUpdatePassword}>
<PencilSimpleLineIcon />
<Trans>Update Password</Trans>
</Button>
) : (
<Button
variant="outline"
nativeButton={false}
render={
<Link to="/auth/forgot-password">
<Trans>Set Password</Trans>
</Link>
}
/>
)}
</ActionButton>
</m.div>
);
}
@@ -3,11 +3,24 @@ import { Trans } from "@lingui/react/macro";
import { LinkBreakIcon, LinkIcon } from "@phosphor-icons/react";
import { m } from "motion/react";
import { useCallback } from "react";
import { match } from "ts-pattern";
import { Button } from "@reactive-resume/ui/components/button";
import { Separator } from "@reactive-resume/ui/components/separator";
import { getProviderIcon, getProviderName, useAuthAccounts, useAuthProviderActions } from "./hooks";
// ponytail: shared hover/tap wrapper — identical in both branches, match(boolean) removed
function ActionButton({ children }: { children: React.ReactNode }) {
return (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
{children}
</m.div>
);
}
type SocialProviderSectionProps = {
provider: AuthProvider;
name?: string;
@@ -48,36 +61,21 @@ export function SocialProviderSection({ provider, name, animationDelay = 0 }: So
{providerName}
</h2>
{match(isConnected)
.with(true, () => (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
<Button variant="outline" onClick={handleUnlink}>
<LinkBreakIcon />
<Trans comment="Authentication settings action to unlink a connected social login provider">
Disconnect
</Trans>
</Button>
</m.div>
))
.with(false, () => (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
<Button variant="outline" onClick={handleLink}>
<LinkIcon />
<Trans comment="Authentication settings action to link a social login provider">Connect</Trans>
</Button>
</m.div>
))
.exhaustive()}
<ActionButton>
{isConnected ? (
<Button variant="outline" onClick={handleUnlink}>
<LinkBreakIcon />
<Trans comment="Authentication settings action to unlink a connected social login provider">
Disconnect
</Trans>
</Button>
) : (
<Button variant="outline" onClick={handleLink}>
<LinkIcon />
<Trans comment="Authentication settings action to link a social login provider">Connect</Trans>
</Button>
)}
</ActionButton>
</div>
</m.div>
);
@@ -2,13 +2,26 @@ import { Trans } from "@lingui/react/macro";
import { KeyIcon, LockOpenIcon, ToggleLeftIcon, ToggleRightIcon } from "@phosphor-icons/react";
import { m } from "motion/react";
import { useCallback } from "react";
import { match } from "ts-pattern";
import { Button } from "@reactive-resume/ui/components/button";
import { Separator } from "@reactive-resume/ui/components/separator";
import { useDialogStore } from "@/dialogs/store";
import { authClient } from "@/libs/auth/client";
import { useAuthAccounts } from "./hooks";
// ponytail: shared hover/tap wrapper — identical in both branches, match(boolean) removed
function ActionButton({ children }: { children: React.ReactNode }) {
return (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
{children}
</m.div>
);
}
export function TwoFactorSection() {
const { openDialog } = useDialogStore();
const { hasAccount } = useAuthAccounts();
@@ -42,34 +55,21 @@ export function TwoFactorSection() {
<Trans>Two-Factor Authentication</Trans>
</h2>
{match(hasTwoFactor)
.with(true, () => (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
<Button variant="outline" onClick={handleTwoFactorAction}>
<ActionButton>
<Button variant="outline" onClick={handleTwoFactorAction}>
{hasTwoFactor ? (
<>
<ToggleLeftIcon />
<Trans>Disable 2FA</Trans>
</Button>
</m.div>
))
.with(false, () => (
<m.div
className="will-change-transform"
whileHover={{ y: -1, scale: 1.01 }}
whileTap={{ scale: 0.99 }}
transition={{ duration: 0.14, ease: "easeOut" }}
>
<Button variant="outline" onClick={handleTwoFactorAction}>
</>
) : (
<>
<ToggleRightIcon />
<Trans>Enable 2FA</Trans>
</Button>
</m.div>
))
.exhaustive()}
</>
)}
</Button>
</ActionButton>
</div>
</m.div>
);