从 node.js 调用已部署的智能合约
Call deployed smart contract from node.js
我有一个小型测试智能合约,已部署到我的测试网络。而我想用一个服务器来调用合约中的函数。这是代码:
payontime.sol
pragma solidity ^0.4.0;
contract payontime{
address public remitter;
address private remittee;
uint value;
bool public start;
/*Only owner can use these function*/
modifier onlyOwner(){
if(msg.sender != remitter) throw;
_;
}
/*Initialize the owner*/
function payontime(address receiver) payable{
remitter = msg.sender;
value = msg.value;
remittee = receiver;
start = true;
if(!remittee.send(value)){
throw;
}
}
function wakeUp() public returns (string){
return "success" ;
}
function getContractAddr() public returns(address){
return this;
}
/*Get the remittee*/
function getRemitee() public returns(address){
return remittee;
}
}
我使用truffle serve
和一个网页来新建合同。
app.js
import { default as Web3} from 'web3';
import { default as contract } from 'truffle-contract'
import payontime_artifacts from '../../build/contracts/payontime.json'
var payontime = contract(payontime_artifacts);
window.App = {
sendCoin : function(){
var sender = web3.eth.accounts[0];
var receiver = document.getElementById('receiver').value;
var amount = parseInt(document.getElementById('amount').value);
web3.eth.getBalance(receiver,function(error,result){
if(!error){
consol.log("Before transfer: " + result );
}else{
console.log("Error: " + error);
}
});
var newContract = payontime.new(receiver,{from:sender, value:amount}).then(
function(myPay){
console.log(myPay.getContractAddr.call());
}).then(
function(){
web3.eth.getBalance(receiver,function(error,result){
if(!error){
console.log("After transfer: " + result );
}else{
console.log("Error: " + error);
}
});
});
}
}
window.addEventListener('load', function() {
// Checking if Web3 has been injected by the browser (Mist/MetaMask)
if (typeof web3 !== 'undefined') {
console.warn("Using web3 detected from external source. If you find that your accounts don't appear or you have 0 MetaCoin, ensure you've configured that source properly. If using MetaMask, see the following link. Feel free to delete this warning. :) http://truffleframework.com/tutorials/truffle-and-metamask")
// Use Mist/MetaMask's provider
window.web3 = new Web3(web3.currentProvider);
} else {
console.warn("No web3 detected. Falling back to http://localhost:8545. You should remove this fallback when you deploy live, as it's inherently insecure. Consider switching to Metamask for development. More info here: http://truffleframework.com/tutorials/truffle-and-metamask");
// fallback - use your fallback strategy (local node / hosted node + in-dapp id mgmt / fail)
window.web3 = new Web3(new Web3.providers.HttpProvider("http://localhost:8545"));
}
payontime.setProvider(web3.currentProvider);
});
app.js
记录地址 0x1d379f2ab48ad20319e9f81cb45af415aa6f2966
,我想使用此地址通过另一个应用程序 index.js
调用 payontime.sol
中的 wakeUp()
。
const Web3 = require('web3');
/* Connect to ethereum node */
const etherUrl = "http://localhost:8545";
const abi = [{"constant":false,"inputs":[],"name":"wakeUp","outputs":[{"name":"","type":"string"}],"payable":false,"type":"function"},{"constant":false,"inputs":[],"name":"getContractAddr","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"remitter","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"start","outputs":[{"name":"","type":"bool"}],"payable":false,"type":"function"},{"constant":false,"inputs":[],"name":"getRemitee","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"inputs":[{"name":"receiver","type":"address"}],"payable":true,"type":"constructor"}];
let web3 = new Web3();
web3.setProvider(new web3.providers.HttpProvider(etherUrl));
/*Call the function which already deployed on ethereum network
Notice: ABI have to modifeid when the smart contract code change*/
var contractInstance = web3.eth.contract(abi).at('0x1d379f2ab48ad20319e9f81cb45af415aa6f2966');
var reply = "false";
reply = contractInstance.wakeUp.call(function(error,result){
if(error){
console.log("Error");
throw error;
}else{
return result;
}
});
console.log(reply);
但是出现错误信息:
BigNumber Error: new BigNumber() not a base 16 number
我发现它可能是由not fully synced引起的。我认为在部署的合约中调用该函数时出现问题。那么如何从 web.js 调用已部署的合约?
contractInstance.wakeUp.call
将函数作为常量调用,但函数未定义为常量:
function wakeUp() public returns (string){
return "success" ;
}
必须是:
function wakeUp() public constant returns (string){
return "success" ;
}
如果您的 Solidity 函数不改变区块链状态而只是读取数据,您应该将其定义为常量。
除了将控制台日志放入回调中之外,您还可以通过以下方式修复大数字错误:
console.log(result.toNumber());
我有一个小型测试智能合约,已部署到我的测试网络。而我想用一个服务器来调用合约中的函数。这是代码: payontime.sol
pragma solidity ^0.4.0;
contract payontime{
address public remitter;
address private remittee;
uint value;
bool public start;
/*Only owner can use these function*/
modifier onlyOwner(){
if(msg.sender != remitter) throw;
_;
}
/*Initialize the owner*/
function payontime(address receiver) payable{
remitter = msg.sender;
value = msg.value;
remittee = receiver;
start = true;
if(!remittee.send(value)){
throw;
}
}
function wakeUp() public returns (string){
return "success" ;
}
function getContractAddr() public returns(address){
return this;
}
/*Get the remittee*/
function getRemitee() public returns(address){
return remittee;
}
}
我使用truffle serve
和一个网页来新建合同。
app.js
import { default as Web3} from 'web3';
import { default as contract } from 'truffle-contract'
import payontime_artifacts from '../../build/contracts/payontime.json'
var payontime = contract(payontime_artifacts);
window.App = {
sendCoin : function(){
var sender = web3.eth.accounts[0];
var receiver = document.getElementById('receiver').value;
var amount = parseInt(document.getElementById('amount').value);
web3.eth.getBalance(receiver,function(error,result){
if(!error){
consol.log("Before transfer: " + result );
}else{
console.log("Error: " + error);
}
});
var newContract = payontime.new(receiver,{from:sender, value:amount}).then(
function(myPay){
console.log(myPay.getContractAddr.call());
}).then(
function(){
web3.eth.getBalance(receiver,function(error,result){
if(!error){
console.log("After transfer: " + result );
}else{
console.log("Error: " + error);
}
});
});
}
}
window.addEventListener('load', function() {
// Checking if Web3 has been injected by the browser (Mist/MetaMask)
if (typeof web3 !== 'undefined') {
console.warn("Using web3 detected from external source. If you find that your accounts don't appear or you have 0 MetaCoin, ensure you've configured that source properly. If using MetaMask, see the following link. Feel free to delete this warning. :) http://truffleframework.com/tutorials/truffle-and-metamask")
// Use Mist/MetaMask's provider
window.web3 = new Web3(web3.currentProvider);
} else {
console.warn("No web3 detected. Falling back to http://localhost:8545. You should remove this fallback when you deploy live, as it's inherently insecure. Consider switching to Metamask for development. More info here: http://truffleframework.com/tutorials/truffle-and-metamask");
// fallback - use your fallback strategy (local node / hosted node + in-dapp id mgmt / fail)
window.web3 = new Web3(new Web3.providers.HttpProvider("http://localhost:8545"));
}
payontime.setProvider(web3.currentProvider);
});
app.js
记录地址 0x1d379f2ab48ad20319e9f81cb45af415aa6f2966
,我想使用此地址通过另一个应用程序 index.js
调用 payontime.sol
中的 wakeUp()
。
const Web3 = require('web3');
/* Connect to ethereum node */
const etherUrl = "http://localhost:8545";
const abi = [{"constant":false,"inputs":[],"name":"wakeUp","outputs":[{"name":"","type":"string"}],"payable":false,"type":"function"},{"constant":false,"inputs":[],"name":"getContractAddr","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"remitter","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"constant":true,"inputs":[],"name":"start","outputs":[{"name":"","type":"bool"}],"payable":false,"type":"function"},{"constant":false,"inputs":[],"name":"getRemitee","outputs":[{"name":"","type":"address"}],"payable":false,"type":"function"},{"inputs":[{"name":"receiver","type":"address"}],"payable":true,"type":"constructor"}];
let web3 = new Web3();
web3.setProvider(new web3.providers.HttpProvider(etherUrl));
/*Call the function which already deployed on ethereum network
Notice: ABI have to modifeid when the smart contract code change*/
var contractInstance = web3.eth.contract(abi).at('0x1d379f2ab48ad20319e9f81cb45af415aa6f2966');
var reply = "false";
reply = contractInstance.wakeUp.call(function(error,result){
if(error){
console.log("Error");
throw error;
}else{
return result;
}
});
console.log(reply);
但是出现错误信息:
BigNumber Error: new BigNumber() not a base 16 number
我发现它可能是由not fully synced引起的。我认为在部署的合约中调用该函数时出现问题。那么如何从 web.js 调用已部署的合约?
contractInstance.wakeUp.call
将函数作为常量调用,但函数未定义为常量:
function wakeUp() public returns (string){
return "success" ;
}
必须是:
function wakeUp() public constant returns (string){
return "success" ;
}
如果您的 Solidity 函数不改变区块链状态而只是读取数据,您应该将其定义为常量。
除了将控制台日志放入回调中之外,您还可以通过以下方式修复大数字错误:
console.log(result.toNumber());