当我尝试 运行 yarn build in next.js 时出现错误
I get an error when I try to run yarn build in next.js
我正在尝试使用 yarn build
命令构建我的 next.js 项目,但我总是收到此错误:
Error: Export encountered errors on following paths:
/settings
at D:\web3\futnft\frontend\node_modules\next\dist\export\index.js:498:19
at runMicrotasks (<anonymous>)
at processTicksAndRejections (node:internal/process/task_queues:96:5)
at async Span.traceAsyncFn (D:\web3\futnft\frontend\node_modules\next\dist\trace\trace.js:75:20)
at async D:\web3\futnft\frontend\node_modules\next\dist\build\index.js:1024:17
at async Span.traceAsyncFn (D:\web3\futnft\frontend\node_modules\next\dist\trace\trace.js:75:20)
at async D:\web3\futnft\frontend\node_modules\next\dist\build\index.js:898:13
at async Span.traceAsyncFn (D:\web3\futnft\frontend\node_modules\next\dist\trace\trace.js:75:20)
at async Object.build [as default] (D:\web3\futnft\frontend\node_modules\next\dist\build\index.js:82:25
这是我在 pages/settings
下的 index.tsx 文件:
import { ethers } from "ethers";
import { NextPage } from "next";
import React from "react";
import { Settings as SettingsComponent } from "../../components/Settings";
interface Props {
setLoader: (loader: boolean) => void;
futNFTTraining: ethers.Contract;
futNFTMatch: ethers.Contract;
}
const Settings: NextPage<Props> = ({
setLoader,
futNFTMatch,
futNFTTraining,
}) => {
return (
<SettingsComponent
setLoader={setLoader}
futNFTMatch={futNFTMatch}
futNFTTraining={futNFTTraining}
/>
);
};
export default Settings;
这是components/
下的Settings.tsx文件:
import { ethers } from "ethers";
import Link from "next/link";
import React, { useState } from "react";
import settingsStyles from "../styles/Settings.module.scss";
interface Props {
setLoader: (loader: boolean) => void;
futNFTTraining: ethers.Contract;
futNFTMatch: ethers.Contract;
}
export const Settings: React.FunctionComponent<Props> = ({
futNFTMatch,
futNFTTraining,
setLoader,
}) => {
const setValue = async (setter: ethers.ContractFunction, value: any) => {
setLoader(true);
const tx = await setter(value);
await tx.wait();
setLoader(false);
};
const [formation, setFormation] = useState<string>("");
const [positions, setPositions] = useState<string[]>([]);
const [signer, _] = useState<ethers.Signer>(
(window as any).provider.getSigner()
);
return (
<div className={settingsStyles.settingsContainer}>
<h2>Mint New NFTs</h2>
<Link href="/mint">
<a className={settingsStyles.link}>Mint</a>
</Link>
<h2>Set State Variables</h2>
<h3>FutNFTTraining Smart Contract</h3>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>cooldown</span>
<input
type="number"
name="cooldown"
id="cooldown"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>seconds</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTTraining.connect(signer).setCooldown,
parseInt(
(document.getElementById("cooldown")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>fee</span>
<input
type="number"
name="fee"
id="fee"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>MATIC</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTTraining.connect(signer).setFee,
parseInt(
(document.getElementById("fee")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>maxLevel</span>
<input
type="number"
name="maxLevel"
id="maxLevel"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}></span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTTraining.connect(signer).setMaxLevel,
parseInt(
(document.getElementById("maxLevel")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<h3>FutNFTMatch Smart Contract</h3>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>
levelPercentSuitablePosition
</span>
<input
type="number"
name="levelPercentSuitablePosition"
id="levelPercentSuitablePosition"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>%</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setLevelPercentSuitablePosition,
parseInt(
(
document.getElementById(
"levelPercentSuitablePosition"
)! as HTMLInputElement
).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>levelPercentNoPosition</span>
<input
type="number"
name="levelPercentNoPosition"
id="levelPercentNoPosition"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>%</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setLevelPercentNoPosition,
parseInt(
(
document.getElementById(
"levelPercentNoPosition"
)! as HTMLInputElement
).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>lineupFee</span>
<input
type="number"
name="lineupFee"
id="lineupFee"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>MATIC</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setLineupFee,
parseInt(
(document.getElementById("lineupFee")! as HTMLInputElement)
.value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>matchFee</span>
<input
type="number"
name="matchFee"
id="matchFee"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>MATIC</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setMatchFee,
parseInt(
(document.getElementById("matchFee")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.formation}>
<h4>Add Formation</h4>
<input
type="text"
name="formationName"
id="formationName"
placeholder="Formation Name"
onChange={() => {
const formationName = (
document.getElementById("formationName")! as HTMLInputElement
).value;
setFormation(formationName);
if (formationName.length == 0) {
setPositions([]);
}
}}
/>
{formation.length > 0 && (
<>
<div>
<input
type="text"
name="position"
id="position"
placeholder="Position"
/>
<button
onClick={() => {
const position = (
document.getElementById("position")! as HTMLInputElement
).value;
if (position.length > 0 && positions.length < 11) {
const newArr = positions;
newArr.push(position);
setPositions(newArr);
}
}}
>
Add Position
</button>
</div>
<div className={settingsStyles.positions}>
{positions.map((position, key) => {
return (
<div className={settingsStyles.position} key={key}>
<p>{position}</p>
<button
onClick={() => {
const index = positions.indexOf(position);
const newArr = positions;
newArr.splice(index, 1);
setPositions(newArr);
}}
>
✗
</button>
</div>
);
})}
</div>
{positions.length == 11 && <button>Add Formation</button>}
</>
)}
</div>
</div>
);
};
export default Settings;
我发现了另一个具有相同问题的 Stack Overflow 问题,但无法解决我的问题。我尝试了很多删除无用道具的方法,但没有用。
当您运行此代码时,您的设置组件中是否定义了window
?由于 Next.js pre-renders 页面 server-side 在发送给客户端之前,它可能不可用。因此,您可能需要在 useEffect
挂钩中执行该逻辑才能在浏览器中执行它。
我在尝试从 localStorage
访问值时遇到了类似的问题。
我正在尝试使用 yarn build
命令构建我的 next.js 项目,但我总是收到此错误:
Error: Export encountered errors on following paths:
/settings
at D:\web3\futnft\frontend\node_modules\next\dist\export\index.js:498:19
at runMicrotasks (<anonymous>)
at processTicksAndRejections (node:internal/process/task_queues:96:5)
at async Span.traceAsyncFn (D:\web3\futnft\frontend\node_modules\next\dist\trace\trace.js:75:20)
at async D:\web3\futnft\frontend\node_modules\next\dist\build\index.js:1024:17
at async Span.traceAsyncFn (D:\web3\futnft\frontend\node_modules\next\dist\trace\trace.js:75:20)
at async D:\web3\futnft\frontend\node_modules\next\dist\build\index.js:898:13
at async Span.traceAsyncFn (D:\web3\futnft\frontend\node_modules\next\dist\trace\trace.js:75:20)
at async Object.build [as default] (D:\web3\futnft\frontend\node_modules\next\dist\build\index.js:82:25
这是我在 pages/settings
下的 index.tsx 文件:
import { ethers } from "ethers";
import { NextPage } from "next";
import React from "react";
import { Settings as SettingsComponent } from "../../components/Settings";
interface Props {
setLoader: (loader: boolean) => void;
futNFTTraining: ethers.Contract;
futNFTMatch: ethers.Contract;
}
const Settings: NextPage<Props> = ({
setLoader,
futNFTMatch,
futNFTTraining,
}) => {
return (
<SettingsComponent
setLoader={setLoader}
futNFTMatch={futNFTMatch}
futNFTTraining={futNFTTraining}
/>
);
};
export default Settings;
这是components/
下的Settings.tsx文件:
import { ethers } from "ethers";
import Link from "next/link";
import React, { useState } from "react";
import settingsStyles from "../styles/Settings.module.scss";
interface Props {
setLoader: (loader: boolean) => void;
futNFTTraining: ethers.Contract;
futNFTMatch: ethers.Contract;
}
export const Settings: React.FunctionComponent<Props> = ({
futNFTMatch,
futNFTTraining,
setLoader,
}) => {
const setValue = async (setter: ethers.ContractFunction, value: any) => {
setLoader(true);
const tx = await setter(value);
await tx.wait();
setLoader(false);
};
const [formation, setFormation] = useState<string>("");
const [positions, setPositions] = useState<string[]>([]);
const [signer, _] = useState<ethers.Signer>(
(window as any).provider.getSigner()
);
return (
<div className={settingsStyles.settingsContainer}>
<h2>Mint New NFTs</h2>
<Link href="/mint">
<a className={settingsStyles.link}>Mint</a>
</Link>
<h2>Set State Variables</h2>
<h3>FutNFTTraining Smart Contract</h3>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>cooldown</span>
<input
type="number"
name="cooldown"
id="cooldown"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>seconds</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTTraining.connect(signer).setCooldown,
parseInt(
(document.getElementById("cooldown")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>fee</span>
<input
type="number"
name="fee"
id="fee"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>MATIC</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTTraining.connect(signer).setFee,
parseInt(
(document.getElementById("fee")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>maxLevel</span>
<input
type="number"
name="maxLevel"
id="maxLevel"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}></span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTTraining.connect(signer).setMaxLevel,
parseInt(
(document.getElementById("maxLevel")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<h3>FutNFTMatch Smart Contract</h3>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>
levelPercentSuitablePosition
</span>
<input
type="number"
name="levelPercentSuitablePosition"
id="levelPercentSuitablePosition"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>%</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setLevelPercentSuitablePosition,
parseInt(
(
document.getElementById(
"levelPercentSuitablePosition"
)! as HTMLInputElement
).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>levelPercentNoPosition</span>
<input
type="number"
name="levelPercentNoPosition"
id="levelPercentNoPosition"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>%</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setLevelPercentNoPosition,
parseInt(
(
document.getElementById(
"levelPercentNoPosition"
)! as HTMLInputElement
).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>lineupFee</span>
<input
type="number"
name="lineupFee"
id="lineupFee"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>MATIC</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setLineupFee,
parseInt(
(document.getElementById("lineupFee")! as HTMLInputElement)
.value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.item}>
<span className={settingsStyles.variable}>matchFee</span>
<input
type="number"
name="matchFee"
id="matchFee"
className={settingsStyles.value}
/>
<span className={settingsStyles.unit}>MATIC</span>
<button
className={settingsStyles.setBtn}
onClick={async () => {
await setValue(
futNFTMatch.connect(signer).setMatchFee,
parseInt(
(document.getElementById("matchFee")! as HTMLInputElement).value
)
);
}}
>
Set
</button>
</div>
<div className={settingsStyles.formation}>
<h4>Add Formation</h4>
<input
type="text"
name="formationName"
id="formationName"
placeholder="Formation Name"
onChange={() => {
const formationName = (
document.getElementById("formationName")! as HTMLInputElement
).value;
setFormation(formationName);
if (formationName.length == 0) {
setPositions([]);
}
}}
/>
{formation.length > 0 && (
<>
<div>
<input
type="text"
name="position"
id="position"
placeholder="Position"
/>
<button
onClick={() => {
const position = (
document.getElementById("position")! as HTMLInputElement
).value;
if (position.length > 0 && positions.length < 11) {
const newArr = positions;
newArr.push(position);
setPositions(newArr);
}
}}
>
Add Position
</button>
</div>
<div className={settingsStyles.positions}>
{positions.map((position, key) => {
return (
<div className={settingsStyles.position} key={key}>
<p>{position}</p>
<button
onClick={() => {
const index = positions.indexOf(position);
const newArr = positions;
newArr.splice(index, 1);
setPositions(newArr);
}}
>
✗
</button>
</div>
);
})}
</div>
{positions.length == 11 && <button>Add Formation</button>}
</>
)}
</div>
</div>
);
};
export default Settings;
我发现了另一个具有相同问题的 Stack Overflow 问题,但无法解决我的问题。我尝试了很多删除无用道具的方法,但没有用。
当您运行此代码时,您的设置组件中是否定义了window
?由于 Next.js pre-renders 页面 server-side 在发送给客户端之前,它可能不可用。因此,您可能需要在 useEffect
挂钩中执行该逻辑才能在浏览器中执行它。
我在尝试从 localStorage
访问值时遇到了类似的问题。