prediction-market-agent-tooling 0.61.1.dev484__py3-none-any.whl → 0.61.1.dev486__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- prediction_market_agent_tooling/markets/seer/data_models.py +0 -96
- prediction_market_agent_tooling/markets/seer/price_manager.py +105 -1
- prediction_market_agent_tooling/markets/seer/seer.py +42 -8
- prediction_market_agent_tooling/markets/seer/seer_contracts.py +1 -1
- {prediction_market_agent_tooling-0.61.1.dev484.dist-info → prediction_market_agent_tooling-0.61.1.dev486.dist-info}/METADATA +1 -1
- {prediction_market_agent_tooling-0.61.1.dev484.dist-info → prediction_market_agent_tooling-0.61.1.dev486.dist-info}/RECORD +9 -9
- {prediction_market_agent_tooling-0.61.1.dev484.dist-info → prediction_market_agent_tooling-0.61.1.dev486.dist-info}/LICENSE +0 -0
- {prediction_market_agent_tooling-0.61.1.dev484.dist-info → prediction_market_agent_tooling-0.61.1.dev486.dist-info}/WHEEL +0 -0
- {prediction_market_agent_tooling-0.61.1.dev484.dist-info → prediction_market_agent_tooling-0.61.1.dev486.dist-info}/entry_points.txt +0 -0
@@ -11,21 +11,12 @@ from prediction_market_agent_tooling.gtypes import (
|
|
11
11
|
ChecksumAddress,
|
12
12
|
HexAddress,
|
13
13
|
HexBytes,
|
14
|
-
Probability,
|
15
|
-
xdai_type,
|
16
14
|
)
|
17
|
-
from prediction_market_agent_tooling.loggers import logger
|
18
15
|
from prediction_market_agent_tooling.markets.data_models import Resolution
|
19
16
|
from prediction_market_agent_tooling.markets.seer.subgraph_data_models import (
|
20
17
|
SeerParentMarket,
|
21
|
-
SeerPool,
|
22
18
|
)
|
23
|
-
from prediction_market_agent_tooling.tools.caches.inmemory_cache import (
|
24
|
-
persistent_inmemory_cache,
|
25
|
-
)
|
26
|
-
from prediction_market_agent_tooling.tools.cow.cow_manager import CowManager
|
27
19
|
from prediction_market_agent_tooling.tools.datetime_utc import DatetimeUTC
|
28
|
-
from prediction_market_agent_tooling.tools.web3_utils import xdai_to_wei
|
29
20
|
|
30
21
|
|
31
22
|
class SeerOutcomeEnum(str, Enum):
|
@@ -165,93 +156,6 @@ class SeerMarket(BaseModel):
|
|
165
156
|
def created_time(self) -> DatetimeUTC:
|
166
157
|
return DatetimeUTC.to_datetime_utc(self.block_timestamp)
|
167
158
|
|
168
|
-
@persistent_inmemory_cache
|
169
|
-
def get_price_for_token(
|
170
|
-
self,
|
171
|
-
token: ChecksumAddress,
|
172
|
-
) -> float:
|
173
|
-
collateral_exchange_amount = xdai_to_wei(xdai_type(1))
|
174
|
-
try:
|
175
|
-
quote = CowManager().get_quote(
|
176
|
-
collateral_token=self.collateral_token_contract_address_checksummed,
|
177
|
-
buy_token=token,
|
178
|
-
sell_amount=collateral_exchange_amount,
|
179
|
-
)
|
180
|
-
except Exception as e:
|
181
|
-
logger.warning(
|
182
|
-
f"Could not get quote for {token=} from Cow, exception {e=}. Falling back to pools. "
|
183
|
-
)
|
184
|
-
price = self.get_token_price_from_pools(token=token)
|
185
|
-
return price
|
186
|
-
|
187
|
-
return collateral_exchange_amount / float(quote.quote.buyAmount.root)
|
188
|
-
|
189
|
-
@staticmethod
|
190
|
-
def _pool_token0_matches_token(token: ChecksumAddress, pool: SeerPool) -> bool:
|
191
|
-
return pool.token0.id.hex().lower() == token.lower()
|
192
|
-
|
193
|
-
def get_token_price_from_pools(
|
194
|
-
self,
|
195
|
-
token: ChecksumAddress,
|
196
|
-
collateral_token_contract_address_checksummed: ChecksumAddress,
|
197
|
-
) -> float:
|
198
|
-
pool = self.subgraph_handler.get_pool_by_token(token_address=token)
|
199
|
-
|
200
|
-
if not pool:
|
201
|
-
logger.warning(f"Could not find a pool for {token=}, returning 0.")
|
202
|
-
return 0
|
203
|
-
# Check if other token is market's collateral (sanity check).
|
204
|
-
|
205
|
-
collateral_address = (
|
206
|
-
pool.token0.id
|
207
|
-
if self._pool_token0_matches_token(token=token, pool=pool)
|
208
|
-
else pool.token1.id
|
209
|
-
)
|
210
|
-
if (
|
211
|
-
collateral_address.hex().lower()
|
212
|
-
!= collateral_token_contract_address_checksummed.lower()
|
213
|
-
):
|
214
|
-
logger.warning(
|
215
|
-
f"Pool {pool.id.hex()} has collateral mismatch with market. Collateral from pool {collateral_address.hex()}, collateral from market {collateral_token_contract_address_checksummed}, returning 0."
|
216
|
-
)
|
217
|
-
return 0
|
218
|
-
|
219
|
-
price_in_collateral_units = (
|
220
|
-
pool.token0Price
|
221
|
-
if self._pool_token0_matches_token(pool)
|
222
|
-
else pool.token1Price
|
223
|
-
)
|
224
|
-
return price_in_collateral_units
|
225
|
-
|
226
|
-
@property
|
227
|
-
def current_p_yes(self) -> Probability:
|
228
|
-
price_data = {}
|
229
|
-
for idx, wrapped_token in enumerate(self.wrapped_tokens):
|
230
|
-
price = self.get_price_for_token(
|
231
|
-
token=Web3.to_checksum_address(wrapped_token),
|
232
|
-
)
|
233
|
-
|
234
|
-
price_data[idx] = price
|
235
|
-
|
236
|
-
if sum(price_data.values()) == 0:
|
237
|
-
logger.warning(
|
238
|
-
f"Could not get p_yes for market {self.id.hex()}, all price quotes are 0."
|
239
|
-
)
|
240
|
-
return Probability(0)
|
241
|
-
|
242
|
-
price_yes = price_data[self.outcome_as_enums[SeerOutcomeEnum.YES]]
|
243
|
-
price_no = price_data[self.outcome_as_enums[SeerOutcomeEnum.NO]]
|
244
|
-
if price_yes and not price_no:
|
245
|
-
# We simply return p_yes since it's probably a bug that p_no wasn't found.
|
246
|
-
return Probability(price_yes)
|
247
|
-
elif price_no and not price_yes:
|
248
|
-
# We return the complement of p_no (and ignore invalid).
|
249
|
-
return Probability(1.0 - price_no)
|
250
|
-
else:
|
251
|
-
# If all prices are available, we normalize price_yes by the other prices for the final probability.
|
252
|
-
price_yes = price_yes / sum(price_data.values())
|
253
|
-
return Probability(price_yes)
|
254
|
-
|
255
159
|
@property
|
256
160
|
def url(self) -> str:
|
257
161
|
chain_id = RPCConfig().chain_id
|
@@ -1,5 +1,109 @@
|
|
1
|
-
from
|
1
|
+
from web3 import Web3
|
2
|
+
|
3
|
+
from prediction_market_agent_tooling.gtypes import ChecksumAddress, xdai_type
|
4
|
+
from prediction_market_agent_tooling.gtypes import Probability
|
5
|
+
from prediction_market_agent_tooling.loggers import logger
|
6
|
+
from prediction_market_agent_tooling.markets.seer.data_models import (
|
7
|
+
SeerMarket,
|
8
|
+
SeerOutcomeEnum,
|
9
|
+
)
|
10
|
+
from prediction_market_agent_tooling.markets.seer.seer_subgraph_handler import (
|
11
|
+
SeerSubgraphHandler,
|
12
|
+
)
|
2
13
|
from prediction_market_agent_tooling.markets.seer.subgraph_data_models import SeerPool
|
14
|
+
from prediction_market_agent_tooling.tools.caches.inmemory_cache import (
|
15
|
+
persistent_inmemory_cache,
|
16
|
+
)
|
17
|
+
from prediction_market_agent_tooling.tools.cow.cow_manager import CowManager
|
18
|
+
from prediction_market_agent_tooling.tools.web3_utils import xdai_to_wei
|
3
19
|
|
4
20
|
|
5
21
|
class PriceManager:
|
22
|
+
def __init__(self, seer_market: SeerMarket, seer_subgraph: SeerSubgraphHandler):
|
23
|
+
self.seer_market = seer_market
|
24
|
+
self.seer_subgraph = seer_subgraph
|
25
|
+
|
26
|
+
def current_p_yes(self) -> Probability:
|
27
|
+
price_data = {}
|
28
|
+
for idx, wrapped_token in enumerate(self.seer_market.wrapped_tokens):
|
29
|
+
price = self.get_price_for_token(
|
30
|
+
token=Web3.to_checksum_address(wrapped_token),
|
31
|
+
)
|
32
|
+
|
33
|
+
price_data[idx] = price
|
34
|
+
|
35
|
+
if sum(price_data.values()) == 0:
|
36
|
+
logger.warning(
|
37
|
+
f"Could not get p_yes for market {self.seer_market.id.hex()}, all price quotes are 0."
|
38
|
+
)
|
39
|
+
return Probability(0)
|
40
|
+
|
41
|
+
price_yes = price_data[self.seer_market.outcome_as_enums[SeerOutcomeEnum.YES]]
|
42
|
+
price_no = price_data[self.seer_market.outcome_as_enums[SeerOutcomeEnum.NO]]
|
43
|
+
if price_yes and not price_no:
|
44
|
+
# We simply return p_yes since it's probably a bug that p_no wasn't found.
|
45
|
+
return Probability(price_yes)
|
46
|
+
elif price_no and not price_yes:
|
47
|
+
# We return the complement of p_no (and ignore invalid).
|
48
|
+
return Probability(1.0 - price_no)
|
49
|
+
else:
|
50
|
+
# If all prices are available, we normalize price_yes by the other prices for the final probability.
|
51
|
+
price_yes = price_yes / sum(price_data.values())
|
52
|
+
return Probability(price_yes)
|
53
|
+
|
54
|
+
@persistent_inmemory_cache
|
55
|
+
def get_price_for_token(
|
56
|
+
self,
|
57
|
+
token: ChecksumAddress,
|
58
|
+
) -> float:
|
59
|
+
collateral_exchange_amount = xdai_to_wei(xdai_type(1))
|
60
|
+
try:
|
61
|
+
quote = CowManager().get_quote(
|
62
|
+
collateral_token=self.seer_market.collateral_token_contract_address_checksummed,
|
63
|
+
buy_token=token,
|
64
|
+
sell_amount=collateral_exchange_amount,
|
65
|
+
)
|
66
|
+
except Exception as e:
|
67
|
+
logger.warning(
|
68
|
+
f"Could not get quote for {token=} from Cow, exception {e=}. Falling back to pools. "
|
69
|
+
)
|
70
|
+
price = self.get_token_price_from_pools(token=token)
|
71
|
+
return price
|
72
|
+
|
73
|
+
return collateral_exchange_amount / float(quote.quote.buyAmount.root)
|
74
|
+
|
75
|
+
@staticmethod
|
76
|
+
def _pool_token0_matches_token(token: ChecksumAddress, pool: SeerPool) -> bool:
|
77
|
+
return pool.token0.id.hex().lower() == token.lower()
|
78
|
+
|
79
|
+
def get_token_price_from_pools(
|
80
|
+
self,
|
81
|
+
token: ChecksumAddress,
|
82
|
+
) -> float:
|
83
|
+
pool = SeerSubgraphHandler().get_pool_by_token(token_address=token)
|
84
|
+
|
85
|
+
if not pool:
|
86
|
+
logger.warning(f"Could not find a pool for {token=}, returning 0.")
|
87
|
+
return 0
|
88
|
+
# Check if other token is market's collateral (sanity check).
|
89
|
+
|
90
|
+
collateral_address = (
|
91
|
+
pool.token0.id
|
92
|
+
if self._pool_token0_matches_token(token=token, pool=pool)
|
93
|
+
else pool.token1.id
|
94
|
+
)
|
95
|
+
if (
|
96
|
+
collateral_address.hex().lower()
|
97
|
+
!= self.seer_market.collateral_token_contract_address_checksummed.lower()
|
98
|
+
):
|
99
|
+
logger.warning(
|
100
|
+
f"Pool {pool.id.hex()} has collateral mismatch with market. Collateral from pool {collateral_address.hex()}, collateral from market {self.seer_market.collateral_token_contract_address_checksummed}, returning 0."
|
101
|
+
)
|
102
|
+
return 0
|
103
|
+
|
104
|
+
price_in_collateral_units = (
|
105
|
+
pool.token0Price
|
106
|
+
if self._pool_token0_matches_token(token=token, pool=pool)
|
107
|
+
else pool.token1Price
|
108
|
+
)
|
109
|
+
return price_in_collateral_units
|
@@ -13,6 +13,7 @@ from prediction_market_agent_tooling.gtypes import (
|
|
13
13
|
wei_type,
|
14
14
|
xDai,
|
15
15
|
xdai_type,
|
16
|
+
Probability,
|
16
17
|
)
|
17
18
|
from prediction_market_agent_tooling.loggers import logger
|
18
19
|
from prediction_market_agent_tooling.markets.agent_market import (
|
@@ -33,16 +34,19 @@ from prediction_market_agent_tooling.markets.market_fees import MarketFees
|
|
33
34
|
from prediction_market_agent_tooling.markets.omen.omen import OmenAgentMarket
|
34
35
|
from prediction_market_agent_tooling.markets.omen.omen_contracts import sDaiContract
|
35
36
|
from prediction_market_agent_tooling.markets.seer.data_models import (
|
36
|
-
NewMarketEvent,
|
37
37
|
SeerMarket,
|
38
38
|
SeerOutcomeEnum,
|
39
39
|
)
|
40
|
+
from prediction_market_agent_tooling.markets.seer.price_manager import PriceManager
|
40
41
|
from prediction_market_agent_tooling.markets.seer.seer_contracts import (
|
41
42
|
SeerMarketFactory,
|
42
43
|
)
|
43
44
|
from prediction_market_agent_tooling.markets.seer.seer_subgraph_handler import (
|
44
45
|
SeerSubgraphHandler,
|
45
46
|
)
|
47
|
+
from prediction_market_agent_tooling.markets.seer.subgraph_data_models import (
|
48
|
+
NewMarketEvent,
|
49
|
+
)
|
46
50
|
from prediction_market_agent_tooling.tools.balances import get_balances
|
47
51
|
from prediction_market_agent_tooling.tools.contract import (
|
48
52
|
ContractERC20OnGnosisChain,
|
@@ -166,6 +170,33 @@ class SeerAgentMarket(AgentMarket):
|
|
166
170
|
def verify_operational_balance(api_keys: APIKeys) -> bool:
|
167
171
|
return OmenAgentMarket.verify_operational_balance(api_keys=api_keys)
|
168
172
|
|
173
|
+
@staticmethod
|
174
|
+
def from_data_model_with_subgraph(
|
175
|
+
model: SeerMarket, seer_subgraph: SeerSubgraphHandler
|
176
|
+
) -> "SeerAgentMarket":
|
177
|
+
p = PriceManager(seer_market=model, seer_subgraph=seer_subgraph)
|
178
|
+
current_p_yes = p.current_p_yes()
|
179
|
+
|
180
|
+
return SeerAgentMarket(
|
181
|
+
id=model.id.hex(),
|
182
|
+
question=model.title,
|
183
|
+
creator=model.creator,
|
184
|
+
created_time=model.created_time,
|
185
|
+
outcomes=model.outcomes,
|
186
|
+
collateral_token_contract_address_checksummed=model.collateral_token_contract_address_checksummed,
|
187
|
+
condition_id=model.condition_id,
|
188
|
+
url=model.url,
|
189
|
+
close_time=model.close_time,
|
190
|
+
wrapped_tokens=[Web3.to_checksum_address(i) for i in model.wrapped_tokens],
|
191
|
+
fees=MarketFees.get_zero_fees(),
|
192
|
+
outcome_token_pool=None,
|
193
|
+
resolution=model.get_resolution_enum(),
|
194
|
+
volume=None,
|
195
|
+
# current_p_yes=model.current_p_yes,
|
196
|
+
current_p_yes=current_p_yes,
|
197
|
+
seer_outcomes=model.outcome_as_enums,
|
198
|
+
)
|
199
|
+
|
169
200
|
@staticmethod
|
170
201
|
def from_data_model(model: SeerMarket) -> "SeerAgentMarket":
|
171
202
|
return SeerAgentMarket(
|
@@ -183,7 +214,7 @@ class SeerAgentMarket(AgentMarket):
|
|
183
214
|
outcome_token_pool=None,
|
184
215
|
resolution=model.get_resolution_enum(),
|
185
216
|
volume=None,
|
186
|
-
current_p_yes=
|
217
|
+
current_p_yes=Probability(123), # ToDo dont use this method
|
187
218
|
seer_outcomes=model.outcome_as_enums,
|
188
219
|
)
|
189
220
|
|
@@ -195,13 +226,16 @@ class SeerAgentMarket(AgentMarket):
|
|
195
226
|
created_after: t.Optional[DatetimeUTC] = None,
|
196
227
|
excluded_questions: set[str] | None = None,
|
197
228
|
) -> t.Sequence["SeerAgentMarket"]:
|
229
|
+
seer_subgraph = SeerSubgraphHandler()
|
230
|
+
markets = seer_subgraph.get_binary_markets(
|
231
|
+
limit=limit, sort_by=sort_by, filter_by=filter_by
|
232
|
+
)
|
233
|
+
|
198
234
|
return [
|
199
|
-
SeerAgentMarket.
|
200
|
-
|
201
|
-
limit=limit,
|
202
|
-
sort_by=sort_by,
|
203
|
-
filter_by=filter_by,
|
235
|
+
SeerAgentMarket.from_data_model_with_subgraph(
|
236
|
+
model=m, seer_subgraph=seer_subgraph
|
204
237
|
)
|
238
|
+
for m in markets
|
205
239
|
]
|
206
240
|
|
207
241
|
def has_liquidity_for_outcome(self, outcome: bool) -> bool:
|
@@ -352,4 +386,4 @@ def extract_market_address_from_tx(
|
|
352
386
|
.process_receipt(tx_receipt)
|
353
387
|
)
|
354
388
|
new_market_event = NewMarketEvent(**event_logs[0]["args"])
|
355
|
-
return Web3.to_checksum_address(new_market_event.
|
389
|
+
return Web3.to_checksum_address(new_market_event.market)
|
@@ -5,7 +5,7 @@ from web3.types import TxReceipt
|
|
5
5
|
|
6
6
|
from prediction_market_agent_tooling.config import APIKeys
|
7
7
|
from prediction_market_agent_tooling.gtypes import ABI, ChecksumAddress, xDai
|
8
|
-
from prediction_market_agent_tooling.markets.seer.
|
8
|
+
from prediction_market_agent_tooling.markets.seer.subgraph_data_models import (
|
9
9
|
CreateCategoricalMarketsParams,
|
10
10
|
)
|
11
11
|
from prediction_market_agent_tooling.tools.contract import (
|
@@ -61,10 +61,10 @@ prediction_market_agent_tooling/markets/polymarket/data_models.py,sha256=Fd5PI5y
|
|
61
61
|
prediction_market_agent_tooling/markets/polymarket/data_models_web.py,sha256=VZhVccTApygSKMmy6Au2G02JCJOKJnR_oVeKlaesuSg,12548
|
62
62
|
prediction_market_agent_tooling/markets/polymarket/polymarket.py,sha256=NRoZK71PtH8kkangMqme7twcAXhRJSSabbmOir-UnAI,3418
|
63
63
|
prediction_market_agent_tooling/markets/polymarket/utils.py,sha256=8kTeVjXPcXC6DkDvWYsZQLY7x8DS6CEp_yznSEazsNU,2037
|
64
|
-
prediction_market_agent_tooling/markets/seer/data_models.py,sha256=
|
65
|
-
prediction_market_agent_tooling/markets/seer/price_manager.py,sha256=
|
66
|
-
prediction_market_agent_tooling/markets/seer/seer.py,sha256=
|
67
|
-
prediction_market_agent_tooling/markets/seer/seer_contracts.py,sha256=
|
64
|
+
prediction_market_agent_tooling/markets/seer/data_models.py,sha256=ECuCDqRcs9vB9rKIec399HxsL915oT7VGSwztcMfGIw,5347
|
65
|
+
prediction_market_agent_tooling/markets/seer/price_manager.py,sha256=fUszpmwUW2iJw5My3FJO2Lim2yXUuaZWQ9aNKX39-d0,4392
|
66
|
+
prediction_market_agent_tooling/markets/seer/seer.py,sha256=kBF7ALzlh0HsAgbdTa3A9XayyXrddtgi-dMWquLZX8Y,14365
|
67
|
+
prediction_market_agent_tooling/markets/seer/seer_contracts.py,sha256=TXGDbv7CI08X8N5re1SAm-X_BaXj8m4ceyzkS_ktQok,2739
|
68
68
|
prediction_market_agent_tooling/markets/seer/seer_subgraph_handler.py,sha256=lcaKbFHxigMYwi4TCePyTb5HXJhGoCu5dJPFWTj5E28,9047
|
69
69
|
prediction_market_agent_tooling/markets/seer/subgraph_data_models.py,sha256=RIt2oO-PbykzbYN11Qltt8tjjYTty-PfjH3Q4D2VEoA,1644
|
70
70
|
prediction_market_agent_tooling/monitor/financial_metrics/financial_metrics.py,sha256=fjIgjDIx5MhH5mwf7S0cspLOOSU3elYLhGYoIiM26mU,2746
|
@@ -119,8 +119,8 @@ prediction_market_agent_tooling/tools/tokens/main_token.py,sha256=7JPgVF4RbiFzLD
|
|
119
119
|
prediction_market_agent_tooling/tools/transaction_cache.py,sha256=K5YKNL2_tR10Iw2TD9fuP-CTGpBbZtNdgbd0B_R7pjg,1814
|
120
120
|
prediction_market_agent_tooling/tools/utils.py,sha256=jLG4nbEoIzzJiZ4RgMx4Q969Zdl0p0s63p8uET_0Fuw,6440
|
121
121
|
prediction_market_agent_tooling/tools/web3_utils.py,sha256=3wfqNxvMn44ivweFRoeKNVb9QRtFd7kFtp7VUY5juEE,12862
|
122
|
-
prediction_market_agent_tooling-0.61.1.
|
123
|
-
prediction_market_agent_tooling-0.61.1.
|
124
|
-
prediction_market_agent_tooling-0.61.1.
|
125
|
-
prediction_market_agent_tooling-0.61.1.
|
126
|
-
prediction_market_agent_tooling-0.61.1.
|
122
|
+
prediction_market_agent_tooling-0.61.1.dev486.dist-info/LICENSE,sha256=6or154nLLU6bELzjh0mCreFjt0m2v72zLi3yHE0QbeE,7650
|
123
|
+
prediction_market_agent_tooling-0.61.1.dev486.dist-info/METADATA,sha256=7XZFv83NtgtmTfYh1aq17OY1M69UzMcLnyhdkuMmNB0,8636
|
124
|
+
prediction_market_agent_tooling-0.61.1.dev486.dist-info/WHEEL,sha256=XbeZDeTWKc1w7CSIyre5aMDU_-PohRwTQceYnisIYYY,88
|
125
|
+
prediction_market_agent_tooling-0.61.1.dev486.dist-info/entry_points.txt,sha256=m8PukHbeH5g0IAAmOf_1Ahm-sGAMdhSSRQmwtpmi2s8,81
|
126
|
+
prediction_market_agent_tooling-0.61.1.dev486.dist-info/RECORD,,
|
File without changes
|
File without changes
|