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

TS2559错误求助:React Post组件类型不匹配问题排查

解决TS2559错误:Type '{ children: never[]; }' 与组件props不匹配

错误信息

undefined; }'.
{posts}
30 | | ^^^^ 31 | 32 | 33 |

问题代码

Feed组件

import React, { useEffect, useState } from 'react';
import { Outlet } from 'react-router';
import Post from './Post';
import {List} from './List'

async function getJSON(url: string) {
  const res = await fetch(url);
  return res.json();
}

export function Feed() {
  const [posts, setPosts] = useState([{id: '', title: 'initial state'}])
  const [page, setCount] = useState(0);

  useEffect(() => {
    async function setData() {
      setPosts(await getJSON(`./data/posts.json?page=${page}`));
    }
    setData();
  }, [page])

  useEffect(() => {
    console.log('render Feed');
    console.log(posts)
  })

  return <div style={{backgroundColor:'#FAFAFA'}}> 
    <List>
      {posts}
      <Post>
        
      </Post>
    </List>
    {/* <Post>
  
    </Post> */}
    <p>
      <button onClick={() => setCount(page + 1)}>Page {page}</button>
    </p>
  </div>
}

Post组件

import React, { useEffect, useState } from 'react';
import { Link, useParams } from "react-router-dom";
import {List} from './List'

async function getJSON(url: string) {
  const res = await fetch(url);
  return res.json();
}

interface IPost {
  id: string;
  title: string;
}

export default function Post({ post }: { post?: IPost }) {

  const [numLikes, addLike] = useState(0);
  const [dynamicPost, setDynamicPost] = useState({ title: '', id: '' });
  const params = useParams();

  useEffect(() => {
    async function setDynamicData() {
      console.log('setDynamicData works')
      setDynamicPost(await getJSON(`./data/post.${params.postId}.json`))
    }
    if (!post) {
      setDynamicData();
    }
    console.log('post is set!')
  }, [params.postId, post]);

  return <div>
    {post ? <div>
      <PostBox>
        <h2><Link style={{color: 'black', textDecoration: 'none' }} to={`/posts/${post?.id}`}>{post?.title || dynamicPost?.title}</Link></h2>
        <p>Num likes {numLikes}</p>
        <Like onLike={() => addLike(numLikes + 1)}>
          <strong>Bla bla</strong>
        </Like>
      </PostBox>
    </div> :
      <div><h2 style={{ color: "red" }}>no posts yet</h2></div>}
  </div>
}

interface IPropsLike {
  onLike: () => void;
  children: JSX.Element;
}

function Like({ onLike, children }: IPropsLike) {
  return <button onClick={onLike}>{children}</button>
}


function PostBox({ children }: { children: JSX.Element[] }) {
  return <div style={{ 
    border: '4px solid black',
     color:"black",
      marginBottom: '1em',
       width: '100%',
        textAlign: 'center'}}>
    {children}
  </div>
}

问题原因及修复方案

核心问题

  1. Post组件未声明接收children:Post组件的props仅定义了post?: IPost,但你在Feed中给<Post>标签添加了空的子节点,TypeScript检测到传递了未声明的children属性,触发类型不匹配错误。
  2. posts数组渲染方式错误:直接在<List>中写{posts}会把数组对象直接输出为文本,无法渲染对应的Post组件。

修复步骤

1. 移除Post组件的空子节点

将Feed中的:

<Post>
  
</Post>

修改为:

<Post />

2. 正确遍历posts数组渲染Post组件

在Feed组件中遍历posts数组,给每个Post组件传递对应的post数据:

<List>
  {posts.map(post => (
    <Post key={post.id} post={post} />
  ))}
</List>

这样既解决了类型错误,又能正确渲染所有帖子内容。

3. 可选:支持Post组件接收children(若有需求)

如果需要Post组件支持子节点,可以修改其props定义:

export default function Post({ post, children }: { post?: IPost; children?: React.ReactNode }) {
  // 原有逻辑保持不变
  return <div>
    {/* 原有渲染内容 */}
    {children}
  </div>
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 15:15:46