【问题标题】:Element type is invalid. Expected a string, found undefined元素类型无效。需要一个字符串,发现未定义
【发布时间】:2021-07-21 16:00:49
【问题描述】:

这是在 next-auth 更新之后发生的。突然抛出这个错误:

Error: Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: undefined. You likely forgot to export your component from the file it's defined in, or you might have mixed up default and named imports.

Check the render method of `MyApp`.

所以我检查了 MyApp 文件,但它似乎没有任何问题,至少我没有看到任何问题。

_app.tsx(next.js 中的_app 文件)

import React from "react";
import { start, done } from "nprogress";
import "nprogress/nprogress.css";
import router from "next/router";
import "./styles/patch.css";
import { Provider } from "next-auth/client";
import { ApolloProvider } from "@apollo/client";
import { useApollo } from "../apollo/apolloClient";

router.events.on("routeChangeStart", () => start());
router.events.on("routeChangeComplete", () => done());
router.events.on("routeChangeError", () => done());

const MyApp = ({ Component, pageProps }) => {
  const apolloClient = useApollo(pageProps.initialApolloState);
  React.useEffect(() => {
    // Remove the server-side injected CSS.
    const jssStyles = document.querySelector("#jss-server-side");
    if (jssStyles) {
      jssStyles.parentElement.removeChild(jssStyles);
    }
  }, []);

  return (
    <ApolloProvider client={apolloClient}>
      <Provider session={pageProps.session}>
        <Component {...pageProps} />
      </Provider>
    </ApolloProvider>
  );
};

export default MyApp;

我是否遗漏了可能导致此错误的内容?

编辑:

显然,当我使用 webpack 4 时很好。在使用 webpack 5 时它抛出了这个错误。但是如果有 webpack 5 的解决方案会很好。

编辑 2:

当我将next 更新到版本10.2 时,它工作得非常好。也许我一定是匆匆忙忙,所以我想一开始就没有任何问题。除此之外,我很欣赏这里的答案。

【问题讨论】:

  • 会导致该错误的一件事是Componentundefined
  • Component 是一个函数参数。这是nextjs中的一个_app文件。

标签: javascript node.js reactjs next.js next-auth


【解决方案1】:

不要使用这样的查询:

  React.useEffect(() => {
     // this is wrong !!! 
    const jssStyles = document.querySelector("#jss-server-side");
    if (jssStyles) {
      jssStyles.parentElement.removeChild(jssStyles);
    }
  }, [])

尝试使用 useRef 挂钩,例如:

function TextInputWithFocusButton() {
  const inputEl = useRef(null);
  const onButtonClick = () => {
    // `current` points to the mounted text input element
    inputEl.current.focus();
  };
  return (
    <>
      <input ref={inputEl} type="text" />
      <button onClick={onButtonClick}>Focus the input</button>
    </>
  );
}

【讨论】:

  • 我忘了说这个文件实际上是nextjs中的_app文件,导出为MyApp(没问题)。基本上,这意味着它是全球性的,无论"#jss-server-side" 是什么,实际上都可以达到,我可以肯定地说,在next-auth 更新之前,该部分工作得很好。
猜你喜欢
  • 2019-05-27
  • 2018-09-14
  • 2021-12-28
  • 2020-05-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-12-31
  • 2018-01-18
相关资源
最近更新 更多