Go-Ethereum

如何估計完成同步的剩餘時間?

  • April 11, 2022

我想知道我的geth節點完成同步大約需要多長時間。之前有一個問題與我的類似,但不太具體,它被關閉以支持關於如何獲得最高塊號的問題。由於無法為已關閉的問題添加答案,並且另一個問題沒有回答我的問題,所以我問的是這個版本的問題。

您可以輸入以下程式碼來估計剩餘時間(以分鐘為單位)。它在兩個不同的時間對目前塊進行採樣以估計剩餘時間。請注意,如果您目前的塊在此期間沒有更改,則它無法估計它。

geth console

function printSyncForecast() {
   if (!eth.syncing) return "Your node isn't syncing."
   var sampleSeconds = 10
   var currentBlock = eth.syncing.currentBlock;
   admin.sleep(sampleSeconds);
   if (!eth.syncing) return "Your node stopped syncing."
   var blocksSynced = eth.syncing.currentBlock - currentBlock
   var blocksPerMinute = blocksSynced * 60 / sampleSeconds;
   if (blocksPerMinute === 0) return "Current block didn't change; try increasing the sample time";
   var blocksRemaining = eth.syncing.highestBlock - eth.syncing.currentBlock;
   var minutesRemaining = blocksRemaining / blocksPerMinute;
   return "node synced " + blocksSynced + " blocks in " + sampleSeconds + " seconds (" + blocksPerMinute + 
     " blocks/minute.)  If these 📈 continue, node will sync the remaining " + blocksRemaining + " blocks in " + 
     minutesRemaining + " minutes."
}
printSyncForecast()

這是使用該程式碼的縮小版本的命令行的單行程式碼:

geth attach --exec '(function(){if(!eth.syncing)return"Your node isnt syncing.";var n=eth.syncing.currentBlock;if(admin.sleep(10),!eth.syncing)return"Your node stopped syncing.";var e=eth.syncing.currentBlock-n,t=60*e/10;if(0===t)return"Current block didnt change; try increasing the sample time";var c=eth.syncing.highestBlock-eth.syncing.currentBlock;return"node synced "+e+" blocks in 10 seconds ("+t+" blocks/minute.)  If these 📈 continue, node will sync the remaining "+c+" blocks in "+c/t+" minutes."})()'

您可以嘗試將其粘貼到 geth 控制台中(geth attach http://localhost:8545打開控制台或其他 URL,具體取決於您的配置),注意調整您感興趣的鏈的塊生產率。例如,在乙太坊上它變成var networkBlocksPerSec = 1 / 13.2;. 請注意,線上浮動的其他片段不考慮網路在您同步時將產生的塊,因此它們沒有給出準確的估計!這個可以:)

(function () {

   var secPerSample = 10;
   var sampleWindow = 200;
   var networkBlocksPerSec = 1 / 2.3; // network block time (polygon makes a block every ~2 seconds)
   var decimals = 3;
   
   var dataPoints = [];
   
   var topBlock = eth.syncing.highestBlock;
   var curBlock = eth.syncing.currentBlock;

   
   function checkETA() {
       if (!eth || !eth.syncing) return 'Your node isn\'t syncing.';

       var blocksSynced = eth.syncing.currentBlock - curBlock;
   
       dataPoints.push(blocksSynced);
   
       console.log('\nMade it from block ' + curBlock + ' to block ' + eth.syncing.currentBlock + ' in the last ' + secPerSample + ' seconds (' + blocksSynced + ' blocks)');
   
       if (dataPoints.length > sampleWindow) {
           dataPoints.splice(0, dataPoints.length - sampleWindow); // keep only 100 data points
       }
   
       var avgBlocksPerWindow = 0;
       for (var i = 0; i < dataPoints.length; i++) {
           avgBlocksPerWindow += dataPoints[i];
       }
   
       avgBlocksPerWindow /= dataPoints.length;

       var avgBlocksPerSecond = avgBlocksPerWindow / secPerSample;
   
       console.log('Catching up ' + avgBlocksPerSecond.toFixed(decimals) + ' blocks/sec on average (' + avgBlocksPerWindow.toFixed(decimals) + ' blocks every ' + secPerSample + ' seconds, over last ' + dataPoints.length + ' samples)');
   

       topBlock = eth.syncing.highestBlock;
       curBlock = eth.syncing.currentBlock;

   
       var blocksRemaining = topBlock - curBlock;
       var secondsToReachTopBlock = blocksRemaining / avgBlocksPerSecond;
   
       console.log('With ' + blocksRemaining + ' blocks left to catch up on, getting to highest block known thus far (' + topBlock + ') should take ' + fancyTimeFormat(secondsToReachTopBlock, false));

       var effectiveCatchupRate = avgBlocksPerSecond - networkBlocksPerSec;

       console.log('Network also creates ' + networkBlocksPerSec.toFixed(decimals) + ' blocks/second, making our effective catchup rate ' + effectiveCatchupRate.toFixed(decimals) + ' blocks/sec');

       if (effectiveCatchupRate > 0) {
           var catchupSeconds = blocksRemaining / effectiveCatchupRate;
           var expectedCaughtUpBlock = topBlock + catchupSeconds * networkBlocksPerSec;
   
           console.log('Factoring in the rate of future block creation, we will be synced in ' + fancyTimeFormat(catchupSeconds, false) + ', at block #' + Math.ceil(expectedCaughtUpBlock));
       } else {
           console.log('At this rate, network is producing faster, so we will never catch up');
       }
   }


   function fancyTimeFormat(duration, withSeconds) {   // duration is in seconds
       var ret = ''; // Hours, minutes and seconds  
       var hrs = ~~(duration / 3600);  
   
       if (hrs > 0) ret += hrs + ' hrs ';
   
       ret += ~~((duration % 3600) / 60) + ' mins';

       if (withSeconds) ret += ' ' + (~~duration % 60) + ' secs';
       return ret;
   }
   
   
   var handle = setInterval(checkETA, secPerSample * 1000);

   function stop() {
       clearInterval(handle)
   }

   this.stopChecking = stop;
})()

要停止按時間間隔執行的函式,stopChecking()請在 geth 控制台中執行

引用自:https://ethereum.stackexchange.com/questions/42192