1. 程式人生 > >以太坊搭建聯盟鏈詳細教程

以太坊搭建聯盟鏈詳細教程

urn ror 當前 self rate 詳細 比特幣 日誌 chris

蟲洞社區簽約作者介紹

風逝 區塊鏈 雲旗天下

安裝以太坊geth客戶端

需要先安裝go環境
安裝教程

下載以太坊源碼
github.com/ethereum/go-ethereum

進入 go-ethereum 目錄

cd go-ethereum
make geth

然後執行make all, 順便安裝一下其他一些命令。

創建組織

在桌面創建兩個文件夾,a,b 兩個文件夾,代表兩個組織
在兩個文件夾內分別創建兩個文件,genesis.json
文件內容

{
    "config": {
          "chainId": 15,
          "homesteadBlock": 0,
          "eip155Block": 0,
          "eip158Block": 0
      },
      "coinbase" : "0x0000000000000000000000000000000000000000",
      "difficulty" : "0x40000",
      "extraData" : "",
      "gasLimit" : "0xffffffff",
      "nonce" : "0x0000000000000042",
      "mixhash" : "0x0000000000000000000000000000000000000000000000000000000000000000",
      "parentHash" : "0x0000000000000000000000000000000000000000000000000000000000000000",
      "timestamp" : "0x00",
      "alloc": { }
}

創建創世區塊

進入a文件夾,執行命令
$ geth --datadir ./data-init1/ init genesis.json
如果不在a 文件夾內,genesis.json 指定其相應的路徑也可.
data-init1 目錄專門用來存放節點數據,執行完會發現在該目錄多出兩個目錄,一個為geth,一個為keystore,其中geth裏面存放數據相關信息,keystore 裏面存放加密過的的私鑰文件,執行完後打印日誌如下:

INFO [09-06|18:01:44.713] Maximum peer count                       ETH=25 LES=0 total=25
INFO [09-06|18:01:44.726] Allocated cache and file handles         database=/Users/qianjianeng/Desktop/a/data-init1/geth/chaindata cache=16 handles=16
INFO [09-06|18:01:44.732] Writing custom genesis block 
INFO [09-06|18:01:44.732] Persisted trie from memory database      nodes=0 size=0.00B time=187.096μs gcnodes=0 gcsize=0.00B gctime=0s livenodes=1 livesize=0.00B
INFO [09-06|18:01:44.733] Successfully wrote genesis state         database=chaindata                                              hash=a0e580…a5e82e
INFO [09-06|18:01:44.733] Allocated cache and file handles         database=/Users/qianjianeng/Desktop/a/data-init1/geth/lightchaindata cache=16 handles=16
INFO [09-06|18:01:44.736] Writing custom genesis block 
INFO [09-06|18:01:44.736] Persisted trie from memory database      nodes=0 size=0.00B time=2.156μs   gcnodes=0 gcsize=0.00B gctime=0s livenodes=1 livesize=0.00B
INFO [09-06|18:01:44.737] Successfully wrote genesis state         database=lightchaindata                                              hash=a0e580…a5e82e

進入b 目錄,執行相同命令
$ geth --datadir ./data-init2/ init genesis.json

啟動控制臺

啟動 a 組織
進入到 a 目錄
$ geth --datadir ./data-init1/ --networkid 22 --nodiscover console

networkid : 1-4系統內部使用 大於5即可
nodiscover: 此參數確保geth不去尋找peers節點,主要是為了控制聯盟鏈接入的節點.
這裏我們需要註意的是在啟動第一個節點時並沒有指定port參數,因此此處采用了默認的port,
也就是30303。以下為執行時打印的日誌,並進入控制臺。通過日誌我們也可以發現端口為

30303。

以下是部分日誌

INFO [09-06|18:16:44.901] Regenerated local transaction journal    transactions=0 accounts=0
INFO [09-06|18:16:44.903] Starting P2P networking 
INFO [09-06|18:16:44.906] RLPx listener up                         self="enode://251a655c56c514f5c4f81f2d08916622c0fff5f0b906ee82be0d976b255a7987c2743195f857b85d5d948c37a172ef365ad426193b939501a420b12ae8393ddc@[::]:30303?discport=0"
INFO [09-06|18:16:44.911] IPC endpoint opened                      url=/Users/qianjianeng/Desktop/a/data-init1/geth.ipc
INFO [09-06|18:16:44.984] Mapped network port                      proto=tcp extport=30303 intport=30303 interface=NAT-PMP(192.168.31.1)
Welcome to the Geth JavaScript console!

instance: Geth/v1.8.12-stable/darwin-amd64/go1.10.3
 modules: admin:1.0 debug:1.0 eth:1.0 miner:1.0 net:1.0 personal:1.0 rpc:1.0 txpool:1.0 web3:1.0

如果出現 Welcome to the Geth JavaScript console!, 則說明網絡啟動成功

新開一個終端,進入b目錄,啟動 b 組織
geth --datadir ./data-init2/ --port 30306 --networkid 22 --nodiscover console
註意,同一臺電腦,a 組織已經占用30303端口,所以 b 需要換一個端口

到這裏,兩個組織網絡都已經啟動成功

###geth網絡啟動參數介紹
--nodiscover
使用此選項可確保未手動添加您的人員無法發現您的節點。否則,如果您的節點具有相同的創世紀文件和網絡ID,則可能無意中將您的節點添加到陌生人的區塊鏈中。
--maxpeers 0
如果您不希望任何其他人連接到您的測試鏈,請使用maxpeers 0。或者,如果您確切知道要連接到節點的對等端數,則可以調整此數字。
--rpc
這將在您的節點上啟用RPC接口。這通常在Geth中默認啟用。
--rpcapi "db,eth,net,web3"
這決定了允許通過RPC訪問哪些API。默認情況下,Geth通過RPC啟用web3接口。
重要提示:請註意,通過RPC / IPC接口提供API將使每個人都可以訪問可以訪問此接口的API(例如dapp)。請註意您啟用的API。默認情況下,geth通過IPC接口啟用所有API,並通過RPC接口啟用db,eth,net和web3 API。
--rpcport "8080"
將8000更改為網絡上打開的任何端口。geth的默認值是8080。
--rpccorsdomain "http://chriseth.github.io/browser-solidity/"
這決定了哪些URL可以連接到您的節點以執行RPC客戶端任務。要非常小心,並鍵入一個特定的URL而不是通配符(*),它允許任何URL連接到您的RP C實例。
--datadir "/home/TestChain1"
這是您的私人鏈數據將存儲在的數據目錄中(在nubits。下選擇一個與您的公共以太坊鏈文件夾分開的位置)。
--port "30303"
這是“網絡偵聽端口”,您將使用它手動連接其他對等端。
--identity "TestnetMainNode"
這將為您的節點設置一個標識,以便在對等列表中更容易識別它。以下是這些身份如何在網絡上顯示的示例。

控制臺操作

進入以太坊 Javascript Console 後,就可以使用裏面的內置對象做一些操作,這些內置對象提供的功能很豐富,比如查看區塊和交易、創建賬戶、挖礦、發送交易、部署智能合約等。

常用命令有:

  • personal.newAccount():創建賬戶;
  • personal.unlockAccount():解鎖賬戶;
  • eth.accounts:枚舉系統中的賬戶;
  • eth.getBalance():查看賬戶余額,返回值的單位是 Wei(Wei 是以太坊中最小貨幣面額單位,類似比特幣中的聰,1 ether = 10^18 Wei);
  • eth.blockNumber:列出區塊總數;
  • eth.getTransaction():獲取交易;
  • eth.getBlock():獲取區塊;
  • miner.start():開始挖礦;
  • miner.stop():停止挖礦;
  • eth.coinbase:挖礦獎勵的賬戶
  • web3.fromWei():Wei 換算成以太幣;
  • web3.toWei():以太幣換算成 Wei;
  • txpool.status:交易池中的狀態;
  • admin.addPeer():連接到其他節點;

????????添加coinbase???????? 賬戶

在a節點上創建一個賬戶
查看a節點上所有賬戶

> personal.listAccounts
[]

當前為空
創建一個賬戶,密碼是123456

> personal.newAccount("123456")
"0x0aab8ad7444c1fc908707a063297520cb10414e8"

再次查看,已經有了一個賬戶

> personal.listAccounts
["0x0aab8ad7444c1fc908707a063297520cb10414e8"]

在b節點也創建一個賬戶

> personal.newAccount("123456")
"0x406133cb63002afa6cbc43a388e8eeb4c479dfaa"

在a節點查看coinbase賬戶
coinbase 即節點挖礦獎勵所在的賬戶

> eth.coinbase
INFO [09-06|18:50:56.130] Etherbase automatically configured       address=0x0AAB8Ad7444C1FC908707A063297520Cb10414E8
"0x0aab8ad7444c1fc908707a063297520cb10414e8"

coinbase賬戶 默認就是節點裏面的第一個賬戶,現在每個節點都只有一個賬戶,都分別為coinbase賬戶。

修改coinbase 賬戶
在a節點再創建一個賬戶

> personal.newAccount("123456")
"0xb99db142c26690d98dc3ea1c1f10e114603c0ec0"

把a節點的coinbase賬戶修改為第二個賬戶

> miner.setEtherbase("0xb99db142c26690d98dc3ea1c1f10e114603c0ec0")
true

再次查看coinbase

> eth.coinbase
"0xb99db142c26690d98dc3ea1c1f10e114603c0ec0"

更改成功

查看節點所有的賬戶詳情

> personal.listWallets
[{
    accounts: [{
        address: "0x0aab8ad7444c1fc908707a063297520cb10414e8",
        url: "keystore:///Users/qianjianeng/Desktop/a/data-init1/keystore/UTC--2018-09-06×××0-46-59.613429718Z--0aab8ad7444c1fc908707a063297520cb10414e8"
    }],
    status: "Locked",
    url: "keystore:///Users/qianjianeng/Desktop/a/data-init1/keystore/UTC--2018-09-06×××0-46-59.613429718Z--0aab8ad7444c1fc908707a063297520cb10414e8"
}, {
    accounts: [{
        address: "0xb99db142c26690d98dc3ea1c1f10e114603c0ec0",
        url: "keystore:///Users/qianjianeng/Desktop/a/data-init1/keystore/UTC--2018-09-06×××0-55-08.643545883Z--b99db142c26690d98dc3ea1c1f10e114603c0ec0"
    }],
    status: "Locked",
    url: "keystore:///Users/qianjianeng/Desktop/a/data-init1/keystore/UTC--2018-09-06×××0-55-08.643545883Z--b99db142c26690d98dc3ea1c1f10e114603c0ec0"
}]

聯盟鏈互通

上面分別是在兩個節點上進行的操作,下面我們需要把兩個節點之間建立起鏈接。首先,我們執 行以下命令查看以下節點的peers的情況。

> admin.peers []

發現節點並沒有鏈接上任何其他節點,這也是我們的nodiscover參數發揮了效果。下面就通過分享enode地址的方式來讓兩個節點建立鏈接。

查看a節點信息

> admin.nodeInfo.enode
"enode://251a655c56c514f5c4f81f2d08916622c0fff5f0b906ee82be0d976b255a7987c2743195f857b85d5d948c37a172ef365ad426193b939501a420b12ae8393ddc@[::]:30303?discport=0"

通過上面命令,我們獲得了節點a的encode信息。這是geth用來連接到不同節點的enode信息,

在這些不同的節點它們能夠分享交易和成功挖掘信息。
查看b節點信息

> admin.nodeInfo.enode
"enode://a16a449053ef07d7088527b46951a6439ddcacf88d4f28dc3862141dd64f5ddba67e5c959e0544d1c758d89b81d4425138ea70a0062e0a2cf4cb940bfca2f20e@[::]:30306?discport=0"

然後在a節點添加b,
a節點執行命令

> admin.addPeer("enode://a16a449053ef07d7088527b46951a6439ddcacf88d4f28dc3862141dd64f5ddba67e5c959e0544d1c758d89b81d4425138ea70a0062e0a2cf4cb940bfca2f20e@[::]:30306?discport=0")

在a節點添加b即可,無需在b節點添加a

返回true即為添加成功
再次執行命令admin.peers驗證

> admin.peers
[{
    caps: ["eth/63"],
    id: "ec9aa0351cbe060366410a9c7403c4d1b76de704127a8c58dd3ad5c21e199c4bc75ab567c1ffba33bb983baefd954f9f647d4e0fb1043613fb43b18dd60824be",
    name: "Geth/v1.8.12-stable/darwin-amd64/go1.10.3",
    network: {
      inbound: false,
      localAddress: "[::1]:64810",
      remoteAddress: "[::1]:30306",
      static: true,
      trusted: false
    },
    protocols: {
      eth: {
        difficulty: 262144,
        head: "0xa0e580c6769ac3dd80894b2a256164a76b796839d2eb7f799ef6b9850ea5e82e",
        version: 63
      }
    }
}]

出現其他節點的信息,表明節點連接成功

查看節點連接數
web3.net.peerCount

以太坊單位

單位 ----------------wei值-----------Wei
wei ---------------- 1 ------------1 wei
Kwei (babbage)------1e3 wei---------1,000
Mwei (lovelace)-----1e6 wei---------1,000,000
Gwei (shannon)------1e9 wei --------1,000,000,000
microether (szabo)--1e12 wei--------1,000,000,000,000
milliether (finney)-1e15 wei--------1,000,000,000,000,000
ether---------------1e18 wei--------1,000,000,000,000,000,000

最常用的就是wei和ether,客戶端顯示一般都是ether,轉賬交易時都需要將ether轉換成wei
1 eth = 1e18 wei

// wei轉換為ether
> web3.fromWei(‘22000000000000‘, ‘ether‘);
"0.000022"

// ether轉換為wei
> web3.toWei(‘1‘,‘ether‘)
"1000000000000000000"

查詢余額

查詢曠工地址余額及查詢指定地址余額

> eth.getBalance(eth.coinbase)
> eth.getBalance("0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5")

挖礦

> miner.start()

> miner.start()
INFO [09-06|22:46:00.911] Updated mining threads                   threads=0
INFO [09-06|22:46:00.911] Transaction pool price threshold updated price=18000000000
INFO [09-06|22:46:00.911] Starting mining operation 
null
> INFO [09-06|22:46:00.912] Commit new mining work                   number=1 txs=0 uncles=0 elapsed=1.046ms
INFO [09-06|22:46:09.002] Successfully sealed new block            number=1 hash=300302…5db299
INFO [09-06|22:46:09.006] ???? mined potential block                  number=1 hash=300302…5db299
INFO [09-06|22:46:09.007] Commit new mining work                   number=2 txs=0 uncles=0 elapsed=874.759μs
INFO [09-06|22:46:09.608] Successfully sealed new block            number=2 hash=186735…3546a7

查看b節點控制臺可以看出,節點a在挖礦,節點b在同步數據

停止挖礦
> miner.stop()

再次查看余額

> eth.getBalance(eth.coinbase)
135000000000000000000

兩個節點也可以同時挖礦

在節點a查詢節點b地址的余額

 > eth.getBalance("0x7af1b2e3ccea944c64b5cd60ecc8dc9c998a211f")
145000000000000000000

節點a也能查詢到節點b地址的信息和余額,說明節點a和節點b的數據是完全同步的

交易轉賬

現在我們從節點a的coinbase賬戶發送一筆交易到節點b的一個新錢包。
轉賬前需要先解鎖賬戶

> personal.unlockAccount(eth.coinbase)
Unlock account 0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5
Passphrase: 
true

轉賬完成後再次查詢余額

> eth.sendTransaction({from: eth.coinbase, to: ‘0x5048b919c2ef522b1313944718ffe0ce84e4e4b4‘, value: 1000000000000000000})
INFO [09-07|10:45:46.443] Submitted transaction                    fullhash=0x706537c56d005b42432ac3b3d4691621efbd35894c924d7dcc3961c155c67217 recipient=0x5048B919c2ef522b1313944718FfE0cE84E4E4b4
"0x706537c56d005b42432ac3b3d4691621efbd35894c924d7dcc3961c155c67217"
> eth.getBalance("0x5048b919c2ef522b1313944718ffe0ce84e4e4b4")
0

發現余額是0,因為還沒有礦工對交易進行挖礦打包。

執行挖礦
miner.start()

再次查詢

> eth.getBalance("0x5048b919c2ef522b1313944718ffe0ce84e4e4b4")
1000000000000000000

一個eth 已經到賬。

帶gas參數的轉賬命令

eth.sendTransaction({from: eth.coinbase, to: "0xa8d003b95ed969e68db9eb077ad333a3df10450a", gas:1000, ‘gasPrice‘: web3.toWei(300, ‘gwei‘), "value": "1"})

智能合約

寫一個簡單的智能合約

pragma solidity ^0.4.24;
contract Sample { 
    uint public value; 
    function Sample(uint v){ 
        value=v; 
    }
    function set(uint v){ 
        value=v; 
    }   
    function get() constant returns (uint){ 
        return value; 
    } 
}

在http://remix.ethereum.org/上編譯得到
ABI和合約的二進制代碼

點擊右上角的 start to complie 之後,在點擊下方的details
在bitecode裏面的object 拿到合約的二進制代碼,然後在前面補上0x.
然後在下一欄拿到ABI文件,復制得到的ABI文件帶有空格,可用json工具(http://www.bejson.com/jsonviewernew)把空格去掉。

將abi代碼去除空格後

[{"constant":true,"inputs":[],"name":"value","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"v","type":"uint256"}],"name":"set","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"get","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"v","type":"uint256"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"}]

然後在節點a輸入

>abi=[{"constant":true,"inputs":[],"name":"value","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"v","type":"uint256"}],"name":"set","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"get","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"v","type":"uint256"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"}]
[{
    constant: true,
    inputs: [],
    name: "value",
    outputs: [{
        name: "",
        type: "uint256"
    }],
    payable: false,
    stateMutability: "view",
    type: "function"
}, {
    constant: false,
    inputs: [{
        name: "v",
        type: "uint256"
    }],
    name: "set",
    outputs: [],
    payable: false,
    stateMutability: "nonpayable",
    type: "function"
}, {
    constant: true,
    inputs: [],
    name: "get",
    outputs: [{
        name: "",
        type: "uint256"
    }],
    payable: false,
    stateMutability: "view",
    type: "function"
}, {
    inputs: [{
        name: "v",
        type: "uint256"
    }],
    payable: false,
    stateMutability: "nonpayable",
    type: "constructor"
}]

在輸入

> sample=eth.contract(abi)
{
  abi: [{
      constant: true,
      inputs: [],
      name: "value",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
  }, {
      constant: false,
      inputs: [{...}],
      name: "set",
      outputs: [],
      payable: false,
      stateMutability: "nonpayable",
      type: "function"
  }, {
      constant: true,
      inputs: [],
      name: "get",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
  }, {
      inputs: [{...}],
      payable: false,
      stateMutability: "nonpayable",
      type: "constructor"
  }],
  eth: {
    accounts: ["0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5"],
    blockNumber: 79,
    coinbase: "0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5",
    compile: {
      lll: function(),
      serpent: function(),
      solidity: function()
    },
    defaultAccount: undefined,
    defaultBlock: "latest",
    gasPrice: 18000000000,
    hashrate: 0,
    mining: false,
    pendingTransactions: [],
    protocolVersion: "0x3f",
    syncing: false,
    call: function(),
    contract: function(abi),
    estimateGas: function(),
    filter: function(options, callback, filterCreationErrorCallback),
    getAccounts: function(callback),
    getBalance: function(),
    getBlock: function(),
    getBlockNumber: function(callback),
    getBlockTransactionCount: function(),
    getBlockUncleCount: function(),
    getCode: function(),
    getCoinbase: function(callback),
    getCompilers: function(),
    getGasPrice: function(callback),
    getHashrate: function(callback),
    getMining: function(callback),
    getPendingTransactions: function(callback),
    getProtocolVersion: function(callback),
    getRawTransaction: function(),
    getRawTransactionFromBlock: function(),
    getStorageAt: function(),
    getSyncing: function(callback),
    getTransaction: function(),
    getTransactionCount: function(),
    getTransactionFromBlock: function(),
    getTransactionReceipt: function(),
    getUncle: function(),
    getWork: function(),
    iban: function(iban),
    icapNamereg: function(),
    isSyncing: function(callback),
    namereg: function(),
    resend: function(),
    sendIBANTransaction: function(),
    sendRawTransaction: function(),
    sendTransaction: function(),
    sign: function(),
    signTransaction: function(),
    submitTransaction: function(),
    submitWork: function()
  },
  at: function(address, callback),
  getData: function(),
  new: function()
}

然後再輸入二進制合約代碼

> SampleHEX="0x608060405234801561001057600080fd5b50604051602080610114833981016040525160005560e1806100336000396000f30060806040526004361060525763ffffffff7c01000000000000000000000000000000000000000000000000000000006000350416633fa4f2458114605757806360fe47b114607b5780636d4ce63c146092575b600080fd5b348015606257600080fd5b50606960a4565b60408051918252519081900360200190f35b348015608657600080fd5b50609060043560aa565b005b348015609d57600080fd5b50606960af565b60005481565b600055565b600054905600a165627a7a7230582084151f58c02538f867209172d079a7bc65c934502439ff9607bcfb0c1f097f000029"
"0x608060405234801561001057600080fd5b50604051602080610114833981016040525160005560e1806100336000396000f30060806040526004361060525763ffffffff7c01000000000000000000000000000000000000000000000000000000006000350416633fa4f2458114605757806360fe47b114607b5780636d4ce63c146092575b600080fd5b348015606257600080fd5b50606960a4565b60408051918252519081900360200190f35b348015608657600080fd5b50609060043560aa565b005b348015609d57600080fd5b50606960af565b60005481565b600055565b600054905600a165627a7a7230582084151f58c02538f867209172d079a7bc65c934502439ff9607bcfb0c1f097f000029"

把合約部署到鏈上

> personal.unlockAccount(eth.coinbase)
Unlock account 0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5
Passphrase: 
true
> thesample=sample.new(1,{from:eth.accounts[0],data:SampleHEX,gas:3000000})
INFO [09-09|18:30:33.352] Submitted contract creation              fullhash=0xd507ca17f199c014a153c08b221107e01c6365c7d10eb609bdad99535de7dd16 contract=0x7D423D420C8a63D86c1116ef71ba2F5d405a7714
{
  abi: [{
      constant: true,
      inputs: [],
      name: "value",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
  }, {
      constant: false,
      inputs: [{...}],
      name: "set",
      outputs: [],
      payable: false,
      stateMutability: "nonpayable",
      type: "function"
  }, {
      constant: true,
      inputs: [],
      name: "get",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
  }, {
      inputs: [{...}],
      payable: false,
      stateMutability: "nonpayable",
      type: "constructor"
  }],
  address: undefined,
  transactionHash: "0xd507ca17f199c014a153c08b221107e01c6365c7d10eb609bdad99535de7dd16"
}

合約中最重要的兩個信息是合約地址和合約hash,上面的contract就是合約地址,也可以通過下面的交易細節獲取到合約地址

挖一會礦miner.start()後停止miner.stop(),根據合約hash查看交易細節

> samplerecpt=eth.getTransactionReceipt("0xd507ca17f199c014a153c08b221107e01c6365c7d10eb609bdad99535de7dd16")
{
  blockHash: "0x54bb9756e7310deff7192a6184833e76d2b203334093aac97b773a8d11081705",
  blockNumber: 80,
  contractAddress: "0x7d423d420c8a63d86c1116ef71ba2f5d405a7714",
  cumulativeGasUsed: 134093,
  from: "0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5",
  gasUsed: 134093,
  logs: [],
  logsBloom: "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
  root: "0xe88933bb56dd158847b0cf443b896be470f0ebd1d44d2e78bac023b1a3ff77d3",
  to: null,
  transactionHash: "0xd507ca17f199c014a153c08b221107e01c6365c7d10eb609bdad99535de7dd16",
  transactionIndex: 0
}

拷貝合約地址並命名,就可以拿到合約並執行合約的方法

> samplecontract=sample.at("0x7D423D420C8a63D86c1116ef71ba2F5d405a7714")
{
  abi: [{
      constant: true,
      inputs: [],
      name: "value",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
  }, {
      constant: false,
      inputs: [{...}],
      name: "set",
      outputs: [],
      payable: false,
      stateMutability: "nonpayable",
      type: "function"
  }, {
      constant: true,
      inputs: [],
      name: "get",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
  }, {
      inputs: [{...}],
      payable: false,
      stateMutability: "nonpayable",
      type: "constructor"
  }],
  address: "0x7D423D420C8a63D86c1116ef71ba2F5d405a7714",
  transactionHash: null,
  allEvents: function(),
  get: function(),
  set: function(),
  value: function()
}

查看合約get方法

> samplecontract.get.call()
1

調用合約set方法,如果賬戶已經鎖定,就先解鎖
調用set方法後,還需要挖礦才能生效

> samplecontract.set.sendTransaction(5, {from:eth.accounts[0], gas:3000000})
INFO [09-09|18:41:44.003] Submitted transaction                    fullhash=0x282aa828d5df526b20775d696b0df8c5ad1caf88adb972d7bad796ba35977fa4 recipient=0x7D423D420C8a63D86c1116ef71ba2F5d405a7714
"0x282aa828d5df526b20775d696b0df8c5ad1caf88adb972d7bad796ba35977fa4"

然後挖礦,查看結果

> samplecontract.get.call()
5

在節點b查看節點a中部署的合約
進入節點b的終端

> samplerecpt=eth.getTransactionReceipt("0xd507ca17f199c014a153c08b221107e01c6365c7d10eb609bdad99535de7dd16")
{
  blockHash: "0x54bb9756e7310deff7192a6184833e76d2b203334093aac97b773a8d11081705",
  blockNumber: 80,
  contractAddress: "0x7d423d420c8a63d86c1116ef71ba2f5d405a7714",
  cumulativeGasUsed: 134093,
  from: "0x635b3b3a6b3b9840edb9531ec91193bbf15f12f5",
  gasUsed: 134093,
  logs: [],
  logsBloom: "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
  root: "0xe88933bb56dd158847b0cf443b896be470f0ebd1d44d2e78bac023b1a3ff77d3",
  to: null,
  transactionHash: "0xd507ca17f199c014a153c08b221107e01c6365c7d10eb609bdad99535de7dd16",
  transactionIndex: 0
}

在節點b中通過合約地址獲取合約,並調用合約方法

> abi=[{"constant":true,"inputs":[],"name":"value","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"v","type":"uint256"}],"name":"set","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"get","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"v","type":"uint256"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"}]

> sample=eth.contract(abi)

  • 通過合約地址獲取二進制文件
> SampleHex=eth.getCode("0x7D423D420C8a63D86c1116ef71ba2F5d405a7714")
"0x60806040526004361060525763ffffffff7c01000000000000000000000000000000000000000000000000000000006000350416633fa4f2458114605757806360fe47b114607b5780636d4ce63c146092575b600080fd5b348015606257600080fd5b50606960a4565b60408051918252519081900360200190f35b348015608657600080fd5b50609060043560aa565b005b348015609d57600080fd5b50606960af565b60005481565b600055565b600054905600a165627a7a7230582084151f58c02538f867209172d079a7bc65c934502439ff9607bcfb0c1f097f000029"
  • 通過合約地址獲取到合約對象
    > sampleContract=sample.at("0x7D423D420C8a63D86c1116ef71ba2F5d405a7714")
    {
    abi: [{
      constant: true,
      inputs: [],
      name: "value",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
    }, {
      constant: false,
      inputs: [{...}],
      name: "set",
      outputs: [],
      payable: false,
      stateMutability: "nonpayable",
      type: "function"
    }, {
      constant: true,
      inputs: [],
      name: "get",
      outputs: [{...}],
      payable: false,
      stateMutability: "view",
      type: "function"
    }, {
      inputs: [{...}],
      payable: false,
      stateMutability: "nonpayable",
      type: "constructor"
    }],
    address: "0x7D423D420C8a63D86c1116ef71ba2F5d405a7714",
    transactionHash: null,
    allEvents: function(),
    get: function(),
    set: function(),
    value: function()
    }
  • 調用合約方法
    > sampleContract.get.call()
    5

加入區塊鏈開發學習交流群,請添加微信:Xhole1024
蟲洞社區:https://www.uzanapp.com/
技術分享圖片

以太坊搭建聯盟鏈詳細教程