leerob.io icon indicating copy to clipboard operation
leerob.io copied to clipboard

May I ask why don't usegenerateStaticParams()

Open talpx0 opened this issue 1 year ago • 4 comments

path "\app\blog[slug]\page.tsx"

export default function Blog({ params }) {
  let post = getBlogPosts().find((post) => post.slug === params.slug);

  if (!post) {
    notFound();
  }

  return (
    <section>
      <script
        type="application/ld+json"
        suppressHydrationWarning
        dangerouslySetInnerHTML={{
          __html: JSON.stringify({
            '@context': 'https://schema.org',
            '@type': 'BlogPosting',
            headline: post.metadata.title,
            datePublished: post.metadata.publishedAt,
            dateModified: post.metadata.publishedAt,
            description: post.metadata.summary,
            image: post.metadata.image
              ? `https://leerob.io${post.metadata.image}`
              : `https://leerob.io/og?title=${post.metadata.title}`,
            url: `https://leerob.io/blog/${post.slug}`,
            author: {
              '@type': 'Person',
              name: 'Lee Robinson',
            },
          }),
        }}
      />
      <h1 className="title font-medium text-2xl tracking-tighter max-w-[650px]">
        {post.metadata.title}
      </h1>
      <div className="flex justify-between items-center mt-2 mb-8 text-sm max-w-[650px]">
        <p className="text-sm text-neutral-600 dark:text-neutral-400">
          {formatDate(post.metadata.publishedAt)}
        </p>
        <Suspense fallback={<p className="h-5" />}>
          <Views slug={post.slug} />
        </Suspense>
      </div>
      <article className="prose prose-quoteless prose-neutral dark:prose-invert">
        <CustomMDX source={post.content} />
      </article>
    </section>
  );
}

let incrementViews = cache(increment);

async function Views({ slug }: { slug: string }) {
  let views = await getViewsCount();
  incrementViews(slug);
  return <ViewCounter allViews={views} slug={slug} />;
}

Why doesn't it have to use generateStaticParams()? Is it because it reads from a local source?

export async function generateStaticParams() {
  const posts = await fetch('https://.../posts').then((res) => res.json())
 
  return posts.map((post) => ({
    slug: post.slug,
  }))
}

talpx0 avatar Nov 29 '23 07:11 talpx0

First, "https://.../posts" would not be a valid URL. But the main server is indeed that the data is read from local sources. Each page load will also update the view counter

PieterDePauw avatar Nov 29 '23 15:11 PieterDePauw

First, "https://.../posts" would not be a valid URL. But the main server is indeed that the data is read from local sources. Each page load will also update the view counter

https://nextjs.org/docs/app/api-reference/functions/generate-static-params

  • So ,my question is like,The generateStaticParams function can be used in combination with dynamic route segments to statically generate routes at build time instead of on-demand at request time. But since it is read from local resources,it will automatically get injected at build time?

talpx0 avatar Nov 29 '23 19:11 talpx0

@talpx0 You're right, you can retrieve the slug and set it with generateStaticParams, which will generate the routes at the build time which I'd recommend.

https://github.com/leerob/leerob.io/blob/e9357c5d53737ae977d4bfcb1b58ac832d155b5f/app/blog/%5Bslug%5D/page.tsx#L10-L13

@PieterDePauw The URL can be valid in many ways for example using the route.ts, GitHub API, etc.

devjiwonchoi avatar Dec 01 '23 17:12 devjiwonchoi

@talpx0 That's my version of doing it. All the posts will be rendered during building time. Checkout my website https://tonywang.io if you're interested.

export const generateStaticParams = async () => {
  const allBlogs = getBlogPosts();  
  const paths = allBlogs.map((post)=> ({slug: post.slug}))
  return paths
}

image

tonywangcn avatar Dec 28 '23 15:12 tonywangcn