diff --git a/packages/valory/skills/decision_maker_abci/behaviours/base.py b/packages/valory/skills/decision_maker_abci/behaviours/base.py index 12b5f921..e2ea9c28 100644 --- a/packages/valory/skills/decision_maker_abci/behaviours/base.py +++ b/packages/valory/skills/decision_maker_abci/behaviours/base.py @@ -355,12 +355,14 @@ def check_balance(self) -> WaitableConditionType: def update_bet_transaction_information(self) -> None: """Get whether the bet's invested amount should be updated.""" sampled_bet = self.sampled_bet - # Update the bet's invested amount, the new bet amount is added to previously invested amount - sampled_bet.invested_amount += self.synchronized_data.bet_amount + + # Update the bet's invested amount + updated = sampled_bet.update_investments(self.synchronized_data.bet_amount) + if not updated: + self.context.logger.error("Could not update the investments!") + # Update bet transaction timestamp sampled_bet.processed_timestamp = self.synced_timestamp - # update no of bets made - sampled_bet.n_bets += 1 # Update Queue number for priority logic sampled_bet.queue_status = sampled_bet.queue_status.next_status() diff --git a/packages/valory/skills/decision_maker_abci/behaviours/decision_receive.py b/packages/valory/skills/decision_maker_abci/behaviours/decision_receive.py index 5ad86dec..596e63e3 100644 --- a/packages/valory/skills/decision_maker_abci/behaviours/decision_receive.py +++ b/packages/valory/skills/decision_maker_abci/behaviours/decision_receive.py @@ -518,8 +518,6 @@ def _update_selected_bet( self.context.logger.info( f"with the timestamp:{datetime.fromtimestamp(active_sampled_bet.processed_timestamp)}" ) - if prediction_response is not None: - active_sampled_bet.n_bets += 1 self.store_bets() diff --git a/packages/valory/skills/market_manager_abci/bets.py b/packages/valory/skills/market_manager_abci/bets.py index df19d206..5bf14ebb 100644 --- a/packages/valory/skills/market_manager_abci/bets.py +++ b/packages/valory/skills/market_manager_abci/bets.py @@ -28,6 +28,8 @@ from typing import Any, Dict, List, Optional, Union +YES = "yes" +NO = "no" P_YES_FIELD = "p_yes" P_NO_FIELD = "p_no" CONFIDENCE_FIELD = "confidence" @@ -136,18 +138,59 @@ class Bet: prediction_response: PredictionResponse = dataclasses.field( default_factory=get_default_prediction_response ) - invested_amount: int = 0 position_liquidity: int = 0 potential_net_profit: int = 0 processed_timestamp: int = 0 - n_bets: int = 0 queue_status: QueueStatus = QueueStatus.FRESH + # a mapping from vote to investment amounts + investments: Dict[str, List[int]] = dataclasses.field(default_factory=dict) + + @property + def yes_investments(self) -> List[int]: + """Get the yes investments.""" + return self.investments[self.yes] + + @property + def no_investments(self) -> List[int]: + """Get the no investments.""" + return self.investments[self.no] + + @property + def n_yes_bets(self) -> int: + """Get the number of yes bets.""" + return len(self.yes_investments) + + @property + def n_no_bets(self) -> int: + """Get the number of no bets.""" + return len(self.no_investments) + + @property + def n_bets(self) -> int: + """Get the number of bets.""" + return self.n_yes_bets + self.n_no_bets + + @property + def invested_amount_yes(self) -> int: + """Get the amount invested in yes bets.""" + return sum(self.yes_investments) + + @property + def invested_amount_no(self) -> int: + """Get the amount invested in no bets.""" + return sum(self.no_investments) + + @property + def invested_amount(self) -> int: + """Get the amount invested in bets.""" + return self.invested_amount_yes + self.invested_amount_no def __post_init__(self) -> None: """Post initialization to adjust the values.""" self._validate() self._cast() self._check_usefulness() + self.investments = {self.yes: [], self.no: []} def __lt__(self, other: "Bet") -> bool: """Implements less than operator.""" @@ -225,7 +268,7 @@ def _get_binary_outcome(self, no: bool) -> str: """Get an outcome only if it is binary.""" if self.outcomeSlotCount == BINARY_N_SLOTS: return self.get_outcome(int(no)) - requested_outcome = "no" if no else "yes" + requested_outcome = NO if no else YES error = ( f"A {requested_outcome!r} outcome is only available for binary questions." ) @@ -241,6 +284,17 @@ def no(self) -> str: """Return the "no" outcome.""" return self._get_binary_outcome(True) + def update_investments(self, amount: int) -> bool: + """Get the investments for the current vote type.""" + vote = self.prediction_response.vote + if vote is None: + return False + + vote_name = self.get_outcome(vote) + to_update = self.investments[vote_name] + to_update.append(amount) + return True + def update_market_info(self, bet: "Bet") -> None: """Update the bet's market information.""" if (