@@ -148,7 +148,8 @@ async def _refresh_exchange_fee_tiers(self, all_markets: list[dict]):
148148 fee_pairs = list (fees_by_tier [next (iter (fees_by_tier ))]) if fees_by_tier else []
149149 self .logger .info (
150150 f"Refreshed { exchange_name } fee tiers. Sample: { sample } . { len (sample )} tiers: { list (sample )} "
151- f"over { len (fee_pairs )} pairs: { fee_pairs } ."
151+ f"over { len (fee_pairs )} pairs: { fee_pairs } . Using fee tiers "
152+ f"{ self ._get_fee_tiers (self .exchange_manager .exchange , not self .exchange_manager .is_backtesting ).value } ."
152153 )
153154
154155 @classmethod
@@ -177,7 +178,7 @@ def register_simulator_connector_fee_methods(
177178 ):
178179 # only called in backtesting
179180 # overrides exchange simulator connector calculate_fees and get_fees to use fetched fees instead
180- fee_tiers = cls ._get_fee_tiers (False )
181+ fee_tiers = cls ._get_fee_tiers (None , False )
181182 simulator_connector .calculate_fees = cls .simulator_connector_calculate_fees_factory (exchange_name , fee_tiers )
182183 simulator_connector .get_fees = cls .simulator_connector_get_fees_factory (exchange_name , fee_tiers )
183184
@@ -188,8 +189,9 @@ def calculate_fees(
188189 # only called in live trading
189190 is_real_trading = not self .exchange_manager .is_backtesting # consider live trading as real to use basic tier
190191 try :
192+ fee_tiers = self ._get_fee_tiers (self .exchange_manager .exchange , is_real_trading )
191193 return self ._calculate_fetched_fees (
192- self .exchange_manager .exchange_name , self . _get_fee_tiers ( is_real_trading ) ,
194+ self .exchange_manager .exchange_name , fee_tiers ,
193195 symbol , order_type , quantity , price , taker_or_maker
194196 )
195197 except errors .MissingFeeDetailsError as err :
@@ -201,7 +203,8 @@ def get_fees(self, symbol):
201203 # only called in live trading
202204 try :
203205 is_real_trading = not self .exchange_manager .is_backtesting # consider live trading as real to use basic tier
204- return self ._get_fees (self .exchange_manager .exchange_name , self ._get_fee_tiers (is_real_trading ), symbol )
206+ fee_tiers = self ._get_fee_tiers (self .exchange_manager .exchange , is_real_trading )
207+ return self ._get_fees (self .exchange_manager .exchange_name , fee_tiers , symbol )
205208 except errors .MissingFeeDetailsError :
206209 self .logger .error (f"Missing fee details, using default value" )
207210 market = self .get_market_status (symbol , with_fixer = False )
@@ -258,7 +261,14 @@ def _calculate_fetched_fees(
258261 }
259262
260263 @classmethod
261- def _get_fee_tiers (cls , is_real_trading : bool ):
264+ def _get_fee_tiers (cls , rest_exchange : typing .Optional [exchanges .RestExchange ], is_real_trading : bool ):
265+ if (
266+ rest_exchange
267+ and isinstance (rest_exchange , hollaex )
268+ and (fee_tiers := rest_exchange .get_configured_fee_tiers ())
269+ ):
270+ return fee_tiers
271+ # default to basic tier
262272 return FeeTiers .BASIC if is_real_trading else FeeTiers .VIP
263273
264274 @classmethod
@@ -320,6 +330,7 @@ class hollaex(exchanges.RestExchange):
320330
321331 BASE_REST_API = "api.hollaex.com"
322332 REST_KEY = "rest"
333+ FEE_TIERS_KEY = "fee_tiers"
323334 HAS_WEBSOCKETS_KEY = "has_websockets"
324335 REQUIRE_ORDER_FEES_FROM_TRADES = True # set True when get_order is not giving fees on closed orders and fees
325336 SUPPORT_FETCHING_CANCELLED_ORDERS = False
@@ -398,16 +409,29 @@ def init_user_inputs_from_class(cls, inputs: dict) -> None:
398409 cls .REST_KEY , commons_enums .UserInputTypes .TEXT , f"https://{ cls .BASE_REST_API } " , inputs ,
399410 title = f"Address of the Hollaex based exchange API (similar to https://{ cls .BASE_REST_API } )"
400411 )
412+ cls .CLASS_UI .user_input (
413+ cls .FEE_TIERS_KEY , commons_enums .UserInputTypes .OPTIONS , FeeTiers .BASIC .value , inputs ,
414+ title = f"Fee tiers to use for the exchange. Used to predict fees." ,
415+ options = [tier .value for tier in FeeTiers ]
416+ )
401417 cls .CLASS_UI .user_input (
402418 cls .HAS_WEBSOCKETS_KEY , commons_enums .UserInputTypes .BOOLEAN , True , inputs ,
403419 title = f"Use websockets feed. To enable only when websockets are supported by the exchange."
404420 )
405421
406422 def get_additional_connector_config (self ):
407423 return {
408- ccxt_enums .ExchangeColumns .URLS .value : self .get_patched_urls (self .tentacle_config [ self . REST_KEY ] )
424+ ccxt_enums .ExchangeColumns .URLS .value : self .get_patched_urls (self .get_api_url () )
409425 }
410426
427+ def get_api_url (self ):
428+ return self .tentacle_config [self .REST_KEY ]
429+
430+ def get_configured_fee_tiers (self ) -> typing .Optional [FeeTiers ]:
431+ if tiers := self .tentacle_config .get (self .FEE_TIERS_KEY ):
432+ return FeeTiers (tiers )
433+ return None
434+
411435 @classmethod
412436 def get_custom_url_config (cls , tentacle_config : dict , exchange_name : str ) -> dict :
413437 if details := cls .get_exchange_details (tentacle_config , exchange_name ):
0 commit comments