Next.js Discord

Discord Forum

useRouter query is empty on first render

Answered
Asiatic Lion posted this in #help-forum
Open in Discord
Asiatic LionOP
When the component is rendered for the first time, useRouter returns {} in query param. How to make it return actual data right away, so it won't require re-render to get them?
Answered by Asiatic Lion
@joulev useRouter().pathname is incorrect on the first render as well, so I need window.location.pathname instead
View full answer

10 Replies

@Asiatic Lion When the component is rendered for the first time, `useRouter` returns `{}` in `query` param. How to make it return actual data right away, so it won't require re-render to get them?
i assume you use the pages router

because useRouter().query contains information from the request instance, during prerendering it is {} unless you have getServerSideProps. so yeah, you need to add an empty getServerSideProps if you want router.query to have valid data immediately.
Asiatic LionOP
@joulev it seems like i can't use it Error: getServerSideProps cannot be used with "output: export"
@Asiatic Lion <@484037068239142956> it seems like i can't use it `Error: getServerSideProps cannot be used with "output: export"`
then you can't. useRouter().query will be empty during the first render and you need to make a loading screen.
@joulev then you can't. `useRouter().query` *will* be empty during the first render and you need to make a loading screen.
Asiatic LionOP
it will be empty, but you are incorrect about the loading screen. it's possible to rely on window.location.pathname and just forget about useRouter. Not the solution I like to have, but at least it's working one
@Asiatic Lion it will be empty, but you are incorrect about the loading screen. it's possible to rely on `window.location.pathname` and just forget about `useRouter`. Not the solution I like to have, but at least it's working one
useRouter().query includes both the dynamic route segments and the search params. the dynamic route can be known in advance but the search params cannot be known in advance. hence it will be empty in first render and if you use it you will need a loading screen.

you are probably looking for useRouter().pathname
Asiatic LionOP
@joulev useRouter().pathname is incorrect on the first render as well, so I need window.location.pathname instead
Answer
@Asiatic Lion <@484037068239142956> `useRouter().pathname` is incorrect on the first render as well, so I need `window.location.pathname` instead
no it should be correct in the first render. source: i use it all the time.

window.location.pathname won't work during server-side prerendering. so you need to use it inside a useEffect. another loading screen
@joulev no it should be correct in the first render. source: i use it all the time. `window.location.pathname` won't work during server-side prerendering. so you need to use it inside a `useEffect`. another loading screen
Asiatic LionOP
no, it's incorrect. source: console.log
it returns me /customer/[id] instead of real pathname. window.location.pathname will work without loading screen, I just need to skip static rendering for it (it doesn't makes sense to render anything statically anyway for dynamic params).
well, alright. since that works for you, if it works it works
Asiatic LionOP
for those who will search for this issue later on - here is the solution for such kind of URL /customer/[id]:

const Page = () => {
  return (
    <NoSSR>
      <Customer id={typeof window !== 'undefined' && window.location.pathname.split('/')[2]} />
    </NoSSR>
  );
};