Fix wrong fee calclulation for gateio futures

This commit is contained in:
Matthias 2022-07-09 08:24:29 +02:00
parent 5b733a723d
commit b7167ec880
6 changed files with 15 additions and 6 deletions

View File

@ -77,6 +77,7 @@ class Exchange:
"mark_ohlcv_price": "mark", "mark_ohlcv_price": "mark",
"mark_ohlcv_timeframe": "8h", "mark_ohlcv_timeframe": "8h",
"ccxt_futures_name": "swap", "ccxt_futures_name": "swap",
"fee_cost_in_contracts": False, # Fee cost needs contract conversion
"needs_trading_fees": False, # use fetch_trading_fees to cache fees "needs_trading_fees": False, # use fetch_trading_fees to cache fees
} }
_ft_has: Dict = {} _ft_has: Dict = {}
@ -1645,13 +1646,18 @@ class Exchange:
fee_curr = fee.get('currency') fee_curr = fee.get('currency')
if fee_curr is None: if fee_curr is None:
return None return None
fee_cost = fee['cost']
if self._ft_has['fee_cost_in_contracts']:
# Convert cost via "contracts" conversion
fee_cost = self._contracts_to_amount(symbol, fee['cost'])
# Calculate fee based on order details # Calculate fee based on order details
if fee_curr == self.get_pair_base_currency(symbol): if fee_curr == self.get_pair_base_currency(symbol):
# Base currency - divide by amount # Base currency - divide by amount
return round(fee['cost'] / amount, 8) return round(fee['cost'] / amount, 8)
elif fee_curr == self.get_pair_quote_currency(symbol): elif fee_curr == self.get_pair_quote_currency(symbol):
# Quote currency - divide by cost # Quote currency - divide by cost
return round(self._contracts_to_amount(symbol, fee['cost']) / cost, 8) if cost else None return round(fee_cost / cost, 8) if cost else None
else: else:
# If Fee currency is a different currency # If Fee currency is a different currency
if not cost: if not cost:
@ -1666,8 +1672,7 @@ class Exchange:
fee_to_quote_rate = self._config['exchange'].get('unknown_fee_rate', None) fee_to_quote_rate = self._config['exchange'].get('unknown_fee_rate', None)
if not fee_to_quote_rate: if not fee_to_quote_rate:
return None return None
return round((self._contracts_to_amount( return round((fee_cost * fee_to_quote_rate) / cost, 8)
symbol, fee['cost']) * fee_to_quote_rate) / cost, 8)
def extract_cost_curr_rate(self, fee: Dict, symbol: str, cost: float, def extract_cost_curr_rate(self, fee: Dict, symbol: str, cost: float,
amount: float) -> Tuple[float, str, Optional[float]]: amount: float) -> Tuple[float, str, Optional[float]]:

View File

@ -32,7 +32,8 @@ class Gateio(Exchange):
} }
_ft_has_futures: Dict = { _ft_has_futures: Dict = {
"needs_trading_fees": True "needs_trading_fees": True,
"fee_cost_in_contracts": False, # Set explicitly to false for clarity
} }
_supported_trading_mode_margin_pairs: List[Tuple[TradingMode, MarginMode]] = [ _supported_trading_mode_margin_pairs: List[Tuple[TradingMode, MarginMode]] = [

View File

@ -28,6 +28,7 @@ class Okx(Exchange):
} }
_ft_has_futures: Dict = { _ft_has_futures: Dict = {
"tickers_have_quoteVolume": False, "tickers_have_quoteVolume": False,
"fee_cost_in_contracts": True,
} }
_supported_trading_mode_margin_pairs: List[Tuple[TradingMode, MarginMode]] = [ _supported_trading_mode_margin_pairs: List[Tuple[TradingMode, MarginMode]] = [

View File

@ -1777,7 +1777,6 @@ class FreqtradeBot(LoggingMixin):
fee_abs = 0.0 fee_abs = 0.0
fee_cost = 0.0 fee_cost = 0.0
trade_base_currency = self.exchange.get_pair_base_currency(trade.pair) trade_base_currency = self.exchange.get_pair_base_currency(trade.pair)
fee_rate_array: List[float] = [] fee_rate_array: List[float] = []
for exectrade in trades: for exectrade in trades:
amount += exectrade['amount'] amount += exectrade['amount']

View File

@ -821,7 +821,7 @@ class LocalTrade():
self.open_rate = total_stake / total_amount self.open_rate = total_stake / total_amount
self.stake_amount = total_stake / (self.leverage or 1.0) self.stake_amount = total_stake / (self.leverage or 1.0)
self.amount = total_amount self.amount = total_amount
self.fee_open_cost = self.fee_open * self.stake_amount self.fee_open_cost = self.fee_open * total_stake
self.recalc_open_trade_value() self.recalc_open_trade_value()
if self.stop_loss_pct is not None and self.open_rate is not None: if self.stop_loss_pct is not None and self.open_rate is not None:
self.adjust_stop_loss(self.open_rate, self.stop_loss_pct) self.adjust_stop_loss(self.open_rate, self.stop_loss_pct)

View File

@ -3584,6 +3584,9 @@ def test_extract_cost_curr_rate(mocker, default_conf, order, expected) -> None:
'fee': {'currency': 'POINT', 'cost': 2.0, 'rate': None}}, 1, 4.0), 'fee': {'currency': 'POINT', 'cost': 2.0, 'rate': None}}, 1, 4.0),
({'symbol': 'POINT/BTC', 'amount': 0.04, 'cost': 0.5, ({'symbol': 'POINT/BTC', 'amount': 0.04, 'cost': 0.5,
'fee': {'currency': 'POINT', 'cost': 2.0, 'rate': None}}, 2, 8.0), 'fee': {'currency': 'POINT', 'cost': 2.0, 'rate': None}}, 2, 8.0),
# Missing currency
({'symbol': 'ETH/BTC', 'amount': 0.04, 'cost': 0.05,
'fee': {'currency': None, 'cost': 0.005}}, None, None),
]) ])
def test_calculate_fee_rate(mocker, default_conf, order, expected, unknown_fee_rate) -> None: def test_calculate_fee_rate(mocker, default_conf, order, expected, unknown_fee_rate) -> None:
mocker.patch('freqtrade.exchange.Exchange.fetch_ticker', return_value={'last': 0.081}) mocker.patch('freqtrade.exchange.Exchange.fetch_ticker', return_value={'last': 0.081})