You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React与Next.js动态路由无法跳转问题求助

Next.js动态路由跳转失败问题修复

问题概述

使用React.js+Next.js开发博客详情页动态路由,创建了blogs文件夹并放置[slug.js]文件,但点击列表页的链接无法跳转到对应详情URL。

现有代码

列表页(Allblog.tsx)链接代码

<Link href={`/blog/${todoList.id}`}>Edit</Link>

详情页(blog/[slug.js])代码

import Axios from "axios";
import  {useRouter}  from "next/router";
import { Editor } from '@tinymce/tinymce-react';

//import LatestBlogs from "../../components/LatestBlogs/LatestBlogs";
import Link from 'next/link'
import { useEffect, useState  } from 'react'
import Sidebar from '../../components/Sidebar'

const slug = ({ posts }) => {
  return(
      <div>
           <h2> Hello World </h2>
      </div>
    );
};

export default slug;

export const getStaticProps = async ({ params }) => {
 const { data } = await Axios.get(`https://xxxxxxxxxxxxxx/api/getblogbyuserid/${params.slug}`);
  const post = data;
  return {
    props: {
      post,
    },
  };
};

export const getStaticPaths = async () => {
  const { data } = await Axios.get("http://xxxxxxxxxxxxxxxxx/api/blogs");
  const posts = data.slice(0, 10);
  const paths = posts.map((post) => ({ params: { slug: post.id.toString() } }));
  return {
    paths,
    fallback: true,
  };
};

核心问题与修复方案

1. 路由路径不匹配

你创建的是blogs文件夹,但链接指向的是/blog/${todoList.id},路径前缀不统一。

  • 方案一:修改Link路径为/blogs/${todoList.id},保持和文件夹名称一致:
    <Link href={`/blogs/${todoList.id}`}>Edit</Link>
    
  • 方案二:将blogs文件夹重命名为blog,匹配现有链接路径。

2. 动态路由文件名错误

动态路由文件必须命名为[slug].js,而非[slug.js]——后者会被Next.js识别为固定文件名,无法触发动态路由解析。直接修改文件名即可。

3. Props传递不匹配

组件接收的参数是{ posts },但getStaticProps返回的是post,导致组件无法获取数据。修正组件参数:

const slug = ({ post }) => {
  return(
      <div>
           <h2> Hello World </h2>
      </div>
    );
};

4. API请求协议不一致

getStaticProps使用https协议,getStaticPaths使用http协议,可能引发跨域或请求失败。统一为相同协议(如全用https):

export const getStaticPaths = async () => {
  const { data } = await Axios.get("https://xxxxxxxxxxxxxxxxx/api/blogs");
  // ... 其余代码不变
};

5. Fallback模式加载状态处理(可选)

当fallback: true时,未预渲染的路径会触发增量静态生成,需在组件中添加加载状态提示:

const slug = ({ post }) => {
  const router = useRouter();
  
  if (router.isFallback) {
    return <div>加载中...</div>;
  }

  return(
      <div>
           <h2>{post?.title || '博客详情'}</h2>
           {/* 渲染博客内容 */}
      </div>
    );
};

修正后完整详情页示例

import Axios from "axios";
import { useRouter } from "next/router";
import Link from 'next/link'
import { useEffect, useState } from 'react'
import Sidebar from '../../components/Sidebar'

const SlugPage = ({ post }) => {
  const router = useRouter();
  
  if (router.isFallback) {
    return <div>加载中...</div>;
  }

  if (!post) {
    return <div>博客不存在</div>;
  }

  return(
      <div>
           <h2>{post.title}</h2>
           <div dangerouslySetInnerHTML={{ __html: post.content }} />
      </div>
    );
};

export default SlugPage;

export const getStaticProps = async ({ params }) => {
  try {
    const { data } = await Axios.get(`https://xxxxxxxxxxxxxx/api/getblogbyuserid/${params.slug}`);
    return {
      props: {
        post: data,
      },
      revalidate: 60, // 每60秒重新验证生成静态页
    };
  } catch (error) {
    return {
      props: { post: null },
    };
  }
};

export const getStaticPaths = async () => {
  try {
    const { data } = await Axios.get("https://xxxxxxxxxxxxxxxxx/api/blogs");
    const posts = data.slice(0, 10);
    const paths = posts.map((post) => ({ params: { slug: post.id.toString() } }));
    return {
      paths,
      fallback: true,
    };
  } catch (error) {
    return {
      paths: [],
      fallback: true,
    };
  }
};

内容的提问来源于stack exchange,提问作者Rick

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.09 08:50:29