首页 > 解决方案 > 警告非确定性路由危险:尝试创建页面:[...] 已存在

问题描述

Gatsby我完成了使用and编写了一个小型博客应用程序React。当我在本地尝试时一切正常。所以我继续gatsby build并将构建文件夹部署到Netlify. 但是,部署后,尽管本地一切正常,但某些页面的内容并未显示。

问题描述:我有一个导航栏,其中包含“家庭”、“医疗保健”、“技术”、“机器人”、“帖子”、“新闻通讯”,并且每次用户点击例如“机器人”时都会出现一系列帖子从该类别显示。现在本地一切正常,但一旦我部署,我只能看到包含所有帖子的“帖子”页面。导航栏中的其他选择不会呈现其他帖子类别。

在我从终端收到的错误下方:

warn Non-deterministic routing danger: Attempting to create page: "/healthcare/", but page "/healthcare" already exists This could lead to non-deterministic routing behavior

warn Non-deterministic routing danger: Attempting to create page: "/robotics/", but page "/robotics" already exists This could lead to non-deterministic routing behavior

warn Non-deterministic routing danger: Attempting to create page: "/technology/", but page "/technology" already exists This could lead to non-deterministic routing behavior

这使我认为某些页面没有在适当的时间呈现,但是,这并不能解释 localhost 完美运行与部署版本无法正常运行之间的区别。

在我的gatsby-node.js下面

const path = require('path')
// create pages dynamically
exports.createPages = async ({ graphql, actions }) => {
 // from actions we can destructure createPage
  const { createPage } = actions
   // below we will be running two queries at the same time 
   // instead of one query only
  const result = await graphql(`
    {
      allMdx {
        nodes {
          frontmatter {
            slug
          }
        }
      }
      category: allMdx {
        distinct(field: frontmatter___category)
      }
    }
  `)

  result.data.allMdx.nodes.forEach(({ frontmatter: { slug } }) => {
    createPage({
      path: `/posts/${slug}`,
      component: path.resolve(`src/templates/post-template.js`),
      context: {
        slug,
      },
    })
  })
  result.data.category.distinct.forEach(category => {
    createPage({
      path: `/${category}`,
      component: path.resolve(`src/templates/category-template.js`),
      context: {
        category,
      },
    })
  })
}

下面也是文件post-template.js

const PostTemplate = ({data}) => {
  const {
    mdx: {
      frontmatter: {title, category, image, date}, 
      body,},
    } = data;

  return ( 
  <Layout>
    <Hero/>
    <Wrapper>
      {/* post info */}
      <article>
        <Image fluid={image.childImageSharp.fluid} />
        <div className="post-info">
          <span>{category}</span>
          <h2>{title}</h2>
          <p>{date}</p>
          <div className="underline"></div>
        </div>
        <MDXRenderer>{body}</MDXRenderer>
      </article>
      {/* banner */}
      <article>
        <Banner/>
      </article>
    </Wrapper>
  </Layout>
  )
}


export const query = graphql`
  query GetSinglePost($slug: String) {
    mdx(frontmatter: {slug: {eq: $slug}}) {
      frontmatter {
        title
        category
        date(formatString: "MMMM Do, YYYY")
        image {
          childImageSharp {
            fluid {
              ...GatsbyImageSharpFluid
            }
          }
        }
      }
      body
    }
  }
`
const Wrapper = styled.section`
// style goes here ...
`

export default PostTemplate

和文件category-template.js

const CategoryTemplate = props => {
  console.log(props);
  const {
    pageContext: { category },
  } = props;

  const {
    data: {
      categories: {nodes:posts}
    }
  } = props;

  return (
    <Layout>
      <Hero/>
      <Posts posts={posts} title={`category / ${category}`}/>
    </Layout>
  )
}

export const query = graphql`
  query GetCategories($category: String) {
    categories: allMdx(sort: {fields: frontmatter___date, order: DESC}, filter: {frontmatter: {category: {eq: $category}}}) {
      nodes {
        excerpt
        frontmatter {
          title
          author
          category
          date(formatString: "MMMM, Do, YYYY")
          slug
          readTime
          image {
            childImageSharp {
              fluid {
                ...GatsbyImageSharpFluid
              }
            }
          }
        }
        id
      }
    }
  }
`
export default CategoryTemplate

在页面组件的结构下方robotics(所有其他页面组件具有相同的确切结构healthcaretechnology所以我只包括一个)

机器人学.js

const robotics = () => {
    return (
        <Layout>
            <SEO title="Robotics"/>
            <Hero />
            <h2>robotics page</h2>
        </Layout>
    )
}

export default robotics

为了解决这个问题,我做了很多研究,但在我想指出我之前已经清理并重新部署了几次相同的应用程序之前。所以我到目前为止所尝试的:

  1. sudo gatsby clean && sudo gatsby develop在它工作之后我做了sudo gatsby build

部署构建文件夹后,一些页面没有正确呈现,所以我:

  1. sudo m -rf node_modules sudo rm -rf public/sudo rm -rf package-lock.json 继续:
  2. sudo npm install(如有必要,您必须这样做sudo nom install --unsafe-perm)和
  3. sudo gatsby develop && sudo gatsby build

但不幸的是,完全相同的结果:localhost everthing 工作正常,并且在Netlify某些页面上根本没有呈现。

所以我做了额外的研究,我研究了这篇文章,它代表了我遇到的同样的问题。不幸的是,没有接受任何答案。但我试图应用这个建议,事实上gatsby-node.js我有:

exports.createPages = async ({ graphql, actions, reporter }) => {
  const yourQuery= await graphql(
          `
            {
              parameters here
            }
          `
  if (yourQuery.errors) {
    reporter.panicOnBuild(`Error while running GraphQL query.`);

    return;
  }

但是什么也没发生。

我也研究了这个这个。这篇文章说“MDX 页面当前不能与 JSX 页面位于同一目录中”,但我不确定这是准确的,也没有在官方文档中看到显示不这样做的示例。

请指导我在这一点上找到一个潜在的解决方案。

标签: javascriptnode.jsreactjsgatsbynetlify

解决方案


您的问题取决于命名,我认为它会影响所有页面(机器人、医疗保健、技术等)。这个:

const robotics = () => {
    return (
        <Layout>
            <SEO title="Robotics"/>
            <Hero />
            <h2>robotics page</h2>
        </Layout>
    )
}

export default robotics

应该:

const Robotics = () => {
    return (
        <Layout>
            <SEO title="Robotics"/>
            <Hero />
            <h2>robotics page</h2>
        </Layout>
    )
}

export default Robotics

注意大写的组件 ( Robotics)。这是因为,在 React 中,所有组件名称都必须大写,否则,React 的分配将永远无法工作。

其余代码,没有 CodeSandbox 很难检查,但看起来不错。

此外,也可能导致这种行为的是插件的使用,例如gatsby-plugin-remove-trailing-slashes,因此请仔细检查您是否正在使用它。


在问题的范围之外(并且因为sudo gatsby develop && sudo gatsby build),您似乎不知道 and 之间的区别gatsby developgatsby build它们不是互补的,使用该命令没有意义。

总而言之,gatsby build创建一个具有生产就绪优化的站点版本,例如打包站点的配置、数据和代码,并创建所有静态 HTML 页面,这些页面最终会重新水合到 React 应用程序中。

gatsby develop只需在后台运行服务器,启用有用的功能,并针对快速反馈和额外的调试信息进行了优化。它不会捆绑和编译您的代码生产环境,可能会隐藏一些将出现在 Netlify 中的问题,因为它运行gatsby build.

使用该命令,您正在开发您的站点并通过运行 退出该过程gatsby build,而不提供它。

因此,为了在将站点推送到 Netlify 之前仔细检查您的站点,我建议在gatsby build && gatsby serve本地运行一个,因为如果 Netlify 和本地的 Node 版本相同,则该项目在两个环境中的行为必须相同。

您可以阅读Gatsby 文档以获得进一步的解释。


我做了额外的研究,我研究了这篇文章,它代表了我遇到的同样的问题。不幸的是,没有接受任何答案。

我回答了那个问题。错误输出可能相同,但它是由完全不同的用例引起的。在这种情况下,问题依赖于错误/未完成的承诺方法,它只影响动态页面,在你的情况下是相反的。在您的场景中,“静态”页面是由于命名错误导致的问题,因为 React 无法解决组件分配。


推荐阅读