• c#使用类库nthereum在.net上开发以太坊的实战示例


    这是一篇文章的早期版本,旨在帮助那些对以太坊区块链平台有基本了解的开发人员,如果想学习如何使用Nethereum .NET库对Ethereum平台进行编程。

    我以后会在这篇文章中添加更多内容,但就目前而言,正在使用它发布.NET 10+的系列C#示例,介绍如何使用Nethereum库执行针对以太坊区块链平台的最常见任务。

    最常见任务列表包括以下内容:

    • 1.获取协议版本
    • 2.获取最大块数
    • 3.获取帐户余额
    • 4.发送以太
    • 5.等待交易收据
    • 6.在区块链中扫描块
    • 7.列出个人账户(及其余额)
    • 8.在区块链中扫描交易
    • 9.与现有(已部署)合同互动
    • 10.用事件和现有(已部署)合约交互
    • 11.获取所有活动更改
    • 12.获取合约金额历史

    这里是c#的主文件:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading;
    using System.Threading.Tasks;
    
    using Nethereum.Hex.HexTypes;
    using Nethereum.Web3;
    
    namespace MWH.MyNethereum.QuickRef
    {
     static public class TaskExamples
     {
     const int UNLOCK_TIMEOUT = 2 * 60; // 2 minutes (arbitrary)
     const int SLEEP_TIME = 5 * 1000; // 5 seconds (arbitrary)
     const int MAX_TIMEOUT = 2 * 60 * 1000; // 2 minutes (arbirtrary)
    
    // These static public variables do not represent a recommended pattern
     static public string LastProtocolVersion = "";
     static public string LastTxHash = "";
     static public Nethereum.RPC.Eth.DTOs.TransactionReceipt LastTxReceipt = null;
     static public HexBigInteger LastMaxBlockNumber = new HexBigInteger(0);
    
    static public async Task GetProtocolVersionExample(Web3 web3)
     {
     Console.WriteLine("GetProtocolVersionExample:");
    
    var protocolVersion = await web3.Eth.ProtocolVersion.SendRequestAsync();
     Console.WriteLine("protocolVersion:	" + protocolVersion.ToString());
     LastProtocolVersion = protocolVersion;
     }
    
    static public async Task GetMaxBlockExample(Web3 web3)
     {
     Console.WriteLine("GetMaxBlockExample:");
    
    var maxBlockNumber = await web3.Eth.Blocks.GetBlockNumber.SendRequestAsync();
     Console.WriteLine("maxBlockNumber:	" + maxBlockNumber.Value.ToString());
     LastMaxBlockNumber = maxBlockNumber;
     }
    
    static public async Task ScanBlocksExample(Web3 web3, ulong startBlockNumber, ulong endBlockNumber)
     {
     Console.WriteLine("ScanBlocksExample:");
    
    long txTotalCount = 0;
     for (ulong blockNumber = startBlockNumber; blockNumber <= endBlockNumber; blockNumber++)
     {
     var blockParameter = new Nethereum.RPC.Eth.DTOs.BlockParameter(blockNumber);
     var block = await web3.Eth.Blocks.GetBlockWithTransactionsByNumber.SendRequestAsync(blockParameter);
     var trans = block.Transactions;
     int txCount = trans.Length;
     txTotalCount += txCount;
     if (blockNumber % 1000 == 0) Console.Write(".");
     if (blockNumber % 10000 == 0)
     {
     DateTime blockDateTime = Helpers.UnixTimeStampToDateTime((double)block.Timestamp.Value);
     Console.WriteLine(blockNumber.ToString() + " " + txTotalCount.ToString() + " " + blockDateTime.ToString());
     }
     }
     Console.WriteLine();
     }
    
    static public async Task ScanTxExample(Web3 web3, ulong startBlockNumber, ulong endBlockNumber)
     {
     Console.WriteLine("ScanTxExample:");
    
    long txTotalCount = 0;
     for (ulong blockNumber = startBlockNumber; blockNumber <= endBlockNumber; blockNumber++)
     {
     var blockParameter = new Nethereum.RPC.Eth.DTOs.BlockParameter(blockNumber);
     var block = await web3.Eth.Blocks.GetBlockWithTransactionsByNumber.SendRequestAsync(blockParameter);
     var trans = block.Transactions;
     int txCount = trans.Length;
     txTotalCount += txCount;
     foreach (var tx in trans)
     {
     try
     {
     var bn = tx.BlockNumber.Value;
     var th = tx.TransactionHash;
     var ti = tx.TransactionIndex.Value;
    
    var rpt = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(th);
     var status = rpt.Status.Value;
    
    var nc = tx.Nonce.Value;
     var from = tx.From;
    
    Console.WriteLine(th.ToString() + " " + ti.ToString() + " " + from.ToString() + " " + status.ToString());
    
    var to = tx.To;
     if (to == null) to = "to:NULL";
     var v = tx.Value.Value;
     var g = tx.Gas.Value;
     var gp = tx.GasPrice.Value;
     Console.WriteLine(th.ToString() + " " + ti.ToString() + " " + nc.ToString() + " " + from.ToString() + " " + to.ToString() + " " + v.ToString() + " " + g.ToString() + " " + gp.ToString());
     }
     catch (Exception ex)
     {
     Console.WriteLine("ScanTxExample.Tx:	" + ex.ToString());
     if (ex.InnerException != null) Console.WriteLine("ScanTxExample.Tx:	" + ex.InnerException.ToString());
     }
     }
     Console.WriteLine();
     }
     }
    
    static public async Task GetAccountBalanceExample(Web3 web3, string accountAddress)
     {
     Console.WriteLine("GetAccountBalanceExample:");
    
    var balanceWei = await web3.Eth.GetBalance.SendRequestAsync(accountAddress);
     var balanceEther = Web3.Convert.FromWei(balanceWei.Value);
     Console.WriteLine("accountAddress:	" + accountAddress.ToString());
     Console.WriteLine("balanceEther:	" + balanceEther.ToString());
     }
    
    static public async Task ListPersonalAccountsExample(Web3 web3)
     {
     Console.WriteLine("ListPersonalAccountsExample:");
    
    var accounts = await web3.Personal.ListAccounts.SendRequestAsync();
     foreach (var account in accounts)
     {
     var balanceWei = await web3.Eth.GetBalance.SendRequestAsync(account);
     var balanceEther = Web3.Convert.FromWei(balanceWei.Value);
     Console.WriteLine("account:	" + account + " balanceEther:	" + balanceEther.ToString());
     }
     }
    
    static public async Task SendEtherExample(Web3 web3, string fromAddress, string fromPassword, string toAddress, long amountWei)
     {
     Console.WriteLine("SendEtherExample:");
    
    var unlockResult = await web3.Personal.UnlockAccount.SendRequestAsync(fromAddress, fromPassword, UNLOCK_TIMEOUT);
     var sendTxHash = await web3.Eth.TransactionManager.SendTransactionAsync(fromAddress, toAddress, new HexBigInteger(amountWei));
     Console.WriteLine("fromAddress:	" + fromAddress.ToString());
     Console.WriteLine("toAddress:	" + toAddress.ToString());
     Console.WriteLine("amountWei:	" + amountWei.ToString());
     Console.WriteLine("sendTxHash:	" + sendTxHash.ToString());
     LastTxHash = sendTxHash;
     }
    
    static public async Task WaitForTxReceiptExample(Web3 web3, string txHash)
     {
     Console.WriteLine("WaitForTxReceiptExample:");
    
    int timeoutCount = 0;
     var txReceipt = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(txHash);
     while (txReceipt == null && timeoutCount < MAX_TIMEOUT)
     {
     Console.WriteLine("Sleeping...");
     Thread.Sleep(SLEEP_TIME);
     txReceipt = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(txHash);
     timeoutCount += SLEEP_TIME;
     }
     Console.WriteLine("timeoutCount " + timeoutCount.ToString());
     LastTxReceipt = txReceipt;
     }
    
    static public async Task InteractWithExistingContractExample(Web3 web3, string fromAddress, string fromPassword, string contractAddress, string contractAbi)
     {
     Console.WriteLine("InteractWithExistingContractExample:");
    
    var contract = web3.Eth.GetContract(contractAbi, contractAddress);
    
    var setMessageFunction = contract.GetFunction("setMsg");
     var getMessageFunction = contract.GetFunction("getMsg");
    
    string nowTimestamp = DateTime.UtcNow.ToString() + " UTC";
     Console.WriteLine("now:	" + nowTimestamp);
    
    var unlockResult = await web3.Personal.UnlockAccount.SendRequestAsync(fromAddress, fromPassword, UNLOCK_TIMEOUT);
     var txHash1 = await setMessageFunction.SendTransactionAsync(fromAddress, new HexBigInteger(900000), null, 1, "Hello World");
     Console.WriteLine("txHash1:	" + txHash1.ToString());
     var txHash2 = await setMessageFunction.SendTransactionAsync(fromAddress, new HexBigInteger(900000), null, 2, nowTimestamp);
     Console.WriteLine("txHash2:	" + txHash2.ToString());
    
    var txReceipt2 = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(txHash2);
     int timeoutCount = 0;
     while (txReceipt2 == null && timeoutCount < MAX_TIMEOUT)
     {
     Console.WriteLine("Sleeping...");
     Thread.Sleep(SLEEP_TIME);
     txReceipt2 = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(txHash2);
     timeoutCount += SLEEP_TIME;
     }
     Console.WriteLine("timeoutCount:	" + timeoutCount.ToString());
    
    var txReceipt3 = await setMessageFunction.SendTransactionAndWaitForReceiptAsync(fromAddress, new HexBigInteger(900000), null, null, 2, nowTimestamp + " Wait");
     Console.WriteLine("txReceipt3:	" + txReceipt3.TransactionHash.ToString());
     Console.WriteLine("txReceipt3:	" + txReceipt3.CumulativeGasUsed.Value.ToString());
    
    var getResult1 = await getMessageFunction.CallAsync<string>(1);
     Console.WriteLine("getResult1:	" + getResult1.ToString());
     var getResult2 = await getMessageFunction.CallAsync<string>(2);
     Console.WriteLine("getResult2:	" + getResult2.ToString());
     }
    
    static public async Task InteractWithExistingContractWithEventsExample(Web3 web3, string fromAddress, string fromPassword, string contractAddress, string contractAbi)
     {
     Console.WriteLine("InteractWithExistingContractWithEventsExample:");
    
    var contract = web3.Eth.GetContract(contractAbi, contractAddress);
    
    var setMessageFunction = contract.GetFunction("setMsg");
     var getMessageFunction = contract.GetFunction("getMsg");
     var multipliedEvent = contract.GetEvent("MultipliedEvent");
     var newMessageEvent = contract.GetEvent("NewMessageEvent");
    
    var filterAllMultipliedEvent = await multipliedEvent.CreateFilterAsync();
     var filterAllNewMessageEvent = await newMessageEvent.CreateFilterAsync();
    
    string nowTimestamp = DateTime.UtcNow.ToString() + " UTC";
     Console.WriteLine("now:	" + nowTimestamp);
    
    var unlockResult = await web3.Personal.UnlockAccount.SendRequestAsync(fromAddress, fromPassword, UNLOCK_TIMEOUT);
     var txHash1 = await setMessageFunction.SendTransactionAsync(fromAddress, new HexBigInteger(900000), null, 1, "Hello World");
     Console.WriteLine("txHash1:	" + txHash1.ToString());
     var txHash2 = await setMessageFunction.SendTransactionAsync(fromAddress, new HexBigInteger(900000), null, 2, nowTimestamp);
     Console.WriteLine("txHash2:	" + txHash2.ToString());
    
    var txReceipt2 = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(txHash2);
     int timeoutCount = 0;
     while (txReceipt2 == null && timeoutCount < MAX_TIMEOUT)
     {
     Console.WriteLine("Sleeping...");
     Thread.Sleep(SLEEP_TIME);
     txReceipt2 = await web3.Eth.Transactions.GetTransactionReceipt.SendRequestAsync(txHash2);
     timeoutCount += SLEEP_TIME;
     }
     Console.WriteLine("timeoutCount:	" + timeoutCount.ToString());
    
    var txReceipt3 = await setMessageFunction.SendTransactionAndWaitForReceiptAsync(fromAddress, new HexBigInteger(900000), null, null, 2, nowTimestamp + " Wait");
     Console.WriteLine("txReceipt3:	" + txReceipt3.TransactionHash.ToString());
     Console.WriteLine("txReceipt3:	" + txReceipt3.CumulativeGasUsed.Value.ToString());
    
    var getResult1 = await getMessageFunction.CallAsync<string>(1);
     Console.WriteLine("getResult1:	" + getResult1.ToString());
     var getResult2 = await getMessageFunction.CallAsync<string>(2);
     Console.WriteLine("getResult2:	" + getResult2.ToString());
    
    var logMultipliedEvents = await multipliedEvent.GetFilterChanges<FunctionOutputHelpers.MultipliedEventArgs>(filterAllMultipliedEvent);
     foreach (var mea in logMultipliedEvents)
     {
     Console.WriteLine("multipliedEvent:	" +
     mea.Event.sender + " " + mea.Event.oldProduct.ToString() + " " + mea.Event.value.ToString() + " " + mea.Event.newProduct.ToString());
     }
    
    var logNewMessageEvents = await newMessageEvent.GetFilterChanges<FunctionOutputHelpers.NewMessageEventArgs>(filterAllNewMessageEvent);
     foreach (var mea in logNewMessageEvents)
     {
     Console.WriteLine("newMessageEvent:	" +
     mea.Event.sender + " " + mea.Event.ind.ToString() + " " + mea.Event.msg.ToString());
     }
     }
    
    static public async Task GetAllChangesExample(Web3 web3, string fromAddress, string fromPassword, string contractAddress, string contractAbi)
     {
     Console.WriteLine("GetAllChangesExample:");
    
    var contract = web3.Eth.GetContract(contractAbi, contractAddress);
     var newMessageEvent = contract.GetEvent("NewMessageEvent");
     var filterAllNewMessageEvent = await newMessageEvent.CreateFilterAsync(fromAddress);
     var logNewMessageEvents = await newMessageEvent.GetAllChanges<FunctionOutputHelpers.NewMessageEventArgs>(filterAllNewMessageEvent);
     foreach (var mea in logNewMessageEvents)
     {
     Console.WriteLine("newMessageEvent:	" +
     mea.Event.sender + " " + mea.Event.ind.ToString() + " " + mea.Event.msg.ToString());
     }
     }
    
    static public async Task GetContractValuesHistoryUniqueOffsetValueExample(Web3 web3, string contractAddress, HexBigInteger recentBlockNumber, ulong numberBlocks, int offset)
     {
     Console.WriteLine("GetContractValuesHistoryUniqueOffsetValueExample:");
    
    string previousValue = "";
     for (ulong blockNumber = (ulong)recentBlockNumber.Value; blockNumber > (ulong)recentBlockNumber.Value - numberBlocks; blockNumber--)
     {
     var blockNumberParameter = new Nethereum.RPC.Eth.DTOs.BlockParameter(blockNumber);
     var valueAtOffset = await web3.Eth.GetStorageAt.SendRequestAsync(contractAddress, new HexBigInteger(offset), blockNumberParameter);
     if (valueAtOffset != previousValue)
     {
     var block = await web3.Eth.Blocks.GetBlockWithTransactionsByNumber.SendRequestAsync(blockNumberParameter);
     DateTime blockDateTime = Helpers.UnixTimeStampToDateTime((double)block.Timestamp.Value);
     Console.WriteLine("blockDateTime:	" + blockDateTime.ToString());
    
    for (int storageOffset = 0; storageOffset < offset+2; storageOffset++)
     {
     var valueAt = await web3.Eth.GetStorageAt.SendRequestAsync(contractAddress, new HexBigInteger(storageOffset), blockNumberParameter);
     Console.WriteLine("value:	" + blockNumber.ToString() + " " + storageOffset.ToString() + " " + valueAt + " " + Helpers.ConvertHex(valueAt.Substring(2)));
     }
     previousValue = valueAtOffset;
     }
     }
     }
     }
    }
    

    以下是一些支持文件:

    FunctionOutputHelpers.cs

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    
    using Nethereum.Web3;
    using Nethereum.ABI.FunctionEncoding.Attributes;
    
    namespace MWH.MyNethereum.QuickRef
    {
     static public class FunctionOutputHelpers
     {
     // event MultipliedEvent(
     // address indexed sender,
     // int oldProduct,
     // int value,
     // int newProduct
     // );
    
    [FunctionOutput]
     public class MultipliedEventArgs
     {
     [Parameter("address", "sender", 1, true)]
     public string sender { get; set; }
    
    [Parameter("int", "oldProduct", 2, false)]
     public int oldProduct { get; set; }
    
    [Parameter("int", "value", 3, false)]
     public int value { get; set; }
    
    [Parameter("int", "newProduct", 4, false)]
     public int newProduct { get; set; }
    
    }
    
    //event NewMessageEvent(
     // address indexed sender,
     // uint256 indexed ind,
     // string msg
     //);
    
    [FunctionOutput]
     public class NewMessageEventArgs
     {
     [Parameter("address", "sender", 1, true)]
     public string sender { get; set; }
    
    [Parameter("uint256", "ind", 2, true)]
     public int ind { get; set; }
    
    [Parameter("string", "msg", 3, false)]
     public string msg { get; set; }
     }
     }
    }
    

    Helpers.cs

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    
    namespace MWH.MyNethereum.QuickRef
    {
     static public class Helpers
     {
     public static string ConvertHex(String hexString)
     {
     try
     {
     string ascii = string.Empty;
    
    for (int i = 0; i < hexString.Length; i += 2)
     {
     String hs = string.Empty;
    
    hs = hexString.Substring(i, 2);
     uint decval = System.Convert.ToUInt32(hs, 16);
     char character = System.Convert.ToChar(decval);
     ascii += character;
    
    }
    
    return ascii;
     }
     catch (Exception ex) { Console.WriteLine(ex.Message); }
    
    return string.Empty;
     }
    
    public static DateTime UnixTimeStampToDateTime(double unixTimeStamp)
     {
     // Unix timestamp is seconds past epoch
     System.DateTime dtDateTime = new DateTime(1970, 1, 1, 0, 0, 0, 0, System.DateTimeKind.Utc);
     dtDateTime = dtDateTime.AddSeconds(unixTimeStamp); // .ToLocalTime();
     return dtDateTime;
     }
    
    public static DateTime JavaTimeStampToDateTime(double javaTimeStamp)
     {
     // Java timestamp is milliseconds past epoch
     System.DateTime dtDateTime = new DateTime(1970, 1, 1, 0, 0, 0, 0, System.DateTimeKind.Utc);
     dtDateTime = dtDateTime.AddMilliseconds(javaTimeStamp); // .ToLocalTime();
     return dtDateTime;
     }
     }
    }
    

    以下是用于实施这些示例时使用的以太坊合约的Solidity代码:

    Test3.sol

    pragma solidity 0.4.19;
    
    contract Test3 {
    
    int public _product;
    string[5] _msgs;
     
    event MultipliedEvent(
    address indexed sender,
    int oldProduct,
    int value,
    int newProduct
    );
     
    event NewMessageEvent(
    address indexed sender,
    uint256 indexed ind,
    string msg
    );
    
    function Test3() public {
    _product = 1;
    }
    
    function multiply(int value) public returns(int product) {
    int old = _product;
    _product = value * _product;
    MultipliedEvent( msg.sender, old, value, _product );
    return _product;
    }
     
    function getProduct() public constant returns(int product) {
    return _product;
    }
    
    function setMsg(uint256 i, string m) public returns(uint256 mi) {
    _msgs[i] = m;
    NewMessageEvent( msg.sender, i, m);
    return -i;
    }
    
    function getMsg(uint256 index) public constant returns(string m) {
    return _msgs[index];
    }
    }
    

    我觉得这是发布代码示例的一种相当简单粗暴的方式。有任何更好建议欢迎留言。

  • 相关阅读:
    第11组 团队Git现场编程实战
    团队项目-需求分析报告
    团队项目-选题报告
    第10组 Alpha事后诸葛亮
    第10组 Alpha冲刺(6/6)
    第10组 Alpha冲刺(5/6)
    第10组 Alpha冲刺(4/6)
    第10组 Alpha冲刺(3/6)
    第10组 Alpha冲刺(2/6)
    第10组 Alpha冲刺(1/6)
  • 原文地址:https://www.cnblogs.com/malakashi/p/9602657.html
Copyright © 2020-2023  润新知