JS React "event.key" 在使用 fetch API 调用时抛出错误

JS React "event.key" throwing errors when using a fetch API call

我正在使用 NASA API 抓取火星探测器拍摄的火星照片。 目前,我的代码可以获取图片,但是我希望它更加动态。 我的代码:

import React, { useEffect, useState } from "react";
import NavBar from "./NavBar";

const apiKey = process.env.REACT_APP_NASA_API_KEY;

function MarsPhoto() {

 const [data, setData] = useState('null')
 const [solDay, setSolDay] = useState('')

 const apiUrl = `https://api.nasa.gov/mars-photos/api/v1/rovers/curiosity/photos?sol=${solDay}&camera=fhaz&api_key=${apiKey}`

 const fetchPhotoData = (event) => {
    if(event.key === 'Enter') {
        fetch(apiUrl)
        .then((response) => response.json())
        .then((data) => setData(data))
    }
}

 useEffect(() => {
    fetchPhotoData()
}, [])


 return(

    <>
        <NavBar/>

        <div className="sol-search">
            <input 
            value={solDay}
            onChange={event => setSolDay(event.target.value)}
            placeholder="Enter a Sol Day"
            type="text"/>
        </div>
    
        <div className="image-fhaz">
            <img src={data.photos ? (data.photos.length !== 0 ? data.photos["0"]["img_src"] : 'https://www.ncenet.com/wp-content/uploads/2020/04/No-image-found.jpg') : 'null'}
            alt="Pitcure"/>
        </div>



    </>
)
}

export default MarsPhoto;

当我说我希望它是动态的时,我希望用户输入 'solDay',然后 API 将显示基于那天太阳的图像。 我已经在 API 中有了 'solDay' 参数。 我使用了一个密钥处理程序,所以当我输入数字时,它将进行 API 调用和 return 图像。 我有事件的输入,但是,它抛出一个“MarsPhoto.js:14 Uncaught TypeError: Cannot read properties of undefined (reading 'key')”,我不确定为什么? 与其用fetch,不如用axios好吗?我更喜欢使用 fetch,因为我对此更熟悉。 我能做什么?

首先,您应该捕获来自 api 的潜在错误响应。 其次,你在你的 fetchPhotoData 函数中请求一个事件参数,你在 useEffect 中调用它,这意味着在你的组件第一次加载时,你的函数将 运行 但是,没有事件参数,你的函数也没有为未定义的参数设置屏蔽...

看看下面的代码,它应该对你有帮助。 :)

const fetchPhotoData = (event) => {
  if (!event?.key) {
    return console.info("[fetchPhotoData] : no event.key params");
  }

  if (event.key === "Enter") {
    fetch(apiUrl)
      .then((response) => response.json())
      .then((data) => setData(data))
      .catch((e) => console.error("[fetchPhotoData] error : ", e));
  }
};

编辑:

on change, set a new data on a useEffect, 但是你没有监听这个变化,所以,你的useEffect不会再次挂载,你应该re-write你的useEffect是这样的:

const fetchPhotoData = useCallback(
    (event) => {
      ... current code
    },
    [apiUrl]
  );

  useEffect(() => {
    fetchPhotoData();
  }, [fetchPhotoData]);

apiURL 被你的 useCallback 函数的 dependecies 数组监听,并且这可以被 useEffect 正确监听。