fix error handler at useAdminRole

This commit is contained in:
NlightN22 2025-02-01 19:01:56 +07:00
parent e61607b5d4
commit 566e69e509
6 changed files with 74 additions and 65 deletions

View File

@ -8,10 +8,11 @@ import { getConfigSchema } from "../services/frigate.proxy/frigate.schema";
export interface AdminRole { export interface AdminRole {
isLoading: boolean isLoading: boolean
isAdmin: boolean isAdmin: boolean
isError: boolean
} }
export const useAdminRole = (): AdminRole => { export const useAdminRole = (): AdminRole => {
const { data: adminConfig, isError, isLoading } = useQuery({ const { data: adminConfig, isError, isLoading, error } = useQuery({
queryKey: [frigateQueryKeys.getAdminRole], queryKey: [frigateQueryKeys.getAdminRole],
queryFn: frigateApi.getAdminRole, queryFn: frigateApi.getAdminRole,
staleTime: 1000 * 60 * 60, staleTime: 1000 * 60 * 60,
@ -21,9 +22,9 @@ export const useAdminRole = (): AdminRole => {
const roles = useRealmAccessRoles() const roles = useRealmAccessRoles()
const [isAdmin, setIsAdmin] = useState(false) const [isAdmin, setIsAdmin] = useState(false)
if (isError) setIsAdmin(false)
useEffect(() => { useEffect(() => {
if (isLoading) return
const parsedConfig = getConfigSchema.safeParse(adminConfig) const parsedConfig = getConfigSchema.safeParse(adminConfig)
if (!isProduction) console.log('useAdminRole parsedConfig success:', parsedConfig.success) if (!isProduction) console.log('useAdminRole parsedConfig success:', parsedConfig.success)
if (!parsedConfig.success) { if (!parsedConfig.success) {
@ -38,5 +39,12 @@ export const useAdminRole = (): AdminRole => {
} }
}, [roles, adminConfig, isLoading]) }, [roles, adminConfig, isLoading])
return { isLoading, isAdmin } useEffect(() => {
if (isError) {
console.error("useAdminRole error: ", error.message);
setIsAdmin(false);
}
}, [isError]);
return { isLoading, isAdmin, isError }
} }

View File

@ -20,7 +20,7 @@ const AccessSettings = () => {
queryKey: [frigateQueryKeys.getRoles], queryKey: [frigateQueryKeys.getRoles],
queryFn: frigateApi.getRoles queryFn: frigateApi.getRoles
}) })
const { isAdmin, isLoading: adminLoading } = useAdminRole() const { isAdmin, isLoading: adminLoading, isError: adminError } = useAdminRole()
@ -29,7 +29,7 @@ const AccessSettings = () => {
if (isPending || adminLoading) return <CenterLoader /> if (isPending || adminLoading) return <CenterLoader />
if (isError || !data) return <RetryErrorPage onRetry={refetch} /> if (isError || adminError || !data) return <RetryErrorPage onRetry={refetch} />
if (!isAdmin) return <Forbidden /> if (!isAdmin) return <Forbidden />
const handleSelectRole = (value: string) => { const handleSelectRole = (value: string) => {

View File

@ -101,11 +101,11 @@ const EditCameraPage = () => {
}, },
}) })
const { isAdmin, isLoading: adminLoading } = useAdminRole() const { isAdmin, isLoading: adminLoading, isError: adminError } = useAdminRole()
if (isPending || adminLoading) return <CenterLoader /> if (isPending || adminLoading) return <CenterLoader />
if (!isAdmin) return <Forbidden /> if (!isAdmin) return <Forbidden />
if (isError) return <RetryErrorPage onRetry={refetch} /> if (isError || adminError) return <RetryErrorPage onRetry={refetch} />
const hostName = mapHostToHostname(camera.frigateHost) const hostName = mapHostToHostname(camera.frigateHost)

View File

@ -24,7 +24,7 @@ const FrigateHostsPage = () => {
queryFn: frigateApi.getHosts, queryFn: frigateApi.getHosts,
}) })
const { isAdmin, isLoading: adminLoading } = useAdminRole() const { isAdmin, isLoading: adminLoading, isError: adminError } = useAdminRole()
const [pageData, setPageData] = useState(data) const [pageData, setPageData] = useState(data)
useEffect(() => { useEffect(() => {
@ -90,7 +90,7 @@ const FrigateHostsPage = () => {
if (hostsPending || adminLoading) return <CenterLoader /> if (hostsPending || adminLoading) return <CenterLoader />
if (!isAdmin) return <Forbidden /> if (!isAdmin) return <Forbidden />
if (hostsError) return <RetryErrorPage /> if (hostsError || adminError) return <RetryErrorPage />
if (!pageData) return <Text>Empty server response</Text> if (!pageData) return <Text>Empty server response</Text>
return ( return (

View File

@ -43,55 +43,55 @@ const MainPage = () => {
const pageSize = 20; const pageSize = 20;
const { // const {
data, // data,
isLoading, // isLoading,
isError, // isError,
fetchNextPage, // fetchNextPage,
hasNextPage, // hasNextPage,
isFetching, // isFetching,
isFetchingNextPage, // isFetchingNextPage,
refetch, // refetch,
} = useInfiniteQuery<GetCameraWHostWConfig[]>({ // } = useInfiniteQuery<GetCameraWHostWConfig[]>({
queryKey: [frigateQueryKeys.getCamerasWHost, selectedHostId, searchQuery, selectedTags], // queryKey: [frigateQueryKeys.getCamerasWHost, selectedHostId, searchQuery, selectedTags],
queryFn: ({ pageParam = 0 }) => // queryFn: ({ pageParam = 0 }) =>
// Pass pagination parameters to the backend // // Pass pagination parameters to the backend
frigateApi.getCamerasWHost({ // frigateApi.getCamerasWHost({
name: searchQuery, // name: searchQuery,
frigateHostId: selectedHostId, // frigateHostId: selectedHostId,
tagIds: selectedTags, // tagIds: selectedTags,
offset: pageParam, // offset: pageParam,
limit: pageSize, // limit: pageSize,
}), // }),
getNextPageParam: (lastPage, pages) => { // getNextPageParam: (lastPage, pages) => {
// If last page size is less than pageSize, no more pages // // If last page size is less than pageSize, no more pages
if (lastPage.length < pageSize) return undefined; // if (lastPage.length < pageSize) return undefined;
// Next page offset is pages.length * pageSize // // Next page offset is pages.length * pageSize
return pages.length * pageSize; // return pages.length * pageSize;
}, // },
initialPageParam: 0, // initialPageParam: 0,
}); // });
const cameras: GetCameraWHostWConfig[] = data?.pages.flat() || []; // const cameras: GetCameraWHostWConfig[] = data?.pages.flat() || [];
// const cameras: GetCameraWHostWConfig[] = []; const cameras: GetCameraWHostWConfig[] = [];
const [visibleCount, setVisibleCount] = useState(pageSize) const [visibleCount, setVisibleCount] = useState(pageSize)
useEffect(() => { // useEffect(() => {
if (inView && !isFetching) { // if (inView && !isFetching) {
if (visibleCount < cameras.length) { // if (visibleCount < cameras.length) {
setVisibleCount(prev => Math.min(prev + pageSize, cameras.length)); // setVisibleCount(prev => Math.min(prev + pageSize, cameras.length));
} else if (hasNextPage && !isFetchingNextPage) { // } else if (hasNextPage && !isFetchingNextPage) {
loadTriggered.current = true; // loadTriggered.current = true;
fetchNextPage().then(() => { // fetchNextPage().then(() => {
// Add a small delay before resetting the flag // // Add a small delay before resetting the flag
setTimeout(() => { // setTimeout(() => {
loadTriggered.current = false; // loadTriggered.current = false;
}, 300); // delay in milliseconds; adjust as needed // }, 300); // delay in milliseconds; adjust as needed
}); // });
} // }
} // }
}, [inView, cameras, visibleCount, hasNextPage, isFetchingNextPage, isFetching, fetchNextPage]) // }, [inView, cameras, visibleCount, hasNextPage, isFetchingNextPage, isFetching, fetchNextPage])
useEffect(() => { useEffect(() => {
const hostId = searchParams.get(mainPageParams.hostId) || '' const hostId = searchParams.get(mainPageParams.hostId) || ''
@ -110,8 +110,8 @@ const MainPage = () => {
selectedTags: deSerializedTags, selectedTags: deSerializedTags,
}) })
setRightChildren(<MainFiltersRightSide />); // setRightChildren(<MainFiltersRightSide />);
return () => setRightChildren(null); // return () => setRightChildren(null);
}, []); }, []);
@ -123,34 +123,35 @@ const MainPage = () => {
debouncedHandleSearchQuery(event.currentTarget.value) debouncedHandleSearchQuery(event.currentTarget.value)
} }
if (isLoading) return <CogwheelLoader />; // if (isLoading) return <CogwheelLoader />;
if (isError) return <RetryErrorPage onRetry={refetch} /> // if (isError) return <RetryErrorPage onRetry={refetch} />
if (!isProduction) console.log('MainPage rendered') if (!isProduction) console.log('MainPage rendered')
return ( return (
<Flex direction='column' h='100%' w='100%' > <Flex direction='column' h='100%' w='100%' >
<Flex w='100%' <Flex w='100%'
justify='center' justify='center'
> >
<ClearableTextInput {/* <ClearableTextInput
clearable clearable
maw={400} maw={400}
style={{ flexGrow: 1 }} style={{ flexGrow: 1 }}
placeholder={t('search')} placeholder={t('search')}
icon={<IconSearch size="0.9rem" stroke={1.5} />} icon={<IconSearch size="0.9rem" stroke={1.5} />}
value={searchQuery || undefined} value={searchQuery || undefined}
// onChange={onInputChange} onChange={onInputChange}
/> /> */}
</Flex> </Flex>
<Flex justify='center' h='100%' direction='column' w='100%' > <Flex justify='center' h='100%' direction='column' w='100%' >
<Grid mt='sm' justify="center" mb='sm' align='stretch'> {/* <Grid mt='sm' justify="center" mb='sm' align='stretch'>
{cameras.slice(0, visibleCount).map(camera => ( {cameras.slice(0, visibleCount).map(camera => (
<CameraCard key={camera.id} camera={camera} /> <CameraCard key={camera.id} camera={camera} />
))} ))}
</Grid> </Grid>
{ isFetching && !isFetchingNextPage ? <CogwheelLoader /> : null} { isFetching && !isFetchingNextPage ? <CogwheelLoader /> : null}
{/* trigger point. Rerender twice when enabled */} {/* trigger point. Rerender twice when enabled */}
<div ref={ref} style={{ height: '50px' }} /> {/* <div ref={ref} style={{ height: '50px' }} /> */}
</Flex> </Flex>
</Flex> </Flex>
); );

View File

@ -50,7 +50,7 @@ export const frigateApi = {
name?: string | null | undefined; name?: string | null | undefined;
frigateHostId?: string | null | undefined; frigateHostId?: string | null | undefined;
tagIds?: string | string[]; tagIds?: string | string[];
offset?: any; offset?: number | unknown;
limit?: number; limit?: number;
} = {}) => } = {}) =>
instanceApi instanceApi