简体   繁体   English

在 React 中调用同步 function 来编辑 API 异步调用 UseEffect

[英]Calling a synchronous function in React to edit API Call in async UseEffect

So I have a UseEffect function which is being called every 2 seconds that returns the price of a crypto currency.所以我有一个 UseEffect function 每 2 秒调用一次,返回加密货币的价格。 When I get a value is returned I call a removeZeroes() in the render section to edit the price format.当我得到一个返回值时,我在渲染部分调用 removeZeroes() 来编辑价格格式。 This causes a lot of weird things to happen这会导致很多奇怪的事情发生

const [price, setPrice] = useState("...")
const [onedaychange, setOnedaychange] = useState("-.--")
const [symbol, setSymbol] = useState("")

const removeZeroes = (rawprice, name) => {
        var tempprice = rawprice
        let isFiat = false
        for (let index = 0; index < fiatCurrencies.fiat.length; index++) {
            const element = fiatCurrencies.fiat[index];
            if (name.includes(fiatCurrencies.fiat[index]) >= 0) {

                isFiat = true
                console.log("if ", isFiat, symbol, fiatCurrencies.fiat[index], name.includes(fiatCurrencies.fiat[index]))
                break;
            }
        }
        if (!isFiat) {
            tempprice = rawprice.toLocaleString('decimal', { minimumFractionDigits: 8 })
        }
        isFiat = false
        return tempprice
}

useEffect(() => {
        if (stock) {
            //console.log(symbol, " is stock")
        } else {
            //console.log(symbol, " is crpyto")
        }
        const getPrice = async (tickprice) => {
            let binance = new ccxt.binance({
                apiKey:
                    myKeys.API_KEY,
                secret:
                    myKeys.SECRET_KEY,
            });
            try {
                tickprice = (await binance.fetchTicker(tickername)).last
                let onedayclose = (await binance.fetchOHLCV(tickername, "1h", Date.now() - 86400000))[0][1]
                setPrice(tickprice)
                setSymbol(tickername)
                setOnedaychange(((tickprice / onedayclose * 100) - 100).toLocaleString('decimal', { minimumFractionDigits: 2 }))
            } catch (error) {
                console.log(error)
                setPrice(error.message)
            }
            //console.log(ticker.tickername)
        }
        var timerID = setInterval(() => {
            getPrice()
        }, 2000);
        return function cleanup() {
            clearInterval(timerID);
        };
    }, [price]);

return (
   <div>
       {removeZeroes(price, symbol)}
   </div>
   )
}
ReactDOM.render(
    <TickerAPIData />,
    document.getElementById('root')
);

This page is a child to the Tickers.JS which uses a map function for each crypto in the database.此页面是 Tickers.JS 的子页面,它对数据库中的每个加密货币使用 map function。 If you look a the long console.log within removeZeroes() with 2 ticker elements this the result I get.如果您在 removeZeroes() 中查看带有 2 个股票代码元素的长 console.log,这就是我得到的结果。

TickerAPIData.js:59 if  true BTC/USDT USD true
TickerAPIData.js:59 if  true ETH/BTC USD false
TickerAPIData.js:59 if  true BTC/USDT USD true
TickerAPIData.js:59 if  true BTC/USDT USD true
TickerAPIData.js:59 if  true ETH/BTC USD false

The for loop, loops once and and the if statement is satisfied as BTC/USDT contains USD. for 循环,循环一次,如果 BTC/USDT 包含 USD,则满足 if 语句。 When the for loops runs for another currency ETH/BTC we see that the isFiat value remains true, even though it is set to false at start.当针对另一种货币 ETH/BTC 运行 for 循环时,我们看到 isFiat 值保持为真,即使它在开始时设置为假。 Also we see that the if statement is satisfied for ETHBTC even though ETH/BTC does not contain USD as seen by the TickerAPIData.js:59 if true ETH/BTC USD "false" <-.我们还看到,即使 ETH/BTC 不包含 USD,如 TickerAPIData.js:59 所示,如果 true ETH/BTC USD "false" <-,则 ETHBTC 满足 if 语句。 This is really confusing me, can someone help explain why this is happening.这真的让我很困惑,有人可以帮助解释为什么会这样。

Don't mind the unneeded code in this page, I was testing everything I could think of to try to figure this out and get it working.不要介意此页面中不需要的代码,我正在测试我能想到的一切,试图弄清楚这一点并让它工作。

This这个

if (name.includes(fiatCurrencies.fiat[index]) >= 0) {
  isFiat = true
  console.log("if ", isFiat, symbol, fiatCurrencies.fiat[index], name.includes(fiatCurrencies.fiat[index]))
  break;
}

would always run irrespective of whatever conditions: you can see that in your log statements无论条件如何,都将始终运行:您可以在log语句中看到

name.includes(fiatCurrencies.fiat[index]) >= 0 -> this would always evaluate to true (test it). name.includes(fiatCurrencies.fiat[index]) >= 0 -> 这总是会评估为真(测试它)。 Is this the actual behaviour you want?这是您想要的实际行为吗?

perhaps change to this:也许改成这样:

if (name.includes(fiatCurrencies.fiat[index])) {
  isFiat = true
  console.log("if ", isFiat, symbol, fiatCurrencies.fiat[index], name.includes(fiatCurrencies.fiat[index]))
  break;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM