diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_contract_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_contract_controller.ex index 377be35b3c..4a965cee84 100644 --- a/apps/block_scout_web/lib/block_scout_web/controllers/address_contract_controller.ex +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_contract_controller.ex @@ -1,7 +1,7 @@ defmodule BlockScoutWeb.AddressContractController do use BlockScoutWeb, :controller - import BlockScoutWeb.AddressController, only: [transaction_count: 1] + import BlockScoutWeb.AddressController, only: [transaction_count: 1, validation_count: 1] alias Explorer.{Chain, Market} alias Explorer.ExchangeRates.Token @@ -9,12 +9,14 @@ defmodule BlockScoutWeb.AddressContractController do def index(conn, %{"address_id" => address_hash_string}) do with {:ok, address_hash} <- Chain.string_to_address_hash(address_hash_string), {:ok, address} <- Chain.find_contract_address(address_hash) do + render( conn, "index.html", address: address, exchange_rate: Market.get_exchange_rate(Explorer.coin()) || Token.null(), - transaction_count: transaction_count(address) + transaction_count: transaction_count(address), + validation_count: validation_count(address) ) else :error -> diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_controller.ex index 2753dc8720..93ea2a688e 100644 --- a/apps/block_scout_web/lib/block_scout_web/controllers/address_controller.ex +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_controller.ex @@ -20,4 +20,8 @@ defmodule BlockScoutWeb.AddressController do def transaction_count(%Address{} = address) do Chain.address_to_transactions_estimated_count(address) end + + def validation_count(%Address{} = address) do + Chain.address_to_validation_count(address) + end end diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_internal_transaction_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_internal_transaction_controller.ex index b7e6079997..36c32740e7 100644 --- a/apps/block_scout_web/lib/block_scout_web/controllers/address_internal_transaction_controller.ex +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_internal_transaction_controller.ex @@ -5,7 +5,7 @@ defmodule BlockScoutWeb.AddressInternalTransactionController do use BlockScoutWeb, :controller - import BlockScoutWeb.AddressController, only: [transaction_count: 1] + import BlockScoutWeb.AddressController, only: [transaction_count: 1, validation_count: 1] import BlockScoutWeb.Chain, only: [current_filter: 1, paging_options: 1, next_page_params: 3, split_list_by_page: 1] alias Explorer.{Chain, Market} @@ -26,7 +26,6 @@ defmodule BlockScoutWeb.AddressInternalTransactionController do |> Keyword.merge(current_filter(params)) internal_transactions_plus_one = Chain.address_to_internal_transactions(address, full_options) - {internal_transactions, next_page} = split_list_by_page(internal_transactions_plus_one) render( @@ -37,7 +36,8 @@ defmodule BlockScoutWeb.AddressInternalTransactionController do exchange_rate: Market.get_exchange_rate(Explorer.coin()) || Token.null(), filter: params["filter"], internal_transactions: internal_transactions, - transaction_count: transaction_count(address) + transaction_count: transaction_count(address), + validation_count: validation_count(address) ) else :error -> diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_read_contract_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_read_contract_controller.ex index 1100fa3c8c..76c5147d2f 100644 --- a/apps/block_scout_web/lib/block_scout_web/controllers/address_read_contract_controller.ex +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_read_contract_controller.ex @@ -11,7 +11,7 @@ defmodule BlockScoutWeb.AddressReadContractController do alias Explorer.{Chain, Market} alias Explorer.ExchangeRates.Token - import BlockScoutWeb.AddressController, only: [transaction_count: 1] + import BlockScoutWeb.AddressController, only: [transaction_count: 1, validation_count: 1] def index(conn, %{"address_id" => address_hash_string}) do with {:ok, address_hash} <- Chain.string_to_address_hash(address_hash_string), @@ -21,7 +21,8 @@ defmodule BlockScoutWeb.AddressReadContractController do "index.html", address: address, exchange_rate: Market.get_exchange_rate(Explorer.coin()) || Token.null(), - transaction_count: transaction_count(address) + transaction_count: transaction_count(address), + validation_count: validation_count(address) ) else :error -> diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_token_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_token_controller.ex index c2c7bea561..d5b77bd470 100644 --- a/apps/block_scout_web/lib/block_scout_web/controllers/address_token_controller.ex +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_token_controller.ex @@ -4,7 +4,7 @@ defmodule BlockScoutWeb.AddressTokenController do alias Explorer.{Chain, Market} alias Explorer.ExchangeRates.Token - import BlockScoutWeb.AddressController, only: [transaction_count: 1] + import BlockScoutWeb.AddressController, only: [transaction_count: 1, validation_count: 1] import BlockScoutWeb.Chain, only: [next_page_params: 3, paging_options: 1, split_list_by_page: 1] def index(conn, %{"address_id" => address_hash_string} = params) do @@ -19,6 +19,7 @@ defmodule BlockScoutWeb.AddressTokenController do address: address, exchange_rate: Market.get_exchange_rate(Explorer.coin()) || Token.null(), transaction_count: transaction_count(address), + validation_count: validation_count(address), next_page_params: next_page_params(next_page, tokens, params), tokens: tokens ) diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_transaction_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_transaction_controller.ex index 5bad1ddbae..584d28efba 100644 --- a/apps/block_scout_web/lib/block_scout_web/controllers/address_transaction_controller.ex +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_transaction_controller.ex @@ -5,7 +5,7 @@ defmodule BlockScoutWeb.AddressTransactionController do use BlockScoutWeb, :controller - import BlockScoutWeb.AddressController, only: [transaction_count: 1] + import BlockScoutWeb.AddressController, only: [transaction_count: 1, validation_count: 1] import BlockScoutWeb.Chain, only: [current_filter: 1, paging_options: 1, next_page_params: 3, split_list_by_page: 1] alias Explorer.{Chain, Market} @@ -37,7 +37,8 @@ defmodule BlockScoutWeb.AddressTransactionController do exchange_rate: Market.get_exchange_rate(Explorer.coin()) || Token.null(), filter: params["filter"], transactions: transactions, - transaction_count: transaction_count(address) + transaction_count: transaction_count(address), + validation_count: validation_count(address) ) else :error -> diff --git a/apps/block_scout_web/lib/block_scout_web/controllers/address_validation_controller.ex b/apps/block_scout_web/lib/block_scout_web/controllers/address_validation_controller.ex new file mode 100644 index 0000000000..0a4078d369 --- /dev/null +++ b/apps/block_scout_web/lib/block_scout_web/controllers/address_validation_controller.ex @@ -0,0 +1,43 @@ + +defmodule BlockScoutWeb.AddressValidationController do + @moduledoc """ + Display all the blocks that this address validates. + """ + use BlockScoutWeb, :controller + + import BlockScoutWeb.AddressController, only: [transaction_count: 1, validation_count: 1] + import BlockScoutWeb.Chain, only: + [paging_options: 1, next_page_params: 3, split_list_by_page: 1] + + alias Explorer.{Chain, Market} + alias Explorer.ExchangeRates.Token + + def index(conn, %{"address_id" => address_hash_string} = params) do + with {:ok, address_hash} <- Chain.string_to_address_hash(address_hash_string), + {:ok, address} <- Chain.hash_to_address(address_hash) do + + full_options = Keyword.merge( + [necessity_by_association: %{miner: :required, transactions: :optional}], + paging_options(params) + ) + + blocks_plus_one = Chain.get_blocks_validated_by_address(full_options, address) + {blocks, next_page} = split_list_by_page(blocks_plus_one) + + render(conn, "index.html", + address: address, + blocks: blocks, + transaction_count: transaction_count(address), + validation_count: validation_count(address), + exchange_rate: Market.get_exchange_rate(Explorer.coin()) || Token.null(), + next_page_params: next_page_params(next_page, blocks, params) + ) + else + :error -> + unprocessable_entity(conn) + + {:error, :not_found} -> + not_found(conn) + end + end +end diff --git a/apps/block_scout_web/lib/block_scout_web/router.ex b/apps/block_scout_web/lib/block_scout_web/router.ex index 44e2b90bd3..21a9838049 100644 --- a/apps/block_scout_web/lib/block_scout_web/router.ex +++ b/apps/block_scout_web/lib/block_scout_web/router.ex @@ -70,7 +70,7 @@ defmodule BlockScoutWeb.Router do resources "/address", AddressController, only: [:show] do resources("/transactions", AddressTransactionController, only: [:index], as: :transaction) - + resources( "/internal_transactions", AddressInternalTransactionController, @@ -78,6 +78,13 @@ defmodule BlockScoutWeb.Router do as: :internal_transaction ) + resources( + "/validations", + AddressValidationController, + only: [:index], + as: :validation + ) + resources( "/contracts", AddressContractController, diff --git a/apps/block_scout_web/lib/block_scout_web/templates/address/overview.html.eex b/apps/block_scout_web/lib/block_scout_web/templates/address/overview.html.eex index ef8b5cd66c..eb593e04a9 100644 --- a/apps/block_scout_web/lib/block_scout_web/templates/address/overview.html.eex +++ b/apps/block_scout_web/lib/block_scout_web/templates/address/overview.html.eex @@ -17,15 +17,19 @@