【问题标题】:waiting for useeffect to finish and then accessing object properties等待 useEffect 完成,然后访问对象属性
【发布时间】:2026-02-14 11:15:01
【问题描述】:

我有以下代码:

const [files, setFiles] = useState([]);
const [greeting, setGreeting] = useState(0);
const [menu, setMenu] = useState([]);
const [options, setOptions] = useState([]);
var customer_id = 1;

useEffect(() => {
    async function getFiles() {
      
      var data = {
        "customer-id": customer_id
      };
      let response = await axios.post(`http://localhost:2000/files/get-files`, data)
      //let response = await axios.post(`/files/get-files`, data)
      for (let i = 0; i < response.data.length; i++) {
        setOptions(oldArray => [...oldArray, {'value': response.data[i]['id'], 'label': response.data[i]['name']}])
      }
      setFiles(response.data)
    }
    async function getIVR() {
      
        var data = {
          "customer-id": customer_id
        };
        let response = await axios.post(`http://localhost:2000/files/get-ivr`, data)
        //let response = await axios.post(`/files/get-ivr`, data)
        
        setGreeting(response.data[0]['greeting'])
        setMenu(response.data[0]['menu'])
    }

    getFiles()
    getIVR() 
}, []);
var test = (options.find(x => x.value === greeting))
console.log(test.get('label'))

上面的代码返回错误:

TypeError: Cannot read property 'get' of undefined

这是因为第一次渲染标签不存在,因为尚未填充选项。但是,当我只是 console.log(test) 时,我可以看到它在几毫秒后被填充,如日志所示:

27GreetingMenu.js:53 undefined
GreetingMenu.js:53 undefined
GreetingMenu.js:53 {value: 3, label: "Test Menu"}
GreetingMenu.js:53 {value: 3, label: "Test Menu"}
GreetingMenu.js:53 {value: 3, label: "Test Menu"}
GreetingMenu.js:53 {value: 3, label: "Test Menu"}

我怎样才能做到,这样我总能得到标签的价值。这可以通过等待 useeffect 完成来完成,这意味着选项很好,这意味着我可以解析它。

告诉我!

【问题讨论】:

  • 与您的问题无关,但您的 useEffect 中有 2 个异步函数有什么原因吗?

标签: javascript reactjs react-hooks use-effect use-state


【解决方案1】:

我认为您在这里尝试解决错误的问题。

首先:这是因为第一次渲染标签不存在,因为尚未填充选项 - 并不完全正确。问题不在于label 属性未设置,而是test 未定义,因为find 没有匹配到。

与其尝试等待 useEffect 完成(您不能直接完成),不如在将 test 用作对象之前进行简单检查以确保其已定义。

var test = (options.find(x => x.value === greeting))

// Easiest solution
console.log(test?.get('label'))

// Without nullsafe operator
console.log(test && test.get('label'))

附带说明,因为接下来您可能会遇到此错误:我没有看到 get 方法被添加到 options 内的对象中?所以你可能会得到一个错误,说.get is not a function。

看起来您可能假设test 将是一个不可变对象?但我没有看到任何地方的代码可以做到这一点。

【讨论】:

    【解决方案2】:

    我认为你可以使用useEffect 取决于optionsgreeting 的变化

    当options有值时,可以获得label

    useEffect(()=>{
      if(options && options.length > 0){
        var test = (options.find(x => x.value === greeting));
        console.log(test && test.get('label'));
      }
    },[options, greeting]);
    

    【讨论】: