Skip to content

Commit 4ebb1a0

Browse files
committed
tests: add new tests for CIP145 behavior in cip_145_fix_test.py
1 parent e0a14a0 commit 4ebb1a0

File tree

3 files changed

+127
-8
lines changed

3 files changed

+127
-8
lines changed
Lines changed: 119 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,119 @@
1+
import pytest
2+
from typing import Type
3+
from integration_tests.test_framework.test_framework import FrameworkOptions
4+
from integration_tests.tests.conftest import ConfluxTestFramework
5+
from cfx_utils import CFX
6+
from conflux_web3 import Web3
7+
from web3.exceptions import Web3RPCError
8+
9+
10+
class CIP145BeforeFixTestEnv(ConfluxTestFramework):
11+
def set_test_params(self):
12+
self.num_nodes = 1
13+
self.conf_parameters["eoa_code_transition_height"] = 1
14+
self.conf_parameters["public_evm_rpc_apis"] = '"all"'
15+
self.conf_parameters["executive_trace"] = "true"
16+
17+
def setup_network(self):
18+
self.add_nodes(self.num_nodes)
19+
self.start_node(0, ["--archive"])
20+
21+
class CIP145AfterFixTestEnv(ConfluxTestFramework):
22+
def set_test_params(self):
23+
self.num_nodes = 1
24+
self.conf_parameters["cip145_fix_transition_height"] = 1
25+
self.conf_parameters["public_evm_rpc_apis"] = '"all"'
26+
self.conf_parameters["executive_trace"] = "true"
27+
28+
def setup_network(self):
29+
self.add_nodes(self.num_nodes)
30+
self.start_node(0, ["--archive"])
31+
32+
33+
# copied from integration_tests/tests/conftest.py to overide fixture scope
34+
@pytest.fixture
35+
def network(framework_class: Type[ConfluxTestFramework], port_min: int, additional_secrets: int, args: FrameworkOptions, request: pytest.FixtureRequest):
36+
try:
37+
framework = framework_class(port_min, additional_secrets, options=args)
38+
except Exception as e:
39+
pytest.fail(f"Failed to setup framework: {e}")
40+
yield framework
41+
framework.teardown(request)
42+
43+
@pytest.fixture
44+
def gas_sponsored_contract(network):
45+
contract = network.deploy_contract("Receivable")
46+
contract_address = contract.address
47+
sponsor_whitelist_control = network.internal_contract("SponsorWhitelistControl")
48+
49+
# contract_addr, upperbound
50+
sponsor_whitelist_control.functions.setSponsorForGas(contract_address, 10 ** 9).transact({
51+
"value": CFX(1)
52+
}).executed()
53+
sponsor_whitelist_control.functions.addPrivilegeByAdmin(contract_address, [network.cw3.address.zero_address()]).transact().executed()
54+
return contract
55+
56+
def fund_new_account(cw3: Web3, value: int):
57+
account = cw3.cfx.account.create()
58+
cw3.wallet.add_account(account)
59+
cw3.cfx.send_transaction({
60+
"value": value,
61+
"to": account.address,
62+
}).executed()
63+
return account
64+
65+
@pytest.mark.parametrize("framework_class", [CIP145BeforeFixTestEnv, CIP145AfterFixTestEnv])
66+
def test_value_enough_behaviour(network, cw3, gas_sponsored_contract):
67+
network.client.generate_blocks_to_state()
68+
assert network.internal_contract("SponsorWhitelistControl").functions.isAllWhitelisted(gas_sponsored_contract.address).call()
69+
sender = fund_new_account(cw3, 100000)
70+
71+
raw_tx = sender.sign_transaction({
72+
"to": gas_sponsored_contract.address,
73+
"value": 100000,
74+
"from": sender.address,
75+
"chainId": network.cw3.cfx.chain_id,
76+
"gas": 30000,
77+
"gasPrice": 1,
78+
"storageLimit": 0,
79+
"epochHeight": 10,
80+
"nonce": 0,
81+
})
82+
receipt = cw3.cfx.send_raw_transaction(raw_tx.raw_transaction).executed()
83+
assert receipt["gasCoveredBySponsor"]
84+
85+
@pytest.mark.parametrize("framework_class", [CIP145BeforeFixTestEnv, CIP145AfterFixTestEnv])
86+
def test_cip145_activated_behaviour(network, cw3, gas_sponsored_contract):
87+
# ensure hardfork transition number
88+
network.client.generate_blocks_to_state()
89+
assert network.internal_contract("SponsorWhitelistControl").functions.isAllWhitelisted(gas_sponsored_contract.address).call()
90+
sender = fund_new_account(cw3, 100000)
91+
92+
raw_tx = sender.sign_transaction({
93+
"to": gas_sponsored_contract.address,
94+
"value": 100001,
95+
"from": sender.address,
96+
"chainId": network.cw3.cfx.chain_id,
97+
"gas": 30000,
98+
"gasPrice": 1,
99+
"storageLimit": 0,
100+
"epochHeight": 10,
101+
"nonce": 0,
102+
})
103+
with pytest.raises(Web3RPCError) as e:
104+
cw3.cfx.send_raw_transaction(raw_tx.raw_transaction)
105+
assert "is discarded due to out of balance, needs 100001 but account balance is 100000" in e.value.message
106+
107+
latest_block = network.cw3.cfx.get_block("latest_mined")
108+
new_block_hash = network.client.generate_custom_block(latest_block["hash"].to_0x_hex(), [], [raw_tx])
109+
parent_block = new_block_hash
110+
for _ in range(10):
111+
parent_block = network.client.generate_block_with_parent(parent_block, num_txs=1)
112+
113+
transaction_hash = raw_tx.hash
114+
transaction_receipt = network.cw3.cfx.get_transaction_receipt(transaction_hash)
115+
assert transaction_receipt["txExecErrorMsg"]== 'NotEnoughCash { required: 100001, got: 100000, actual_gas_cost: 30000, max_storage_limit_cost: 0 }'
116+
assert not transaction_receipt["gasCoveredBySponsor"]
117+
118+
119+

integration_tests/tests/conftest.py

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -154,32 +154,32 @@ def port_min(worker_id: str) -> int:
154154
index = int(worker_id.split("gw")[1]) if "gw" in worker_id else 0
155155
return PORT_MIN + index * PORT_RANGE
156156

157-
@pytest.fixture(scope="module")
157+
@pytest.fixture
158158
def additional_secrets():
159159
return 0
160160

161-
@pytest.fixture(scope="module")
161+
@pytest.fixture
162162
def cw3(network: ConfluxTestFramework):
163163
return network.cw3
164164

165-
@pytest.fixture(scope="module")
165+
@pytest.fixture
166166
def ew3(network: ConfluxTestFramework):
167167
return network.ew3
168168

169-
@pytest.fixture(scope="module")
169+
@pytest.fixture
170170
def ew3_tracing(ew3):
171171
tracing: 'Tracing' = ew3.tracing
172172
return tracing
173173

174-
@pytest.fixture(scope="module")
174+
@pytest.fixture
175175
def core_accounts(network: ConfluxTestFramework):
176176
return network.core_accounts
177177

178-
@pytest.fixture(scope="module")
178+
@pytest.fixture
179179
def evm_accounts(network: ConfluxTestFramework):
180180
return network.evm_accounts
181181

182-
@pytest.fixture(scope="module")
182+
@pytest.fixture
183183
def internal_contracts(network: ConfluxTestFramework):
184184
return {
185185
"AdminControl": network.internal_contract("AdminControl"),

0 commit comments

Comments
 (0)