Fetch API只在第二次按下回车键后才能正常工作。

huangapple go评论98阅读模式
英文:

Fetch api only works after second Enter key input NextJS

问题

组件应该在将输入键入搜索栏并单击回车键后,在控制台日志中显示JSON数据。它确实可以实现这一点,但它会滞后,直到再次单击回车键才会显示。接下来,当您更改搜索栏中的输入并单击回车键时,它将显示上一次搜索的结果。只有再次单击回车键才会获取当前搜索的结果。

对于搜索栏输入,您可以使用"Reinforcements"或"Contact"。

import { Box, Input } from "@chakra-ui/react";
import styles from "../styles/search.module.css";
import React, { useState } from "react";

export default function Search() {
  const [cardName, setCardName] = useState("");
  const [searchCard, setSearchCard] = useState("");

  const handleChange = (event) => {
    setCardName(event.target.value);
  };
  const handleKeyDown = (event) => {
    if (event.key == "Enter") {
      setSearchCard(cardName);
      fetch(`https://db.ygoprodeck.com/api/v7/cardinfo.php?name=${searchCard}`)
        .then((response) => response.json())
        .then((json) => console.log(json));
    }
  };

  return (
    <>
      <Box className={styles.container}>
        <Input
          size="lg"
          bg="#e8f1f2"
          placeholder="Search for a card"
          id="cardName"
          name="cardName"
          value={cardName}
          onChange={handleChange}
          onKeyDown={handleKeyDown}
          className={styles.input}
        ></Input>
        <ul className={styles.list"></ul>
      </Box>
    </>
  );
}
英文:

How the component is suppose to work is after typing the input into the search bar and clicking on the enter key, it should show in the console log the json data. It does this, but it lags behind and won't show until clicking the enter key a second time. Next when changing the input in the search bar and clicking the enter key, it'll show the results of the previous search. You won't get the current search until you clicking the enter key again.

For the search bar input, you can use Reinforcements or Contact.

import { Box, Input } from &quot;@chakra-ui/react&quot;;
import styles from &quot;../styles/search.module.css&quot;;
import React, { useState } from &quot;react&quot;;

export default function Search() {
  const [cardName, setCardName] = useState(&quot;&quot;);
  const [searchCard, setSearchCard] = useState(&quot;&quot;);

  const handleChange = (event) =&gt; {
    setCardName(event.target.value);
  };
  const handleKeyDown = (event) =&gt; {
    if (event.key == &quot;Enter&quot;) {
      setSearchCard(cardName);
      fetch(`https://db.ygoprodeck.com/api/v7/cardinfo.php?name=${searchCard}`)
        .then((response) =&gt; response.json())
        .then((json) =&gt; console.log(json));
    }
  };

  return (
    &lt;&gt;
      &lt;Box className={styles.container}&gt;
        &lt;Input
          size=&quot;lg&quot;
          bg=&quot;#e8f1f2&quot;
          placeholder=&quot;Search for a card&quot;
          id=&quot;cardName&quot;
          name=&quot;cardName&quot;
          value={cardName}
          onChange={handleChange}
          onKeyDown={handleKeyDown}
          className={styles.input}
        &gt;&lt;/Input&gt;
        &lt;ul className={styles.list}&gt;&lt;/ul&gt;
      &lt;/Box&gt;
    &lt;/&gt;
  );
}

答案1

得分: 1

以下是代码部分的翻译:

setSearchCard(cardName); // 第一行
fetch(`https://db.ygoprodeck.com/api/v7/cardinfo.php?name=${searchCard}`) // 第二行
  .then((response) => response.json())
  .then((json) => console.log(json));

在第一行中,您更新了 searchCard,然后在第二行中基于 searchCard 调用了您的 API。

在第一行中,您更新了 searchCard,然后在第二行中基于 searchCard 调用了您的 API。

所以,您期望 searchCard 立即更新,但这不是 React 的工作方式。状态只在组件重新渲染时才会更新。

所以,在这里,您需要做以下更改:

setSearchCard(cardName);
fetch(`https://db.ygoprodeck.com/api/v7/cardinfo.php?name=${cardName}`)
  .then((response) => response.json())
  .then((json) => console.log(json));

发生的情况是,假设您执行了 setCardName("first"),然后调用了 API(因为组件尚未重新渲染),此时 cardName 仍然等于 ''。当组件重新渲染时(因为 useState 钩子已更新),然后您再次点击 setCardName("second"),然后再次调用 API(因为组件尚未重新渲染),此时 cardName 仍然等于 "first"。这就是为什么您认为需要点击两次才能获得有效响应的原因。

英文:

look at this :

setSearchCard(cardName); // first line
fetch(`https://db.ygoprodeck.com/api/v7/cardinfo.php?name=${searchCard}`) // second line
.then((response) =&gt; response.json())
.then((json) =&gt; console.log(json));

In the first line you update searchCard then in the second line you call your API based on searchCard.<br>
so you expected searchCard to be updated immediately but this is not how react works the state will be updated only when the component rerenders<br>
so here what you have to do is :

setSearchCard(cardName); 
fetch(`https://db.ygoprodeck.com/api/v7/cardinfo.php?name=${cardName}`) 
.then((response) =&gt; response.json())
.then((json) =&gt; console.log(json));

So what is happening is if we suppose that you setCardName(&quot;first&quot;) then you call the API (since the component didn't rerendered yet) cardName is still equal to &#39;&#39;<br> when the component rerenders (because a useState hook is updated) and you click again to setCardName(&quot;second&quot;) then you call the API (since the component didn't rerendered yet) cardName is still equal to &quot;first&quot; that's why you think you have to click twice to get a valid response

huangapple
  • 本文由 发表于 2023年3月12日 09:04:50
  • 转载请务必保留本文链接:https://go.coder-hub.com/75710519.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定