在Next.js中导入react-hook-mousetrap时出现“无法在模块外使用import语句”错误

问题描述 投票:0回答:3

尝试 Next.js 但我遇到了以下问题。只是尝试安装

react-hook-mousetrap
并像平常一样导入它:

import useMousetrap from "react-hook-mousetrap";

这给了我以下错误:

SyntaxError: Cannot use import statement outside a module
1 > module.exports = require("react-hook-mousetrap");

我不确定这意味着什么?然后我认为这可能是 Nextjs 的 SSR 的问题,因为我的库启用了热键并且将使用一些浏览器 API。如果您已经知道我在这里走错了路,您现在可以停止阅读。

接下来我做的是这个,我尝试了动态导入:

1。使用 next/dynamic 动态导入

我遇到的第一件事是

next/dynamic
,但这似乎仅适用于 JSX / React 组件(如果我错了,请纠正我)。在这里,我将导入并使用 React hook

2。使用await (...).default

动态导入

所以我尝试将其作为模块动态导入,但我不确定如何准确执行此操作。

我需要在组件的顶层使用我的钩子,无法使该组件异步,现在不知道该怎么办?

const MyComponent = () => {  
    
 // (1) TRIED THIS:
 const useMousetrap = await import("react-hook-mousetrap").default;
 //can't use the hook here since my Component is not async; Can't make the Component async, since this breaks stuff
 
 // (2) TRIED THIS:
    (async () => {
 const useMousetrap = (await import("react-hook-mousetrap")).default;
 // in this async function i can't use the hook, because it needs to be called at the top level.

    })()

 //....
}

如有任何建议,我们将不胜感激!

javascript reactjs react-hooks next.js es6-modules
3个回答
50
投票

发生错误是因为

react-hook-mousetrap
导出为 ESM 库。

Next.js 13.1 之前

您可以让 Next.js 在您的 next-transpile-modules

 中使用 
next.config.js
 来转译它。

const withTM = require('next-transpile-modules')(['react-hook-mousetrap']);

module.exports = withTM({ /* Your Next.js config */});

来自 Next.js 13.1

从 Next.js 13.1 开始,原生支持转译,不再需要使用

next-transpile-modules

module.exports = {
    transpilePackages: ['react-hook-mousetrap'],
    /* Your Next.js config */
};

2
投票

我不知道我的答案是否真实,但我今天面临这个问题,以及我做了什么:

//test component for modal 
const Button: React.FC<{close?: () => void}> = ({ close }) => (
 <React.Fragment>
    <button type="button" onClick={ close }>Close</button>
 </React.Fragment>
);

// async call import react custom hook in next js whithout a dynamic 
//import
let newHook;

(async () => {
 const { hookFromNodeModules } = 
 await import('path/to/hook');

 newHook = hookFromNodeModules;
})();

export default function Home() {
// check if hook is available
const openModal = newHook && newHook();

const { t } = useTranslation('common');

// useCallback for update call function when hook is available
const handleOpen = React.useCallback(() => {
    openModal?.openModal(Button, {});
}, [openModal]);

 return ( ...your code )
}

希望这有帮助!)

screen from next.js app


0
投票

如果您遇到诸如“SyntaxError: Unexpected token 'export'”或“'SyntaxError: Cannot use import statements Outside a module'”之类的错误以及类似问题,则有必要将导致问题的模块包含在 transpilePackages 配置中.

next.config.mjs 或 next.config.js

const nextConfig = {
  reactStrictMode: false,
  transpilePackages: [
    "antd",
    "rc-util",
    "@babel/runtime",
    "@ant-design/icons",
    "@ant-design/icons-svg",
    "rc-pagination",
    "rc-picker",
    "rc-tree",
    "rc-table",
  ],
};

export default nextConfig;
© www.soinside.com 2019 - 2024. All rights reserved.