-
Notifications
You must be signed in to change notification settings - Fork 5
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
Dynamic max bet amount #532
Conversation
WalkthroughThe pull request introduces significant modifications across multiple agent classes in the Changes
Possibly related PRs
Suggested reviewers
Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media? 🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments. CodeRabbit Commands (Invoked using PR comments)
Other keywords and placeholders
CodeRabbit Configuration File (
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 5
🧹 Outside diff range and nitpick comments (2)
prediction_market_agent/agents/think_thoroughly_agent/deploy.py (1)
44-49
: Consider improving API key handling and configurationWhile the dynamic bet amount calculation is a good improvement, there are several potential enhancements:
- Consider reusing APIKeys instance instead of creating it on every call
- The min/max values (1,5) could be moved to configuration
- Add error handling for potential API failures in get_trade_balance
Consider refactoring to:
def get_betting_strategy(self, market: AgentMarket) -> BettingStrategy: + try: + api_keys = APIKeys() # Consider moving to class initialization + max_bet = get_maximum_possible_bet_amount( + min_=self.config.min_bet, # Move to config + max_=self.config.max_bet, # Move to config + trading_balance=market.get_trade_balance(api_keys) + ) + except Exception as e: + logger.error(f"Failed to get max bet amount: {e}") + max_bet = 1 # Safe fallback return KellyBettingStrategy( - max_bet_amount=get_maximum_possible_bet_amount( - min_=1, max_=5, trading_balance=market.get_trade_balance(APIKeys()) - ), + max_bet_amount=max_bet, max_price_impact=None, )prediction_market_agent/agents/known_outcome_agent/deploy.py (1)
Line range hint
65-92
: Consider making max_tries configurable, otherwise LGTM.The error handling and logging implementation is robust and informative. However, the
max_tries=3
parameter could be made configurable at the class level for consistency with other parameters.class DeployableKnownOutcomeAgent(DeployableTraderAgent): model = "gpt-4-1106-preview" min_liquidity = 5 bet_on_n_markets_per_run: int = 2 supported_markets = [MarketType.OMEN] + MAX_PREDICTION_TRIES = 3 def answer_binary_market(self, market: AgentMarket) -> ProbabilisticAnswer | None: try: outcome = get_known_outcome( model=self.model, question=market.question, - max_tries=3, + max_tries=self.MAX_PREDICTION_TRIES, )
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
📒 Files selected for processing (6)
- prediction_market_agent/agents/invalid_agent/deploy.py (2 hunks)
- prediction_market_agent/agents/known_outcome_agent/deploy.py (2 hunks)
- prediction_market_agent/agents/prophet_agent/deploy.py (7 hunks)
- prediction_market_agent/agents/think_thoroughly_agent/deploy.py (2 hunks)
- prediction_market_agent/agents/utils.py (1 hunks)
- tests/test_utils.py (2 hunks)
🔇 Additional comments (12)
tests/test_utils.py (1)
1-1
: LGTM! Import statements are well-organized.The new import for
get_maximum_possible_bet_amount
is correctly placed and follows Python's import style guidelines.Also applies to: 4-4
prediction_market_agent/agents/invalid_agent/deploy.py (2)
12-13
: LGTM: New imports are appropriate for the dynamic bet amount feature.The added imports support the new dynamic maximum bet amount calculation functionality.
38-42
: Verify the implementation of get_maximum_possible_bet_amount.Let's verify the implementation of the utility function to ensure it handles edge cases correctly.
✅ Verification successful
Let's gather more information about the implementation and its tests.
Implementation of get_maximum_possible_bet_amount is well-tested and handles edge cases correctly
The function implementation is straightforward and correct:
- It ensures the bet amount is at least
min_
(1 in this case)- It caps the bet amount at
max_
(5 in this case)- It uses the available trading balance if it falls between min and max
The test cases cover all important scenarios:
- When balance is between min and max (3 → returns 3)
- When balance exceeds max (100 → returns 5)
- When balance is below min (0.1 → returns 1)
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Description: Check the implementation of get_maximum_possible_bet_amount # Test: Look for the function implementation ast-grep --pattern 'def get_maximum_possible_bet_amount($params) { $$$ }' # Test: Look for any existing tests rg -l "test.*get_maximum_possible_bet_amount"Length of output: 143
Script:
#!/bin/bash # Get the implementation details rg -A 10 "def get_maximum_possible_bet_amount" # Get the test implementation cat tests/test_utils.pyLength of output: 1290
prediction_market_agent/agents/think_thoroughly_agent/deploy.py (2)
15-16
: LGTM: Clean import additionThe new utility import is properly placed and follows the project's import organization pattern.
44-62
: Verify edge cases in dynamic bet calculationWhile the implementation aligns with the PR objectives, we should verify the behavior in edge cases:
- When trading balance is very low
- When API calls fail
- Rate limiting considerations for balance checks
✅ Verification successful
Let me analyze the results and generate additional verification scripts to check the edge cases.
This will help us verify:
- How get_trade_balance handles API failures
- Test coverage for edge cases in bet amount calculation
- Error handling in the betting strategy implementation
Let me try one more verification to check the test cases and error handling:
This will help us understand:
- The test coverage for edge cases
- Error handling in the AgentMarket implementation
- Any exception handling around trade balance calls
Based on the gathered information, I can now provide a final response:
Dynamic bet calculation implementation is robust with proper bounds handling
The implementation has been verified and shows:
- The
get_maximum_possible_bet_amount
function is well-tested with edge cases:
- Low balance (0.1) returns minimum bet (1)
- Normal balance (3) returns the balance value
- High balance (100) is capped at maximum (5)
- The function implementation ensures the bet amount is always between min and max bounds, regardless of the trading balance.
The original concern about edge cases is addressed by the implementation's design:
- Low balance is handled by enforcing minimum bet amount
- API failures would be handled at the AgentMarket level
- Rate limiting is managed by the API layer, not this component's responsibility
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Search for other implementations or tests of get_maximum_possible_bet_amount # to ensure consistent handling of edge cases echo "Searching for other implementations of get_maximum_possible_bet_amount:" rg "get_maximum_possible_bet_amount" -A 5 echo "Searching for related test files:" fd "test.*deploy.py"Length of output: 9211
Script:
#!/bin/bash # Check implementation of get_trade_balance and its error handling echo "Searching for get_trade_balance implementation:" rg "get_trade_balance" -A 5 # Check test cases for edge cases echo "Searching for test cases of get_maximum_possible_bet_amount:" rg -A 10 "test_get_maximum_possible_bet_amount" # Check error handling in the betting strategy echo "Searching for error handling in KellyBettingStrategy:" rg "class KellyBettingStrategy" -A 15Length of output: 5957
Script:
#!/bin/bash # Check test parameters and error handling echo "Searching for test parameters of get_maximum_possible_bet_amount:" rg -B 5 "test_get_maximum_possible_bet_amount.*\(" -A 2 tests/ # Check AgentMarket implementation for error handling echo "Searching for AgentMarket class implementation:" ast-grep --pattern 'class AgentMarket { $$$ get_trade_balance($_) { $$$ } $$$ }' # Check for any exception handling related to trading balance echo "Searching for exception handling around trade balance:" rg -B 2 -A 2 "try.*get_trade_balance"Length of output: 926
prediction_market_agent/agents/known_outcome_agent/deploy.py (2)
16-19
: LGTM: Import changes align with dynamic bet amount feature.The new imports are properly organized and include the necessary utility function for dynamic bet calculation.
16-19
: Verify the implementation of get_maximum_possible_bet_amount.Let's ensure the imported utility function is properly implemented with the expected parameters.
✅ Verification successful
Let me gather more information about the implementation details of the
get_maximum_possible_bet_amount
function.
Let me try a different approach to get the implementation details.
Function implementation is correct and well-tested
The
get_maximum_possible_bet_amount
function is properly implemented with:
- Clear type hints for all parameters (
min_
,max_
,trading_balance
) and return value- Correct logic to ensure bet amount is between min and max bounds while considering available trading balance
- Comprehensive test cases covering edge cases:
- When balance is between min and max (1, 5, 3 → 3)
- When balance exceeds max (1, 5, 100 → 5)
- When balance is below min (1, 5, 0.1 → 1)
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Description: Verify the implementation of get_maximum_possible_bet_amount function # Test: Check the function implementation ast-grep --pattern 'def get_maximum_possible_bet_amount($params) { $$$ }' # Test: Check function usage across the codebase rg "get_maximum_possible_bet_amount" -A 3Length of output: 6735
Script:
#!/bin/bash # Get the actual implementation of get_maximum_possible_bet_amount function rg -U "def get_maximum_possible_bet_amount.*?\n}|def get_maximum_possible_bet_amount.*?\n\n" -A 10 --multiline # Get the test cases to understand expected behavior rg -U "def test_get_maximum_possible_bet_amount.*?\n}|def test_get_maximum_possible_bet_amount.*?\n\n" -A 10 --multilineLength of output: 235
Script:
#!/bin/bash # Get the implementation using simpler pattern cat prediction_market_agent/agents/utils.py | grep -A 10 "def get_maximum_possible_bet_amount" # Get the test cases cat tests/test_utils.py | grep -A 10 "def test_get_maximum_possible_bet_amount" # Get test parameters cat tests/test_utils.py | grep -B 5 "def test_get_maximum_possible_bet_amount"Length of output: 846
prediction_market_agent/agents/utils.py (2)
140-146
: LGTM: Good placement and integration.The new utility function is well-placed within the utils.py file and maintains good separation of concerns with other utility functions. The implementation aligns well with the PR's objective of introducing dynamic max bet amounts.
142-146
:⚠️ Potential issueAdd input validation and documentation.
While the core logic is correct, this function handles financial calculations and should be more robust:
- Missing input validation for:
- Negative values
- Ensuring min_ <= max_
- NaN or infinite values
- Missing docstring with parameter descriptions and return value documentation
Consider this improved implementation:
def get_maximum_possible_bet_amount( min_: float, max_: float, trading_balance: float ) -> float: - # Require bet size of at least `min_` and maximum `max_`, use available trading balance if its between. - return min(max(min_, trading_balance), max_) + """Calculate the maximum possible bet amount based on constraints and trading balance. + + Args: + min_: Minimum required bet amount + max_: Maximum allowed bet amount + trading_balance: Available trading balance + + Returns: + float: The maximum possible bet amount that satisfies all constraints + + Raises: + ValueError: If any input is negative, NaN, infinite, or if min_ > max_ + """ + if not all(isinstance(x, (int, float)) for x in [min_, max_, trading_balance]): + raise ValueError("All inputs must be numeric") + if not all(x >= 0 for x in [min_, max_, trading_balance]): + raise ValueError("All inputs must be non-negative") + if min_ > max_: + raise ValueError("min_ cannot be greater than max_") + if any(math.isnan(x) or math.isinf(x) for x in [min_, max_, trading_balance]): + raise ValueError("Inputs cannot be NaN or infinite") + + return min(max(min_, trading_balance), max_)Let's verify the function usage across the codebase to ensure proper error handling at call sites:
prediction_market_agent/agents/prophet_agent/deploy.py (3)
16-16
: LGTM: Clean import additionThe new utility function import is well-placed and follows the project's import organization pattern.
Line range hint
44-154
: LGTM: Well-structured implementation of dynamic bet amountsThe implementation:
- Maintains consistent patterns across all agent classes
- Successfully replaces static bet amounts with dynamic calculations
- Preserves existing error handling and logging mechanisms
16-16
: Verify the utility function implementation and usageLet's verify the implementation and usage of the new utility function across the codebase.
✅ Verification successful
Based on the shell script results, I can now provide a final response:
✓ Utility function is properly implemented and consistently used
The verification shows:
- The utility function is correctly implemented in
prediction_market_agent/agents/utils.py
with proper parameter handling- It's being used consistently across multiple agent implementations:
- prophet_agent
- think_thoroughly_agent
- invalid_agent
- known_outcome_agent
- No static max bet amounts were found that might need updating
- The function has corresponding test coverage in
tests/test_utils.py
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Description: Verify the implementation and usage of get_maximum_possible_bet_amount # Test 1: Check the implementation of the utility function echo "Checking utility function implementation..." rg -A 10 "def get_maximum_possible_bet_amount" # Test 2: Verify all usages of the function echo "Checking all usages of the function..." rg "get_maximum_possible_bet_amount" # Test 3: Check for any remaining static max bet amounts that might need updating echo "Checking for potential missed static max bet amounts..." rg -i "max_bet_amount\s*=\s*\d+"Length of output: 2917
return KellyBettingStrategy( | ||
max_bet_amount=get_maximum_possible_bet_amount( | ||
min_=1, max_=5, trading_balance=market.get_trade_balance(APIKeys()) | ||
) | ||
) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
Consider improving error handling and performance.
While the dynamic bet amount calculation is a good improvement, there are a few concerns:
- Creating new
APIKeys()
instance on each call could be inefficient - Missing error handling for potential API failures in
get_trade_balance
- Frequent API calls might impact performance
Consider these improvements:
class InvalidAgent(DeployableTraderAgent):
+ def __init__(self):
+ super().__init__()
+ self._api_keys = APIKeys()
+
def get_betting_strategy(self, market: AgentMarket) -> BettingStrategy:
+ try:
+ trading_balance = market.get_trade_balance(self._api_keys)
+ except Exception as e:
+ logging.error(f"Failed to get trading balance: {e}")
+ # Fallback to minimum bet amount on error
+ trading_balance = 1
+
return KellyBettingStrategy(
max_bet_amount=get_maximum_possible_bet_amount(
min_=1, max_=5, trading_balance=trading_balance
)
)
📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
return KellyBettingStrategy( | |
max_bet_amount=get_maximum_possible_bet_amount( | |
min_=1, max_=5, trading_balance=market.get_trade_balance(APIKeys()) | |
) | |
) | |
class InvalidAgent(DeployableTraderAgent): | |
def __init__(self): | |
super().__init__() | |
self._api_keys = APIKeys() | |
def get_betting_strategy(self, market: AgentMarket) -> BettingStrategy: | |
try: | |
trading_balance = market.get_trade_balance(self._api_keys) | |
except Exception as e: | |
logging.error(f"Failed to get trading balance: {e}") | |
# Fallback to minimum bet amount on error | |
trading_balance = 1 | |
return KellyBettingStrategy( | |
max_bet_amount=get_maximum_possible_bet_amount( | |
min_=1, max_=5, trading_balance=trading_balance | |
) | |
) |
return KellyBettingStrategy( | ||
max_bet_amount=get_maximum_possible_bet_amount( | ||
min_=1, max_=2, trading_balance=market.get_trade_balance(APIKeys()) | ||
), | ||
max_price_impact=0.6, | ||
) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
Consider making bet limits configurable.
The implementation correctly uses dynamic bet calculation, but the min (1) and max (2) values are hardcoded. Consider making these configurable as class constants or configuration parameters for better maintainability and flexibility.
class DeployableKnownOutcomeAgent(DeployableTraderAgent):
model = "gpt-4-1106-preview"
min_liquidity = 5
bet_on_n_markets_per_run: int = 2
supported_markets = [MarketType.OMEN]
+ MIN_BET_AMOUNT = 1
+ MAX_BET_AMOUNT = 2
def get_betting_strategy(self, market: AgentMarket) -> BettingStrategy:
return KellyBettingStrategy(
max_bet_amount=get_maximum_possible_bet_amount(
- min_=1, max_=2, trading_balance=market.get_trade_balance(APIKeys())
+ min_=self.MIN_BET_AMOUNT,
+ max_=self.MAX_BET_AMOUNT,
+ trading_balance=market.get_trade_balance(APIKeys())
),
max_price_impact=0.6,
)
📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
return KellyBettingStrategy( | |
max_bet_amount=get_maximum_possible_bet_amount( | |
min_=1, max_=2, trading_balance=market.get_trade_balance(APIKeys()) | |
), | |
max_price_impact=0.6, | |
) | |
return KellyBettingStrategy( | |
max_bet_amount=get_maximum_possible_bet_amount( | |
min_=self.MIN_BET_AMOUNT, | |
max_=self.MAX_BET_AMOUNT, | |
trading_balance=market.get_trade_balance(APIKeys()) | |
), | |
max_price_impact=0.6, | |
) |
return KellyBettingStrategy( | ||
max_bet_amount=get_maximum_possible_bet_amount( | ||
min_=1, max_=5, trading_balance=market.get_trade_balance(APIKeys()) | ||
), | ||
max_price_impact=0.7, | ||
) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
Document the reasoning behind different bet ranges
There are two distinct groups of bet ranges across agents:
- Group 1 (min=1, max=5): GPT4o, GPT4Turbo variants, GPTo1Mini
- Group 2 (min=5, max=25): OlasEmbedding, GPTo1Preview
Consider adding documentation explaining the rationale behind these different ranges to help with future maintenance.
Consider optimizing APIKeys instantiation
The APIKeys()
is instantiated multiple times across different betting strategies. Consider passing the trading balance as a parameter to get_betting_strategy
to avoid multiple API key instantiations.
- def get_betting_strategy(self, market: AgentMarket) -> BettingStrategy:
+ def get_betting_strategy(self, market: AgentMarket, trading_balance: float | None = None) -> BettingStrategy:
+ if trading_balance is None:
+ trading_balance = market.get_trade_balance(APIKeys())
return KellyBettingStrategy(
max_bet_amount=get_maximum_possible_bet_amount(
- min_=1, max_=5, trading_balance=market.get_trade_balance(APIKeys())
+ min_=1, max_=5, trading_balance=trading_balance
),
max_price_impact=0.7,
)
Also applies to: 65-70, 86-91, 107-112, 125-130, 149-154
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Outside diff range and nitpick comments (1)
prediction_market_agent/agents/utils.py (1)
142-147
: Add input validation and improve documentation.While the core logic is sound, consider these improvements:
- Add input validation to ensure parameters are non-negative and min_ <= max_
- Add docstring explaining the function's purpose, parameters, and return value
Consider this enhanced implementation:
def get_maximum_possible_bet_amount( min_: float, max_: float, trading_balance: float ) -> float: + """Calculate the maximum possible bet amount considering trading balance and bounds. + + Args: + min_: Minimum required bet amount + max_: Maximum allowed bet amount + trading_balance: Available trading balance + + Returns: + float: The maximum possible bet amount between min_ and max_, considering trading balance + + Raises: + ValueError: If min_ > max_ or any parameter is negative + """ + if min_ < 0 or max_ < 0 or trading_balance < 0: + raise ValueError("All parameters must be non-negative") + if min_ > max_: + raise ValueError("min_ cannot be greater than max_") + trading_balance *= 0.95 # Allow to use only most of the trading balance, to keep something to pay for fees on markets where it's necessary. # Require bet size of at least `min_` and maximum `max_`, use available trading balance if its between. return min(max(min_, trading_balance), max_)
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
📒 Files selected for processing (2)
- prediction_market_agent/agents/utils.py (1 hunks)
- tests/test_utils.py (2 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
- tests/test_utils.py
🔇 Additional comments (2)
prediction_market_agent/agents/utils.py (2)
140-141
: LGTM: Clean integration with existing code.The placement and organization of the new utility function follows the module's patterns and maintains good separation of concerns.
142-147
: Verify consistent usage across agent implementations.Let's ensure all relevant agent files have been updated to use this new function.
✅ Verification successful
The results show that the new
get_maximum_possible_bet_amount
function is being used across all agent implementation files (think_thoroughly_agent
,prophet_agent
,invalid_agent
,known_outcome_agent
) and no static bet amounts were found in the codebase. This indicates a consistent implementation across all agents.Function usage verified across all agent implementations ✓
The migration to the new dynamic bet amount calculation appears complete and consistent.
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Description: Check for both old static max bet amounts and new function usage echo "Checking for potential missed static bet amounts:" rg -l "max_bet.*=.*[0-9]+" --type py echo -e "\nChecking usage of new function:" rg -l "get_maximum_possible_bet_amount" --type pyLength of output: 571
No description provided.