Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

deposits performance tests bot #1745

Merged
merged 59 commits into from
Oct 19, 2020
Merged
Show file tree
Hide file tree
Changes from 53 commits
Commits
Show all changes
59 commits
Select commit Hold shift + click to select a range
9fef7f5
make deposits with Chaperon
ayrat555 Sep 23, 2020
12c2852
validate balances after deposit
ayrat555 Sep 24, 2020
62de790
send value on the childchain and check balances
ayrat555 Sep 24, 2020
aaf0a7f
fix assertions
ayrat555 Sep 25, 2020
5b0670c
add error rate
ayrat555 Sep 28, 2020
881d138
add ui subproject
ayrat555 Sep 29, 2020
a79e253
remove js, views; rename into front
ayrat555 Oct 2, 2020
dffdf9c
add monitoring process
ayrat555 Oct 2, 2020
221d4f9
fix feefeed container
ayrat555 Oct 7, 2020
9e68a81
use hornet to run tests
ayrat555 Oct 7, 2020
b95deb0
add aliases
ayrat555 Oct 7, 2020
28d1174
add aggregator and runner
ayrat555 Oct 7, 2020
ef4ea7c
Merge branch 'master' into ayrat555/deposits-perf-tests
ayrat555 Oct 7, 2020
27da28f
get rid off compilation warnings
ayrat555 Oct 7, 2020
8f0f9fe
format code
ayrat555 Oct 7, 2020
745fe57
periodically dump test run data to the db
ayrat555 Oct 7, 2020
5f3a49a
refactor process_transaction_result
ayrat555 Oct 7, 2020
d3541ca
remove front app, return chaperon as test library
ayrat555 Oct 8, 2020
0ddd01e
update mix.lock
ayrat555 Oct 8, 2020
edb967b
add test runner
ayrat555 Oct 8, 2020
63d25a5
remove prod configs
ayrat555 Oct 8, 2020
04a9bcc
fix exit codes and default env vars
ayrat555 Oct 9, 2020
66e2267
add config parsing to config module
ayrat555 Oct 9, 2020
630da31
break create_deposit function
ayrat555 Oct 9, 2020
4dfb2ff
fix credo
ayrat555 Oct 9, 2020
d9ebad2
Update priv/perf/apps/load_test/lib/ethereum/ethereum.ex
ayrat555 Oct 9, 2020
8b62d3a
fix cr issues
ayrat555 Oct 12, 2020
3f21e86
add doc
ayrat555 Oct 12, 2020
1e76ee7
fail if coudn't fetch result in n tries
ayrat555 Oct 12, 2020
f9e45e6
add typespecs to Etherum module
ayrat555 Oct 12, 2020
84d3de6
fix credo
ayrat555 Oct 12, 2020
8816743
add description
ayrat555 Oct 12, 2020
624dd91
Update priv/perf/apps/load_test/lib/ethereum/ethereum.ex
ayrat555 Oct 13, 2020
09e62d6
log message during retry
ayrat555 Oct 13, 2020
824fca3
add error loggging
ayrat555 Oct 13, 2020
9a47f9c
mix format
ayrat555 Oct 13, 2020
ba77876
use sync module in ethereum module
ayrat555 Oct 13, 2020
b7f109a
use the same retry function
ayrat555 Oct 13, 2020
bdcda46
fix tests
ayrat555 Oct 13, 2020
105e7bb
Update priv/perf/apps/load_test/lib/scenario/deposits.ex
ayrat555 Oct 13, 2020
2a2d199
use error_rate
ayrat555 Oct 13, 2020
acabe85
use default values
ayrat555 Oct 13, 2020
4779c92
mix format
ayrat555 Oct 13, 2020
44d2990
fix credo
ayrat555 Oct 13, 2020
3071f82
add percentile
ayrat555 Oct 13, 2020
4fedb8b
Update priv/perf/apps/load_test/lib/ethereum/ethereum.ex
ayrat555 Oct 14, 2020
81ce526
Update priv/perf/apps/load_test/lib/child_chain/deposit.ex
ayrat555 Oct 14, 2020
1e034a7
address cr comments
ayrat555 Oct 14, 2020
0bcec40
move functions from Ethereum module
ayrat555 Oct 14, 2020
77f3a3b
Merge branch 'master' into ayrat555/deposits-perf-tests
ayrat555 Oct 14, 2020
955f17f
use alias
ayrat555 Oct 14, 2020
59f8ff1
add dockerfile and k8s job
ayrat555 Oct 15, 2020
c6fbac2
remove dockerfile and kubernetes job
ayrat555 Oct 16, 2020
5981f3b
remove default parameters
ayrat555 Oct 19, 2020
0d72467
add comments
ayrat555 Oct 19, 2020
c871c1b
add gas_price
ayrat555 Oct 19, 2020
9a526d0
allow to customize test config through file
ayrat555 Oct 19, 2020
b984197
add notes about customization
ayrat555 Oct 19, 2020
f854756
increase timeout for geth startup
ayrat555 Oct 19, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docker-compose.feefeed.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ services:
- GITHUB_TOKEN=""
- GITHUB_ORGANISATION=omgnetwork
- GITHUB_REPO=fee-rules-public
- SENTRY_DSN=""
- GITHUB_BRANCH=master
- RULES_FETCH_INTERVAL=20
- RATES_FETCH_INTERVAL=20
Expand Down
64 changes: 42 additions & 22 deletions priv/perf/apps/load_test/lib/child_chain/deposit.ex
Original file line number Diff line number Diff line change
Expand Up @@ -16,37 +16,57 @@ defmodule LoadTest.ChildChain.Deposit do
@moduledoc """
Utility functions for deposits on a child chain
"""

require Logger

alias ExPlasma.Encoding
alias ExPlasma.Transaction.Deposit
alias ExPlasma.Utxo
alias LoadTest.Ethereum
alias LoadTest.Ethereum.Account
alias LoadTest.Service.Sync

@eth <<0::160>>
@poll_interval 5_000

@doc """
Deposits funds into the childchain.

If currency is ETH, funds will be deposited into the EthVault.
If currency is ERC20, 'approve()' will be called before depositing funds into the Erc20Vault.

Returns the utxo created by the deposit.
This function accepts three required parameters:
1. depositor account
2. the amount to be deposited
3. currency

Accepts optional parameters:
- deposit_finality_margin - the number of verifications
- gas_price - gas price of the transaction
- return - it can be :utxo or :txhash

Returns the utxo created by the deposit or the hash of the the deposit transaction.
"""
@spec deposit_from(
LoadTest.Ethereum.Account.t(),
pos_integer(),
LoadTest.Ethereum.Account.t(),
pos_integer(),
pos_integer()
) :: Utxo.t()
def deposit_from(%Account{} = depositor, amount, currency, deposit_finality_margin, gas_price) do
@spec deposit_from(Account.t(), pos_integer(), Account.t(), non_neg_integer(), non_neg_integer, atom()) ::
Utxo.t() | binary()
def deposit_from(
%Account{} = depositor,
ayrat555 marked this conversation as resolved.
Show resolved Hide resolved
amount,
currency,
deposit_finality_margin \\ 5,
gas_price \\ 180_000,
return \\ :utxo
) do
deposit_utxo = %Utxo{amount: amount, owner: depositor.addr, currency: currency}

{:ok, deposit} = Deposit.new(deposit_utxo)
{:ok, {deposit_blknum, eth_blknum}} = send_deposit(deposit, depositor, amount, currency, gas_price)
{:ok, {deposit_blknum, eth_blknum, eth_txhash}} = send_deposit(deposit, depositor, amount, currency, gas_price)

:ok = wait_deposit_finality(eth_blknum, deposit_finality_margin)
Utxo.new(%{blknum: deposit_blknum, txindex: 0, oindex: 0, amount: amount})

case return do
:utxo -> Utxo.new(%{blknum: deposit_blknum, txindex: 0, oindex: 0, amount: amount})
_ -> eth_txhash
end
end

defp send_deposit(deposit, account, value, @eth, gas_price) do
Expand Down Expand Up @@ -84,20 +104,20 @@ defmodule LoadTest.ChildChain.Deposit do
%{"topics" => [_topic, _addr, blknum | _]} =
Enum.find(logs, fn %{"address" => address} -> address == vault_address end)

{:ok, {Encoding.to_int(blknum), eth_blknum}}
{:ok, {Encoding.to_int(blknum), eth_blknum, tx_hash}}
end

defp wait_deposit_finality(deposit_eth_blknum, finality_margin) do
{:ok, current_blknum} = Ethereumex.HttpClient.eth_block_number()
current_blknum = Encoding.to_int(current_blknum)

if current_blknum >= deposit_eth_blknum + finality_margin do
:ok
else
_ = Logger.info("Waiting for deposit finality")
Process.sleep(@poll_interval)
wait_deposit_finality(deposit_eth_blknum, finality_margin)
func = fn ->
{:ok, current_blknum} = Ethereumex.HttpClient.eth_block_number()
current_blknum = Encoding.to_int(current_blknum)

if current_blknum >= deposit_eth_blknum + finality_margin do
:ok
end
end

Sync.repeat_until_success(func, :infinity, "Waiting for deposit finality")
end

defp approve(contract, vault_address, account, value, gas_price) do
Expand Down
40 changes: 18 additions & 22 deletions priv/perf/apps/load_test/lib/child_chain/exit.ex
Original file line number Diff line number Diff line change
Expand Up @@ -25,12 +25,12 @@ defmodule LoadTest.ChildChain.Exit do
alias LoadTest.Ethereum
alias LoadTest.Ethereum.Account
alias LoadTest.Ethereum.Crypto
alias LoadTest.Service.Sync

@gas_start_exit 500_000
@gas_challenge_exit 300_000
@gas_add_exit_queue 800_000
@standard_exit_bond 14_000_000_000_000_000
@poll_interval 1_000

@doc """
Returns the exit data of a utxo.
Expand Down Expand Up @@ -63,21 +63,18 @@ defmodule LoadTest.ChildChain.Exit do
Retries until the exit data of a utxo is found.
"""
@spec wait_for_exit_data(Utxo.t(), pos_integer()) :: any()
def wait_for_exit_data(utxo_pos, counter \\ 10)
def wait_for_exit_data(_, 0), do: :error
def wait_for_exit_data(utxo_pos, timeout \\ 100_000) do
func = fn ->
data = get_exit_data(utxo_pos)

def wait_for_exit_data(utxo_pos, counter) do
data = get_exit_data(utxo_pos)
if not is_nil(data.proof) do
ayrat555 marked this conversation as resolved.
Show resolved Hide resolved
{:ok, data}
end
end

case data.proof do
nil ->
_ = Logger.info("Waiting for exit data")
Process.sleep(@poll_interval)
wait_for_exit_data(utxo_pos, counter - 1)
{:ok, result} = Sync.repeat_until_success(func, timeout, "waiting for exit data")

_ ->
data
end
result
end

@doc """
Expand Down Expand Up @@ -130,20 +127,19 @@ defmodule LoadTest.ChildChain.Exit do

{:ok, receipt_hash} = Ethereum.send_raw_transaction(tx, from)
Ethereum.transact_sync(receipt_hash)
wait_for_exit_queue(vault_id, token, 100)
wait_for_exit_queue(vault_id, token)
receipt_hash
end
end

defp wait_for_exit_queue(_vault_id, _token, 0), do: exit(1)

defp wait_for_exit_queue(vault_id, token, counter) do
if has_exit_queue?(vault_id, token) do
:ok
else
Process.sleep(1_000)
wait_for_exit_queue(vault_id, token, counter - 1)
defp wait_for_exit_queue(vault_id, token, timeout \\ 100_000) do
func = fn ->
if has_exit_queue?(vault_id, token) do
:ok
end
end

Sync.repeat_until_success(func, timeout, "waiting for exit queue")
end

defp has_exit_queue?(vault_id, token) do
Expand Down
30 changes: 12 additions & 18 deletions priv/perf/apps/load_test/lib/child_chain/transaction.ex
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,8 @@ defmodule LoadTest.ChildChain.Transaction do
alias ExPlasma.Transaction
alias ExPlasma.Utxo
alias LoadTest.Connection.ChildChain, as: Connection
alias LoadTest.Service.Sync

@retry_interval 1_000
# safe, reasonable amount, equal to the testnet block gas limit
@lots_of_gas 5_712_388
@gas_price 1_000_000_000
Expand All @@ -48,16 +48,16 @@ defmodule LoadTest.ChildChain.Transaction do
Utxo.address_binary(),
pos_integer()
) :: list(Utxo.t())
def spend_utxo(utxo, amount, fee, signer, receiver, currency, retries \\ 0)
def spend_utxo(utxo, amount, fee, signer, receiver, currency, retries \\ 120_000)

def spend_utxo(utxo, amount, fee, signer, receiver, currency, retries) when byte_size(currency) == 20 do
def spend_utxo(utxo, amount, fee, signer, receiver, currency, timeout) when byte_size(currency) == 20 do
change_amount = utxo.amount - amount - fee
receiver_output = %Utxo{owner: receiver.addr, currency: currency, amount: amount}
do_spend(utxo, receiver_output, change_amount, currency, signer, retries)
do_spend(utxo, receiver_output, change_amount, currency, signer, timeout)
end

def spend_utxo(utxo, amount, fee, signer, receiver, currency, retries) do
spend_utxo(utxo, amount, fee, signer, receiver, Encoding.to_binary(currency), retries)
def spend_utxo(utxo, amount, fee, signer, receiver, currency, timeout) do
spend_utxo(utxo, amount, fee, signer, receiver, Encoding.to_binary(currency), timeout)
end

def tx_defaults() do
Expand All @@ -77,7 +77,7 @@ defmodule LoadTest.ChildChain.Transaction do
list(LoadTest.Ethereum.Account.t()),
pos_integer()
) :: list(Utxo.t())
def submit_tx(inputs, outputs, signers, retries \\ 0) do
def submit_tx(inputs, outputs, signers, retries \\ 120_000) do
{:ok, tx} = Transaction.Payment.new(%{inputs: inputs, outputs: outputs})

keys =
Expand Down Expand Up @@ -204,17 +204,11 @@ defmodule LoadTest.ChildChain.Transaction do
defp parse_uint256(binary) when byte_size(binary) > 32, do: {:error, :encoded_uint_too_big}
defp parse_uint256(_), do: {:error, :malformed_uint256}

defp try_submit_tx(tx, 0), do: do_submit_tx(tx)
defp try_submit_tx(tx, timeout) do
{:ok, {blknum, txindex}} =
Sync.repeat_until_success(fn -> do_submit_tx(tx) end, timeout, "Failed to submit transaction")

defp try_submit_tx(tx, retries) do
case do_submit_tx(tx) do
{:error, "submit:utxo_not_found"} ->
Process.sleep(@retry_interval)
try_submit_tx(tx, retries - 1)

result ->
result
end
{:ok, blknum, txindex}
end

defp do_submit_tx(tx) do
Expand All @@ -230,7 +224,7 @@ defmodule LoadTest.ChildChain.Transaction do
|> case do
%{"blknum" => blknum, "txindex" => txindex} ->
_ = Logger.debug("[Transaction submitted successfully {#{inspect(blknum)}, #{inspect(txindex)}}")
{:ok, blknum, txindex}
{:ok, {blknum, txindex}}

%{"code" => reason} ->
_ =
Expand Down
18 changes: 9 additions & 9 deletions priv/perf/apps/load_test/lib/child_chain/utxos.ex
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,7 @@ defmodule LoadTest.ChildChain.Utxos do
alias ExPlasma.Encoding
alias ExPlasma.Utxo
alias LoadTest.ChildChain.Transaction

@poll_interval 2_000
alias LoadTest.Service.Sync

@doc """
Returns an addresses utxos.
Expand Down Expand Up @@ -107,18 +106,19 @@ defmodule LoadTest.ChildChain.Utxos do
Retries until the utxo is found.
"""
@spec wait_for_utxo(Utxo.address_binary(), Utxo.t(), pos_integer()) :: :ok
def wait_for_utxo(address, utxo, counter \\ 100)
def wait_for_utxo(_address, _utxo, 0), do: :error
def wait_for_utxo(address, utxo, timeout \\ 100_000) do
func = fn ->
find_utxo(address, utxo)
end

Sync.repeat_until_success(func, timeout, "waiting for utxo")
end

def wait_for_utxo(address, utxo, counter) do
defp find_utxo(address, utxo) do
utxos = get_utxos(address)

if Enum.find(utxos, fn x -> Utxo.pos(x) == Utxo.pos(utxo) end) do
:ok
else
_ = Logger.info("Waiting for utxo")
Process.sleep(@poll_interval)
wait_for_utxo(address, utxo, counter - 1)
end
end
end
10 changes: 8 additions & 2 deletions priv/perf/apps/load_test/lib/child_chain/watcher_sync.ex
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ defmodule LoadTest.ChildChain.WatcherSync do

require Logger

alias LoadTest.Ethereum.Sync
alias LoadTest.Service.Sync

@doc """
Blocks the caller until the watcher configured reports to be fully synced up (both child chain blocks and eth events)
Expand All @@ -35,7 +35,13 @@ defmodule LoadTest.ChildChain.WatcherSync do

_ = Logger.info("Waiting for the watcher to synchronize")

:ok = Sync.repeat_until_success(fn -> watcher_synchronized?(root_chain_height, service) end, 500_000)
:ok =
Sync.repeat_until_success(
fn -> watcher_synchronized?(root_chain_height, service) end,
500_000,
"Failed to sync watcher"
)

# NOTE: allowing some more time for the dust to settle on the synced Watcher
# otherwise some of the freshest UTXOs to exit will appear as missing on the Watcher
# related issue to remove this `sleep` and fix properly is https://github.com/omisego/elixir-omg/issues/1031
Expand Down
Loading