private static void Parser(RpcClients rpcClients) { if (rpcClients != null && rpcClients.Clients != null && rpcClients.Clients.Count > 0) { foreach (var cl in rpcClients.Clients) { ClientServer s = new ClientServer() { RouterType = cl.RouterType, ServerName = cl.ServerName, }; List <ClientItem> cs = new List <ClientItem>(); foreach (var it in cl.Items) { if (!it.Enable) { logger.LogInformation($"服务{s.ServerName}的Ip={it.Ip},Port={it.Port}的服务被下线,路由将被忽略...."); continue; } cs.Add(new ClientItem { Ip = it.Ip, Port = it.Port, Server = s, ServerType = it.ServerType, Pool = it.Pool, Enable = it.Enable, TimeOut = it.TimeOut, }); } s.UpdateClient(cs.ToArray(), true); Register(s); } } }
private async Task Listen() { try { while (await _Channel.Reader.WaitToReadAsync(_Cts.Token) && _Channel.Reader.TryRead(out var item)) { if (!_Progress.TryGetValue(item, out var workItem)) { Logs.Explorer.LogError($"{workItem.Network.CryptoCode}: Work has been scheduled for {item}, but the work has not been found in _Progress dictionary. This is likely a bug, contact NBXplorer developers."); continue; } Logs.Explorer.LogInformation($"{workItem.Network.CryptoCode}: Start scanning {workItem.DerivationStrategy.ToPrettyString()} from index {workItem.Options.From} with gap limit {workItem.Options.GapLimit}, batch size {workItem.Options.BatchSize}"); var rpc = RpcClients.GetRPCClient(workItem.Network); var chain = Chains.GetChain(workItem.Network); try { var repo = Repositories.GetRepository(workItem.Network); workItem.State.Progress = new ScanUTXOProgress() { Count = Math.Max(1, Math.Min(workItem.Options.BatchSize, workItem.Options.GapLimit)), From = workItem.Options.From, StartedAt = DateTimeOffset.UtcNow }; foreach (var feature in workItem.Options.DerivationFeatures) { workItem.State.Progress.HighestKeyIndexFound.Add(feature, null); } workItem.State.Progress.UpdateRemainingBatches(workItem.Options.GapLimit); workItem.State.Status = ScanUTXOStatus.Pending; var scannedItems = GetScannedItems(workItem, workItem.State.Progress); var scanning = rpc.StartScanTxoutSetAsync(scannedItems.Descriptors.ToArray()); while (true) { var progress = await rpc.GetStatusScanTxoutSetAsync(); if (progress != null) { workItem.State.Progress.CurrentBatchProgress = (int)Math.Round(progress.Value); workItem.State.Progress.UpdateOverallProgress(); } using (var cts = CancellationTokenSource.CreateLinkedTokenSource(_Cts.Token)) { cts.CancelAfter(TimeSpan.FromSeconds(5.0)); try { var result = await scanning.WithCancellation(cts.Token); var progressObj = workItem.State.Progress.Clone(); progressObj.BatchNumber++; progressObj.From += progressObj.Count; progressObj.Found += result.Outputs.Length; progressObj.TotalSearched += scannedItems.Descriptors.Count; progressObj.UpdateRemainingBatches(workItem.Options.GapLimit); progressObj.UpdateOverallProgress(); Logs.Explorer.LogInformation($"{workItem.Network.CryptoCode}: Scanning of batch {workItem.State.Progress.BatchNumber} for {workItem.DerivationStrategy.ToPrettyString()} complete with {result.Outputs.Length} UTXOs fetched"); await UpdateRepository(workItem.DerivationStrategy, repo, chain, result.Outputs, scannedItems, progressObj); if (progressObj.RemainingBatches <= -1) { progressObj.BatchNumber--; progressObj.From -= progressObj.Count; progressObj.TotalSizeOfUTXOSet = result.SearchedItems; progressObj.CompletedAt = DateTimeOffset.UtcNow; progressObj.RemainingBatches = 0; progressObj.CurrentBatchProgress = 100; progressObj.UpdateRemainingBatches(workItem.Options.GapLimit); progressObj.UpdateOverallProgress(); workItem.State.Progress = progressObj; workItem.State.Status = ScanUTXOStatus.Complete; Logs.Explorer.LogInformation($"{workItem.Network.CryptoCode}: Scanning {workItem.DerivationStrategy.ToPrettyString()} complete {progressObj.Found} UTXOs found in total"); break; } else { scannedItems = GetScannedItems(workItem, progressObj); workItem.State.Progress = progressObj; scanning = rpc.StartScanTxoutSetAsync(scannedItems.Descriptors.ToArray()); } } catch (OperationCanceledException) when(cts.Token.IsCancellationRequested) { } } } } catch (Exception ex) when(!_Cts.IsCancellationRequested) { workItem.State.Status = ScanUTXOStatus.Error; workItem.State.Error = ex.Message; var progress = workItem.State.Progress.Clone(); progress.CompletedAt = DateTimeOffset.UtcNow; workItem.State.Progress = progress; Logs.Explorer.LogError(ex, $"{workItem.Network.CryptoCode}: Error while scanning {workItem.DerivationStrategy.ToPrettyString()}"); } finally { await rpc.AbortScanTxoutSetAsync(); } workItem.Finished = true; } } catch (OperationCanceledException) when(_Cts.IsCancellationRequested) { } }