使用路由时将匹配参数和props都传递到react组件中

IT技术 javascript reactjs
2021-05-15 10:56:44

我有一个功能性的 React 组件,想在我的组件中为选定的人呈现一些属性。

所以我首先映射一个简单的列表,其中包含每个人的链接

      {props.persons.map((person, i) =>{
      return(
     <li key={i}>
      <Link to={`/topics/${person.id}`}>{person.name}</Link>
     </li>
      )
    })}
  </ul>

然后我做路线

<Route path={`/topics/:id`} render={() => <Topic persons={props.persons} />} />

截至目前,我只是通过人。

但是我也希望能够传入 id,这样我就可以找到特定的人,并呈现有关该人的信息。我曾尝试使用匹配属性,但这似乎也禁止我传入 props。

任何解决方法的提示?

也许可以只传递所选人员的属性?

编辑:

这是我迄今为止尝试过的。

   const Topic = (props) =>{
  console.log('props are ', props) //logs array of persons
  return(
    <div>
      <h2>Topic</h2>
      <p>I have been rendered</p>
    </div>
  )
}




 const Topic = ({match}) =>{
  console.log('match is ', match) //logs match parameter, but now i can't access persons
  return(
    <div>
      <h2>Topic</h2>
      <p>I have been rendered</p>
    </div>
  )
}
4个回答

当您使用的render一个props上的<Route>组件,该render函数传递与对象matchlocationhistory信息。

https://reacttraining.com/react-router/web/api/Route/route-props

<Route 
  path={`/topics/:id`} 
  render={({match}) => (
    <Topic id={match.params.id} persons={props.persons} />
  )} 
/>

您无需将 id 作为props传递给路由的 Topic 组件,因此要获取路径参数的 id,您可以在组件中执行以下操作以获取 id

在主题组件中

您可以使用

  props.match.params.id

根据https://reacttraining.com/react-router/web/api/Route

所有三个渲染方法都将传递相同的三个路由props

  • 比赛
  • 地点
  • 历史

因此,在路线的渲染props中,您应该能够引用匹配项并将其传递:

<Route 
  path={`/topics/:id`} 
  render={({match}) => (
    <Topic 
      persons={props.persons} 
      id={match.params.id} 
    />
  )} 
/>

这是因为渲染函数基本上是一个函数组件,函数组件的第一个参数是 props。(但是,您不必将第一个参数引用为propsrenderProps例如,您可以使用,或者match像我上面所做的那样将其重组为您需要的 ( ) )

然后在主题:

 const Topic = ({id, persons}) =>{
  console.log('id is ', id) //logs id parameter
  console.log('persons is ', persons) //logs persons parameter
  return(
    <div>
      <h2>Topic</h2>
      <p>I have been rendered for id {id}</p>
      <code>{JSON.stringify(persons)}</code>
    </div>
  )
}

您可以使用 useRouteMatch

所以在你的例子中:

<Route path={`/topics/:id`} render={() => <Topic persons={props.persons} />} />

变成:

<Route exact path={`/topics/:id`} component={() => <Topic persons={props.persons} />}/>

Topic.js 变成:

import { useRouteMatch } from "react-router-dom"; // Import this
const Topic = (props) =>{
 
  let match =useRouteMatch('/topics/:id').url.split('/'); // Get url and separate with /
  match=match[match.length-1]; // The id is at the end of link, so access last array index
  console.log('match id is ', match);
  console.log('persons is ', persons);

 return(
   <div>
     <h2>Topic</h2>
     <p>I have been rendered</p>
   </div>
 )
}