mirror of https://github.com/nucypher/nucypher.git
Fixes staking and locking client methods, concise test narrative for miners.
parent
9972063ef1
commit
e6f212a1cc
|
@ -152,14 +152,15 @@ class Miner(TokenActor):
|
|||
def collect_staking_reward(self) -> str:
|
||||
"""Withdraw tokens rewarded for staking."""
|
||||
|
||||
token_amount_bytes = self.miner_agent.contract.functions.getMinerInfo(self.miner_agent.MinerInfo.VALUE.value,
|
||||
self.address, 0).call()
|
||||
token_amount_bytes = self.miner_agent.contract.functions.minerInfo(self.address).call()[0]
|
||||
token_amount = self.blockchain.provider.w3.toInt(token_amount_bytes)
|
||||
|
||||
token_amount = self.blockchain._chain.web3.toInt(token_amount_bytes)
|
||||
collection_txhash = self.miner_agent.contract.functions.withdraw(token_amount).transact({'from': self.address})
|
||||
|
||||
# reward_amount = TODO
|
||||
self.blockchain.wait_for_receipt(collection_txhash)
|
||||
self._transactions.append((datetime.utcnow(), collection_txhash))
|
||||
|
||||
reward_txhash = self.miner_agent.contract.functions.withdraw(token_amount).transact({'from': self.address})
|
||||
return collection_txhash
|
||||
|
||||
def __validate_stake(self, amount: int, periods: int) -> bool:
|
||||
|
||||
|
@ -171,7 +172,7 @@ class Miner(TokenActor):
|
|||
else:
|
||||
return True
|
||||
|
||||
def stake(self, amount, locktime, entire_balance=False):
|
||||
def stake(self, amount, periods, entire_balance=False):
|
||||
"""
|
||||
High level staking method for Miners.
|
||||
"""
|
||||
|
@ -182,9 +183,9 @@ class Miner(TokenActor):
|
|||
raise self.StakingError("Specify an amount or entire balance, not both")
|
||||
|
||||
if entire_balance is True:
|
||||
balance_bytes = self.miner_agent.contract.functions.getMinerInfo(self.miner_agent.MinerInfo.VALUE.value,
|
||||
self.address, 0).call()
|
||||
amount = self.blockchain._chain.web3.toInt(balance_bytes)
|
||||
amount = self.miner_agent.contract.functions.getMinerInfo(self.miner_agent.MinerInfo.VALUE.value,
|
||||
self.address, 0).call()
|
||||
amount = self.blockchain.provider.w3.toInt(amount)
|
||||
|
||||
assert self.__validate_stake(amount=amount, periods=periods)
|
||||
|
||||
|
|
|
@ -5,92 +5,53 @@ from nucypher.blockchain.eth.actors import Miner
|
|||
from nucypher.blockchain.eth.agents import MinerAgent
|
||||
|
||||
|
||||
@pytest.mark.skip("Last 5 stubborn blockchain tests.")
|
||||
def test_miner_locking_tokens(chain, token_agent, mock_token_deployer, mock_miner_agent):
|
||||
@pytest.fixture(scope='module')
|
||||
def miner(chain, mock_token_agent, mock_miner_agent):
|
||||
mock_token_agent.token_airdrop(amount=100000 * mock_token_agent._M)
|
||||
_origin, ursula, *everybody_else = chain.provider.w3.eth.accounts
|
||||
miner = Miner(miner_agent=mock_miner_agent, address=ursula)
|
||||
return miner
|
||||
|
||||
chain._token_airdrop(token_agent=token_agent, amount=10000)
|
||||
|
||||
miner = Miner(miner_agent=mock_miner_agent, address=chain.provider.w3.eth.accounts[1])
|
||||
def test_miner_locking_tokens(chain, miner, mock_miner_agent):
|
||||
|
||||
an_amount_of_tokens = 1000 * mock_token_deployer._M
|
||||
miner.stake(amount=an_amount_of_tokens, locktime=mock_miner_agent._deployer._min_locked_periods)
|
||||
assert mock_miner_agent.min_allowed_locked < miner.token_balance(), "Insufficient miner balance"
|
||||
|
||||
# Verify that the escrow is allowed to receive tokens
|
||||
miner.stake(amount=mock_miner_agent.min_allowed_locked, # Lock the minimum amount of tokens
|
||||
periods=mock_miner_agent.min_locked_periods) # ... for the fewest number of periods
|
||||
|
||||
# Verify that the escrow is "approved" to receive tokens
|
||||
assert mock_miner_agent.token_agent.contract.functions.allowance(miner.address, mock_miner_agent.contract_address).call() == 0
|
||||
|
||||
# Stake starts after one period
|
||||
assert miner.token_balance() == 0
|
||||
# Staking starts after one period
|
||||
assert mock_miner_agent.contract.functions.getLockedTokens(miner.address).call() == 0
|
||||
|
||||
# Wait for it...
|
||||
chain.time_travel(mock_miner_agent._deployer._hours_per_period)
|
||||
|
||||
assert mock_miner_agent.contract.functions.getLockedTokens(miner.address).call() == an_amount_of_tokens
|
||||
chain.time_travel(periods=1)
|
||||
assert mock_miner_agent.contract.functions.getLockedTokens(miner.address).call() == mock_miner_agent.min_allowed_locked
|
||||
|
||||
|
||||
@pytest.mark.skip("Last 5 stubborn blockchain tests.")
|
||||
def test_mine_then_withdraw_tokens(chain, mock_token_deployer, token_agent, mock_miner_agent, mock_miner_escrow_deployer):
|
||||
"""
|
||||
- Airdrop tokens to everyone
|
||||
- Create a Miner (Ursula)
|
||||
- Spawn additional miners
|
||||
- All miners lock tokens
|
||||
- Wait (with time)
|
||||
- Miner (Ursula) mints new tokens
|
||||
"""
|
||||
def test_miner_collects_staking_reward_tokens(chain, miner, mock_token_agent, mock_miner_agent):
|
||||
|
||||
_origin, *everybody = chain.provider.w3.eth.accounts
|
||||
|
||||
ursula_address, *everyone_else = everybody
|
||||
|
||||
miner = Miner(miner_agent=mock_miner_agent, address=ursula_address)
|
||||
|
||||
# Miner has no locked tokens
|
||||
assert miner.locked_tokens == 0
|
||||
|
||||
# Capture the initial token balance of the miner
|
||||
# Capture the current token balance of the miner
|
||||
initial_balance = miner.token_balance()
|
||||
assert token_agent.get_balance(miner.address) == miner.token_balance()
|
||||
|
||||
# Stake a random amount of tokens
|
||||
# stake_amount = (10 + random.randrange(9000)) * mock_token_deployer._M
|
||||
half_of_stake = initial_balance // 2
|
||||
|
||||
miner.stake(amount=half_of_stake, locktime=1)
|
||||
|
||||
# Ensure the miner has the right amount of staked tokens
|
||||
assert miner.locked_tokens == half_of_stake
|
||||
|
||||
# Ensure the MinerEscrow contract is allowed to receive tokens form Alice
|
||||
# assert miner.token_agent.contract.functions.allowance(miner.address, miner.miner_agent.contract_address).call() == half_of_stake
|
||||
|
||||
# Blockchain staking starts after one period
|
||||
# assert mock_miner_agent.contract.functions.getAllLockedTokens().call() == 0
|
||||
|
||||
# Wait for it...
|
||||
# chain.wait_time(2)
|
||||
assert mock_token_agent.get_balance(miner.address) == miner.token_balance()
|
||||
|
||||
# Have other address lock tokens
|
||||
chain.spawn_miners(miner_agent=mock_miner_agent,
|
||||
addresses=everyone_else,
|
||||
locktime=1,
|
||||
m=mock_token_deployer._M)
|
||||
|
||||
# The miner starts unlocking periods...
|
||||
_origin, ursula, *everybody_else = chain.provider.w3.eth.accounts
|
||||
mock_miner_agent.spawn_random_miners(addresses=everybody_else)
|
||||
|
||||
# ...wait out the lock period...
|
||||
for _ in range(28):
|
||||
chain.time_travel(periods=1)
|
||||
miner.confirm_activity()
|
||||
|
||||
# ...wait more...
|
||||
chain.time_travel(mock_miner_agent._deployer._hours_per_period)
|
||||
|
||||
# miner.confirm_activity()
|
||||
|
||||
# ...wait more...
|
||||
chain.time_travel(mock_miner_agent._deployer._hours_per_period)
|
||||
|
||||
chain.time_travel(periods=2)
|
||||
miner.mint()
|
||||
miner.collect_staking_reward()
|
||||
|
||||
final_balance = token_agent.get_balance(miner.address)
|
||||
final_balance = mock_token_agent.get_balance(miner.address)
|
||||
assert final_balance > initial_balance
|
||||
|
||||
|
||||
|
|
Loading…
Reference in New Issue