making list of categories available

This commit is contained in:
Jakub Werner (jakubikan) 2024-09-25 21:11:52 +02:00
parent 50f07e7b11
commit 0dbe507b26
2 changed files with 52 additions and 31 deletions

View File

@ -38,6 +38,11 @@ class __OptionPairlistParameter(__PairlistParameterBase):
default: Union[str, None]
options: List[str]
class __ListPairListParamenter(__PairlistParameterBase):
type: Literal["list"]
default: Union[List[str], None]
options: List[str]
class __BoolPairlistParameter(__PairlistParameterBase):
type: Literal["boolean"]
@ -49,6 +54,7 @@ PairlistParameter = Union[
__StringPairlistParameter,
__OptionPairlistParameter,
__BoolPairlistParameter,
__ListPairListParamenter
]
@ -68,12 +74,12 @@ class IPairList(LoggingMixin, ABC):
supports_backtesting: SupportsBacktesting = SupportsBacktesting.NO
def __init__(
self,
exchange: Exchange,
pairlistmanager,
config: Config,
pairlistconfig: Dict[str, Any],
pairlist_pos: int,
self,
exchange: Exchange,
pairlistmanager,
config: Config,
pairlistconfig: Dict[str, Any],
pairlist_pos: int,
) -> None:
"""
:param exchange: Exchange instance
@ -213,7 +219,7 @@ class IPairList(LoggingMixin, ABC):
return self._pairlistmanager.verify_blacklist(pairlist, logmethod)
def verify_whitelist(
self, pairlist: List[str], logmethod, keep_invalid: bool = False
self, pairlist: List[str], logmethod, keep_invalid: bool = False
) -> List[str]:
"""
Proxy method to verify_whitelist for easy access for child classes.

View File

@ -14,7 +14,6 @@ from freqtrade.exchange.exchange_types import Tickers
from freqtrade.plugins.pairlist.IPairList import IPairList, PairlistParameter, SupportsBacktesting
from freqtrade.util.coin_gecko import FtCoinGeckoApi
logger = logging.getLogger(__name__)
@ -35,7 +34,7 @@ class MarketCapPairList(IPairList):
self._number_assets = self._pairlistconfig["number_assets"]
self._max_rank = self._pairlistconfig.get("max_rank", 30)
self._refresh_period = self._pairlistconfig.get("refresh_period", 86400)
self._category = self._pairlistconfig.get("category", None)
self._categories = self._pairlistconfig.get("categories", [])
self._marketcap_cache: TTLCache = TTLCache(maxsize=1, ttl=self._refresh_period)
self._def_candletype = self._config["candle_type_def"]
@ -46,14 +45,14 @@ class MarketCapPairList(IPairList):
is_demo=_coingecko_config.get("is_demo", True),
)
if self._category:
if self._categories:
categories = self._coingecko.get_coins_categories_list()
category_ids = [cat["category_id"] for cat in categories]
category_ids = [cat['category_id'] for cat in categories]
if self._category not in category_ids:
raise OperationalException(
f"category not in coingecko category list you can choose from {category_ids}"
)
for category in self._categories:
if category not in category_ids:
raise OperationalException(
f"category not in coingecko category list you can choose from {category_ids}")
if self._max_rank > 250:
raise OperationalException("This filter only support marketcap rank up to 250.")
@ -95,11 +94,11 @@ class MarketCapPairList(IPairList):
"description": "Max rank of assets",
"help": "Maximum rank of assets to use from the pairlist",
},
"category": {
"type": "string",
"default": None,
"description": "The Category",
"help": "Th Category of the coin e.g layer-1 default None",
"categories": {
"type": "list",
"default": [],
"description": "The Categories to be set",
"help": "The Category of the coin e.g layer-1 default [] (https://www.coingecko.com/en/categories)",
},
"refresh_period": {
"type": "number",
@ -148,16 +147,32 @@ class MarketCapPairList(IPairList):
"""
marketcap_list = self._marketcap_cache.get("marketcap")
default_kwargs = {
"vs_currency": "usd",
"order": "market_cap_desc",
"per_page": "250",
"page": "1",
"sparkline": "false",
"locale": "en",
}
if marketcap_list is None:
data = self._coingecko.get_coins_markets(
vs_currency="usd",
order="market_cap_desc",
per_page="250",
page="1",
sparkline="false",
locale="en",
**({"category": self._category} if self._category else {}),
)
data = []
if not self._categories:
data = self._coingecko.get_coins_markets(
**default_kwargs
)
else:
for category in self._categories:
category_data = self._coingecko.get_coins_markets(
**default_kwargs,
**({"category": category} if category else {})
)
data += category_data
data.sort(key=lambda d: float(d['market_cap'] or 0.0), reverse=True)
if data:
marketcap_list = [row["symbol"] for row in data]
self._marketcap_cache["marketcap"] = marketcap_list
@ -170,11 +185,11 @@ class MarketCapPairList(IPairList):
if market == "futures":
pair_format += f":{self._stake_currency.upper()}"
top_marketcap = marketcap_list[: self._max_rank :]
top_marketcap = marketcap_list[: self._max_rank:]
for mc_pair in top_marketcap:
test_pair = f"{mc_pair.upper()}/{pair_format}"
if test_pair in pairlist:
if test_pair in pairlist and test_pair not in filtered_pairlist:
filtered_pairlist.append(test_pair)
if len(filtered_pairlist) == self._number_assets:
break