关于web3.js中与交易发送交易签名智能合约函数调用相关api的理解

Posted kugool

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了关于web3.js中与交易发送交易签名智能合约函数调用相关api的理解相关的知识,希望对你有一定的参考价值。

web3.js中有一些与交易发送、签名、合约函数调用相关的api,初学者(如me)常常搞不清什么情况下应该调用哪个,以及它们之间的区别。现将个人浅见记录如下,备忘。

  • sendTransaction

web3.eth.sendTransaction(transactionObject [, callback])

transactionObject对象设置交易的各种参数(不包括签名r,s,v),签名过程由api根据from地址自动完成。

  • sendSignedTransaction

web3.eth.sendSignedTransaction(signedTransactionData [, callback])

发送已签名的交易,交易签名可以通过 web3.eth.accounts.signTransaction 生成。

  •  signTransaction

web3.eth.signTransaction(transactionObject, address [, callback])

 签名交易,由address指定对应的账户进行签名。

  • sign

web3.eth.sign(dataToSign, address [, callback])

使用指定账户对数据进行签名

  • call

web3.eth.call(callObject [, defaultBlock] [, callback])

执行一个消息调用交易,消息调用交易直接在节点旳 VM 中而不需要通过区块链挖矿来执行。

callObject交易对象的data属性包含合约函数调用数据的 ABI 字节字符串 ,对合约创建交易来说,其值为合约初始化代码。

  • new contract

new web3.eth.Contract(jsonInterface[, address][, options])

生成合约实例,若不设置address参数,则部署新的合约实例到网络中。

  • methods.myMethod.call

myContract.methods.myMethod([param1[, param2[, ...]]]).call(options[, callback])

将在不发送交易的情况下调用该“常量”方法并在 EVM 中执行其智能合约方法。注意此种调用方式无法改变智能合约状态。

  • methods.myMethod.send

myContract.methods.myMethod([param1[, param2[, ...]]]).send(options[, callback])

向合约发送交易来执行其方法。注意这会改变合约状态。

  • methods.myMethod.encodeABI

myContract.methods.myMethod([param1[, param2[, ...]]]).encodeABI()

为指定的合约方法进行 ABI 编码,可用于发送交易、调用方法或向另一个合约方法传递参数。

  • signTransaction

web3.eth.accounts.signTransaction(tx, privateKey [, callback]);

使用给定的私钥签名以太坊交易。

  • sign

web3.eth.accounts.sign(data, privateKey);

签名任意数据。注意,此函数与web3.eth.sign(dataToSign, address [, callback])的区别,后者只需要通过地址来指定由谁来签名,api内部必定可以获取其私钥。

上述函数具体用法请参照对应版本web3.js的文档说明,如:web3.eth.accounts — web3.js 中文文档 — 登链社区https://learnblockchain.cn/docs/web3.js/web3-eth-accounts.html#sign

 注:理论上,所有发起交易的函数都必须有私钥进行签名操作。但上述某些函数只需指定公钥地址就能完成该功能,原因是web3.js所连接的providers为指定的公钥地址保存了对应的私钥,在后台可以自动完成签名动作,当然这种情形多见于使用ganache等测试环境中。正常情况下(如在Dapp中)需要web3.js连接用户的私钥钱包,签名动作由用户手动确认完成。

补充:web3.js会在底层将函数调用转为json-rpc的请求,其中不用创建交易的使用eth_call,创建交易的使用eth_sendTransaction,若需要在本地签名然后发送交易则使用eth_sendRawTransaction

我们可以在智能合约中使用 Solidity 获取过去区块中记录的交易信息吗?

【中文标题】我们可以在智能合约中使用 Solidity 获取过去区块中记录的交易信息吗?【英文标题】:Can we get transaction information recorded in the past block using Solidity in the Smart contract? 【发布时间】:2018-11-30 15:55:44 【问题描述】:

我正在研究以太坊的区块链,我想在使用 Solidity 的智能合约中使用过去的交易数据。 如果我在用javascript编写的程序中使用Web3.js模块,我可以很容易地得到这些数据。 但我无法使用 Solidity 在智能合约中获取这些数据。

Solidity 的参考说我们可以通过“block.number”和“block.blockhash(uint blockNumber)”函数获取当前区块号、blockhash 等,但没有提到获取交易数据。 (http://solidity.readthedocs.io/en/latest/units-and-global-variables.html#special-variables-and-functions)

enter image description here

请帮帮我。

【问题讨论】:

【参考方案1】:

答案很简单。不幸的是,您根本无法从 Solidity 访问链上的旧交易或区块数据。最多可以访问最后 256 个区块的哈希(参见 documentation 中的 blockhash

或者,作为一种解决方法,您可以考虑使用Oraclize。 Oraclize 代表在链上读取链下数据的方式,因此您可以尝试从 Etherscan Web API 读取交易数据。 Oraclize 的工作方式是:

    您向 Oraclize 智能合约请求您想从互联网获取哪些数据(某些 URL) Oraclize 链下服务器然后检测您的链上请求 查找您想要的数据(他们会向您提供的 URL 发出一些 http 请求) 一旦他们得到响应,他们就会将包含您请求的数据的交易发送到您的合约(调用特定的回调方法)

但是,使用这种方法,您依赖的是:

    EtherScan 已启动并运行 Oraclize 未运行。

如果您只关心与智能合约相关的交易数据,另一种方法是将交易数据存储在链上。如果您能告诉我们更多关于您要解决的具体问题,也许我们可以给您更多建议。

【讨论】:

非常感谢您的及时回复。使用 Oraclize 的方式也很有帮助。我正在尝试开发一个智能合约来从过去的交易信息中检查新注册信息的有效性,所以我想获取智能合约的交易信息。

以上是关于关于web3.js中与交易发送交易签名智能合约函数调用相关api的理解的主要内容,如果未能解决你的问题,请参考以下文章

使用 web3.js 的“发送”有啥问题?

web3使用web3.js发布并执行智能合约

在 Web3.js 中使用本地私钥

我们可以在智能合约中使用 Solidity 获取过去区块中记录的交易信息吗?

将签名的交易发送到 Ropsten

Web3.js sendSignedTransaction 给出“错误:无法检查交易收据”