Manual fetch benefeciaries

pull/5560/head
Qwerty5Uiop 3 years ago
parent 8e4c73cfd4
commit 81534addc5
  1. 5
      .gitignore
  2. 57
      apps/explorer/lib/explorer/chain.ex
  3. 42
      apps/explorer/test/explorer/chain_test.exs
  4. 3
      apps/indexer/config/config.exs
  5. 65
      apps/indexer/lib/indexer/block/fetcher.ex
  6. 513
      apps/indexer/test/indexer/block/realtime/fetcher_test.exs

5
.gitignore vendored

@ -37,7 +37,7 @@ screenshots/
# Sobelow # Sobelow
.sobelow .sobelow
# osx # osx
.DS_Store .DS_Store
# mix phx.gen.cert self-signed certs for dev # mix phx.gen.cert self-signed certs for dev
@ -45,3 +45,6 @@ screenshots/
/docker-compose/postgres-data /docker-compose/postgres-data
/docker-compose/tmp /docker-compose/tmp
.idea/
*.iml

@ -800,6 +800,53 @@ defmodule Explorer.Chain do
end end
end end
@uncle_reward_coef 1 / 32
def block_reward_by_parts(block, transactions) do
%{hash: block_hash, number: block_number} = block
base_fee_per_gas = Map.get(block, :base_fee_per_gas)
txn_fees =
Enum.reduce(transactions, Decimal.new(0), fn %{gas_used: gas_used, gas_price: gas_price}, acc ->
gas_used
|> Decimal.new()
|> Decimal.mult(Decimal.new(gas_price))
|> Decimal.add(acc)
end)
static_reward =
Repo.one(
from(
er in EmissionReward,
where: fragment("int8range(?, ?) <@ ?", ^block_number, ^block_number, er.block_range),
select: er.reward
)
) || %Wei{value: Decimal.new(0)}
burned_fee_counter =
transactions
|> Enum.filter(fn tx -> not is_nil(Map.get(tx, :max_priority_fee_per_gas)) end)
|> Enum.reduce(Decimal.new(0), fn %{gas_used: gas_used}, acc ->
gas_used
|> Decimal.new()
|> Decimal.add(acc)
end)
has_uncles? = is_list(block.uncles) and not Enum.empty?(block.uncles)
burned_fees = base_fee_per_gas && Wei.mult(base_fee_per_gas, burned_fee_counter)
uncle_reward = (has_uncles? && Wei.mult(static_reward, Decimal.from_float(@uncle_reward_coef))) || nil
%{
block_number: block_number,
block_hash: block_hash,
miner_hash: block.miner_hash,
static_reward: static_reward,
txn_fees: %Wei{value: txn_fees},
burned_fees: burned_fees || %Wei{value: Decimal.new(0)},
uncle_reward: uncle_reward || %Wei{value: Decimal.new(0)}
}
end
@doc """ @doc """
The `t:Explorer.Chain.Wei.t/0` paid to the miners of the `t:Explorer.Chain.Block.t/0`s with `hash` The `t:Explorer.Chain.Wei.t/0` paid to the miners of the `t:Explorer.Chain.Block.t/0`s with `hash`
`Explorer.Chain.Hash.Full.t/0` by the signers of the transactions in those blocks to cover the gas fee `Explorer.Chain.Hash.Full.t/0` by the signers of the transactions in those blocks to cover the gas fee
@ -893,7 +940,7 @@ defmodule Explorer.Chain do
select: select:
sum( sum(
fragment( fragment(
"CASE "CASE
WHEN COALESCE(?,?) = 0 THEN 0 WHEN COALESCE(?,?) = 0 THEN 0
WHEN COALESCE(?,?) - ? < COALESCE(?,?) THEN (COALESCE(?,?) - ?) * ? WHEN COALESCE(?,?) - ? < COALESCE(?,?) THEN (COALESCE(?,?) - ?) * ?
ELSE COALESCE(?,?) * ? END", ELSE COALESCE(?,?) * ? END",
@ -2951,7 +2998,7 @@ defmodule Explorer.Chain do
right_join: right_join:
missing_range in fragment( missing_range in fragment(
""" """
(SELECT b1.number (SELECT b1.number
FROM generate_series(0, (?)::integer) AS b1(number) FROM generate_series(0, (?)::integer) AS b1(number)
WHERE NOT EXISTS WHERE NOT EXISTS
(SELECT 1 FROM blocks b2 WHERE b2.number=b1.number AND b2.consensus)) (SELECT 1 FROM blocks b2 WHERE b2.number=b1.number AND b2.consensus))
@ -3038,7 +3085,7 @@ defmodule Explorer.Chain do
right_join: right_join:
missing_range in fragment( missing_range in fragment(
""" """
(SELECT distinct b1.number (SELECT distinct b1.number
FROM generate_series((?)::integer, (?)::integer) AS b1(number) FROM generate_series((?)::integer, (?)::integer) AS b1(number)
WHERE NOT EXISTS WHERE NOT EXISTS
(SELECT 1 FROM blocks b2 WHERE b2.number=b1.number AND b2.consensus)) (SELECT 1 FROM blocks b2 WHERE b2.number=b1.number AND b2.consensus))
@ -3976,7 +4023,7 @@ defmodule Explorer.Chain do
Updates a `t:SmartContract.t/0`. Updates a `t:SmartContract.t/0`.
Has the similar logic as create_smart_contract/1. Has the similar logic as create_smart_contract/1.
Used in cases when you need to update row in DB contains SmartContract, e.g. in case of changing Used in cases when you need to update row in DB contains SmartContract, e.g. in case of changing
status `partially verified` to `fully verified` (re-verify). status `partially verified` to `fully verified` (re-verify).
""" """
@spec update_smart_contract(map()) :: {:ok, SmartContract.t()} | {:error, Ecto.Changeset.t()} @spec update_smart_contract(map()) :: {:ok, SmartContract.t()} | {:error, Ecto.Changeset.t()}
@ -5039,7 +5086,7 @@ defmodule Explorer.Chain do
# Fetches custom metadata for bridged tokens from the node. # Fetches custom metadata for bridged tokens from the node.
# Currently, gets Balancer token composite tokens with their weights # Currently, gets Balancer token composite tokens with their weights
# from foreign chain # from foreign chain
defp get_bridged_token_custom_metadata(foreign_token_address_hash, json_rpc_named_arguments, foreign_json_rpc) defp get_bridged_token_custom_metadata(foreign_token_address_hash, json_rpc_named_arguments, foreign_json_rpc)
when not is_nil(foreign_json_rpc) and foreign_json_rpc !== "" do when not is_nil(foreign_json_rpc) and foreign_json_rpc !== "" do
eth_call_foreign_json_rpc_named_arguments = eth_call_foreign_json_rpc_named_arguments =

@ -3415,6 +3415,48 @@ defmodule Explorer.ChainTest do
end end
end end
describe "block_reward_by_parts/1" do
setup do
{:ok, emission_reward: insert(:emission_reward)}
end
test "without uncles", %{emission_reward: %{reward: reward, block_range: range}} do
block = build(:block, number: range.from, base_fee_per_gas: %Wei{value: Decimal.new(5)}, uncles: [])
tx1 = build(:transaction, gas_price: 1, gas_used: 1, block_number: block.number, block_hash: block.hash)
tx2 = build(:transaction, gas_price: 1, gas_used: 2, block_number: block.number, block_hash: block.hash)
tx3 =
build(:transaction,
gas_price: 1,
gas_used: 3,
block_number: block.number,
block_hash: block.hash,
max_priority_fee_per_gas: 1
)
expected_txn_fees = %Wei{value: Decimal.new(6)}
expected_burned_fees = %Wei{value: Decimal.new(15)}
expected_uncle_reward = %Wei{value: Decimal.new(0)}
assert %{
static_reward: ^reward,
txn_fees: ^expected_txn_fees,
burned_fees: ^expected_burned_fees,
uncle_reward: ^expected_uncle_reward
} = Chain.block_reward_by_parts(block, [tx1, tx2, tx3])
end
test "with uncles", %{emission_reward: %{reward: reward, block_range: range}} do
block =
build(:block, number: range.from, uncles: ["0xe670ec64341771606e55d6b4ca35a1a6b75ee3d5145a99d05921026d15273311"])
expected_uncle_reward = Wei.mult(reward, Decimal.from_float(1 / 32))
assert %{uncle_reward: ^expected_uncle_reward} = Chain.block_reward_by_parts(block, [])
end
end
describe "gas_payment_by_block_hash/1" do describe "gas_payment_by_block_hash/1" do
setup do setup do
number = 1 number = 1

@ -34,7 +34,8 @@ config :indexer,
first_block: System.get_env("FIRST_BLOCK") || "", first_block: System.get_env("FIRST_BLOCK") || "",
last_block: System.get_env("LAST_BLOCK") || "", last_block: System.get_env("LAST_BLOCK") || "",
trace_first_block: System.get_env("TRACE_FIRST_BLOCK") || "", trace_first_block: System.get_env("TRACE_FIRST_BLOCK") || "",
trace_last_block: System.get_env("TRACE_LAST_BLOCK") || "" trace_last_block: System.get_env("TRACE_LAST_BLOCK") || "",
fetch_rewards_way: System.get_env("FETCH_REWARDS_WAY", "trace_block")
config :indexer, Indexer.Fetcher.PendingTransaction.Supervisor, config :indexer, Indexer.Fetcher.PendingTransaction.Supervisor,
disabled?: disabled?:

@ -11,7 +11,7 @@ defmodule Indexer.Block.Fetcher do
alias EthereumJSONRPC.{Blocks, FetchedBeneficiaries} alias EthereumJSONRPC.{Blocks, FetchedBeneficiaries}
alias Explorer.Chain alias Explorer.Chain
alias Explorer.Chain.{Address, Block, Hash, Import, Transaction} alias Explorer.Chain.{Address, Block, Hash, Import, Transaction, Wei}
alias Explorer.Chain.Block.Reward alias Explorer.Chain.Block.Reward
alias Explorer.Chain.Cache.Blocks, as: BlocksCache alias Explorer.Chain.Cache.Blocks, as: BlocksCache
alias Explorer.Chain.Cache.{Accounts, BlockNumber, Transactions, Uncles} alias Explorer.Chain.Cache.{Accounts, BlockNumber, Transactions, Uncles}
@ -136,7 +136,7 @@ defmodule Indexer.Block.Fetcher do
%{token_transfers: token_transfers, tokens: tokens} = TokenTransfers.parse(logs), %{token_transfers: token_transfers, tokens: tokens} = TokenTransfers.parse(logs),
%{mint_transfers: mint_transfers} = MintTransfers.parse(logs), %{mint_transfers: mint_transfers} = MintTransfers.parse(logs),
%FetchedBeneficiaries{params_set: beneficiary_params_set, errors: beneficiaries_errors} = %FetchedBeneficiaries{params_set: beneficiary_params_set, errors: beneficiaries_errors} =
fetch_beneficiaries(blocks, json_rpc_named_arguments), fetch_beneficiaries(blocks, transactions_with_receipts, json_rpc_named_arguments),
addresses = addresses =
Addresses.extract_addresses(%{ Addresses.extract_addresses(%{
block_reward_contract_beneficiaries: MapSet.to_list(beneficiary_params_set), block_reward_contract_beneficiaries: MapSet.to_list(beneficiary_params_set),
@ -160,10 +160,8 @@ defmodule Indexer.Block.Fetcher do
blocks: blocks blocks: blocks
} }
|> AddressCoinBalancesDaily.params_set(), |> AddressCoinBalancesDaily.params_set(),
beneficiaries_with_gas_payment <- beneficiaries_with_gas_payment =
beneficiary_params_set beneficiaries_with_gas_payment(blocks, beneficiary_params_set, transactions_with_receipts),
|> add_gas_payments(transactions_with_receipts, blocks)
|> BlockReward.reduce_uncle_rewards(),
address_token_balances = AddressTokenBalances.params_set(%{token_transfers_params: token_transfers}), address_token_balances = AddressTokenBalances.params_set(%{token_transfers_params: token_transfers}),
{:ok, inserted} <- {:ok, inserted} <-
__MODULE__.import( __MODULE__.import(
@ -336,7 +334,48 @@ defmodule Indexer.Block.Fetcher do
quantity_to_integer(block_quantity) quantity_to_integer(block_quantity)
end end
defp fetch_beneficiaries(blocks, json_rpc_named_arguments) do defp fetch_beneficiaries(blocks, all_transactions, json_rpc_named_arguments) do
case Application.get_env(:indexer, :fetch_rewards_way) do
"manual" -> fetch_beneficiaries_manual(blocks, all_transactions)
_ -> fetch_beneficiaries_by_trace_block(blocks, json_rpc_named_arguments)
end
end
def fetch_beneficiaries_manual(blocks, all_transactions) when is_list(blocks) do
block_transactions_map = Enum.group_by(all_transactions, & &1.block_number)
blocks
|> Enum.map(fn block -> fetch_beneficiaries_manual(block, block_transactions_map[block.number] || []) end)
|> Enum.reduce(%FetchedBeneficiaries{}, fn params_set, %{params_set: acc_params_set} = acc ->
%FetchedBeneficiaries{acc | params_set: MapSet.union(acc_params_set, params_set)}
end)
end
def fetch_beneficiaries_manual(block, transactions) do
block
|> Chain.block_reward_by_parts(transactions)
|> reward_parts_to_beneficiaries()
end
defp reward_parts_to_beneficiaries(reward_parts) do
reward =
reward_parts.static_reward
|> Wei.sum(reward_parts.txn_fees)
|> Wei.sub(reward_parts.burned_fees)
|> Wei.sum(reward_parts.uncle_reward)
MapSet.new([
%{
address_hash: reward_parts.miner_hash,
block_hash: reward_parts.block_hash,
block_number: reward_parts.block_number,
reward: reward,
address_type: :validator
}
])
end
defp fetch_beneficiaries_by_trace_block(blocks, json_rpc_named_arguments) do
hash_string_by_number = hash_string_by_number =
Enum.into(blocks, %{}, fn %{number: number, hash: hash_string} Enum.into(blocks, %{}, fn %{number: number, hash: hash_string}
when is_integer(number) and is_binary(hash_string) -> when is_integer(number) and is_binary(hash_string) ->
@ -400,6 +439,18 @@ defmodule Indexer.Block.Fetcher do
|> Enum.into(MapSet.new()) |> Enum.into(MapSet.new())
end end
defp beneficiaries_with_gas_payment(blocks, beneficiary_params_set, transactions_with_receipts) do
case Application.get_env(:indexer, :fetch_rewards_way) do
"manual" ->
beneficiary_params_set
_ ->
beneficiary_params_set
|> add_gas_payments(transactions_with_receipts, blocks)
|> BlockReward.reduce_uncle_rewards()
end
end
defp add_gas_payments(beneficiaries, transactions, blocks) do defp add_gas_payments(beneficiaries, transactions, blocks) do
transactions_by_block_number = Enum.group_by(transactions, & &1.block_number) transactions_by_block_number = Enum.group_by(transactions, & &1.block_number)

@ -5,7 +5,7 @@ defmodule Indexer.Block.Realtime.FetcherTest do
import Mox import Mox
alias Explorer.Chain alias Explorer.Chain
alias Explorer.Chain.{Address, Transaction} alias Explorer.Chain.{Address, Transaction, Wei}
alias Indexer.Block.Catchup.Sequence alias Indexer.Block.Catchup.Sequence
alias Indexer.Block.Realtime alias Indexer.Block.Realtime
alias Indexer.Fetcher.{ContractCode, InternalTransaction, ReplacedTransaction, Token, TokenBalance, UncleBlock} alias Indexer.Fetcher.{ContractCode, InternalTransaction, ReplacedTransaction, Token, TokenBalance, UncleBlock}
@ -536,10 +536,519 @@ defmodule Indexer.Block.Realtime.FetcherTest do
} }
], ],
blocks: [%Chain.Block{number: 3_946_079}, %Chain.Block{number: 3_946_080}], blocks: [%Chain.Block{number: 3_946_079}, %Chain.Block{number: 3_946_080}],
transactions: [%Transaction{hash: transaction_hash}] transactions: [%Transaction{hash: _transaction_hash}]
}, },
errors: [] errors: []
}} = Indexer.Block.Fetcher.fetch_and_import_range(block_fetcher, 3_946_079..3_946_080) }} = Indexer.Block.Fetcher.fetch_and_import_range(block_fetcher, 3_946_079..3_946_080)
end end
@tag :no_geth
test "in range with internal transactions and manual reward fetching", %{
block_fetcher: %Indexer.Block.Fetcher{} = block_fetcher,
json_rpc_named_arguments: json_rpc_named_arguments
} do
Application.put_env(:indexer, :fetch_rewards_way, "manual")
{:ok, sequence} = Sequence.start_link(ranges: [], step: 2)
Sequence.cap(sequence)
Token.Supervisor.Case.start_supervised!(json_rpc_named_arguments: json_rpc_named_arguments)
ContractCode.Supervisor.Case.start_supervised!(json_rpc_named_arguments: json_rpc_named_arguments)
InternalTransaction.Supervisor.Case.start_supervised!(json_rpc_named_arguments: json_rpc_named_arguments)
UncleBlock.Supervisor.Case.start_supervised!(
block_fetcher: %Indexer.Block.Fetcher{json_rpc_named_arguments: json_rpc_named_arguments}
)
ReplacedTransaction.Supervisor.Case.start_supervised!()
if json_rpc_named_arguments[:transport] == EthereumJSONRPC.Mox do
EthereumJSONRPC.Mox
|> expect(:json_rpc, fn [
%{
id: 0,
jsonrpc: "2.0",
method: "eth_getBlockByNumber",
params: ["0x3C365F", true]
},
%{
id: 1,
jsonrpc: "2.0",
method: "eth_getBlockByNumber",
params: ["0x3C3660", true]
}
],
_ ->
{:ok,
[
%{
id: 0,
jsonrpc: "2.0",
result: %{
"author" => "0x5ee341ac44d344ade1ca3a771c59b98eb2a77df2",
"difficulty" => "0xfffffffffffffffffffffffffffffffe",
"extraData" => "0xd583010b088650617269747986312e32372e32826c69",
"gasLimit" => "0x7a1200",
"gasUsed" => "0x2886e",
"hash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"logsBloom" =>
"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
"miner" => "0x5ee341ac44d344ade1ca3a771c59b98eb2a77df2",
"number" => "0x3c365f",
"parentHash" => "0x57f6d66e07488defccd5216c4d2968dd6afd3bd32415e284de3b02af6535e8dc",
"receiptsRoot" => "0x111be72e682cea9c93e02f1ef503fb64aa821b2ef510fd9177c49b37d0af98b5",
"sealFields" => [
"0x841246c63f",
"0xb841ba3d11db672fd7893d1b7906275fa7c4c7f4fbcc8fa29eab0331480332361516545ef10a36d800ad2be2b449dde8d5703125156a9cf8a035f5a8623463e051b700"
],
"sha3Uncles" => "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347",
"signature" =>
"ba3d11db672fd7893d1b7906275fa7c4c7f4fbcc8fa29eab0331480332361516545ef10a36d800ad2be2b449dde8d5703125156a9cf8a035f5a8623463e051b700",
"size" => "0x33e",
"stateRoot" => "0x7f73f5fb9f891213b671356126c31e9795d038844392c7aa8800ed4f52307209",
"step" => "306628159",
"timestamp" => "0x5b61df3b",
"totalDifficulty" => "0x3c365effffffffffffffffffffffffed7f0362",
"transactions" => [
%{
"blockHash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"blockNumber" => "0x3c365f",
"chainId" => "0x63",
"condition" => nil,
"creates" => nil,
"from" => "0x40b18103537c0f15d5e137dd8ddd019b84949d16",
"gas" => "0x3d9c5",
"gasPrice" => "0x3b9aca00",
"hash" => "0xd3937e70fab3fb2bfe8feefac36815408bf07de3b9e09fe81114b9a6b17f55c8",
"input" =>
"0x8841ac11000000000000000000000000000000000000000000000000000000000000006c000000000000000000000000000000000000000000000000000000000000000500000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000005",
"nonce" => "0x65b",
"publicKey" =>
"0x89c2123ed4b5d141cf1f4b6f5f3d754418f03aea2e870a1c50888d94bf5531f74237e2fea72d0bc198ef213272b62c6869615720757255e6cba087f9db6e759f",
"r" => "0x55a1a93541d7f782f97f6699437bb60fa4606d63760b30c1ee317e648f93995",
"raw" =>
"0xf8f582065b843b9aca008303d9c594698bf6943bab687b2756394624aa183f434f65da8901158e4f216242a000b8848841ac11000000000000000000000000000000000000000000000000000000000000006c00000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000005000000000000000000000000000000000000000000000000000000000000000581eaa0055a1a93541d7f782f97f6699437bb60fa4606d63760b30c1ee317e648f93995a06affd4da5eca84fbca2b016c980f861e0af1f8d6535e2fe29d8f96dc0ce358f7",
"s" => "0x6affd4da5eca84fbca2b016c980f861e0af1f8d6535e2fe29d8f96dc0ce358f7",
"standardV" => "0x1",
"to" => "0x698bf6943bab687b2756394624aa183f434f65da",
"transactionIndex" => "0x0",
"v" => "0xea",
"value" => "0x1158e4f216242a000"
}
],
"transactionsRoot" => "0xd7c39a93eafe0bdcbd1324c13dcd674bed8c9fa8adbf8f95bf6a59788985da6f",
"uncles" => ["0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cd"]
}
},
%{
id: 1,
jsonrpc: "2.0",
result: %{
"author" => "0x66c9343c7e8ca673a1fedf9dbf2cd7936dbbf7e3",
"difficulty" => "0xfffffffffffffffffffffffffffffffe",
"extraData" => "0xd583010a068650617269747986312e32362e32826c69",
"gasLimit" => "0x7a1200",
"gasUsed" => "0x0",
"hash" => "0xfb483e511d316fa4072694da3f7abc94b06286406af45061e5e681395bdc6815",
"logsBloom" =>
"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
"miner" => "0x66c9343c7e8ca673a1fedf9dbf2cd7936dbbf7e3",
"number" => "0x3c3660",
"parentHash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"receiptsRoot" => "0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421",
"sealFields" => [
"0x841246c640",
"0xb84114db3fd7526b7ea3635f5c85c30dd8a645453aa2f8afe5fd33fe0ec663c9c7b653b0fb5d8dc7d0b809674fa9dca9887d1636a586bf62191da22255eb068bf20800"
],
"sha3Uncles" => "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347",
"signature" =>
"14db3fd7526b7ea3635f5c85c30dd8a645453aa2f8afe5fd33fe0ec663c9c7b653b0fb5d8dc7d0b809674fa9dca9887d1636a586bf62191da22255eb068bf20800",
"size" => "0x243",
"stateRoot" => "0x3174c461989e9f99e08fa9b4ffb8bce8d9a281c8fc9f80694bb9d3acd4f15559",
"step" => "306628160",
"timestamp" => "0x5b61df40",
"totalDifficulty" => "0x3c365fffffffffffffffffffffffffed7f0360",
"transactions" => [],
"transactionsRoot" => "0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421",
"uncles" => []
}
}
]}
end)
|> expect(:json_rpc, fn [
%{
id: 0,
jsonrpc: "2.0",
method: "eth_getTransactionReceipt",
params: ["0xd3937e70fab3fb2bfe8feefac36815408bf07de3b9e09fe81114b9a6b17f55c8"]
}
],
_ ->
{:ok,
[
%{
id: 0,
jsonrpc: "2.0",
result: %{
"blockHash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"blockNumber" => "0x3c365f",
"contractAddress" => nil,
"cumulativeGasUsed" => "0x2886e",
"gasUsed" => "0x2886e",
"logs" => [],
"logsBloom" =>
"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
"root" => nil,
"status" => "0x1",
"transactionHash" => "0xd3937e70fab3fb2bfe8feefac36815408bf07de3b9e09fe81114b9a6b17f55c8",
"transactionIndex" => "0x0"
}
}
]}
end)
|> expect(:json_rpc, 3, fn
[
%{
id: 0,
jsonrpc: "2.0",
method: "eth_getBlockByNumber",
params: ["0x3C365F", true]
}
],
_ ->
{:ok,
[
%{
id: 0,
jsonrpc: "2.0",
result: %{
"author" => "0x5ee341ac44d344ade1ca3a771c59b98eb2a77df2",
"difficulty" => "0xfffffffffffffffffffffffffffffffe",
"extraData" => "0xd583010b088650617269747986312e32372e32826c69",
"gasLimit" => "0x7a1200",
"gasUsed" => "0x2886e",
"hash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"logsBloom" =>
"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
"miner" => "0x5ee341ac44d344ade1ca3a771c59b98eb2a77df2",
"number" => "0x3c365f",
"parentHash" => "0x57f6d66e07488defccd5216c4d2968dd6afd3bd32415e284de3b02af6535e8dc",
"receiptsRoot" => "0x111be72e682cea9c93e02f1ef503fb64aa821b2ef510fd9177c49b37d0af98b5",
"sealFields" => [
"0x841246c63f",
"0xb841ba3d11db672fd7893d1b7906275fa7c4c7f4fbcc8fa29eab0331480332361516545ef10a36d800ad2be2b449dde8d5703125156a9cf8a035f5a8623463e051b700"
],
"sha3Uncles" => "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347",
"signature" =>
"ba3d11db672fd7893d1b7906275fa7c4c7f4fbcc8fa29eab0331480332361516545ef10a36d800ad2be2b449dde8d5703125156a9cf8a035f5a8623463e051b700",
"size" => "0x33e",
"stateRoot" => "0x7f73f5fb9f891213b671356126c31e9795d038844392c7aa8800ed4f52307209",
"step" => "306628159",
"timestamp" => "0x5b61df3b",
"totalDifficulty" => "0x3c365effffffffffffffffffffffffed7f0362",
"transactions" => [
%{
"blockHash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"blockNumber" => "0x3c365f",
"chainId" => "0x63",
"condition" => nil,
"creates" => nil,
"from" => "0x40b18103537c0f15d5e137dd8ddd019b84949d16",
"gas" => "0x3d9c5",
"gasPrice" => "0x3b9aca00",
"hash" => "0xd3937e70fab3fb2bfe8feefac36815408bf07de3b9e09fe81114b9a6b17f55c8",
"input" =>
"0x8841ac11000000000000000000000000000000000000000000000000000000000000006c000000000000000000000000000000000000000000000000000000000000000500000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000005",
"nonce" => "0x65b",
"publicKey" =>
"0x89c2123ed4b5d141cf1f4b6f5f3d754418f03aea2e870a1c50888d94bf5531f74237e2fea72d0bc198ef213272b62c6869615720757255e6cba087f9db6e759f",
"r" => "0x55a1a93541d7f782f97f6699437bb60fa4606d63760b30c1ee317e648f93995",
"raw" =>
"0xf8f582065b843b9aca008303d9c594698bf6943bab687b2756394624aa183f434f65da8901158e4f216242a000b8848841ac11000000000000000000000000000000000000000000000000000000000000006c00000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000005000000000000000000000000000000000000000000000000000000000000000581eaa0055a1a93541d7f782f97f6699437bb60fa4606d63760b30c1ee317e648f93995a06affd4da5eca84fbca2b016c980f861e0af1f8d6535e2fe29d8f96dc0ce358f7",
"s" => "0x6affd4da5eca84fbca2b016c980f861e0af1f8d6535e2fe29d8f96dc0ce358f7",
"standardV" => "0x1",
"to" => "0x698bf6943bab687b2756394624aa183f434f65da",
"transactionIndex" => "0x0",
"v" => "0xea",
"value" => "0x1158e4f216242a000"
}
],
"transactionsRoot" => "0xd7c39a93eafe0bdcbd1324c13dcd674bed8c9fa8adbf8f95bf6a59788985da6f",
"uncles" => ["0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cd"]
}
}
]}
[
%{
id: 0,
jsonrpc: "2.0",
method: "eth_getBlockByNumber",
params: ["0x3C3660", true]
}
],
_ ->
{:ok,
[
%{
id: 0,
jsonrpc: "2.0",
result: %{
"author" => "0x66c9343c7e8ca673a1fedf9dbf2cd7936dbbf7e3",
"difficulty" => "0xfffffffffffffffffffffffffffffffe",
"extraData" => "0xd583010a068650617269747986312e32362e32826c69",
"gasLimit" => "0x7a1200",
"gasUsed" => "0x0",
"hash" => "0xfb483e511d316fa4072694da3f7abc94b06286406af45061e5e681395bdc6815",
"logsBloom" =>
"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
"miner" => "0x66c9343c7e8ca673a1fedf9dbf2cd7936dbbf7e3",
"number" => "0x3c3660",
"parentHash" => "0xa4ec735cabe1510b5ae081b30f17222580b4588dbec52830529753a688b046cc",
"receiptsRoot" => "0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421",
"sealFields" => [
"0x841246c640",
"0xb84114db3fd7526b7ea3635f5c85c30dd8a645453aa2f8afe5fd33fe0ec663c9c7b653b0fb5d8dc7d0b809674fa9dca9887d1636a586bf62191da22255eb068bf20800"
],
"sha3Uncles" => "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347",
"signature" =>
"14db3fd7526b7ea3635f5c85c30dd8a645453aa2f8afe5fd33fe0ec663c9c7b653b0fb5d8dc7d0b809674fa9dca9887d1636a586bf62191da22255eb068bf20800",
"size" => "0x243",
"stateRoot" => "0x3174c461989e9f99e08fa9b4ffb8bce8d9a281c8fc9f80694bb9d3acd4f15559",
"step" => "306628160",
"timestamp" => "0x5b61df40",
"totalDifficulty" => "0x3c365fffffffffffffffffffffffffed7f0360",
"transactions" => [],
"transactionsRoot" => "0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421",
"uncles" => []
}
}
]}
[
%{
id: 0,
jsonrpc: "2.0",
method: "trace_replayBlockTransactions",
params: [
"0x3C3660",
["trace"]
]
},
%{
id: 1,
jsonrpc: "2.0",
method: "trace_replayBlockTransactions",
params: [
"0x3C365F",
["trace"]
]
}
],
_ ->
{:ok,
[
%{id: 0, jsonrpc: "2.0", result: []},
%{
id: 1,
jsonrpc: "2.0",
result: [
%{
"output" => "0x",
"stateDiff" => nil,
"trace" => [
%{
"action" => %{
"callType" => "call",
"from" => "0x40b18103537c0f15d5e137dd8ddd019b84949d16",
"gas" => "0x383ad",
"input" =>
"0x8841ac11000000000000000000000000000000000000000000000000000000000000006c000000000000000000000000000000000000000000000000000000000000000500000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000005",
"to" => "0x698bf6943bab687b2756394624aa183f434f65da",
"value" => "0x1158e4f216242a000"
},
"result" => %{"gasUsed" => "0x23256", "output" => "0x"},
"subtraces" => 5,
"traceAddress" => [],
"type" => "call"
},
%{
"action" => %{
"callType" => "call",
"from" => "0x698bf6943bab687b2756394624aa183f434f65da",
"gas" => "0x36771",
"input" => "0x6352211e000000000000000000000000000000000000000000000000000000000000006c",
"to" => "0x11c4469d974f8af5ba9ec99f3c42c07c848c861c",
"value" => "0x0"
},
"result" => %{
"gasUsed" => "0x495",
"output" => "0x00000000000000000000000040b18103537c0f15d5e137dd8ddd019b84949d16"
},
"subtraces" => 0,
"traceAddress" => [0],
"type" => "call"
},
%{
"action" => %{
"callType" => "call",
"from" => "0x698bf6943bab687b2756394624aa183f434f65da",
"gas" => "0x35acb",
"input" => "0x33f30a43000000000000000000000000000000000000000000000000000000000000006c",
"to" => "0x11c4469d974f8af5ba9ec99f3c42c07c848c861c",
"value" => "0x0"
},
"result" => %{
"gasUsed" => "0x52d2",
"output" =>
"0x00000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000058000000000000000000000000000000000000000000000000000000000000001c000000000000000000000000000000000000000000000000000000000000004e000000000000000000000000000000000000000000000000000000000000004f000000000000000000000000000000000000000000000000000000000000004d000000000000000000000000000000000000000000000000000000000000004b000000000000000000000000000000000000000000000000000000000000004f00000000000000000000000000000000000000000000000000000000000000b000000000000000000000000000000000000000000000000000000000000000080000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001c0000000000000000000000000000000000000000000000000000000000000005000000000000000000000000000000000000000000000000000000000000044000000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000078000000000000000000000000000000000000000000000000000000005b61df09000000000000000000000000000000000000000000000000000000005b61df5e000000000000000000000000000000000000000000000000000000005b61df8b000000000000000000000000000000000000000000000000000000005b61df2c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000006c00000000000000000000000000000000000000000000000000000000000000fd000000000000000000000000000000000000000000000000000000000000004e000000000000000000000000000000000000000000000000000000000000007a000000000000000000000000000000000000000000000000000000000000004e0000000000000000000000000000000000000000000000000000000000000015000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000189000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000054c65696c61000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002566303430313037303331343330303332333036303933333235303131323036303730373131000000000000000000000000000000000000000000000000000000"
},
"subtraces" => 0,
"traceAddress" => [1],
"type" => "call"
},
%{
"action" => %{
"callType" => "call",
"from" => "0x698bf6943bab687b2756394624aa183f434f65da",
"gas" => "0x2fc79",
"input" => "0x1b8ef0bb000000000000000000000000000000000000000000000000000000000000006c",
"to" => "0x11c4469d974f8af5ba9ec99f3c42c07c848c861c",
"value" => "0x0"
},
"result" => %{
"gasUsed" => "0x10f2",
"output" => "0x0000000000000000000000000000000000000000000000000000000000000013"
},
"subtraces" => 0,
"traceAddress" => [2],
"type" => "call"
},
%{
"action" => %{
"callType" => "call",
"from" => "0x698bf6943bab687b2756394624aa183f434f65da",
"gas" => "0x2e21f",
"input" =>
"0xcf5f87d0000000000000000000000000000000000000000000000000000000000000006c0000000000000000000000000000000000000000000000000000000000000003000000000000000000000000000000000000000000000000000000000000000a",
"to" => "0x11c4469d974f8af5ba9ec99f3c42c07c848c861c",
"value" => "0x0"
},
"result" => %{"gasUsed" => "0x1ca1", "output" => "0x"},
"subtraces" => 0,
"traceAddress" => [3],
"type" => "call"
},
%{
"action" => %{
"callType" => "call",
"from" => "0x698bf6943bab687b2756394624aa183f434f65da",
"gas" => "0x8fc",
"input" => "0x",
"to" => "0x40b18103537c0f15d5e137dd8ddd019b84949d16",
"value" => "0x9184e72a000"
},
"result" => %{"gasUsed" => "0x0", "output" => "0x"},
"subtraces" => 0,
"traceAddress" => [4],
"type" => "call"
}
],
"transactionHash" => "0xd3937e70fab3fb2bfe8feefac36815408bf07de3b9e09fe81114b9a6b17f55c8",
"vmTrace" => nil
}
]
}
]}
[
%{
id: 0,
jsonrpc: "2.0",
method: "eth_getBalance",
params: ["0x40b18103537c0f15d5e137dd8ddd019b84949d16", "0x3C365F"]
},
%{
id: 1,
jsonrpc: "2.0",
method: "eth_getBalance",
params: ["0x5ee341ac44d344ade1ca3a771c59b98eb2a77df2", "0x3C365F"]
},
%{
id: 2,
jsonrpc: "2.0",
method: "eth_getBalance",
params: ["0x66c9343c7e8ca673a1fedf9dbf2cd7936dbbf7e3", "0x3C3660"]
},
%{
id: 3,
jsonrpc: "2.0",
method: "eth_getBalance",
params: ["0x698bf6943bab687b2756394624aa183f434f65da", "0x3C365F"]
}
],
_ ->
{:ok,
[
%{id: 0, jsonrpc: "2.0", result: "0x148adc763b603291685"},
%{id: 1, jsonrpc: "2.0", result: "0x53474fa377a46000"},
%{id: 2, jsonrpc: "2.0", result: "0x53507afe51f28000"},
%{id: 3, jsonrpc: "2.0", result: "0x3e1a95d7517dc197108"}
]}
end)
end
first_expected_reward = %Wei{value: Decimal.new(165_998_000_000_000)}
second_expected_reward = %Wei{value: Decimal.new(0)}
assert {:ok,
%{
inserted: %{
addresses: [
%Address{hash: first_address_hash, fetched_coin_balance_block_number: 3_946_079},
%Address{hash: second_address_hash, fetched_coin_balance_block_number: 3_946_079},
%Address{hash: third_address_hash, fetched_coin_balance_block_number: 3_946_080},
%Address{hash: fourth_address_hash, fetched_coin_balance_block_number: 3_946_079}
],
address_coin_balances: [
%{
address_hash: first_address_hash,
block_number: 3_946_079
},
%{
address_hash: second_address_hash,
block_number: 3_946_079
},
%{
address_hash: third_address_hash,
block_number: 3_946_080
},
%{
address_hash: fourth_address_hash,
block_number: 3_946_079
}
],
block_rewards: [
%{
address_hash: second_address_hash,
address_type: :validator,
reward: ^first_expected_reward
},
%{
address_hash: third_address_hash,
address_type: :validator,
reward: ^second_expected_reward
}
],
blocks: [%Chain.Block{number: 3_946_079}, %Chain.Block{number: 3_946_080}],
transactions: [%Transaction{hash: _transaction_hash}]
},
errors: []
}} = Indexer.Block.Fetcher.fetch_and_import_range(block_fetcher, 3_946_079..3_946_080)
Application.put_env(:indexer, :fetch_rewards_way, nil)
end
end end
end end

Loading…
Cancel
Save