Skip to content

Commit

Permalink
Integrate Eth Bytecode DB (blockscout#7187)
Browse files Browse the repository at this point in the history
* Add Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand

* Add smart_contract_was_verified broadcast

* Changelog

* Rollback rename

* Refactoring

* Fix warning on rendering contracts without constructor args

* Add metadata to the verification request to microservice

* Add ETH_BYTECODE_DB_INTERVAL_BETWEEN_LOOKUPS

* Add MICROSERVICE_ prefix to MICROSERVICE_ETH_BYTECODE_DB_INTERVAL_BETWEEN_LOOKUPS; Add MICROSERVICE_SC_VERIFIER_TYPE

* Fix tests

* Update runtime.exs

* Update common-blockscout.env

---------

Co-authored-by: Victor Baranov <baranov.viktor.27@gmail.com>
  • Loading branch information
nikitosing and vbaranov authored Apr 10, 2023
1 parent 46f7779 commit 3633b7d
Show file tree
Hide file tree
Showing 22 changed files with 579 additions and 273 deletions.
26 changes: 13 additions & 13 deletions .github/workflows/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-
Expand Down Expand Up @@ -100,7 +100,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand All @@ -124,7 +124,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand All @@ -147,7 +147,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -187,7 +187,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand All @@ -213,7 +213,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -242,7 +242,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -287,7 +287,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -333,7 +333,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -390,7 +390,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -444,7 +444,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -509,7 +509,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down Expand Up @@ -573,7 +573,7 @@ jobs:
path: |
deps
_build
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_15-${{ hashFiles('mix.lock') }}
key: ${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-mixlockhash_16-${{ hashFiles('mix.lock') }}
restore-keys: |
${{ runner.os }}-${{ env.ELIXIR_VERSION }}-${{ env.OTP_VERSION }}-${{ env.MIX_ENV }}-deps-"
Expand Down
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

### Features

- [#7187](https://github.com/blockscout/blockscout/pull/7187) - Integrate [Eth Bytecode DB](https://github.com/blockscout/blockscout-rs/tree/main/eth-bytecode-db/eth-bytecode-db)
- [#7185](https://github.com/blockscout/blockscout/pull/7185) - Aave v3 transaction actions indexer
- [#7148](https://github.com/blockscout/blockscout/pull/7148), [#7244](https://github.com/blockscout/blockscout/pull/7244) - API v2 improvements: API rate limiting, `/tokens/{address_hash}/instances/{token_id}/holders` and other changes

Expand Down
4 changes: 4 additions & 0 deletions apps/block_scout_web/lib/block_scout_web/notifier.ex
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,10 @@ defmodule BlockScoutWeb.Notifier do
Endpoint.broadcast("addresses:#{to_string(address_hash)}", "changed_bytecode", %{})
end

def handle_event({:chain_event, :smart_contract_was_verified, :on_demand, [address_hash]}) do
Endpoint.broadcast("addresses:#{to_string(address_hash)}", "smart_contract_was_verified", %{})
end

def handle_event(_), do: nil

def fetch_compiler_version(compiler) do
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ defmodule BlockScoutWeb.RealtimeEventHandler do
Subscriber.to(:contract_verification_result, :on_demand)
Subscriber.to(:token_total_supply, :on_demand)
Subscriber.to(:changed_bytecode, :on_demand)
Subscriber.to(:smart_contract_was_verified, :on_demand)
# Does not come from the indexer
Subscriber.to(:exchange_rate)
Subscriber.to(:transaction_stats)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -216,7 +216,8 @@ defmodule BlockScoutWeb.API.V2.SmartContractView do
}
end

def format_constructor_arguments(abi, constructor_arguments) do
def format_constructor_arguments(abi, constructor_arguments)
when not is_nil(abi) and not is_nil(constructor_arguments) do
constructor_abi = Enum.find(abi, fn el -> el["type"] == "constructor" && el["inputs"] != [] end)

input_types = Enum.map(constructor_abi["inputs"], &FunctionSelector.parse_specification_type/1)
Expand All @@ -242,6 +243,8 @@ defmodule BlockScoutWeb.API.V2.SmartContractView do
nil
end

def format_constructor_arguments(_abi, _constructor_arguments), do: nil

defp prepare_smart_contract_for_list(%SmartContract{} = smart_contract) do
token = smart_contract.address.token

Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
defmodule BlockScoutWeb.API.V2.SmartContractControllerTest do
use BlockScoutWeb.ConnCase
use BlockScoutWeb.ChannelCase, async: false

import Mox

alias BlockScoutWeb.AddressContractView
alias BlockScoutWeb.Models.UserFromAuth
alias Explorer.Chain.{Address, SmartContract}
alias Plug.Conn

setup :set_mox_from_context

Expand Down Expand Up @@ -295,6 +297,117 @@ defmodule BlockScoutWeb.API.V2.SmartContractControllerTest do

assert correct_response == response
end

test "automatically verify contract via Eth Bytecode Interface", %{conn: conn} do
{:ok, pid} = Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand.start_link([])

bypass = Bypass.open()
eth_bytecode_response = File.read!("./test/support/fixture/smart_contract/eth_bytecode_db_search_response.json")

old_env = Application.get_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour)

Application.put_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour,
service_url: "http://localhost:#{bypass.port}",
enabled: true
)

address = insert(:contract_address)

insert(:transaction,
created_contract_address_hash: address.hash,
input:
"0x608060405234801561001057600080fd5b5060df8061001f6000396000f3006080604052600436106049576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806360fe47b114604e5780636d4ce63c146078575b600080fd5b348015605957600080fd5b5060766004803603810190808035906020019092919050505060a0565b005b348015608357600080fd5b50608a60aa565b6040518082815260200191505060405180910390f35b8060008190555050565b600080549050905600a165627a7a7230582061b7676067d537e410bb704932a9984739a959416170ea17bda192ac1218d2790029"
)
|> with_block()

topic = "addresses:#{address.hash}"

{:ok, _reply, _socket} =
BlockScoutWeb.UserSocketV2
|> socket("no_id", %{})
|> subscribe_and_join(topic)

Bypass.expect_once(bypass, "POST", "/api/v2/bytecodes/sources:search", fn conn ->
Conn.resp(conn, 200, eth_bytecode_response)
end)

request = get(conn, "/api/v2/smart-contracts/#{Address.checksum(address.hash)}")

assert_receive %Phoenix.Socket.Message{
payload: %{},
event: "smart_contract_was_verified",
topic: ^topic
},
:timer.seconds(1)

response = json_response(request, 200)

assert response ==
%{
"is_self_destructed" => false,
"deployed_bytecode" => to_string(address.contract_code),
"creation_bytecode" =>
"0x608060405234801561001057600080fd5b5060df8061001f6000396000f3006080604052600436106049576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806360fe47b114604e5780636d4ce63c146078575b600080fd5b348015605957600080fd5b5060766004803603810190808035906020019092919050505060a0565b005b348015608357600080fd5b50608a60aa565b6040518082815260200191505060405180910390f35b8060008190555050565b600080549050905600a165627a7a7230582061b7676067d537e410bb704932a9984739a959416170ea17bda192ac1218d2790029"
}

request = get(conn, "/api/v2/smart-contracts/#{Address.checksum(address.hash)}")
assert %{"is_verified" => true} = json_response(request, 200)

Application.put_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour, old_env)
Bypass.down(bypass)
GenServer.stop(pid)
end

test "check fetch interval for LookUpSmartContractSourcesOnDemand", %{conn: conn} do
{:ok, pid} = Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand.start_link([])

bypass = Bypass.open()
address = insert(:contract_address)

insert(:transaction,
created_contract_address_hash: address.hash,
input:
"0x608060405234801561001057600080fd5b5060df8061001f6000396000f3006080604052600436106049576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806360fe47b114604e5780636d4ce63c146078575b600080fd5b348015605957600080fd5b5060766004803603810190808035906020019092919050505060a0565b005b348015608357600080fd5b50608a60aa565b6040518082815260200191505060405180910390f35b8060008190555050565b600080549050905600a165627a7a7230582061b7676067d537e410bb704932a9984739a959416170ea17bda192ac1218d2790029"
)
|> with_block()

old_env = Application.get_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour)

Application.put_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour,
service_url: "http://localhost:#{bypass.port}",
enabled: true
)

old_interval_env = Application.get_env(:explorer, Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand)

Application.put_env(:explorer, Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand, fetch_interval: 0)

Bypass.expect_once(bypass, "POST", "/api/v2/bytecodes/sources:search", fn conn ->
Conn.resp(conn, 200, "{\"sources\": []}")
end)

_request = get(conn, "/api/v2/smart-contracts/#{Address.checksum(address.hash)}")

Bypass.expect_once(bypass, "POST", "/api/v2/bytecodes/sources:search", fn conn ->
Conn.resp(conn, 200, "{\"sources\": []}")
end)

_request = get(conn, "/api/v2/smart-contracts/#{Address.checksum(address.hash)}")

Application.put_env(:explorer, Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand, fetch_interval: 10000)

Bypass.expect_once(bypass, "POST", "/api/v2/bytecodes/sources:search", fn conn ->
Conn.resp(conn, 200, "{\"sources\": []}")
end)

_request = get(conn, "/api/v2/smart-contracts/#{Address.checksum(address.hash)}")
_request = get(conn, "/api/v2/smart-contracts/#{Address.checksum(address.hash)}")

Application.put_env(:explorer, Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand, old_interval_env)
Application.put_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour, old_env)
Bypass.down(bypass)
GenServer.stop(pid)
end
end

describe "/smart-contracts/{address_hash}/methods-read" do
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
{
"sources": [
{
"fileName": "Test.sol",
"contractName": "Test",
"compilerVersion": "v0.8.17+commit.8df45f5f",
"compilerSettings": "{\"libraries\":{\"Test.sol\":{}},\"metadata\":{\"bytecodeHash\":\"ipfs\"},\"optimizer\":{\"enabled\":true,\"runs\":199},\"outputSelection\":{\"*\":{\"\":[\"ast\"],\"*\":[\"abi\",\"evm.bytecode\",\"evm.deployedBytecode\",\"evm.methodIdentifiers\"]}}}",
"sourceType": "SOLIDITY",
"sourceFiles": {
"Test.sol": "// SPDX-License-Identifier: MIT\r\n\r\npragma solidity 0.8.17;\r\n\r\ncontract Test {\r\n enum E {\r\n V1, V2, V3, V4\r\n }\r\n struct A {\r\n E a;\r\n uint256[] b;\r\n B[] c;\r\n }\r\n\r\n struct B {\r\n uint256 d;\r\n uint256 e;\r\n }\r\n\r\n function get(uint256 x) external pure returns (A memory) {\r\n uint256[] memory b = new uint256[](3);\r\n b[0] = 1;\r\n b[1] = 2;\r\n b[2] = 3;\r\n B[] memory c = new B[](3);\r\n c[0] = B(1, 2);\r\n c[1] = B(3, 4);\r\n c[2] = B(5, 6);\r\n return A(E.V3, b, c);\r\n }\r\n}"
},
"abi": "[{\"inputs\":[{\"internalType\":\"uint256\",\"name\":\"x\",\"type\":\"uint256\"}],\"name\":\"get\",\"outputs\":[{\"components\":[{\"type\":\"uint8\"},{\"type\":\"uint256[]\"},{\"components\":[{\"type\":\"uint256\"},{\"type\":\"uint256\"}],\"type\":\"tuple[]\"}],\"internalType\":\"struct Test.A\",\"name\":\"\",\"type\":\"tuple\"}],\"stateMutability\":\"pure\",\"type\":\"function\"}]",
"constructorArguments": null,
"matchType": "PARTIAL"
}
]
}
13 changes: 12 additions & 1 deletion apps/explorer/lib/explorer/application.ex
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,8 @@ defmodule Explorer.Application do
configure(MinMissingBlockNumber),
configure(TokenTransferTokenIdMigration.Supervisor),
configure(Explorer.Chain.Fetcher.CheckBytecodeMatchingOnDemand),
configure(Explorer.Chain.Fetcher.FetchValidatorInfoOnDemand)
configure(Explorer.Chain.Fetcher.FetchValidatorInfoOnDemand),
sc_microservice_configure(Explorer.Chain.Fetcher.LookUpSmartContractSourcesOnDemand)
]
|> List.flatten()
end
Expand All @@ -128,6 +129,16 @@ defmodule Explorer.Application do
end
end

defp sc_microservice_configure(process) do
config = Application.get_env(:explorer, Explorer.SmartContract.RustVerifierInterfaceBehaviour, [])

if config[:enabled] && config[:type] == "eth_bytecode_db" do
process
else
[]
end
end

defp datadog_port do
Application.get_env(:explorer, :datadog)[:port]
end
Expand Down
13 changes: 12 additions & 1 deletion apps/explorer/lib/explorer/chain.ex
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ defmodule Explorer.Chain do

alias Explorer.Chain.Cache.Block, as: BlockCache
alias Explorer.Chain.Cache.Helper, as: CacheHelper
alias Explorer.Chain.Fetcher.CheckBytecodeMatchingOnDemand
alias Explorer.Chain.Fetcher.{CheckBytecodeMatchingOnDemand, LookUpSmartContractSourcesOnDemand}
alias Explorer.Chain.Import.Runner
alias Explorer.Chain.InternalTransaction.{CallType, Type}

Expand Down Expand Up @@ -1950,8 +1950,11 @@ defmodule Explorer.Chain do
%{smart_contract: smart_contract} ->
if smart_contract do
CheckBytecodeMatchingOnDemand.trigger_check(address_result, smart_contract)
LookUpSmartContractSourcesOnDemand.trigger_fetch(address_result, smart_contract)
address_result
else
LookUpSmartContractSourcesOnDemand.trigger_fetch(address_result, nil)

address_verified_twin_contract =
get_minimal_proxy_template(hash, options) ||
get_address_verified_twin_contract(hash, options).verified_contract
Expand All @@ -1960,6 +1963,7 @@ defmodule Explorer.Chain do
end

_ ->
LookUpSmartContractSourcesOnDemand.trigger_fetch(address_result, nil)
address_result
end

Expand Down Expand Up @@ -4428,6 +4432,13 @@ defmodule Explorer.Chain do
end
end

@spec address_hash_to_smart_contract(Hash.Address.t()) :: SmartContract.t() | nil
def address_hash_to_one_smart_contract(hash) do
SmartContract
|> where([sc], sc.address_hash == ^hash)
|> Repo.one()
end

@spec address_hash_to_smart_contract_without_twin(Hash.Address.t(), [api?]) :: SmartContract.t() | nil
def address_hash_to_smart_contract_without_twin(address_hash, options) do
query =
Expand Down
2 changes: 1 addition & 1 deletion apps/explorer/lib/explorer/chain/events/publisher.ex
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ defmodule Explorer.Chain.Events.Publisher do
Publishes events related to the Chain context.
"""

@allowed_events ~w(addresses address_coin_balances address_token_balances blocks block_rewards internal_transactions last_block_number token_transfers transactions contract_verification_result token_total_supply changed_bytecode)a
@allowed_events ~w(addresses address_coin_balances address_token_balances blocks block_rewards internal_transactions last_block_number token_transfers transactions contract_verification_result token_total_supply changed_bytecode smart_contract_was_verified)a

def broadcast(_data, false), do: :ok

Expand Down
Loading

0 comments on commit 3633b7d

Please sign in to comment.