BCSkill (Block chain skill )
区块链中文技术社区

只讨论区块链底层技术
遵守一切相关法律政策!

Ethereum HD Wallet derivations in Go

https://github.com/miguelmota/go-ethereum-hdwallet.git

Install

go get -u github.com/miguelmota/go-ethereum-hdwallet

Documenation

https://godoc.org/github.com/miguelmota/go-ethereum-hdwallet

Getting started

package main

import (
    "fmt"
    "log"

    "github.com/miguelmota/go-ethereum-hdwallet"
)

func main() {
    mnemonic := "tag volcano eight thank tide danger coast health above argue embrace heavy"
    wallet, err := hdwallet.NewFromMnemonic(mnemonic)
    if err != nil {
        log.Fatal(err)
    }

    path := hdwallet.MustParseDerivationPath("m/44'/60'/0'/0/0")
    account, err := wallet.Derive(path, false)
    if err != nil {
        log.Fatal(err)
    }

    fmt.Println(account.Address.Hex()) // 0xC49926C4124cEe1cbA0Ea94Ea31a6c12318df947

    path = hdwallet.MustParseDerivationPath("m/44'/60'/0'/0/1")
    account, err = wallet.Derive(path, false)
    if err != nil {
        log.Fatal(err)
    }

    fmt.Println(account.Address.Hex()) // 0x8230645aC28A4EdD1b0B53E7Cd8019744E9dD559
}

Signing transaction

package main

import (
    "log"
    "math/big"

    "github.com/davecgh/go-spew/spew"
    "github.com/ethereum/go-ethereum/common"
    "github.com/ethereum/go-ethereum/core/types"
    "github.com/miguelmota/go-ethereum-hdwallet"
)

func main() {
    mnemonic := "tag volcano eight thank tide danger coast health above argue embrace heavy"
    wallet, err := hdwallet.NewFromMnemonic(mnemonic)
    if err != nil {
        log.Fatal(err)
    }

    path := hdwallet.MustParseDerivationPath("m/44'/60'/0'/0/0")
    account, err := wallet.Derive(path, true)
    if err != nil {
        log.Fatal(err)
    }

    nonce := uint64(0)
    value := big.NewInt(1000000000000000000)
    toAddress := common.HexToAddress("0x0")
    gasLimit := uint64(21000)
    gasPrice := big.NewInt(21000000000)
    var data []byte

    tx := types.NewTransaction(nonce, toAddress, value, gasLimit, gasPrice, data)
    signedTx, err := wallet.SignTx(account, tx, nil)
    if err != nil {
        log.Fatal(err)
    }

    spew.Dump(signedTx)
}

CLI

go get -u github.com/miguelmota/go-ethereum-hdwallet/cmd/geth-hdwallet
$ geth-hdwallet -mnemonic "tag volcano eight thank tide danger coast health above argue embrace heavy" -path "m/44'/60'/0'/0/0"

public address: 0xC49926C4124cEe1cbA0Ea94Ea31a6c12318df947
private key: 63e21d10fd50155dbba0e7d3f7431a400b84b4c2ac1ee38872f82448fe3ecfb9

Test

make test

弹性的以太坊事件监听器,可将您的智能合约事件和后端微服务联系起来

https://github.com/eventeum/eventeum

以太坊事件监听器,将您的智能合约事件和后端微服务联系起来。Eventeum侦听以太坊网络发出的特定事件,并将这些事件广播到您的中间件层。这提供了不同的关注点分离,并且意味着您的微服务不必直接将事件订阅到以太坊节点。

eth poa 链加油站gasprice

部署安装

git clone https://github.com/bcskill/eth-gasprices.git
cd eth-gasprices
pip3 install -r requirements.txt

服务运行

export ETH_RPC_URL=http://ip:8545
python3 gasprice.py -h 0.0.0.0 -p 8000
服务启动
cp gasprice.service /etc/systemd/system/gasprice.service
systemctl daemon-reload
systemctl start gasprice.service
systemctl status gasprice.service

或者

python3 gasprice.py -h 0.0.0.0 -p 8000 "$@" > ./stdout.txt 2> ./stderr.txt &  echo $! > ./nodeos.pid
tail -f stderr.txt

测试访问

http://127.0.0.1:8000/

测试数据

{
    "health": true,
    "block_number": 26972,
    "block_time": 2.261,
    "slow": 24,
    "standard": 25,
    "fast": 54.955,
    "instant": 100
}
数据解释
  • slow 慢
  • standard 标准
  • fast 快速
  • instant 即时

“慢”,“标准”,“快速”和“即时”值代表最近200个区块的最低汽油价格。 默认情况下,慢表示30%的概率,标准为60%,快为90%,即时为100%。

常见问题

numpy: Something is wrong with the numpy installation.
python3 gasprice.py
Traceback (most recent call last):
  File "gasprice.py", line 4, in <module>
    import pandas as pd
  File "/home/surou/.local/lib/python3.6/site-packages/pandas/__init__.py", line 17, in <module>
    "Unable to import required dependencies:\n" + "\n".join(missing_dependencies)
ImportError: Unable to import required dependencies:
numpy: Something is wrong with the numpy installation. While importing we detected an older version of numpy in ['/home/surou/.local/lib/python3.6/site-packages/numpy']. One method of fixing this is to repeatedly uninstall numpy until none is found, then reinstall this version.
解决方法
rm -rf ~/.local/lib/python3.6/site-packages/numpy
pip install numpy
No module named 'click'
ModuleNotFoundError: No module named 'click'
解决方法
pip3 install click

Web3.py 安装和使用

安装python3

 sudo apt-get install python3-dev -y

设置python3默认

sudo update-alternatives --install /usr/bin/python python /usr/bin/python3 150
sudo update-alternatives --config python

安装pip3

sudo apt-get install python3-pip

安装web3

pip3 install web3

测试合约代码

import time
from web3 import Web3
from web3.contract import Contract, ContractFunctions
from web3 import Web3

false = False
true = True
CONTRACT_ADDRESS = "0xD8B0c34024deA0B9ABaf187E58Dbb3e81a033367"
CONTRACT_ABI = [{"constant":true,"inputs":[],"name":"name","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_spender","type":"address"},{"name":"_value","type":"uint256"}],"name":"approve","outputs":[{"name":"success","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"totalSupply","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_to","type":"address"},{"name":"_value","type":"uint256"}],"name":"transferFrom","outputs":[{"name":"success","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"decimals","outputs":[{"name":"","type":"uint8"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_value","type":"uint256"}],"name":"burn","outputs":[{"name":"success","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"","type":"address"}],"name":"balanceOf","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_value","type":"uint256"}],"name":"burnFrom","outputs":[{"name":"success","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"symbol","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_to","type":"address"},{"name":"_value","type":"uint256"}],"name":"transfer","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"name":"_spender","type":"address"},{"name":"_value","type":"uint256"},{"name":"_extraData","type":"bytes"}],"name":"approveAndCall","outputs":[{"name":"success","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"","type":"address"},{"name":"","type":"address"}],"name":"allowance","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"initialSupply","type":"uint256"},{"name":"tokenName","type":"string"},{"name":"tokenSymbol","type":"string"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"name":"from","type":"address"},{"indexed":true,"name":"to","type":"address"},{"indexed":false,"name":"value","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"owner","type":"address"},{"indexed":true,"name":"spender","type":"address"},{"indexed":false,"name":"value","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"from","type":"address"},{"indexed":false,"name":"value","type":"uint256"}],"name":"Burn","type":"event"}]

w3 = Web3(Web3.HTTPProvider('http://。。。:8545'))
acct = w3.eth.account.privateKeyToAccount("e9bc9ae61053。。。。。69fd59d7986b9f4f49c025cc")

if __name__ == "__main__":
    print("getTransactionCount:", w3.eth.getTransactionCount(acct.address))
    print("gasPrice:", w3.eth.gasPrice)

    contract = w3.eth.contract(address=Web3.toChecksumAddress(CONTRACT_ADDRESS), abi=CONTRACT_ABI)
    TokenConstruct_txn = contract.functions.transfer(Web3.toChecksumAddress("0xc65dD4299C682f335d6e15e2B5774D015E01E479"), w3.toWei(2, 'ether')).buildTransaction({
        'from': acct.address,
        'nonce': w3.eth.getTransactionCount(acct.address),
        'gas': 100000,
        'gasPrice': w3.eth.gasPrice})
    TokenSigned = acct.signTransaction(TokenConstruct_txn)
    print("Pre-calculated transactionHash:", w3.toHex(w3.sha3(TokenSigned.rawTransaction)))
    TokenTx_hash = w3.eth.sendRawTransaction(TokenSigned.rawTransaction)
    print("transactionHash:", TokenTx_hash.hex())
    #TokenTx_receipt = w3.eth.waitForTransactionReceipt(TokenTx_hash)
    #TokenContract_address = TokenTx_receipt['contractAddress']
    #print("Contract Deployed At:", TokenContract_address)

参考

https://web3py.readthedocs.io/en/latest/quickstart.html

常见问题

  1. Command "python setup.py egg_info" failed with error code 1
    pip3 install --upgrade setuptools
    python3 -m pip install --upgrade pip