最近元宇宙火起来了,也一直在和朋友们聊,那什么是元宇宙(VR虚拟现实,现实世界的数字孪生体),然后就有聊到了web3.0,现实的讲元宇宙和web3.0都还是些模糊的感念,但是却都有了一些现实的技术解决方案,今天我不讲元宇宙(其实互联网本身就是无处不在的元宇宙。
我不讲是因为VR技术我不太懂,不过现在国内傻瓜化工具已经很多了thingjs,优诺科技都有不错产品,国外就不说了),今天我要聊聊web3.0一个未来人人可以拥有的互联网;简单的说web1.0是个只读网络(代表网易),web2.0是读写网络(代表微博微信)。
前两代网络都是中心化网络难以保证网络用户的信息权利也就是内容确权很难,web3.0能确保你的所有权。好吧,怎么确保所有权呢,其实就是区块链,元宇宙其实也避不开这个问题,所有未来网络貌似都需要区块链,不过现阶段区块链无论主链还是侧链都慢,要写那么多区块确权现阶段技术还是慢这个还是现实。
公司(公:数人的财产;司:运转的意思)。现代社会在发展,公司与公司的经济生产合作,人与人的经济生产合作越来越复杂,尤其互联网下的各类合作越来越多,如何确认这数人或许多人的财产在一个或多个经济生产活动中的价值是互联网需要解决的问题。疫情居家办公,自由职业者,新的社会生产关系的需要在不停的催生web3.0和元宇宙的完善。
Solidity语言是一种面向合约的高级编程语言,用于在以太坊区块链网络上实现智能合约。它的开发工具Remix,推荐用它的在线编辑器[https://remix.ethereum.org],在线编辑器与matemask可以无缝对接,区块链智能合约必须能和智能钱包结合。
是一个基于以太坊虚拟机(EVM)的本地化智能合约开发环境,测试框架和上链工具。
geth可以搭建一个完整的以太坊节点,这里不做过多介绍,因为开发用本地内存虚拟Ganache就够了。
Ganache可以快速启动个人以太坊区块链,并可以使用它来运行测试,执行命令、检查状态,同时控制链条的运行方式。
我介绍的web3.0的技术方案都是基于npm安装的,包括truffle,Ganache都基于npm 安装。下面的文章默认大家都了解node js知识。
以下是一个有关投票的简单合约
pragma solidity ^0.4.0;
contract Voting{
//投票列表
bytes32[] public candidateList;
//对应的票数
mapping(bytes32=>uint8) public votesReceived;
//构造投票列表
constructor(bytes32[] memory candidateListName) public{
candidateList = candidateListName;
}
//判断投票信息是否在待投票列表
function valiCandidate(bytes32 candidateName) internal view returns(bool)
{
for(uint8 i=0;i〈candidateList.length;i++)
{
if (candidateName==candidateList[i])
{
return true;
}
}
return false;
}
//对投票人增加投票
function voteForCandidate(bytes32 candidateName) public{
require(valiCandidate(candidateName));
votesReceived[candidateName] = votesReceived[candidateName] + 1;
}
function totalVotesFor(bytes32 candidateName) view public returns(uint8){
require(valiCandidate(candidateName));
//返回票数
return votesReceived[candidateName];
}
}
记得加-g 全局安装
npm install ganache-cli -g# 6.12
npm install ganache -g# 7.0
ganache-cli -d #启动它ganache
记得加-g 全局安装
npm install truffle -g
mkdir voting
cd voting
truffle unbox webpack
APP目录下是一个node js的web3.0项目;build下是合约编译后的目录用于调用;contracts是remix里编写的合约,migrations下是合约部署文件;test目录是测试文件;truffle-config.js是配置文件。
取消选中部分注释 127.0.0.1 port 8545 表示链接本地Ganache。
truffle compile
项目默认合约放在此目录下:执行一下命令(truffle compile),进行编译,编译完成在build/contracts下会多出一个Voting.json文件
const Voting = artifacts.require("Voting");
//0x4100000000000000000000000000000000000000000000000000000000000000 代表 A
//0x4200000000000000000000000000000000000000000000000000000000000000 代表 B
module.exports = function(deployer) {
//初始化合约 第二是投标列表参数
deployer.deploy(Voting, ["0x4100000000000000000000000000000000000000000000000000000000000000","0x4200000000000000000000000000000000000000000000000000000000000000"]);
};
truffle migrate
contract address是合约的地址 account是部署账户的地址。
import Web3 from "web3";
import votingArtifact from "../../build/contracts/Voting.json";
const aInBytes32 ="0x4100000000000000000000000000000000000000000000000000000000000000";
const bInBytes32 ="0x4200000000000000000000000000000000000000000000000000000000000000";
const App = {
web3: null,
account: null,
meta: null,
start: async function() {
const { web3 } = this;
try {
const networkId = await web3.eth.net.getId();
const deployedNetwork = votingArtifact.networks[networkId];
this.voting = new web3.eth.Contract(
votingArtifact.abi,
deployedNetwork.address,
);
const accounts = await web3.eth.getAccounts();
this.account = accounts[0];
this.ready();
this.refreshBalance();
} catch (error) {
console.error("Could not connect to contract or chain.");
}
},
ready:async function(){
try{
this.refresh("Alice",aInBytes32);
this.refresh("Bob",bInBytes32);
}catch(err){
console.log(err)
}
},
refresh:async function(id,nameBytes32){
const {totalVotesFor} = this.voting.methods;
const tickets = await totalVotesFor(nameBytes32).call();
const el = document.getElementById(id);
el.innerHTML = tickets.toString();
},
voteForCandidate:async function(){
try{
const {voteForCandidate} = this.voting.methods;
const condidateName = document.getElementById("candidate").value;
console.log(condidateName)
if (condidateName == "Alice")
{
await voteForCandidate(aInBytes32).send({from:this.account});
this.refresh("Alice",aInBytes32);
}
else{
await voteForCandidate(bInBytes32).send({from:this.account});
this.refresh("Bob",bInBytes32);
}
}catch(err){
console.log(err)
}
}
};
window.App = App;
window.addEventListener("load", function() {
if (window.ethereum) {
// use MetaMask's provider
App.web3 = new Web3(window.ethereum);
window.ethereum.enable(); // get permission to access accounts
} else {
console.warn(
"No web3 detected. Falling back to http://127.0.0.1:8545. You should remove this fallback when you deploy live",
);
// fallback - use your fallback strategy (local node / hosted node + in-dapp id mgmt / fail)
App.web3 = new Web3(
new Web3.providers.HttpProvider("http://127.0.0.1:8545"),
);
}
App.start();
});
import Web3 from "web3";
import votingArtifact from "../../build/contracts/Voting.json";
const aInBytes32 ="0x4100000000000000000000000000000000000000000000000000000000000000";
const bInBytes32 ="0x4200000000000000000000000000000000000000000000000000000000000000";
start: async function() {
const { web3 } = this;
try {
// get contract instance
const networkId = await web3.eth.net.getId();
const deployedNetwork = votingArtifact.networks[networkId];
this.voting = new web3.eth.Contract(
votingArtifact.abi,
deployedNetwork.address,
);
// get accounts
const accounts = await web3.eth.getAccounts();
this.account = accounts[0];
this.ready();
this.refreshBalance();
} catch (error) {
console.error("Could not connect to contract or chain.");
}
},
});
voteForCandidate:async function(){
try{
const {voteForCandidate} = this.voting.methods;
const condidateName = document.getElementById("candidate").value;
console.log(condidateName)
if (condidateName == "Alice")
{
await voteForCandidate(aInBytes32).send({from:this.account});
this.refresh("Alice",aInBytes32);
}
else{
await voteForCandidate(bInBytes32).send({from:this.account});
this.refresh("Bob",bInBytes32);
}
}catch(err){
console.log(err)
}
}
My Voting Dapp
Voting Dapp
Alice loading... tickets
Bob loading... tickets
npm install
npm run dev
访问http://localhost:8080/voting.html输入Alice--》点击send(matemask钱包会告诉你需要花些eth币确认就好,我这个是本地的模拟币随便花)确认完会发现Alice投票数变成2了,这个可是区块链上的无法串改哦。
在合约solidity语言中storage是需要花gas的会永久存在区块中 ,我们就是用了这个特性写了投票合约,这样的投票久不会被串改,还有一种memory是存在内存的不用花费gas。这样我们可以发觉web3.0或者说dapp就是把那些需要信用保证的内容通过智能合约保存在区块链中,起到去中心化的信任作用,也保证了归属权的保证。用这种方式web3.0为之前读写网络又提供了确权的功能及所属权,为元宇宙打下基础的基石。