You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

NextJS getStaticProps传值组件时缺失legalDocuments属性报错

问题原因

这个TS报错由两个核心问题导致:

  1. 你定义的组件Props类型仅声明了documentType字段,但组件实际解构接收了legalDocuments参数,TS自动推导组件要求传入两个必填参数,和手动定义的Props类型不匹配。
  2. Next.js的getStaticProps生命周期仅会在pages目录下的页面级组件中执行,普通公共组件里编写的getStaticProps不会运行,自然也不会自动把legalDocuments注入到组件props中。就算给Props补上legalDocuments类型,直接调用组件时还是需要手动传入该参数,不符合你只传documentType的使用需求。
可行解决方案

方案1:将文档加载逻辑内聚到组件中(推荐,符合使用预期)

把markdown文件读取逻辑直接放到组件内部,不需要依赖外部传入legalDocuments,调用组件时仅需传入documentType即可。注意要给nodejs原生API加环境判断,避免客户端打包时执行fs相关逻辑报错。
修正后的完整代码如下:

import marked from 'marked';
import getConfig from 'next/config';
import path from 'path';
import fs from 'fs';
import { useRouter } from 'next/router';

// 限定合法的文档类型,避免传参错误
type DocumentType = 'legalNotice' | 'privacyPolicy' | 'termsOfService'
type Props = {
    documentType: DocumentType
}

const LegalDocument = ({ documentType }: Props) => {
    const { locale, defaultLocale } = useRouter();
    let documentContent = ''

    // 仅在服务端环境执行文件读取,避免客户端打包报错
    if (typeof window === 'undefined') {
        const { serverRuntimeConfig } = getConfig()
        // 入参与实际文件名的映射关系
        const fileKeyMap: Record<DocumentType, string> = {
            legalNotice: 'legal_notice',
            privacyPolicy: 'privacy_policy',
            termsOfService: 'terms_of_service'
        }
        const supportLangs = ['de', 'en', 'es', 'fr', 'it']
        // 优先匹配当前语言,匹配失败回退到默认语言
        const targetLang = supportLangs.includes(locale as string) ? locale : defaultLocale
        try {
            const filePath = path.join(
                serverRuntimeConfig.PROJECT_ROOT,
                './legal',
                `${fileKeyMap[documentType]}.${targetLang}.md`
            )
            documentContent = marked.parse(fs.readFileSync(filePath, 'utf8'))
        } catch (e) {
            // 读取失败兜底
            documentContent = documentType
        }
    }
    
    return (
        <div dangerouslySetInnerHTML={{ __html: documentContent }} />
    )
}

export default LegalDocument

注意:marked解析后返回的是HTML字符串,直接通过{变量}渲染会把标签转义为普通文本,需要用dangerouslySetInnerHTML才能正常渲染富文本格式。

方案2:保留getStaticProps逻辑,作为页面级组件使用

如果你需要保留getStaticProps的预加载逻辑,可以把该组件放到pages目录下作为页面组件使用,同时补全Props类型定义:

// 补全完整的Props类型
type LegalDocLocaleMap = Record<string, string>
type LegalDocuments = Record<DocumentType, LegalDocLocaleMap>
type Props = {
    documentType: DocumentType,
    legalDocuments: LegalDocuments
}

该方案的缺点是无法在其他公共组件中直接通过<LegalDocument documentType="legalNotice" />的方式调用,只能通过路由参数传递documentType,由页面的getStaticProps预加载数据后传递给组件渲染。

内容的提问来源于stack exchange,提问作者Florian

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.28 23:01:10