利用express+ganache写一个带智能合约的dapp
1,编写合约pragma solidity >=0.4.22;contract Counter{uint256 count;constructor() public{count = 1;}function skipCount(uint256 skip) public{count += skip;}function allCount() public view returns(uint256)
1,编写合约
pragma solidity >=0.4.22;
contract Counter{
uint256 count;
constructor() public{
count = 1;
}
function skipCount(uint256 skip) public{
count += skip;
}
function allCount() public view returns(uint256){
return count;
}
}
2,部署合约
mkdir MyDapp2
cd MyDapp2
mkdir deploy
cd deploy
vim deploy.js
在deploy.js中输入如下内容
前三行的代码自己编写,是连接私有链的代码
后面的可以在remix中获取到,remix中部署完成后,在compile界面有个compile detail
打开后找到WEB3DEPLOY,复制内容即可
此外要注意,部署合约的账户,也就是send后面的from内容,我们要改成启动私有链后的账户,例如,我这里用的是ganache启动的私有链,我把第一个账户复制到这里了
var Web3 = require('web3');
var web3 = new Web3(new Web3.providers.HttpProvider('http://localhost:8545'));
web3.eth.getAccounts().then(console.log);
var counterContract = new web3.eth.Contract([{"inputs":[],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"allCount","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"skip","type":"uint256"}],"name":"skipCount","outputs":[],"stateMutability":"nonpayable","type":"function"}]);
var counter = counterContract.deploy({
data: '0x608060405234801561001057600080fd5b5060016000819055506101e6806100286000396000f3fe608060405234801561001057600080fd5b50600436106100365760003560e01c80635aa3e33d1461003b578063e233e22914610057575b600080fd5b610055600480360381019061005091906100ae565b610075565b005b61005f610090565b60405161006c91906100ea565b60405180910390f35b806000808282546100869190610105565b9250508190555050565b60008054905090565b6000813590506100a881610199565b92915050565b6000602082840312156100c4576100c3610194565b5b60006100d284828501610099565b91505092915050565b6100e48161015b565b82525050565b60006020820190506100ff60008301846100db565b92915050565b60006101108261015b565b915061011b8361015b565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff038211156101505761014f610165565b5b828201905092915050565b6000819050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b600080fd5b6101a28161015b565b81146101ad57600080fd5b5056fea26469706673582212203fef557aded8980597657bb29f4c5c6acd89fa38f24fc401f9cfe2b07ad2ef5064736f6c63430008070033',
arguments: [
]
}).send({
from: '0x93200EAf6cdFD4D445A223Ee3673D5BF992cc8D5',
gas: '4700000'
}, function (e, contract){
console.log(e, contract);
if (typeof contract.address !== 'undefined') {
console.log('Contract mined! address: ' + contract.address + ' transactionHash: ' + contract.transactionHash);
}
}).then(function(contract){
console.log("contract address: " , contract.options.address)
})
编写完成后,直接node deploy.js即可。
返回的结果
3,调用合约
3.1 安装express工程
这里可以参考我前一篇文章
链接: express开发dapp.
cd MyDapp2
express -e dapp
cd dapp
npm install
测试一下是否创建成功
npm start
若成功,则在127.0.0.1:4000(默认为3000)网页中返回Express
有可能没有安装web3 导致安装失败 可以 npm install web3 -save
3.2 修改文件
3.2.1 修改app.js
把app.js文件中的引擎修改为html。
var createError = require('http-errors');
var express = require('express');
var path = require('path');
var cookieParser = require('cookie-parser');
var logger = require('morgan');
var indexRouter = require('./routes/index');
var usersRouter = require('./routes/users');
var app = express();
var ejs = require('ejs');
// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.engine('.html', ejs.__express);
app.set('view engine','html');
//app.set('view engine', 'ejs');
app.use(logger('dev'));
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use('/', indexRouter);
app.use('/users', usersRouter);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
next(createError(404));
});
// error handler
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
module.exports = app;
3.2.2 修改/routs/index.js
var express = require('express');
var router = express.Router();
// 连接底层区块链
var Web3 = require('web3');
var web3 = new Web3(new Web3.providers.HttpProvider('http://localhost:8545'));
web3.eth.getAccounts().then(console.log);
// 这里是创建一个合约实例,new web3.eth.Contract([{}],'')
// 两个参数,第一个参数是abi文件,第二个参数是合约的地址,就是上述部署好的合约的地址
// abi 可以从remix中直接复制过来
var myContract = new web3.eth.Contract([
{
"inputs": [
{
"internalType": "uint256",
"name": "skip",
"type": "uint256"
}
],
"name": "skipCount",
"outputs": [],
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [],
"stateMutability": "nonpayable",
"type": "constructor"
},
{
"inputs": [],
"name": "allCount",
"outputs": [
{
"internalType": "uint256",
"name": "",
"type": "uint256"
}
],
"stateMutability": "view",
"type": "function"
}
],'0x9Cf3E1d695324cbc89eB1a81d40fB1109E052676');
// 这里的from 是调用合约的地址,我们可以从ganache中随便复制一个过来
// allCount是我们合约中的方法
myContract.methods.allCount().call({from: '0xf3A1CCe288Ec7C35E592dCb0a71518065f4566AE'}, function(error, result){
console.log("counter: ", result);
});
/* GET home page. */
router.get('/', function(req, res, next) {
res.render('index', { title: 'Express' });
});
module.exports = router;
3.2.3 增加文件/views/index.html
<!DOCTYPE html>
<html>
<head>
<title><%= title %></title>
<link rel='stylesheet' href='/stylesheets/style.css' />
</head>
<body>
<h1><%= title %></h1>
<p>Welcome to <%= title %></p>
</body>
</html>
文件修改完成
4, 启动调用
在/MyDapp2/dapp/中输入
npm start
可以看到结果
4.2 调用skip方法
4.2.1 在index.js 文件中修改代码为如下代码
var express = require('express');
var router = express.Router();
// 连接底层区块链
var Web3 = require('web3');
var web3 = new Web3(new Web3.providers.HttpProvider('http://localhost:8545'));
web3.eth.getAccounts().then(console.log);
var myContract = new web3.eth.Contract([
{
"inputs": [
{
"internalType": "uint256",
"name": "skip",
"type": "uint256"
}
],
"name": "skipCount",
"outputs": [],
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [],
"stateMutability": "nonpayable",
"type": "constructor"
},
{
"inputs": [],
"name": "allCount",
"outputs": [
{
"internalType": "uint256",
"name": "",
"type": "uint256"
}
],
"stateMutability": "view",
"type": "function"
}
],'0xaD003c9D3834c6Cd4158D77E054AB61aF88C6FAE');
// myContract.methods.allCount().call({from: '0xf3A1CCe288Ec7C35E592dCb0a71518065f4566AE'}, function(error, result){
// console.log("counter: ", result);
// });
var init_counter = 0 ;
var current_counter = 0 ;
// 这里也可以不指定from
myContract.methods.allCount().call().then(function(counter){
console.log("init counter: ", counter);
init_counter = counter;
});
/* GET home page. */
router.get('/', function(req, res, next) {
myContract.methods.skipCount(10).send({from: '0x1886Ca782DA0b258acC211856551d6Fe03C8cf21'})
.then(function(){
myContract.methods.allCount().call().then(function(counter){
console.log("current counter: ", counter);
current_counter = counter;
res.render('index', { init: init_counter,current: current_counter});
});
});
});
module.exports = router;
4.2.2 修改index.html
<!DOCTYPE html>
<html>
<head>
<title>调用智能合约</title>
<link rel='stylesheet' href='/stylesheets/style.css' />
</head>
<body>
<h1>init: <%= init %></h1>
<h1>counter: <%= current %></h1>
</body>
</html>
4.2.3 小恶魔启动
npm start
在网页上可以看到
更多推荐
所有评论(0)