Skip to content

Commit 59c6942

Browse files
committed
chore(*): merged latest
2 parents 6935ba3 + 51b50c0 commit 59c6942

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

45 files changed

+761
-338
lines changed

examples/react/index.html

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,9 @@
2323
<title>Vite + React</title>
2424
</head>
2525
<body class="dark:bg-neutral-900 dark:text-white">
26+
<script>
27+
document.documentElement.classList.toggle("dark", localStorage.theme === "dark" || (!("theme" in localStorage) && window.matchMedia("(prefers-color-scheme: dark)").matches));
28+
</script>
2629
<div id="root"></div>
2730
<script type="module" src="/src/main.tsx"></script>
2831
<link rel="stylesheet" href="src/index.css">

examples/react/src/App.tsx

Lines changed: 36 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ import { routes } from "./routes";
1919
import { useUser } from "./firebase/hooks";
2020
import { auth } from "./firebase/firebase";
2121
import { multiFactor, sendEmailVerification, signOut } from "firebase/auth";
22+
import { MultiFactorAuthAssertionScreen, useUI } from "@firebase-ui/react";
2223

2324
function App() {
2425
const user = useUser();
@@ -31,6 +32,13 @@ function App() {
3132
}
3233

3334
function UnauthenticatedApp() {
35+
const ui = useUI();
36+
37+
// This can trigger if the user is not on a screen already, and gets an MFA challenge - e.g. on One-Tap sign in.
38+
if (ui.multiFactorResolver) {
39+
return <MultiFactorAuthAssertionScreen />;
40+
}
41+
3442
return (
3543
<div className="max-w-sm mx-auto pt-36 space-y-6 pb-36">
3644
<div className="text-center space-y-4">
@@ -40,7 +48,7 @@ function UnauthenticatedApp() {
4048
Welcome to Firebase UI, choose an example screen below to get started!
4149
</p>
4250
</div>
43-
<div className="border border-neutral-800 rounded divide-y divide-neutral-800 overflow-hidden">
51+
<div className="border border-neutral-200 dark:border-neutral-800 rounded divide-y divide-neutral-200 dark:divide-neutral-800 overflow-hidden">
4452
{routes.map((route) => (
4553
<Link
4654
key={route.path}
@@ -51,7 +59,7 @@ function UnauthenticatedApp() {
5159
<h2 className="font-medium text-sm">{route.name}</h2>
5260
<p className="text-xs text-gray-400 dark:text-gray-300">{route.description}</p>
5361
</div>
54-
<div>
62+
<div className="text-neutral-600 dark:text-neutral-400">
5563
<span className="text-xl">&rarr;</span>
5664
</div>
5765
</Link>
@@ -68,27 +76,32 @@ function AuthenticatedApp() {
6876

6977
return (
7078
<div className="max-w-sm mx-auto pt-36 space-y-6 pb-36">
71-
<div className="border border-neutral-800 rounded p-4 space-y-4">
79+
<div className="border border-neutral-200 dark:border-neutral-800 rounded-md p-4 space-y-4">
7280
<h1 className="text-md font-medium">Welcome, {user.displayName || user.email || user.phoneNumber}</h1>
73-
{user.emailVerified ? (
74-
<div className="text-green-500">Email verified</div>
75-
) : (
76-
<button
77-
className="bg-red-500 text-white px-3 py-1.5 rounded text-sm"
78-
onClick={async () => {
79-
try {
80-
await sendEmailVerification(user);
81-
alert("Email verification sent, please check your email");
82-
} catch (error) {
83-
console.error(error);
84-
alert("Error sending email verification, check console");
85-
}
86-
}}
87-
>
88-
Verify Email &rarr;
89-
</button>
90-
)}
91-
<hr className="opacity-20" />
81+
{user.email ? (
82+
<>
83+
{user.emailVerified ? (
84+
<div className="text-green-500">Email verified</div>
85+
) : (
86+
<button
87+
className="bg-red-500 text-white px-3 py-1.5 rounded text-sm"
88+
onClick={async () => {
89+
try {
90+
await sendEmailVerification(user);
91+
alert("Email verification sent, please check your email");
92+
} catch (error) {
93+
console.error(error);
94+
alert("Error sending email verification, check console");
95+
}
96+
}}
97+
>
98+
Verify Email &rarr;
99+
</button>
100+
)}
101+
</>
102+
) : null}
103+
104+
<hr className="opacity-30" />
92105
<h2 className="text-sm font-medium">Multi-factor Authentication</h2>
93106
{mfa.enrolledFactors.map((factor) => {
94107
return (
@@ -105,7 +118,7 @@ function AuthenticatedApp() {
105118
>
106119
Add MFA Factor &rarr;
107120
</button>
108-
<hr className="opacity-20" />
121+
<hr className="opacity-30" />
109122
<button
110123
className="bg-blue-500 text-white px-3 py-1.5 rounded text-sm"
111124
onClick={async () => await signOut(auth)}

examples/react/src/firebase/firebase.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,8 @@
1818

1919
import { initializeApp, getApps } from "firebase/app";
2020
import { firebaseConfig } from "./config";
21-
import { getAuth } from "firebase/auth";
22-
import { initializeUI, oneTapSignIn, countryCodes } from "@invertase/firebaseui-core";
21+
import { connectAuthEmulator, getAuth } from "firebase/auth";
22+
import { initializeUI, oneTapSignIn, countryCodes } from "@firebase-ui/core";
2323

2424
export const firebaseApp = getApps().length === 0 ? initializeApp(firebaseConfig) : getApps()[0];
2525

@@ -40,6 +40,6 @@ export const ui = initializeUI({
4040
],
4141
});
4242

43-
// if (import.meta.env.MODE === "development") {
44-
// connectAuthEmulator(auth, "http://localhost:9099");
45-
// }
43+
if (import.meta.env.MODE === "development") {
44+
connectAuthEmulator(auth, "http://localhost:9099");
45+
}

examples/react/src/index.css

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
*/
1616

1717
@import "tailwindcss";
18+
@custom-variant dark (&:where(.dark, .dark *));
1819
@import "@invertase/firebaseui-styles/tailwind";
1920

2021
/* @import "@firebase-ui/styles/src/themes/dark.css"; */

examples/react/src/main.tsx

Lines changed: 57 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414
* limitations under the License.
1515
*/
1616

17-
import { BrowserRouter, Routes, Route } from "react-router";
17+
import { BrowserRouter, Routes, Route, Outlet, NavLink } from "react-router";
1818

1919
import ReactDOM from "react-dom/client";
2020
import { FirebaseUIProvider } from "@invertase/firebaseui-react";
@@ -37,13 +37,66 @@ auth.authStateReady().then(() => {
3737
privacyPolicyUrl: "https://www.google.com",
3838
}}
3939
>
40+
<ThemeToggle />
4041
<Routes>
4142
<Route path="/" element={<App />} />
42-
{allRoutes.map((route) => (
43-
<Route key={route.path} path={route.path} element={<route.component />} />
44-
))}
43+
<Route element={<ScreenRoute />}>
44+
{allRoutes.map((route) => (
45+
<Route key={route.path} path={route.path} element={<route.component />} />
46+
))}
47+
</Route>
4548
</Routes>
4649
</FirebaseUIProvider>
4750
</BrowserRouter>
4851
);
4952
});
53+
54+
function ScreenRoute() {
55+
return (
56+
<div className="p-8">
57+
<NavLink
58+
to="/"
59+
className="border border-gray-300 dark:border-gray-700 border-rounded px-4 py-2 rounded-md text-sm"
60+
>
61+
&larr; Back to overview
62+
</NavLink>
63+
<div className="pt-12">
64+
<Outlet />
65+
</div>
66+
</div>
67+
);
68+
}
69+
70+
function ThemeToggle() {
71+
return (
72+
<button
73+
className="fixed z-10 top-8 right-8 border border-gray-300 dark:border-gray-700 rounded-md p-2 group/toggle extend-touch-target"
74+
onClick={() => {
75+
document.documentElement.classList.toggle("dark", !document.documentElement.classList.contains("dark"));
76+
localStorage.theme = document.documentElement.classList.contains("dark") ? "dark" : "light";
77+
}}
78+
title="Toggle theme"
79+
>
80+
<svg
81+
xmlns="http://www.w3.org/2000/svg"
82+
width="24"
83+
height="24"
84+
viewBox="0 0 24 24"
85+
fill="none"
86+
stroke="currentColor"
87+
strokeWidth="2"
88+
strokeLinecap="round"
89+
strokeLinejoin="round"
90+
className="size-4.5"
91+
>
92+
<path stroke="none" d="M0 0h24v24H0z" fill="none" />
93+
<path d="M12 12m-9 0a9 9 0 1 0 18 0a9 9 0 1 0 -18 0" />
94+
<path d="M12 3l0 18" />
95+
<path d="M12 9l4.65 -4.65" />
96+
<path d="M12 14.3l7.37 -7.37" />
97+
<path d="M12 19.6l8.85 -8.85" />
98+
</svg>
99+
<span className="sr-only">Toggle theme</span>
100+
</button>
101+
);
102+
}

examples/react/src/screens/sign-up-auth-screen-w-handlers.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ export default function SignUpAuthScreenWithHandlersPage() {
2424

2525
return (
2626
<SignUpAuthScreen
27-
onBackToSignInClick={() => {
27+
onSignInClick={() => {
2828
navigate("/screens/sign-in-auth-screen");
2929
}}
3030
onSignUp={(credential) => {

examples/shadcn/package.json

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,10 @@
1313
},
1414
"dependencies": {
1515
"@hookform/resolvers": "^5.2.2",
16-
"@invertase/firebaseui-core": "0.0.5",
17-
"@invertase/firebaseui-react": "workspace:*",
18-
"@invertase/firebaseui-styles": "0.0.9",
19-
"@invertase/firebaseui-translations": "0.0.4",
16+
"@invertase/firebaseui-core": "*",
17+
"@invertase/firebaseui-react": "*",
18+
"@invertase/firebaseui-styles": "*",
19+
"@invertase/firebaseui-translations": "*",
2020
"@radix-ui/react-accordion": "^1.2.12",
2121
"@radix-ui/react-alert-dialog": "^1.1.15",
2222
"@radix-ui/react-aspect-ratio": "^1.1.7",

packages/react/src/auth/forms/mfa/sms-multi-factor-enrollment-form.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ export function useSmsMultiFactorEnrollmentPhoneAuthFormAction() {
2828
);
2929
}
3030

31-
type UseSmsMultiFactorEnrollmentPhoneNumberForm = {
31+
export type UseSmsMultiFactorEnrollmentPhoneNumberForm = {
3232
recaptchaVerifier: RecaptchaVerifier;
3333
onSuccess: (verificationId: string, displayName?: string) => void;
3434
formatPhoneNumber?: (phoneNumber: string) => string;

packages/react/src/auth/forms/mfa/totp-multi-factor-assertion-form.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ export function useTotpMultiFactorAssertionFormAction() {
1616
);
1717
}
1818

19-
type UseTotpMultiFactorAssertionForm = {
19+
export type UseTotpMultiFactorAssertionForm = {
2020
hint: MultiFactorInfo;
2121
onSuccess: (credential: UserCredential) => void;
2222
};
@@ -43,7 +43,7 @@ export function useTotpMultiFactorAssertionForm({ hint, onSuccess }: UseTotpMult
4343
});
4444
}
4545

46-
type TotpMultiFactorAssertionFormProps = {
46+
export type TotpMultiFactorAssertionFormProps = {
4747
hint: MultiFactorInfo;
4848
onSuccess?: (credential: UserCredential) => void;
4949
};

packages/react/src/auth/forms/mfa/totp-multi-factor-enrollment-form.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ export function useTotpMultiFactorSecretGenerationFormAction() {
1818
}, [ui]);
1919
}
2020

21-
type UseTotpMultiFactorEnrollmentForm = {
21+
export type UseTotpMultiFactorEnrollmentForm = {
2222
onSuccess: (secret: TotpSecret, displayName: string) => void;
2323
};
2424

0 commit comments

Comments
 (0)