React不会渲染异步函数返回的东西

时间:2020-07-22 08:48:42

标签: javascript reactjs

我有一个类似这样的功能,该功能旨在列出交易清单并返回交易,此功能一切正常。没有错误。

        function ListTX() {
          (async () => {
          const arweave = Arweave.init();
          var address = window.sessionStorage.getItem("WalletAddress");
          const txids = await arweave.arql({
                op: 'and',
                expr1:
                {
                  op: 'equals',
                  expr1: 'from',
                  expr2: address
                },
                expr2:
                {
                  op: 'equals',
                  expr1: 'App-Name',
                  expr2: 'arshard'
                }
          })
          console.log(txids);
          const all_transactions = txids.map((transaction, idx) => {
              return <li key={idx}>{transaction}</li>;
          });
          console.log(all_transactions);
        return (
          <ul>
            {all_transactions}
          </ul>
          );
        })();
        }

即使all_transactions不为空,React也不会渲染它。相同的功能实际上可以使用正常功能。


        return (
            <div>
                <Header/>
                <main>
                    <article>
                {ListTX()}
                    </article>
                </main>
            </div>
        );

这是完整的课程:

class Construct extends React.Component {
    render() {

        if (window.sessionStorage.getItem("wallet")) {
        function ListTX() {
          (async () => {
          const arweave = Arweave.init();
          var address = window.sessionStorage.getItem("WalletAddress");
          const txids = await arweave.arql({
                op: 'and',
                expr1:
                {
                  op: 'equals',
                  expr1: 'from',
                  expr2: address
                },
                expr2:
                {
                  op: 'equals',
                  expr1: 'App-Name',
                  expr2: 'arshard'
                }
          })
          console.log(txids);
          const all_transactions = txids.map((transaction, idx) => {
              return <li key={idx}>{transaction}</li>;
          });
          console.log(all_transactions);
        })();
        return (
          <ul>
            {all_transactions}
          </ul>
          );
        }
        return (
            <div>
                <Header/>
                <main>
                    <article>
                {ListTX()}
                    </article>
                </main>
            </div>
        );
      }
      else {
        return (<Redirect to="/upload_wallet"/>);
      }
    };
};
}
export default Construct;

这是console.log(all_transactions)返回的内容:

[
  {
    "type": "li",
    "key": "0",
    "ref": null,
    "props": {
      "children": "QWCFEHGEa0Lf2zywL_nBYmnEXhG3hLqyFcxQykhJhAc"
    },
    "_owner": null,
    "_store": {}
  },
  {
    "type": "li",
    "key": "1",
    "ref": null,
    "props": {
      "children": "cbVaHaRayhOkXR0lLL_1KFNnbyP8EEAWVQIGSKxo_2Y"
    },
    "_owner": null,
    "_store": {}
  },
  {
    "type": "li",
    "key": "2",
    "ref": null,
    "props": {
      "children": "gOrpgD3cVNEzf-u2fqI4KI5G49qaBA9jMwq-VMiQp_Q"
    },
    "_owner": null,
    "_store": {}
  },
  {
    "type": "li",
    "key": "3",
    "ref": null,
    "props": {
      "children": "PYT3WoT5dtzhyxjCQ_2dn-8ZJCqEtfZBI4-RaWJCBks"
    },
    "_owner": null,
    "_store": {}
  },
  {
    "type": "li",
    "key": "4",
    "ref": null,
    "props": {
      "children": "HJymy5uP2sqTwX5nbbzuqEXMyXliwodpIgjT5s0puxI"
    },
    "_owner": null,
    "_store": {}
  }
]

如果我做这样的事情就可以了

        if (window.sessionStorage.getItem("wallet")) {
        function ListTX() {
          (async () => {
          const arweave = Arweave.init();
          var address = window.sessionStorage.getItem("WalletAddress");
          const txids = await arweave.arql({
                op: 'and',
                expr1:
                {
                  op: 'equals',
                  expr1: 'from',
                  expr2: address
                },
                expr2:
                {
                  op: 'equals',
                  expr1: 'App-Name',
                  expr2: 'arshard'
                }
          })
          console.log(txids);
          const all_transactions = txids.map((transaction, idx) => {
              return <li key={idx}>{transaction}</li>;
          });
          console.log(all_transactions);
        })();
        return (
          <p>
            test
          </p>
          );
        }

,测试写在网页上。这就是为什么我怀疑它与异步功能有关的原因,如果我尝试在异步中执行相同操作,那么它将无法正常工作。

在我们的外部函数ListTX()中呈现此列表的真正方法是什么?

3 个答案:

答案 0 :(得分:0)

Ciao,为了“说” React来渲染某些内容,您必须设置state组件。所以我的建议是像这样将all_transactions存储到state中:

class Construct extends React.Component {
....
constructor(props){
  super(props);
  this.state : {
    state_all_transactions: [];
  }

 // then when you retrieve all_transactions
 ...
 this.setState({state_all_transactions: all_transactions});
 ...
}

然后返回:

return (
      <ul>
        {this.stete.state_all_transactions}
      </ul>
);

尝试一下,应该可以解决您的问题。

答案 1 :(得分:0)

您可以像这样重新编写代码

import React, {useEffect, useState} from "react";

function ListTX() {
  const arweave = Arweave.init();
  const [txids, setTxids] = useState([]);
  useEffect(() => {
    getTxids()
  }, []);
  const getTxids = async() => {
    const address = window.sessionStorage.getItem("WalletAddress");
    const tx = await arweave.arql({
      op: 'and',
      expr1:
        {
          op: 'equals',
          expr1: 'from',
          expr2: address
        },
      expr2:
        {
          op: 'equals',
          expr1: 'App-Name',
          expr2: 'arshard'
        }
    });
    setTxids(tx);
  };
  const all_transactions = txids.map((transaction, idx) => {
    return <li key={idx}>{transaction}</li>;
  });
  console.log(all_transactions);
  return (
    <ul>
      {all_transactions}
    </ul>
  );
}

然后将其用作:

return (
    <div>
        <Header/>
        <main>
            <article>
                <ListTX/>
            </article>
        </main>
    </div>
);

答案 2 :(得分:0)

这是一个CodeSandbox,显示了我建议如何构造组件。

Edit morning-firefly-xlvqo

基本上如下:

class Construct extends React.Component {
  state = {
    all_transactions: []
  };

  componentDidMount() {
    if (window.sessionStorage.getItem("wallet")) {
      (async () => {
        const arweave = Arweave.init();
        var address = window.sessionStorage.getItem("WalletAddress");
        const txids = await arweave.arql({
          op: "and",
          expr1: {
            op: "equals",
            expr1: "from",
            expr2: address
          },
          expr2: {
            op: "equals",
            expr1: "App-Name",
            expr2: "arshard"
          }
        });
        console.log(txids);
        this.setState({ all_transactions: txids });
      })();
    }
  }

  render() {
    return (
      <div>
        <Header />
        <main>
          <article>
            <ul>
              {this.state.all_transactions.map(tx => (
                <li key={tx.key}>{tx.props.children}</li>
              ))}
            </ul>
          </article>
        </main>
      </div>
    );
  }
}

export default Construct;

相关问题