web-dev-qa-db-ja.com

web3.js1.0を使用してコントラクトメソッドを認証および送信する方法

Web31.0ライブラリを使用してコントラクトのメソッドを実行する方法について混乱しています。

このコードは機能します(最初に手動でアカウントのロックを解除する限り):

var contract = new web3.eth.Contract(contractJson, contractAddress);
contract.methods
  .transfer("0x0e0479bC23a96F6d701D003c5F004Bb0f28e773C", 1000)
  .send({
    from: "0x2EBd0A4729129b45b23aAd4656b98026cf67650A"
  })
  .on('confirmation', (confirmationNumber, receipt) => {
    io.emit('confirmation', confirmationNumber);
  });

このエラーが発生します(最初に手動でロックを解除しない場合):

返されたエラー:認証が必要です:パスワードまたはロック解除

上記のコードはnode.jsのAPIエンドポイントであるため、プログラムでロックを解除または認証する必要があります。

Web3.js 1.0には、アカウントのロックを解除する方法はありません。

私もこれが必要だとは思いません(少なくともそれは私が混乱していることです)。私はアカウントを管理しているので、秘密鍵が何であるかを知っています。

トランザクションは秘密鍵で署名する必要があると思いますか?これは正しいです?これは事実上、「アカウントのロック解除」と同じことですか?

私はこれをやってみました:

var contract = new web3.eth.Contract(contractJson, contractAddress);

var tx = {
  from: "...{fromAddress -- address that has the private key below}",
  to: "...",
  value: ...
};

var signed = web3.eth.accounts.signTransaction(tx, 
  "...{privateKey}");

console.log(signed);

var promise = web3.eth.sendSignedTransaction(signed);

このエラーが発生します:

返されたエラー:メソッドnet_versionが存在しない/使用できません

トランザクションを認証して送信する最も簡単な方法は何ですか?

理想的には、コードサンプルの最初のアプローチを使用したいと思います。これが最もクリーンだからです。

6
Nick Young

このコードを使用すると、作成したアカウントのprivateKeyを使用して(web3.eth.accounts.create()を使用して)トランザクションサーバー側(node.js)に署名し、署名したトランザクションをネットワークに送信できますなしアカウントのロックを解除する必要があります。

Geth1.7.1を使用しています

  var contract = new web3.eth.Contract(contractJson, contractAddress);
  var transfer = contract.methods.transfer("0x...", 490);
  var encodedABI = transfer.encodeABI();

  var tx = {
    from: "0x...",
    to: contractAddress,
    gas: 2000000,
    data: encodedABI
  }; 

  web3.eth.accounts.signTransaction(tx, privateKey).then(signed => {
    var tran = web3.eth.sendSignedTransaction(signed.rawTransaction);

    tran.on('confirmation', (confirmationNumber, receipt) => {
      console.log('confirmation: ' + confirmationNumber);
    });

    tran.on('transactionHash', hash => {
      console.log('hash');
      console.log(hash);
    });

    tran.on('receipt', receipt => {
      console.log('reciept');
      console.log(receipt);
    });

    tran.on('error', console.error);
  });
21
Nick Young

トランザクションに明示的に署名せずにコントラクトメソッドを呼び出すことができる方法は次のとおりです(web3js 1.0.0):

const privateKey = 'e0f3440344e4814d0dea8a65c1b9c488bab4295571c72fb879f5c29c8c861937';
const account = web3.eth.accounts.privateKeyToAccount('0x' + privateKey);
web3.eth.accounts.wallet.add(account);
web3.eth.defaultAccount = account.address;

// ...
contract = new web3.eth.Contract(JSON_INTERFACE, address);
contract.methods.myMethod(myParam1, myParam2)
        .send({
            from: this.web3.eth.defaultAccount,
            gas: myConfig.gas,
            gasPrice: myConfig.gasPrice
        })
8
Gediminas Rimsa

これは、ローカルウォレットアカウントなしでトランザクションに署名する方法の完全な例です。トランザクションにinfuraを使用している場合に特に便利です。これはのために書かれました

'use strict';
const Web3 = require('web3');

const wsAddress = 'wss://rinkeby.infura.io/ws';
const contractJson = '(taken from solc or remix online compiler)';
const privateKey = '0xOOOX';
const contractAddress = '0xOOOX';
const walletAddress = '0xOOOX';

const webSocketProvider = new Web3.providers.WebsocketProvider(wsAddress);
const web3 = new Web3(new Web3.providers.WebsocketProvider(webSocketProvider));
const contract = new web3.eth.Contract(
  JSON.parse(contractJson),
  contractAddress
);
// change this to whatever contract method you are trying to call, E.G. SimpleStore("Hello World")
const query = contract.methods.SimpleStore('Hello World');
const encodedABI = query.encodeABI();
const tx = {
  from: walletAddress,
  to: contractAddress,
  gas: 2000000,
  data: encodedABI,
};

const account = web3.eth.accounts.privateKeyToAccount(privateKey);
console.log(account);
web3.eth.getBalance(walletAddress).then(console.log);

web3.eth.accounts.signTransaction(tx, privateKey).then(signed => {
  const tran = web3.eth
    .sendSignedTransaction(signed.rawTransaction)
    .on('confirmation', (confirmationNumber, receipt) => {
      console.log('=> confirmation: ' + confirmationNumber);
    })
    .on('transactionHash', hash => {
      console.log('=> hash');
      console.log(hash);
    })
    .on('receipt', receipt => {
      console.log('=> reciept');
      console.log(receipt);
    })
    .on('error', console.error);
});

使用する

"web3": "1.0.0-beta.30"

3
Zibyl