Coverage for yield_analysis_sdk\type.py: 100%

78 statements  

« prev     ^ index     » next       coverage.py v7.9.1, created at 2025-07-16 17:09 +0800

1from enum import Enum 

2from typing import Any, List, Optional, Tuple 

3 

4from pydantic import BaseModel, Field 

5 

6from .validators import ( 

7 ChainValidatorMixin, 

8 UnderlyingTokenValidatorMixin, 

9 VaultAddressValidatorMixin, 

10) 

11 

12 

13class Chain(Enum): 

14 ETHEREUM = "ethereum" 

15 ARBITRUM = "arbitrum" 

16 BASE = "base" 

17 OPTIMISM = "optimism" 

18 POLYGON = "polygon" 

19 BSC = "bsc" 

20 GNOS = "gnos" 

21 AVALANCHE = "avalanche" 

22 FANTOM = "fantom" 

23 HARMONY = "harmony" 

24 MOONBEAM = "moonbeam" 

25 MOONRIVER = "moonriver" 

26 OTHER = "other" 

27 

28 @classmethod 

29 def _missing_(cls, value: Any) -> "Chain": 

30 """Handle unknown chain values by returning OTHER.""" 

31 return cls.OTHER 

32 

33 

34class StrategyType(Enum): 

35 # Core Yield Strategies 

36 LIQUID_STAKING = "liquid_staking" 

37 LIQUID_RESTAKING = "liquid_restaking" 

38 LENDING = "lending" 

39 YIELD_AGGREGATOR = "yield_aggregator" 

40 

41 # Trading & DeFi 

42 BASIS_TRADING = "basis_trading" 

43 ARBITRAGE = "arbitrage" 

44 CDP = "cdp" 

45 DEXES = "dexes" 

46 

47 # Index & Basket 

48 INDEXES = "index" 

49 BASKET = "basket" 

50 

51 # Farming 

52 YIELD_FARMING = "yield_farming" 

53 LIQUIDITY_MINING = "liquidity_mining" 

54 

55 # Other 

56 OTHER = "other" 

57 

58 

59class AuditStatus(Enum): 

60 AUDITED = "audited" 

61 NOT_AUDITED = "not_audited" 

62 PARTIALLY_AUDITED = "partially_audited" 

63 UNKNOWN = "unknown" 

64 

65 

66class RegistrationRequest(VaultAddressValidatorMixin, ChainValidatorMixin, BaseModel): 

67 chain: Chain 

68 vault_address: str 

69 

70 

71class RegistrationResponse(BaseModel): 

72 is_registered: bool 

73 message: str 

74 contract_tx_hash: Optional[str] = None 

75 

76 

77class AnalysisRequest(UnderlyingTokenValidatorMixin, ChainValidatorMixin, BaseModel): 

78 chain: Chain = Field(..., description="The chain of vaults to analyze") 

79 underlying_token: str = Field( 

80 ..., description="The underlying token of vaults to analyze" 

81 ) 

82 

83 

84class VaultInfo(VaultAddressValidatorMixin, ChainValidatorMixin, BaseModel): 

85 # Basic Vault Information 

86 chain: Chain 

87 vault_address: str 

88 vault_name: str 

89 protocol: str = Field( 

90 ..., description="The protocol/platform this vault belongs to" 

91 ) 

92 

93 # Fee Structure (Critical for allocation decisions) 

94 entry_fee_bps: int = Field(0, description="Entry fee rate in basis points") 

95 exit_fee_bps: int = Field(0, description="Exit fee rate in basis points") 

96 

97 # Vault Capacity 

98 max_deposit_amount: float = Field( 

99 0.0, 

100 description="Maximum amount of underlying token that can be deposited into the vault", 

101 ) 

102 

103 # Analysis Context 

104 risk_free_rate: float = Field( 

105 0.05, description="Risk-free rate used for Sharpe ratio calculation" 

106 ) 

107 

108 # Analysis Metadata 

109 last_updated_timestamp: int = Field( 

110 ..., description="Last update timestamp in seconds" 

111 ) 

112 

113 

114class PerformanceAnalysis(BaseModel): 

115 # Core Performance Metrics (Mandatory for allocation decisions) 

116 apy_7d: float = Field(..., description="7-day annualized percentage yield") 

117 apy_30d: float = Field(..., description="30-day annualized percentage yield") 

118 apy_90d: float = Field(..., description="90-day annualized percentage yield") 

119 

120 # Essential Risk Metrics 

121 volatility_30d: float = Field(..., description="30-day APY volatility") 

122 max_drawdown: float = Field( 

123 ..., description="Maximum historical drawdown percentage" 

124 ) 

125 sharpe_ratio: float = Field(..., description="Risk-adjusted return ratio") 

126 

127 # Current State 

128 current_price: float = Field(..., description="Current share price") 

129 

130 # Analysis Metadata 

131 analysis_period_days: int = Field( 

132 ..., description="Number of days in the analysis period" 

133 ) 

134 

135 

136class AnalysisResult(BaseModel): 

137 # Combined vault info and performance analysis 

138 vault_info: VaultInfo 

139 performance: PerformanceAnalysis 

140 

141 

142class AnalysisResponse(BaseModel): 

143 analyses: List[AnalysisResult] = Field(..., description="List of vault analyses") 

144 

145 

146class SharePriceHistory(VaultAddressValidatorMixin, BaseModel): 

147 vault_name: str 

148 vault_address: str 

149 price_history: List[Tuple[int, float]]