简体   繁体   English

使用智能合约中的项目更新 React JS 中的 state 数组

[英]Update state array in React JS with item from Smart Contract

I have a state array in react which I am trying to add items from a smart contract我有一个 state 数组在反应,我正在尝试从智能合约中添加项目

The state array is initialised as state 数组初始化为

const [products, setProducts] = useState([]);常量 [产品,setProducts] = useState([]);

  1. and 2. below did not work, but 3. does work when the array is set outside the loop和 2. 下面没有工作,但 3. 当数组设置在循环之外时工作

What am I doing wrong in 1. and 2?我在 1. 和 2 中做错了什么?

—————————————————————— ———————————————————————

  1. did not work不工作
  for (var i = 1; i <= productCount; i++) {
        const product = await marketplace.methods.products(i).call()
        setProducts({
          products: [...this.state.products, product]
        })
      }

—————————————————————— ———————————————————————

  1. did not work不工作
  for (var i = 1; i <= productCount; i++) {
        const product = await marketplace.methods.products(i).call()
         setProducts(prevState => ({
            products: [...prevState.products, product]
         }))
      }

—————————————————————— ———————————————————————

  1. worked工作过
  let productArray =[]
  for (var i = 1; i <= productCount; i++) {
        const product = await marketplace.methods.products(i).call()
        productArray.push[product]
      }
  setProduct(productArray)

—————————————————————— ———————————————————————

You're using a functional component, not a class component, so you shouldn't be using this or this.state - that's why (1) doesn't work.您使用的是功能组件,而不是 class 组件,因此您不应该使用thisthis.state - 这就是 (1) 不起作用的原因。

(2) doesn't work because your initial products are a plain array - it's not an object with a products property: (2) 不起作用,因为您的初始产品是一个普通数组- 它不是具有products属性的 object:

const [products, setProducts] = useState([]);

so所以

     setProducts(prevState => ({
        products: [...prevState.products, product]
     }))

doesn't make sense - prevState is an array, not an object with a products property.没有意义 - prevState是一个数组,而不是具有products属性的 object 。

With a small tweak, (2) could be made to work:稍加调整,(2)就可以工作:

     setProducts(prevState => ([...prevState, product]));

There's also almost certainly no need to use .call , and you can speed up the process by using Promise.all instead of waiting for each function to finish individually:几乎可以肯定不需要使用.call ,您可以通过使用Promise.all来加快该过程,而不是等待每个 function 单独完成:

Promise.all(
  Array.from(
    { length: productCount },
    (_, i) => marketplace.methods.products(i + 1)()
  )
)
  .then((newProducts) => {
    setProducts([...products, ...newProducts]);
  })
  // .catch(handleErrors);

That's the version I'd prefer, if your code permits you to make all the requests at once.如果您的代码允许您一次发出所有请求,那是我更喜欢的版本。

1 and 2 disobey the one of the basic rules of hooks in React. 1 和 2 违反了 React 中钩子的基本规则之一。

Only Call Hooks at the Top Level . Only Call Hooks at the Top Level ie You should avoid calling hooks in loops, nested functions or conditionals.即你应该避免在循环、嵌套函数或条件中调用钩子。

As already stated also, there is no reason for the use of this in the first approach considering the fact that you're using a React hook.如前所述,考虑到您正在使用 React 钩子this事实,没有理由在第一种方法中使用它。

Read more about Hooks Rules on the docs .docs上阅读有关 Hooks 规则的更多信息。

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

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