Skip to content

Commit

Permalink
Merge pull request #628 from NethermindEth/getblockrlp
Browse files Browse the repository at this point in the history
Added support for the debug_getBlockRlp JSON RPC method
  • Loading branch information
tkstanczak authored Jul 11, 2019
2 parents 39c09c8 + e583156 commit 06e400f
Show file tree
Hide file tree
Showing 13 changed files with 242 additions and 61 deletions.
43 changes: 31 additions & 12 deletions docs/source/cli.rst
Original file line number Diff line number Diff line change
@@ -1,9 +1,13 @@
CLI
***

CLI access is not currently included in the Nethermind launcher but will be added very soon.

clique
^^^^^^

- clique.discard(address) -

- clique.getSigners() -

- clique.getSignersAnnotated() -
Expand All @@ -20,22 +24,26 @@ clique

- clique.propose(address, vote) -

- clique.discard(address) -

debug
^^^^^

- debug.getBlockRlp(number) -

- debug.getBlockRlpByHash(hash) -

- debug.config(category, name) -

- debug.traceBlock(hash) -
- debug.traceBlock(hash, options) -

- debug.traceBlockByHash(hash, options) -

- debug.traceBlockByHash(hash) -
- debug.traceBlockByNumber(number, options) -

- debug.traceBlockByNumber(number) -
- debug.traceTransaction(hash, options) -

- debug.traceTransactionByBlockAndIndex(hash) -
- debug.traceTransactionByBlockAndIndex(hash, options) -

- debug.traceTransactionByBlockhashAndIndex(hash) -
- debug.traceTransactionByBlockhashAndIndex(hash, options) -

diag
^^^^
Expand All @@ -59,6 +67,8 @@ eth

- eth.getCode(address, blockParameter) -

- eth.getStorageAt(address, positionIndex, blockParameter) -

- eth.getTransactionByBlockNumberAndIndex(blockParameter, index) -

- eth.getTransactionReceipt(txHash) -
Expand Down Expand Up @@ -95,12 +105,10 @@ node

- node.uri -

trace
^^^^^

- trace.replayBlockTransactions(blockNumber, traceTypes) -
parity
^^^^^^

- trace.replayTransaction(txHash, traceTypes) -
- parity.pendingTransactions() - Returns the pending transactions using Parity format

personal
^^^^^^^^
Expand All @@ -120,6 +128,17 @@ system

- system.memory -

trace
^^^^^

- trace.replayBlockTransactions(blockNumber, traceTypes) - Replays all transactions in a block returning the requested traces for each transaction.

- trace.replayTransaction(txHash, traceTypes) - Replays a transaction, returning the traces.

- trace.block(blockNumber) - Returns traces created at given block.

- trace.transaction(txHash) - Returns all traces of given transaction

web3
^^^^

Expand Down
3 changes: 3 additions & 0 deletions docs/source/configuration.rst
Original file line number Diff line number Diff line change
Expand Up @@ -229,6 +229,8 @@ InitConfig
UDP port number for incoming discovery connections.
default value: 30303

EnableRc7Fix

EnableUnsecuredDevWallet
If 'true' then it enables the wallet / key store in the application.
default value: false
Expand Down Expand Up @@ -579,6 +581,7 @@ Sample configuration (mainnet)
"ChainSpecPath" : null,
"DiscoveryEnabled" : true,
"DiscoveryPort" : 30303,
"EnableRc7Fix" : [MISSING_DOCS],
"EnableUnsecuredDevWallet" : false,
"GenesisHash" : null,
"HttpHost" : "127.0.0.1",
Expand Down
25 changes: 16 additions & 9 deletions docs/source/jsonrpc.rst
Original file line number Diff line number Diff line change
Expand Up @@ -52,31 +52,33 @@ debug

- [NOT IMPLEMENTED]debug_gcStats()

- debug_getBlockRlp(blockParameter)
- debug_getBlockRlp(number)

- debug_getBlockRlpByHash(hash)

- debug_getConfigValue(category, name)

- debug_getFromDb(dbName, key)
- [NOT IMPLEMENTED]debug_getFromDb(dbName, key)

- [NOT IMPLEMENTED]debug_memStats(blockParameter)

- [NOT IMPLEMENTED]debug_seedHash(blockParameter)

- [NOT IMPLEMENTED]debug_setHead(blockParameter)

- debug_traceBlock(blockRlp)
- debug_traceBlock(blockRlp, options)

- debug_traceBlockByHash(blockHash)
- debug_traceBlockByHash(blockHash, options)

- debug_traceBlockByNumber(number)
- debug_traceBlockByNumber(number, options)

- [NOT IMPLEMENTED]debug_traceBlockFromFile(fileName)
- [NOT IMPLEMENTED]debug_traceBlockFromFile(fileName, options)

- debug_traceTransaction(transactionHash, traceOptions)
- debug_traceTransaction(transactionHash, options)

- debug_traceTransactionByBlockAndIndex(blockParameter, txIndex)
- debug_traceTransactionByBlockAndIndex(blockParameter, txIndex, options)

- debug_traceTransactionByBlockhashAndIndex(blockHash, txIndex)
- debug_traceTransactionByBlockhashAndIndex(blockHash, txIndex, options)

eth
^^^
Expand Down Expand Up @@ -174,6 +176,11 @@ net

- net_version()

parity
^^^^^^

- parity_pendingTransactions()

personal
^^^^^^^^

Expand Down
12 changes: 12 additions & 0 deletions src/Nethermind/Nethermind.Cli/Modules/DebugCliModule.cs
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,18 @@ public JsValue GetConfigValue(string category, string name)
{
return NodeManager.PostJint("debug_getConfigValue", category, name).Result;
}

[CliFunction("debug", "getBlockRlpByHash")]
public string GetBlockRlpByHash(string hash)
{
return NodeManager.Post<string>("debug_getBlockRlpByHash", CliParseHash(hash)).Result;
}

[CliFunction("debug", "getBlockRlp")]
public string GetBlockRlp(long number)
{
return NodeManager.Post<string>("debug_getBlockRlp", number).Result;
}

public DebugCliModule(ICliEngine cliEngine, INodeManager nodeManager) : base(cliEngine, nodeManager)
{
Expand Down
59 changes: 59 additions & 0 deletions src/Nethermind/Nethermind.JsonRpc.Test/Modules/DebugModuleTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
using System.Collections.Generic;
using Nethermind.Config;
using Nethermind.Core.Crypto;
using Nethermind.Core.Encoding;
using Nethermind.Core.Extensions;
using Nethermind.Core.Test.Builders;
using Nethermind.Evm.Tracing;
Expand Down Expand Up @@ -63,6 +64,64 @@ public void Get_from_db_null_value()
Assert.IsNull(response.Result, "result");
}

[Test]
public void Get_block_rlp_by_hash()
{
BlockDecoder decoder = new BlockDecoder();
IDebugBridge debugBridge = Substitute.For<IDebugBridge>();
byte[] rlp = decoder.Encode(Build.A.Block.WithNumber(1).TestObject).Bytes;
debugBridge.GetBlockRlp(Keccak.Zero).Returns(rlp);

DebugModule module = new DebugModule(NullLogManager.Instance, debugBridge);
JsonRpcResponse response = RpcTest.TestRequest<IDebugModule>(module, "debug_getBlockRlpByHash", $"{Keccak.Zero.Bytes.ToHexString()}");

Assert.IsNull(response.Error, response.Error?.Message);
Assert.AreEqual(rlp, (byte[])response.Result);
}

[Test]
public void Get_block_rlp()
{
BlockDecoder decoder = new BlockDecoder();
IDebugBridge debugBridge = Substitute.For<IDebugBridge>();
byte[] rlp = decoder.Encode(Build.A.Block.WithNumber(1).TestObject).Bytes;
debugBridge.GetBlockRlp(1).Returns(rlp);

DebugModule module = new DebugModule(NullLogManager.Instance, debugBridge);
JsonRpcResponse response = RpcTest.TestRequest<IDebugModule>(module, "debug_getBlockRlp", "1");

Assert.IsNull(response.Error, response.Error?.Message);
Assert.AreEqual(rlp, (byte[])response.Result);
}

[Test]
public void Get_block_rlp_when_missing()
{
BlockDecoder decoder = new BlockDecoder();
IDebugBridge debugBridge = Substitute.For<IDebugBridge>();
byte[] rlp = decoder.Encode(Build.A.Block.WithNumber(1).TestObject).Bytes;
debugBridge.GetBlockRlp(1).Returns((byte[])null);

DebugModule module = new DebugModule(NullLogManager.Instance, debugBridge);
JsonRpcResponse response = RpcTest.TestRequest<IDebugModule>(module, "debug_getBlockRlp", "1");

Assert.AreEqual(-32601, response.Error.Code);
}

[Test]
public void Get_block_rlp_by_hash_when_missing()
{
BlockDecoder decoder = new BlockDecoder();
IDebugBridge debugBridge = Substitute.For<IDebugBridge>();
byte[] rlp = decoder.Encode(Build.A.Block.WithNumber(1).TestObject).Bytes;
debugBridge.GetBlockRlp(Keccak.Zero).Returns((byte[])null);

DebugModule module = new DebugModule(NullLogManager.Instance, debugBridge);
JsonRpcResponse response = RpcTest.TestRequest<IDebugModule>(module, "debug_getBlockRlpByHash", $"{Keccak.Zero.Bytes.ToHexString()}");

Assert.AreEqual(-32601, response.Error.Code);
}

[Test]
public void Get_trace()
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
using System.Threading;
using Nethermind.Blockchain;
using Nethermind.Config;
using Nethermind.Core;
using Nethermind.Core.Crypto;
using Nethermind.Core.Encoding;
using Nethermind.Dirichlet.Numerics;
Expand All @@ -34,14 +35,15 @@ public class DebugBridge : IDebugBridge
{
private readonly IConfigProvider _configProvider;
private readonly ITracer _tracer;
private readonly IBlockTree _blockTree;
private Dictionary<string, IDb> _dbMappings;

public DebugBridge(IConfigProvider configProvider, IReadOnlyDbProvider dbProvider, ITracer tracer, IBlockchainProcessor receiptsProcessor)
public DebugBridge(IConfigProvider configProvider, IReadOnlyDbProvider dbProvider, ITracer tracer, IBlockchainProcessor receiptsProcessor, IBlockTree blockTree)
{
IBlockchainProcessor receiptsProcessor1 = receiptsProcessor ?? throw new ArgumentNullException(nameof(receiptsProcessor));
receiptsProcessor1.ProcessingQueueEmpty += (sender, args) => _receiptProcessedEvent.Set();
_configProvider = configProvider ?? throw new ArgumentNullException(nameof(configProvider));
receiptsProcessor.ProcessingQueueEmpty += (sender, args) => _receiptProcessedEvent.Set();
_configProvider = configProvider ?? throw new ArgumentNullException(nameof(configProvider));
_tracer = tracer ?? throw new ArgumentNullException(nameof(tracer));
_blockTree = blockTree ?? throw new ArgumentNullException(nameof(blockTree));
dbProvider = dbProvider ?? throw new ArgumentNullException(nameof(dbProvider));
IDb blockInfosDb = dbProvider.BlockInfosDb ?? throw new ArgumentNullException(nameof(dbProvider.BlockInfosDb));
IDb blocksDb = dbProvider.BlocksDb ?? throw new ArgumentNullException(nameof(dbProvider.BlocksDb));
Expand All @@ -50,7 +52,7 @@ public DebugBridge(IConfigProvider configProvider, IReadOnlyDbProvider dbProvide
IDb codeDb = dbProvider.CodeDb ?? throw new ArgumentNullException(nameof(dbProvider.CodeDb));
IDb pendingTxsDb = dbProvider.PendingTxsDb ?? throw new ArgumentNullException(nameof(dbProvider.PendingTxsDb));
IDb traceDb = dbProvider.TraceDb ?? throw new ArgumentNullException(nameof(dbProvider.TraceDb));

_dbMappings = new Dictionary<string, IDb>(StringComparer.InvariantCultureIgnoreCase)
{
{DbNames.State, dbProvider.StateDb},
Expand All @@ -62,14 +64,14 @@ public DebugBridge(IConfigProvider configProvider, IReadOnlyDbProvider dbProvide
{DbNames.Receipts, receiptsDb},
{DbNames.PendingTxs, pendingTxsDb},
{DbNames.Trace, traceDb}
};
};
}

public byte[] GetDbValue(string dbName, byte[] key)
{
return _dbMappings[dbName][key];
}

public GethLikeTxTrace GetTransactionTrace(Keccak transactionHash, GethTraceOptions gethTraceOptions = null)
{
return _tracer.Trace(transactionHash, gethTraceOptions ?? GethTraceOptions.Default);
Expand All @@ -94,18 +96,33 @@ public GethLikeTxTrace[] GetBlockTrace(long blockNumber, GethTraceOptions gethTr
{
return _tracer.TraceBlock(blockNumber, gethTraceOptions ?? GethTraceOptions.Default);
}

public GethLikeTxTrace[] GetBlockTrace(Rlp blockRlp, GethTraceOptions gethTraceOptions = null)
{
return _tracer.TraceBlock(blockRlp, gethTraceOptions ?? GethTraceOptions.Default);
}


public byte[] GetBlockRlp(Keccak blockHash)
{
return _dbMappings[DbNames.Blocks].Get(blockHash);
}

public byte[] GetBlockRlp(long number)
{
BlockHeader header = _blockTree.FindHeader(number);
if (header == null)
{
return null;
}

return _dbMappings[DbNames.Blocks].Get(header.Hash);
}

public string GetConfigValue(string category, string name)
{
return _configProvider.GetRawValue(category, name);
}

private AutoResetEvent _receiptProcessedEvent = new AutoResetEvent(false);

}
}
Original file line number Diff line number Diff line change
Expand Up @@ -138,9 +138,26 @@ public ResultWrapper<GcStats> debug_gcStats()
throw new NotImplementedException();
}

public ResultWrapper<byte[]> debug_getBlockRlp(BlockParameter blockParameter)
public ResultWrapper<byte[]> debug_getBlockRlp(long blockNumber)
{
throw new NotImplementedException();
byte[] rlp = _debugBridge.GetBlockRlp(blockNumber);
if (rlp == null)
{
return ResultWrapper<byte[]>.Fail($"Block {blockNumber} was not found", ErrorType.NotFound);
}

return ResultWrapper<byte[]>.Success(rlp);
}

public ResultWrapper<byte[]> debug_getBlockRlpByHash(Keccak hash)
{
byte[] rlp = _debugBridge.GetBlockRlp(hash);
if (rlp == null)
{
return ResultWrapper<byte[]>.Fail($"Block {hash} was not found", ErrorType.NotFound);
}

return ResultWrapper<byte[]>.Success(rlp);
}

public ResultWrapper<MemStats> debug_memStats(BlockParameter blockParameter)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ public interface IDebugBridge
GethLikeTxTrace[] GetBlockTrace(Keccak blockHash, GethTraceOptions gethTraceOptions = null);
GethLikeTxTrace[] GetBlockTrace(long blockNumber, GethTraceOptions gethTraceOptions = null);
GethLikeTxTrace[] GetBlockTrace(Rlp blockRlp, GethTraceOptions gethTraceOptions = null);
byte[] GetBlockRlp(Keccak blockHash);
byte[] GetBlockRlp(long number);
byte[] GetDbValue(string dbName, byte[] key);
string GetConfigValue(string category, string name);
}
Expand Down
Loading

0 comments on commit 06e400f

Please sign in to comment.