React Native, useState, похоже, не устанавливает значение - PullRequest
0 голосов
/ 04 августа 2020

Я выполняю запрос ax ios get, и значение, похоже, не устанавливается с первой попытки.

странно то, что оно устанавливается при второй попытке.

Я указываю на идентификатор.

хук

const [id, setId] = useState("");

на первом проходе, однако идентификатор пуст (вы можете увидеть мой комментарий)

Вот запрос ax ios.

const setDevice = async () => {
    setIsLoading(true);
    setShowModal(false);
    try {
      console.log("trying")
      console.log("Serial Number is " + serialNumber)
      const response = await axios.get(
        url + serialNumber,
        {
          headers: { Authorization: authHeader },
        }
        
      );
      //This does not seem to be working
      setId(response.data.mobile_devices[0].id);
    } catch (err) {
      console.log("Failed");
      setError("Something went Wrong");
      setIsLoading(false);
      setShowModal(false);
      setShowErrorModal(true);
    }
    //because this is blank
    console.log("trying to put with id of " + id)
    await axios.put(
      url + id,
      body,
      {
        headers: {
          Authorization: authHeader,
          "Content-Type": "application/xml",
        },
      }
    );
    setIsLoading(false);
  };

Это данные, которые есть в запросе на получение

Object {
  "mobile_devices": Array [
    Object {
      "department": "",
      "department_name": "",
      "email": "",
      "email_address": "",
      "id": 1,
      "position": "",
      "realname": "",
      "room": "",
      "username": "",
    },
  ],
}

Ответы [ 2 ]

1 голос
/ 04 августа 2020

Проблема в том, что обновление состояния, выполняемое с помощью setId(<some id>), является асинхронным c. Поэтому вы не сможете сразу получить доступ к вновь установленному идентификатору.

Для обработки таких ситуаций, в которых некоторый код зависит от обновленного состояния, был введен хук useEffect . Он вызывается после того, как ваш компонент обновляется с новым состоянием и принимает массив зависимостей (в вашем случае это id).

В вашем случае вы можете использовать его так:

useEffect(() => {
    // check that id is already set
    if (id) {
      axios.put(
        url + id,
        body,
        {
          headers: {
            Authorization: authHeader,
            "Content-Type": "application/xml",
          },
        }
      ).then(() => {
        setIsLoading(false);
      }).catch(error => {
         //handle errors here if needed.
      })
    }
}, [id, setIsLoading]);

Обратите внимание, поместите это под функцией useState (const [id, setId] = useState("");)

UPDATE

Оказалось, что идентификатор не нужен в состоянии и запрос на размещение должен выполняться при вызове setDevice, а не при изменении идентификатора. В этом случае использование хука useEffect не требуется, и запрос на размещение может быть выполнен с полученным id:

const setDevice = async () => {
    try {
      const response = await axios.get("url" + serialNumber, {
        headers: { Authorization: authHeader },
      });
      const id = response.data.mobile_devices[0].id;
      await axios.put(
          url + id,
          body,
          {
            headers: {
              Authorization: authHeader,
              "Content-Type": "application/xml",
            },
          }
        )
    } catch (err) {
      setError("Something went Wrong");
      setIsLoading(false);
      setShowModal(false);
      setShowErrorModal(true);
    }
  };
0 голосов
/ 04 августа 2020

Ciao, к сожалению, такое поведение совершенно нормально. В хуках setId является asyn c, поэтому не гарантируется, что в следующей строке id будет значение, установленное в setId.

Если вы хотите получать значение id каждый раз, когда это меняет свое значение, вы должны использовать хук useEffect. Что-то вроде:

useEffect(() => {
   console.log("this is the value of id: " + id);
}, [id]);

Как видите, я поместил id в список useEffect deps. Это означает, что useEffect будет запускаться каждый раз при изменении значения id.

...