Refactor authentication listener to be a hook

The previous authentication listener component was transformed into a `useAuthChangeListener` hook. All relevant functionality was preserved in this transition. The purpose of this change was to improve flexibility and code reusability by enabling the auth listener to be integrated in various parts of the application as needed. The old component was also removed from the exported packages in the `package.json`.
This commit is contained in:
giancarlo
2024-04-22 19:46:45 +08:00
parent a074e1ec3b
commit 8c5b0496da
4 changed files with 32 additions and 39 deletions

View File

@@ -9,7 +9,7 @@ import { ThemeProvider } from 'next-themes';
import { CaptchaProvider } from '@kit/auth/captcha/client';
import { I18nProvider } from '@kit/i18n/provider';
import { MonitoringProvider } from '@kit/monitoring/components';
import { AuthChangeListener } from '@kit/supabase/components/auth-change-listener';
import { useAuthChangeListener } from '@kit/supabase/hooks/use-auth-change-listener';
import appConfig from '~/config/app.config';
import authConfig from '~/config/auth.config';
@@ -50,7 +50,7 @@ export function RootProviders({
<CaptchaProvider>
<CaptchaTokenSetter siteKey={captchaSiteKey} />
<AuthChangeListener appHomePath={pathsConfig.app.home}>
<AuthProvider>
<ThemeProvider
attribute="class"
enableSystem
@@ -60,7 +60,7 @@ export function RootProviders({
>
{children}
</ThemeProvider>
</AuthChangeListener>
</AuthProvider>
</CaptchaProvider>
</I18nProvider>
</ReactQueryStreamedHydration>
@@ -68,3 +68,12 @@ export function RootProviders({
</MonitoringProvider>
);
}
// we place this below React Query since it uses the QueryClient
function AuthProvider(props: React.PropsWithChildren) {
useAuthChangeListener({
appHomePath: pathsConfig.app.home,
});
return props.children;
}

View File

@@ -1,5 +1,9 @@
import { pino } from 'pino';
/**
* @name Logger
* @description A logger implementation using Pino
*/
const Logger = pino({
browser: {
asObject: true,
@@ -8,6 +12,7 @@ const Logger = pino({
base: {
env: process.env.NODE_ENV,
},
errorKey: 'error',
});
export { Logger };

View File

@@ -18,7 +18,6 @@
"./check-requires-mfa": "./src/check-requires-mfa.ts",
"./require-user": "./src/require-user.ts",
"./hooks/*": "./src/hooks/*.ts",
"./components/*": "./src/components/*.tsx",
"./database": "./src/database.types.ts"
},
"devDependencies": {

View File

@@ -4,24 +4,28 @@ import { useEffect } from 'react';
import { usePathname, useRouter } from 'next/navigation';
import { isBrowser } from '@supabase/ssr';
import { useSupabase } from '../hooks/use-supabase';
import {
useRevalidateUserSession,
useUserSession,
} from '../hooks/use-user-session';
import { useSupabase } from './use-supabase';
import { useRevalidateUserSession, useUserSession } from './use-user-session';
/**
* @name PRIVATE_PATH_PREFIXES
* @description A list of private path prefixes
*/
const PRIVATE_PATH_PREFIXES = ['/home', '/admin', '/join', '/update-password'];
function AuthRedirectListener({
children,
/**
* @name AuthRedirectListener
* @description A component that listens to auth state changes and redirects users
* @param privatePathPrefixes
* @param appHomePath
*/
export function useAuthChangeListener({
privatePathPrefixes = PRIVATE_PATH_PREFIXES,
appHomePath,
}: React.PropsWithChildren<{
}: {
appHomePath: string;
privatePathPrefixes?: string[];
}>) {
}) {
const client = useSupabase();
const pathName = usePathname();
const router = useRouter();
@@ -63,30 +67,6 @@ function AuthRedirectListener({
pathName,
appHomePath,
]);
return <>{children}</>;
}
export function AuthChangeListener({
children,
appHomePath,
}: React.PropsWithChildren<{
appHomePath: string;
privateRoutes?: string[];
}>) {
const shouldActivateListener = isBrowser();
// we only activate the listener if
// we are rendering in the browser
if (!shouldActivateListener) {
return <>{children}</>;
}
return (
<AuthRedirectListener appHomePath={appHomePath}>
{children}
</AuthRedirectListener>
);
}
/**