Add infinite scroll error handling

This commit is contained in:
Sam Becker 2024-01-15 15:30:10 -06:00
parent 023a286ff8
commit f772ec7daa
2 changed files with 28 additions and 37 deletions

View File

@ -37,15 +37,17 @@ export default async function HomePage() {
itemsPerRequest={LARGE_PHOTOS_TO_SHOW}
getNextComponent={async (offset, limit) => {
'use server';
const photos = await getPhotosCached({ limit: offset + limit });
console.log(photos.length);
const nextPhotos = photos.slice(offset);
console.log('Getting next component', { offset, limit });
console.log(`Sending: ${nextPhotos.map(p => p.id).join(', ')}`);
return {
nextComponent: <PhotosLarge photos={nextPhotos} />,
isFinished: offset + limit >= count,
};
const photos = await getPhotosCached({ limit: offset + limit })
.catch(() => undefined);
if (!photos) {
return { didError: true };
} else {
const nextPhotos = photos.slice(offset);
return {
nextComponent: <PhotosLarge photos={nextPhotos} />,
isFinished: offset + limit >= count,
};
}
}}
/>
</Suspense>

View File

@ -15,8 +15,9 @@ export default function MoreComponents({
initialOffset: number
itemsPerRequest: number
getNextComponent: (offset: number, limit: number) => Promise<{
nextComponent: JSX.Element,
isFinished: boolean,
nextComponent?: JSX.Element,
isFinished?: boolean,
didError?: boolean,
}>
label?: string
triggerOnView?: boolean
@ -35,14 +36,10 @@ export default function MoreComponents({
lastIndexToLoad === undefined ||
lastIndexToLoad > indexToView;
// (lastIndexToLoad ?? 0) > indexToView;
useEffect(() => {
if (
!isLoading &&
// (lastIndexToLoad === undefined || indexToLoad <= lastIndexToLoad) &&
// indexToLoad >= 1 &&
indexToLoad > indexToView &&
indexToLoad >= indexToView &&
indexToLoad > indexLoaded
) {
setIsLoading(true);
@ -50,22 +47,23 @@ export default function MoreComponents({
initialOffset + (indexToLoad - 1) * itemsPerRequest,
itemsPerRequest,
)
.then(({ nextComponent, isFinished }) => {
setComponents(current => {
const updatedComponents = [...current];
updatedComponents[indexToLoad] = nextComponent;
return updatedComponents;
});
setIndexLoaded(indexToLoad);
if (isFinished) {
setLastIndexToLoad(indexToLoad);
.then(({ nextComponent, isFinished, didError }) => {
if (!didError && nextComponent) {
setComponents(current => {
const updatedComponents = [...current];
updatedComponents[indexToLoad] = nextComponent;
return updatedComponents;
});
setIndexLoaded(indexToLoad);
if (isFinished) {
setLastIndexToLoad(indexToLoad);
}
}
})
.finally(() => setIsLoading(false));
}
}, [
isLoading,
// lastIndexToLoad,
indexToLoad,
indexToView,
indexLoaded,
@ -77,7 +75,7 @@ export default function MoreComponents({
const buttonRef = useRef<HTMLButtonElement>(null);
const advance = useCallback(() => {
if (indexToView < indexLoaded) {
if (indexToView <= indexLoaded) {
setIndexToView(i => i + 1);
}
}, [indexToView, indexLoaded]);
@ -100,15 +98,6 @@ export default function MoreComponents({
}
}, [triggerOnView, advance]);
// console.log({
// indexToLoad,
// indexToView,
// // indexLoaded,
// lastIndexToLoad,
// componentsLength: components.length,
// componentsToView: components.slice(0, indexToView + 1).length,
// });
return <>
{components.slice(0, indexToView + 1)}
{showMoreButton &&
@ -120,7 +109,7 @@ export default function MoreComponents({
onClick={!triggerOnView ? advance : undefined}
disabled={triggerOnView || isLoading}
>
{isLoading
{isLoading || triggerOnView
? <span className="relative inline-block translate-y-[3px]">
<Spinner size={16} />
</span>