/// <summary> /// Configure the components of the wallet /// </summary> /// <param name="group">The group to use</param> public void Configure(NodesGroup group) { if (group == null) { throw new ArgumentNullException("group"); } var parameters = group.NodeConnectionParameters; group.Requirements.SupportSPV = true; var chain = parameters.TemplateBehaviors.Find <ChainBehavior>(); if (chain == null) { chain = new ChainBehavior(new ConcurrentChain(_Parameters.Network)); parameters.TemplateBehaviors.Add(chain); } if (chain.Chain.Genesis.HashBlock != _Parameters.Network.GetGenesis().GetHash()) { throw new InvalidOperationException("ChainBehavior with invalid network chain detected"); } var addrman = parameters.TemplateBehaviors.Find <AddressManagerBehavior>(); if (addrman == null) { addrman = new AddressManagerBehavior(new AddressManager()); parameters.TemplateBehaviors.Add(addrman); } var tracker = parameters.TemplateBehaviors.Find <TrackerBehavior>(); if (tracker == null) { tracker = new TrackerBehavior(new Tracker(), chain.Chain); parameters.TemplateBehaviors.Add(tracker); } var wallet = FindWalletBehavior(parameters.TemplateBehaviors); if (wallet == null) { wallet = new WalletBehavior(this); parameters.TemplateBehaviors.Add(wallet); } var broadcast = parameters.TemplateBehaviors.Find <BroadcastHubBehavior>(); if (broadcast == null) { broadcast = new BroadcastHubBehavior(); parameters.TemplateBehaviors.Add(broadcast); } _Group = group; if (_ListenedTracker != null) { _ListenedTracker.NewOperation -= _ListenerTracked_NewOperation; } _ListenedTracker = tracker.Tracker; _ListenedTracker.NewOperation += _ListenerTracked_NewOperation; }
//private byte[] genesisBlockHash = new byte[] { 0x01, 0x02 }; public ConsoleNode() { var p = new TestTransactionPool(); p.Add("t1", 1); p.Add("t2", 0); p.Add("t3", 0); p.Spend("t2", "t1", 0); p.Render(); var genesisBlock = new TestBlock(p.TakeOut("t1").Value); var block1 = new TestBlock(p.TakeOut("t2").Value, p.TakeOut("t3").Value); block1.Parent = genesisBlock; genesisBlock.Render(); block1.Render(); Settings settings = JsonLoader <Settings> .Instance.Value; var ipEndpoint = new System.Net.IPEndPoint(IPAddress.Parse(settings.ExternalIPAddress), settings.ServerPort); var blockChain = new BlockChain.BlockChain("db", genesisBlock.Value.Key); if (blockChain.GetBlock(genesisBlock.Value.Key) == null) { Console.WriteLine("Initializing blockchain..."); blockChain.HandleNewBlock(genesisBlock.Value.Value); blockChain.HandleNewBlock(block1.Value.Value); } else { Console.WriteLine("Blockchain initialized."); } OwnResource(blockChain); blockChain.OnAddedToMempool += transaction => { Console.WriteLine("\n** Got Transaction **\n"); }; var server = new Server(this, ipEndpoint, BetaNetwork.Instance); var addressManagerBehavior = server.Behaviors.Find <AddressManagerBehavior>(); var addressManager = addressManagerBehavior.AddressManager; addressManager.Add( new NetworkAddress(ipEndpoint), ipEndpoint.Address ); addressManager.Connected(new NetworkAddress(ipEndpoint)); var broadcastHubBehavior = new BroadcastHubBehavior(); Miner miner = new Miner(blockChain); OwnResource(miner); server.Behaviors.Add(broadcastHubBehavior); server.Behaviors.Add(new SPVBehavior(blockChain, broadcastHubBehavior.BroadcastHub)); server.Behaviors.Add(new MinerBehavior(miner)); server.Behaviors.Add(new ChainBehavior(blockChain)); server.Start(); }
public void CanBroadcastTransaction() { using (NodeServerTester servers = new NodeServerTester(Network.TestNet)) { var notifiedTransactions = new List <WalletTransaction>(); var chainBuilder = new BlockchainBuilder(); SetupSPVBehavior(servers, chainBuilder); var tx = new Transaction(); Wallet wallet = new Wallet(new WalletCreation() { Network = Network.TestNet, RootKeys = new[] { new ExtKey().Neuter() }, UseP2SH = false }, keyPoolSize: 11); NodesGroup connected = CreateGroup(servers, 2); wallet.Configure(connected); wallet.Connect(); AutoResetEvent evt = new AutoResetEvent(false); bool passed = false; bool rejected = false; var broadcasting = wallet.BroadcastTransactionAsync(tx); wallet.TransactionBroadcasted += (t) => { passed = true; evt.Set(); }; wallet.TransactionRejected += (t, r) => { rejected = true; evt.Set(); }; BroadcastHub hub = BroadcastHub.GetBroadcastHub(connected.NodeConnectionParameters); BroadcastHubBehavior behavior = null; while (behavior == null || behavior.AttachedNode.State != NodeState.HandShaked) { behavior = connected.ConnectedNodes.Select(n => n.Behaviors.Find <BroadcastHubBehavior>()).FirstOrDefault(); Thread.Sleep(1); } if (broadcasting.Status != TaskStatus.RanToCompletion) { Assert.Equal(1, behavior.Broadcasts.Count()); Assert.Equal(1, hub.BroadcastingTransactions.Count()); } Assert.True(evt.WaitOne(20000)); Assert.True(broadcasting.Status == TaskStatus.RanToCompletion); Assert.True(passed); evt.Reset(); Assert.Equal(0, behavior.Broadcasts.Count()); Assert.Equal(0, hub.BroadcastingTransactions.Count()); Assert.Null(broadcasting.Result); broadcasting = wallet.BroadcastTransactionAsync(tx); if (broadcasting.Status != TaskStatus.RanToCompletion) { Assert.Equal(1, behavior.Broadcasts.Count()); } Assert.True(evt.WaitOne(20000)); Assert.True(rejected); Assert.Equal(0, behavior.Broadcasts.Count()); Assert.Equal(0, hub.BroadcastingTransactions.Count()); Assert.NotNull(broadcasting.Result); } }
public async Task Connect(NetworkInfo networkInfo) { IPAddress ipAddress = null; WireSerialization.Instance.Magic = networkInfo.Magic; NodeServerTrace.Information($"Magic is {networkInfo.Magic}"); var natManager = new NATManager(networkInfo.DefaultPort); #if DEBUG if (networkInfo.IsLANHost) { ipAddress = natManager.InternalIPAddress ?? IPAddress.Loopback; networkInfo.PeersToFind = 0; } else if (networkInfo.IsLANClient) { var ipAddressStr = (natManager.InternalIPAddress ?? IPAddress.Loopback).ToString(); networkInfo.PeersToFind = 1; if (networkInfo.Seeds.Count == 0 && !networkInfo.Seeds.Contains(ipAddressStr)) { networkInfo.Seeds.Add(ipAddressStr); } } else #endif if (!string.IsNullOrEmpty(networkInfo.ExternalIPAddress)) { ipAddress = IPAddress.Parse(networkInfo.ExternalIPAddress); } else if (networkInfo.DisableUPnP) { StatusMessageProducer.OutboundStatus = OutboundStatusEnum.Disabled; } else { StatusMessageProducer.OutboundStatus = OutboundStatusEnum.Initializing; await natManager.Init(); if (natManager.DeviceFound && natManager.Mapped.Value && natManager.ExternalIPVerified.HasValue && natManager.ExternalIPVerified.Value) { StatusMessageProducer.OutboundStatus = OutboundStatusEnum.HasValidAddress; ipAddress = natManager.ExternalIPAddress; } else { StatusMessageProducer.OutboundStatus = OutboundStatusEnum.HasInvalidAddress; } } _BroadcastHubBehavior = new BroadcastHubBehavior(); _MinerBehavior = new MinerBehavior(); _NodeConnectionParameters.TemplateBehaviors.Add(_BroadcastHubBehavior); _NodeConnectionParameters.TemplateBehaviors.Add(_MinerBehavior); _NodeConnectionParameters.TemplateBehaviors.Add(new SPVBehavior(_BlockChain, _BroadcastHubBehavior.BroadcastHub)); _NodeConnectionParameters.TemplateBehaviors.Add(new ChainBehavior(_BlockChain)); AddressManagerBehavior.GetAddrman(_NodeConnectionParameters).PeersToFind = networkInfo.PeersToFind; if (ipAddress != null) { _NodeConnectionParameters.TemplateBehaviors.Find <AddressManagerBehavior>().Mode = AddressManagerBehaviorMode.AdvertizeDiscover; //parameters.Advertize = true; _NodeConnectionParameters.AddressFrom = new System.Net.IPEndPoint(ipAddress, networkInfo.DefaultPort); } else { _NodeConnectionParameters.TemplateBehaviors.Find <AddressManagerBehavior>().Mode = AddressManagerBehaviorMode.Discover; } if (ipAddress != null) { _Server = new Server(ipAddress, networkInfo, _NodeConnectionParameters); OwnResource(_Server); if (_Server.Start()) { NodeServerTrace.Information($"Server started at {ipAddress}:{networkInfo.DefaultPort}"); StatusMessageProducer.OutboundStatus = OutboundStatusEnum.Accepting; } else { NodeServerTrace.Information($"Could not start server at {ipAddress}:{networkInfo.DefaultPort}"); } } if (networkInfo.Seeds.Count == 0) { NodeServerTrace.Information("No seeds defined"); } else { _NodesGroup = new NodesGroup(networkInfo, _NodeConnectionParameters); OwnResource(_NodesGroup); _NodesGroup.AllowSameGroup = true; //TODO _NodesGroup.MaximumNodeConnection = networkInfo.MaximumNodeConnection; #if TRACE _NodesGroup.ConnectedNodes.Added += (object sender, NodeEventArgs e) => { NodeServerTrace.Information("Peer found: " + e.Node.RemoteSocketAddress + ":" + e.Node.RemoteSocketPort); }; #endif _NodesGroup.Connect(); } }