-
{descriptionText}
-
+
+ {primaryActionVariant === "button" ? (
+
+ ) : (
+
+ )}
>
);
diff --git a/src/components/SmartLoginForm.tsx b/src/components/SmartLoginForm.tsx
index 24f2acb72..164311b7b 100644
--- a/src/components/SmartLoginForm.tsx
+++ b/src/components/SmartLoginForm.tsx
@@ -15,15 +15,18 @@ import {
FormMessage
} from "@app/components/ui/form";
import { Alert, AlertDescription } from "@app/components/ui/alert";
+import Link from "next/link";
import { useRouter } from "next/navigation";
import { useUserLookup } from "@app/hooks/useUserLookup";
+import { useEnvContext } from "@app/hooks/useEnvContext";
import { LookupUserResponse } from "@server/routers/auth/lookupUser";
import { useTranslations } from "next-intl";
import LoginPasswordForm from "@app/components/LoginPasswordForm";
import LoginOrgSelector from "@app/components/LoginOrgSelector";
import UserProfileCard from "@app/components/UserProfileCard";
-import { ArrowLeft } from "lucide-react";
import SecurityKeyAuthButton from "@app/components/SecurityKeyAuthButton";
+import { Separator } from "@app/components/ui/separator";
+import OrgSignInLink from "@app/components/OrgSignInLink";
const identifierSchema = z.object({
identifier: z.string().min(1, "Username or email is required")
@@ -39,10 +42,17 @@ const isValidEmail = (str: string): boolean => {
}
};
+type OrgSignInConfig = {
+ href: string;
+ linkText: string;
+ descriptionText: string;
+};
+
type SmartLoginFormProps = {
redirect?: string;
forceLogin?: boolean;
defaultUser?: string;
+ orgSignIn?: OrgSignInConfig;
};
type ViewState =
@@ -58,12 +68,31 @@ type ViewState =
lookupResult: LookupUserResponse;
};
+function buildResetPasswordHref(
+ dashboardUrl: string,
+ identifier: string,
+ redirectParam?: string
+) {
+ const trimmed = identifier.trim();
+ const params = new URLSearchParams();
+ if (isValidEmail(trimmed)) {
+ params.set("email", trimmed);
+ }
+ if (redirectParam) {
+ params.set("redirect", redirectParam);
+ }
+ const qs = params.toString();
+ return `${dashboardUrl}/auth/reset-password${qs ? `?${qs}` : ""}`;
+}
+
export default function SmartLoginForm({
redirect,
forceLogin,
- defaultUser
+ defaultUser,
+ orgSignIn
}: SmartLoginFormProps) {
const router = useRouter();
+ const { env } = useEnvContext();
const { lookup, loading, error } = useUserLookup();
const t = useTranslations();
const [viewState, setViewState] = useState
({ type: "initial" });
@@ -78,6 +107,13 @@ export default function SmartLoginForm({
}
});
+ const watchedIdentifier = form.watch("identifier");
+ const resetPasswordHref = buildResetPasswordHref(
+ env.app.dashboardUrl,
+ watchedIdentifier,
+ redirect
+ );
+
const hasAutoLookedUp = useRef(false);
useEffect(() => {
if (defaultUser?.trim() && !hasAutoLookedUp.current) {
@@ -209,6 +245,15 @@ export default function SmartLoginForm({
)}
/>
+
+
+ {t("passwordForgot")}
+
+
+
{(error || securityKeyError) && (
@@ -219,7 +264,7 @@ export default function SmartLoginForm({
-
+
+
+ {orgSignIn && (
+ <>
+
+
+
+
+
+
+ {t("idpContinue")}
+
+
+
+
+ >
+ )}
);