github.com/linapex/ethereum-go-chinese@v0.0.0-20190316121929-f8b7a73c3fa1/cmd/puppeth/wizard_node.go (about) 1 2 //<developer> 3 // <name>linapex 曹一峰</name> 4 // <email>linapex@163.com</email> 5 // <wx>superexc</wx> 6 // <qqgroup>128148617</qqgroup> 7 // <url>https://jsq.ink</url> 8 // <role>pku engineer</role> 9 // <date>2019-03-16 19:16:33</date> 10 //</624450070195998720> 11 12 13 package main 14 15 import ( 16 "encoding/json" 17 "fmt" 18 "time" 19 20 "github.com/ethereum/go-ethereum/accounts/keystore" 21 "github.com/ethereum/go-ethereum/common" 22 "github.com/ethereum/go-ethereum/log" 23 ) 24 25 //deploynode基于一些用户输入创建一个新的节点配置。 26 func (w *wizard) deployNode(boot bool) { 27 //在用户浪费输入时间之前做一些健全性检查 28 if w.conf.Genesis == nil { 29 log.Error("No genesis block configured") 30 return 31 } 32 if w.conf.ethstats == "" { 33 log.Error("No ethstats server configured") 34 return 35 } 36 //选择要与之交互的服务器 37 server := w.selectServer() 38 if server == "" { 39 return 40 } 41 client := w.servers[server] 42 43 //从服务器检索任何活动节点配置 44 infos, err := checkNode(client, w.network, boot) 45 if err != nil { 46 if boot { 47 infos = &nodeInfos{port: 30303, peersTotal: 512, peersLight: 256} 48 } else { 49 infos = &nodeInfos{port: 30303, peersTotal: 50, peersLight: 0, gasTarget: 7.5, gasLimit: 10, gasPrice: 1} 50 } 51 } 52 existed := err == nil 53 54 infos.genesis, _ = json.MarshalIndent(w.conf.Genesis, "", " ") 55 infos.network = w.conf.Genesis.Config.ChainID.Int64() 56 57 //找出用户希望存储持久数据的位置 58 fmt.Println() 59 if infos.datadir == "" { 60 fmt.Printf("Where should data be stored on the remote machine?\n") 61 infos.datadir = w.readString() 62 } else { 63 fmt.Printf("Where should data be stored on the remote machine? (default = %s)\n", infos.datadir) 64 infos.datadir = w.readDefaultString(infos.datadir) 65 } 66 if w.conf.Genesis.Config.Ethash != nil && !boot { 67 fmt.Println() 68 if infos.ethashdir == "" { 69 fmt.Printf("Where should the ethash mining DAGs be stored on the remote machine?\n") 70 infos.ethashdir = w.readString() 71 } else { 72 fmt.Printf("Where should the ethash mining DAGs be stored on the remote machine? (default = %s)\n", infos.ethashdir) 73 infos.ethashdir = w.readDefaultString(infos.ethashdir) 74 } 75 } 76 //找出要监听的端口 77 fmt.Println() 78 fmt.Printf("Which TCP/UDP port to listen on? (default = %d)\n", infos.port) 79 infos.port = w.readDefaultInt(infos.port) 80 81 //计算允许多少对等点(根据节点类型不同) 82 fmt.Println() 83 fmt.Printf("How many peers to allow connecting? (default = %d)\n", infos.peersTotal) 84 infos.peersTotal = w.readDefaultInt(infos.peersTotal) 85 86 //计算允许多少光对等(根据节点类型不同) 87 fmt.Println() 88 fmt.Printf("How many light peers to allow connecting? (default = %d)\n", infos.peersLight) 89 infos.peersLight = w.readDefaultInt(infos.peersLight) 90 91 // 92 fmt.Println() 93 if infos.ethstats == "" { 94 fmt.Printf("What should the node be called on the stats page?\n") 95 infos.ethstats = w.readString() + ":" + w.conf.ethstats 96 } else { 97 fmt.Printf("What should the node be called on the stats page? (default = %s)\n", infos.ethstats) 98 infos.ethstats = w.readDefaultString(infos.ethstats) + ":" + w.conf.ethstats 99 } 100 //如果节点是矿工/签名者,则加载所需的凭据 101 if !boot { 102 if w.conf.Genesis.Config.Ethash != nil { 103 // 104 fmt.Println() 105 if infos.etherbase == "" { 106 fmt.Printf("What address should the miner use?\n") 107 for { 108 if address := w.readAddress(); address != nil { 109 infos.etherbase = address.Hex() 110 break 111 } 112 } 113 } else { 114 fmt.Printf("What address should the miner use? (default = %s)\n", infos.etherbase) 115 infos.etherbase = w.readDefaultAddress(common.HexToAddress(infos.etherbase)).Hex() 116 } 117 } else if w.conf.Genesis.Config.Clique != nil { 118 //如果已经设置了以前的签名者,则建议重新使用它 119 if infos.keyJSON != "" { 120 if key, err := keystore.DecryptKey([]byte(infos.keyJSON), infos.keyPass); err != nil { 121 infos.keyJSON, infos.keyPass = "", "" 122 } else { 123 fmt.Println() 124 fmt.Printf("Reuse previous (%s) signing account (y/n)? (default = yes)\n", key.Address.Hex()) 125 if !w.readDefaultYesNo(true) { 126 infos.keyJSON, infos.keyPass = "", "" 127 } 128 } 129 } 130 //基于集团的签名者需要一个密钥文件和解锁密码,询问是否不可用 131 if infos.keyJSON == "" { 132 fmt.Println() 133 fmt.Println("Please paste the signer's key JSON:") 134 infos.keyJSON = w.readJSON() 135 136 fmt.Println() 137 fmt.Println("What's the unlock password for the account? (won't be echoed)") 138 infos.keyPass = w.readPassword() 139 140 if _, err := keystore.DecryptKey([]byte(infos.keyJSON), infos.keyPass); err != nil { 141 log.Error("Failed to decrypt key with given passphrase") 142 return 143 } 144 } 145 } 146 //建立签名者实施的气体动力学 147 fmt.Println() 148 fmt.Printf("What gas limit should empty blocks target (MGas)? (default = %0.3f)\n", infos.gasTarget) 149 infos.gasTarget = w.readDefaultFloat(infos.gasTarget) 150 151 fmt.Println() 152 fmt.Printf("What gas limit should full blocks target (MGas)? (default = %0.3f)\n", infos.gasLimit) 153 infos.gasLimit = w.readDefaultFloat(infos.gasLimit) 154 155 fmt.Println() 156 fmt.Printf("What gas price should the signer require (GWei)? (default = %0.3f)\n", infos.gasPrice) 157 infos.gasPrice = w.readDefaultFloat(infos.gasPrice) 158 } 159 // 160 nocache := false 161 if existed { 162 fmt.Println() 163 fmt.Printf("Should the node be built from scratch (y/n)? (default = no)\n") 164 nocache = w.readDefaultYesNo(false) 165 } 166 if out, err := deployNode(client, w.network, w.conf.bootnodes, infos, nocache); err != nil { 167 log.Error("Failed to deploy Ethereum node container", "err", err) 168 if len(out) > 0 { 169 fmt.Printf("%s\n", out) 170 } 171 return 172 } 173 //一切正常,运行网络扫描以获取任何更改 174 log.Info("Waiting for node to finish booting") 175 time.Sleep(3 * time.Second) 176 177 w.networkStats() 178 } 179