当我尝试使用
React.lazy
将一个 React 组件导入另一个组件时出现 TypeScript 错误
模板/BugReport/index.tsx
import { useEffect, useContext } from 'react';
import BugReportStatic from '@tamm/ui-lib-v2-bug-report';
import baseUrl from 'client/utils/baseUrl';
import { StoreContext } from 'client/services/context';
function BugReport() {
const store = useContext(StoreContext);
useEffect(() => {
BugReportStatic.init({
bugReportIntegrationApi: `${baseUrl}/pub/feedback/bugReport`,
store,
isStore: !!store,
});
return () => {
BugReportStatic.destroy();
};
}, []);
return null;
}
export default BugReport;
模板/页脚/index.tsx
const BugReport = lazy(() =>
import(/* webpackChunkName: "bug-report" */ 'client/templates/BugReport'),
);
我在
Footer
中遇到 TypeScript 错误,尽管我在 BugReport
中有默认导出
Type 'Promise<typeof import("/Users/hayksimonyan/Desktop/JTUpdates/dcd/src/client/templates/BugReport/index")>' is not assignable to type 'Promise<{ default: ComponentType<any>; }>'.
Property 'default' is missing in type 'typeof import("/Users/hayksimonyan/Desktop/JTUpdates/dcd/src/client/templates/BugReport/index")' but required in type '{ default: ComponentType<any>; }'.ts(2322)
index.d.ts(789, 34): 'default' is declared here.
index.d.ts(789, 18): The expected type comes from the return type of this signature.
module "/Users/hayksimonyan/Desktop/JTUpdates/dcd/src/client/templates/BugReport/index"
这里有一个注释,我在 BugReport 文件夹中也有
index.ts
文件,当我删除该文件时错误消失,但它需要在那里
我知道我回答晚了,但也许其他人将来也会遇到同样的问题,就像我刚才所做的并自己解决的那样,但不是在进入此页面并且找不到任何答案之前😀。
您正在使用 Typescript,而无需将函数键入为 React 组件。
React.lazy() 期望 React 组件作为输入。
由于你的函数返回 null 并且没有键入,React.Lazy 无法知道它是一个 React 组件。
要解决此问题,您可以:
选项 1 - 将返回值从 null 更改为片段,例如
return <></>;
,或
选项 2 - 从函数组件切换到类组件。由于 Clas 组件必须具有
render()
方法,因此即使具有 return null;
或 ,它也会被检测为 React 组件
选项 3 - 切换到箭头函数并向其添加类型,例如 React.FC 或 React.FunctionComponent。 -
const BugReport: FC = () => null;
对于未来进入这里的任何人。在我输入的时候,为了让 React.lazy() 工作,你应该遵循上面提到的三个选项之一,并且,正如 @Hayk 所说,你的组件必须有一个
export default YourComponent
。
应用程序/layout.tsx
const ToastProvider = lazy(() => import("./providers/ToastProvider"))
应用程序/providers/ToastProdivder.tsx
不正确
"use client"
import useToast from "@/store/ui/useToast"
import { AnimatePresence } from "framer-motion"
const Toast = async () => {
const toast = import("@/components/ui/Toast")
const { Toast } = await toast
return <Toast />
}
export function ToastProvider() {
const toast = useToast()
return <AnimatePresence>{toast.isOpen && <Toast />}</AnimatePresence>
}
正确
"use client"
import useToast from "@/store/ui/useToast"
import { AnimatePresence } from "framer-motion"
const Toast = async () => {
const toast = import("@/components/ui/Toast")
const { Toast } = await toast
return <Toast />
}
export default function ToastProvider() {
const toast = useToast()
return <AnimatePresence>{toast.isOpen && <Toast />}</AnimatePresence>
}