Suspense, Layouts, Dynamic Routes
Answered
Oriental chestnut gall wasp posted this in #help-forum
Oriental chestnut gall waspOP
I have a project structure like this:
Inside
In my local environment, the Suspense works as expected. In production, the
What am I doing wrong?
Repo link: https://github.com/shroommu/pokemon-battler/tree/master/src/app/pokedex/%5Bpokemon%5D
app
|
-- route
|
-- layout.js
-- page.js
-- [dynamic_route]
|
-- layout.js
-- page.jsInside
app/route/[dynamic_route]/layout.js, I have the following code:import { Suspense } from "react";
import Skeleton from "./components/Skeleton";
export default function Layout({ children }) {
return <Suspense fallback={<Skeleton />}>{children}</Suspense>;
}In my local environment, the Suspense works as expected. In production, the
fallback never renders. Sometimes the child page takes upwards of 3 seconds to load, so this is not a great user experience.What am I doing wrong?
Repo link: https://github.com/shroommu/pokemon-battler/tree/master/src/app/pokedex/%5Bpokemon%5D
Answered by Oriental chestnut gall wasp
I'm really pulling my hair out here, I don't know what else to try.
47 Replies
@American app/api/ routenamefolder/ route.ts.... not app/route
Oriental chestnut gall waspOP
assume that
route in my directory structure is routenamefolderalso i thought the
/api folder was optional and just for api calls?American
oh, my bad, I thought u trying to make api call.
Oriental chestnut gall waspOP
nope, just trying to figure out a Suspense issue 🙂
American
I got your problem
try to check with useTimeOut does your skeleton loading or not
Oriental chestnut gall waspOP
the skeleton never appears no matter what i do
i don't think it's anything to do with a timeout
American
you fetching data right and return data
?
Oriental chestnut gall waspOP
Nope, just waiting for pages to fetch through
LinkAmerican
so, try to check with useTimeout
Oriental chestnut gall waspOP
I don't understand what you mean by that
Can you provide an example?
American
https://nextjs.org/_next/image?url=%2Fdocs%2Flight%2Floading-overview.png&w=1920&q=75&dpl=dpl_HKaTZdkuaarspU2J2iNiqNmkbJqv
instead of Skeleton Component try to check with simple div
instead of Skeleton Component try to check with simple div
Oriental chestnut gall waspOP
Okay, I've already tried that and it does not show up. It doesn't matter what I set
fallback equal to, it does not render.American
const [loading, setLoading] = useState(true);
useEffect(() => {
const delayTimeout = setTimeout(() => {
setLoading(false);
}, 2000);
return () => clearTimeout(delayTimeout);
}, []);
<Suspense fallback={<LoadingFallback />}>
{!loading ? <YourComponentWithSuspense /> : null}
</Suspense>
useEffect(() => {
const delayTimeout = setTimeout(() => {
setLoading(false);
}, 2000);
return () => clearTimeout(delayTimeout);
}, []);
<Suspense fallback={<LoadingFallback />}>
{!loading ? <YourComponentWithSuspense /> : null}
</Suspense>
untill your page or component is ready, your skeleton should be visible
if this code does'nt show your loading, problem is in your suspense component
Oriental chestnut gall waspOP
HMMMMM I think I might be getting something here. So
Suspense renders the fallback if the children of the Suspense is null?American
yes
something like this
Oriental chestnut gall waspOP
Okay, that's good to know.
I think I'll try some console logs and see if i can figure out what
children is returningAmerican
suspense will show loading if his child doesn't downloaded yet
when your component is ready, loading will hidden
const [loading, setLoading] = useState(true);
useEffect(() => {
const delayTimeout = setTimeout(() => {
setLoading(false);
}, 2000);
return () => clearTimeout(delayTimeout);
}, []);
<Suspense fallback={<LoadingFallback />}>
{!loading ? <YourComponentWithSuspense /> : null}
</Suspense>try this code
then, reply me
we should solve my problem🤣
I don't know how to create input...
Oriental chestnut gall waspOP
@American so I got it working in local dev, but when I push to production, the skeleton never shows up
I think the issue is this:
Because the
layout.js with the Suspense is in a dynamic route, it gets fetched at the same time as the pageI think in production, the
Suspense never activates because the page.js is loaded by the time the layout.js loads.So I think I need to put my
Suspense in a different file. I just don't know which one.@Oriental chestnut gall wasp Because the `layout.js` with the `Suspense` is in a dynamic route, it gets fetched at the same time as the `page`
American
wait, what? did you create loading.tsx?
@Oriental chestnut gall wasp <@350186302735646721> so I got it working in local dev, but when I push to production, the skeleton never shows up
American
if you created loading.jsx/tsx you Skeleton must shown
Oriental chestnut gall waspOP
I don't have a
loading.js, I've gone down that route already haha. I couldn't get it to work in production.I can send you the production link, you can test for yourself that my skeleton never shows up. The most frustrating part of figuring this out is that local and production seem to work completely differently.
So every time i think I've fixed it, I send it to production, wait 5 minutes for it to build, and then find out it doesn't work.
Oriental chestnut gall waspOP
I've moved the
Suspense to app/route/layout.js and I think I know what the problem ischildren is never nullso the
fallback never gets renderedOriental chestnut gall waspOP
I'm really pulling my hair out here, I don't know what else to try.
Answer