Home > front end >  How can i create path with uuid4()
How can i create path with uuid4()

Time:08-17

I have created a project with api. With categories it is possible to change the incoming data, but there is one thing where I want to get more detailed information when I click on the newsItem card. That api doesn't have id value, so I used uuid. Information corresponding to the id value should come with useParams. But it doesn't work. How can I fix this problem?

CodePudding user response:

The first issue is that you are generating a GUID when rendering the state array which won't necessarily correlate to any data you are trying to match/filter by in the NewsDetail component.

state.map((data,index) => (
  <NewsItem
    imageUrl={data.imageUrl}
    author={data.author}
    title={data.title}
    content={data.content}
    date={data.date}
    id={uuidv4()} // <-- new id each render cycle
    key={index}
  />
))

You want to inject the id property when the data is fetch so that it's a stable reference that lives as long as the data does. In other words, it should be an intrinsic property of the data.

Example:

const fetchValue = async (category) => {
  setLoading(true);

  try {
    const res = await fetch(`https://inshorts-api.herokuapp.com/news?category=${category}`);
    const { data } = await res.json();
    setState(data.map(el => ({
      ...el,
      id: uuidv4(), // <-- map and inject id here
    })));
  } catch(error) {
    console.log(error);
  } finally {
    setLoading(false);
  }
};

...

state.map((data) => (
  <NewsItem
    key={data.id} // <-- use as React key
    data={data} // <-- pass entire data object as prop
  />
))

NewsItem

const NewsItem = ({ data }) => {
  const { imageUrl, title, author, content, date, id } = data;

  return (
    ...
  );
};

NewsDetail

const NewsDetail = ({ state }) => {
  const { id } = useParams();

  return (
    <div>
      {state
        .filter((card) => card.id === id)
        .map((card) => (
          <div className="card" key={card.id}>
            <h2>{card.title}</h2>
            <h2>{card.content}</h2>
            <img src={card.imageUrl} alt="" />
          </div>
        ))
      }
    </div>
  );
};
  • Related