Override ccxt's marketOrderRequiresPrice settings for gate

This commit is contained in:
Matthias 2023-03-28 06:55:55 +02:00
parent cde432fef0
commit 19b78fbc22
3 changed files with 28 additions and 7 deletions

View File

@ -80,6 +80,8 @@ class Exchange:
"fee_cost_in_contracts": False, # Fee cost needs contract conversion "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
"order_props_in_contracts": ['amount', 'cost', 'filled', 'remaining'], "order_props_in_contracts": ['amount', 'cost', 'filled', 'remaining'],
# Override createMarketBuyOrderRequiresPrice where ccxt has it wrong
"marketOrderRequiresPrice": False,
} }
_ft_has: Dict = {} _ft_has: Dict = {}
_ft_has_futures: Dict = {} _ft_has_futures: Dict = {}
@ -1040,6 +1042,13 @@ class Exchange:
params.update({'reduceOnly': True}) params.update({'reduceOnly': True})
return params return params
def _order_needs_price(self, ordertype: str) -> bool:
return (
ordertype != 'market'
or self._api.options.get("createMarketBuyOrderRequiresPrice", False)
or self._ft_has.get('marketOrderRequiresPrice', False)
)
def create_order( def create_order(
self, self,
*, *,
@ -1062,8 +1071,7 @@ class Exchange:
try: try:
# Set the precision for amount and price(rate) as accepted by the exchange # Set the precision for amount and price(rate) as accepted by the exchange
amount = self.amount_to_precision(pair, self._amount_to_contracts(pair, amount)) amount = self.amount_to_precision(pair, self._amount_to_contracts(pair, amount))
needs_price = (ordertype != 'market' needs_price = self._order_needs_price(ordertype)
or self._api.options.get("createMarketBuyOrderRequiresPrice", False))
rate_for_order = self.price_to_precision(pair, rate) if needs_price else None rate_for_order = self.price_to_precision(pair, rate) if needs_price else None
if not reduceOnly: if not reduceOnly:

View File

@ -5,7 +5,6 @@ from typing import Any, Dict, List, Optional, Tuple
from freqtrade.constants import BuySell from freqtrade.constants import BuySell
from freqtrade.enums import MarginMode, PriceType, TradingMode from freqtrade.enums import MarginMode, PriceType, TradingMode
from freqtrade.exceptions import OperationalException
from freqtrade.exchange import Exchange from freqtrade.exchange import Exchange
from freqtrade.misc import safe_value_fallback2 from freqtrade.misc import safe_value_fallback2
@ -28,10 +27,12 @@ class Gate(Exchange):
"order_time_in_force": ['GTC', 'IOC'], "order_time_in_force": ['GTC', 'IOC'],
"stoploss_order_types": {"limit": "limit"}, "stoploss_order_types": {"limit": "limit"},
"stoploss_on_exchange": True, "stoploss_on_exchange": True,
"marketOrderRequiresPrice": True,
} }
_ft_has_futures: Dict = { _ft_has_futures: Dict = {
"needs_trading_fees": True, "needs_trading_fees": True,
"marketOrderRequiresPrice": False,
"tickers_have_bid_ask": False, "tickers_have_bid_ask": False,
"fee_cost_in_contracts": False, # Set explicitly to false for clarity "fee_cost_in_contracts": False, # Set explicitly to false for clarity
"order_props_in_contracts": ['amount', 'filled', 'remaining'], "order_props_in_contracts": ['amount', 'filled', 'remaining'],

View File

@ -1439,7 +1439,10 @@ def test_buy_prod(default_conf, mocker, exchange_name):
assert api_mock.create_order.call_args[0][1] == order_type assert api_mock.create_order.call_args[0][1] == order_type
assert api_mock.create_order.call_args[0][2] == 'buy' assert api_mock.create_order.call_args[0][2] == 'buy'
assert api_mock.create_order.call_args[0][3] == 1 assert api_mock.create_order.call_args[0][3] == 1
assert api_mock.create_order.call_args[0][4] is None if exchange._order_needs_price(order_type):
assert api_mock.create_order.call_args[0][4] == 200
else:
assert api_mock.create_order.call_args[0][4] is None
api_mock.create_order.reset_mock() api_mock.create_order.reset_mock()
order_type = 'limit' order_type = 'limit'
@ -1544,7 +1547,10 @@ def test_buy_considers_time_in_force(default_conf, mocker, exchange_name):
assert api_mock.create_order.call_args[0][1] == order_type assert api_mock.create_order.call_args[0][1] == order_type
assert api_mock.create_order.call_args[0][2] == 'buy' assert api_mock.create_order.call_args[0][2] == 'buy'
assert api_mock.create_order.call_args[0][3] == 1 assert api_mock.create_order.call_args[0][3] == 1
assert api_mock.create_order.call_args[0][4] is None if exchange._order_needs_price(order_type):
assert api_mock.create_order.call_args[0][4] == 200
else:
assert api_mock.create_order.call_args[0][4] is None
# Market orders should not send timeInForce!! # Market orders should not send timeInForce!!
assert "timeInForce" not in api_mock.create_order.call_args[0][5] assert "timeInForce" not in api_mock.create_order.call_args[0][5]
@ -1588,7 +1594,10 @@ def test_sell_prod(default_conf, mocker, exchange_name):
assert api_mock.create_order.call_args[0][1] == order_type assert api_mock.create_order.call_args[0][1] == order_type
assert api_mock.create_order.call_args[0][2] == 'sell' assert api_mock.create_order.call_args[0][2] == 'sell'
assert api_mock.create_order.call_args[0][3] == 1 assert api_mock.create_order.call_args[0][3] == 1
assert api_mock.create_order.call_args[0][4] is None if exchange._order_needs_price(order_type):
assert api_mock.create_order.call_args[0][4] == 200
else:
assert api_mock.create_order.call_args[0][4] is None
api_mock.create_order.reset_mock() api_mock.create_order.reset_mock()
order_type = 'limit' order_type = 'limit'
@ -1682,7 +1691,10 @@ def test_sell_considers_time_in_force(default_conf, mocker, exchange_name):
assert api_mock.create_order.call_args[0][1] == order_type assert api_mock.create_order.call_args[0][1] == order_type
assert api_mock.create_order.call_args[0][2] == 'sell' assert api_mock.create_order.call_args[0][2] == 'sell'
assert api_mock.create_order.call_args[0][3] == 1 assert api_mock.create_order.call_args[0][3] == 1
assert api_mock.create_order.call_args[0][4] is None if exchange._order_needs_price(order_type):
assert api_mock.create_order.call_args[0][4] == 200
else:
assert api_mock.create_order.call_args[0][4] is None
# Market orders should not send timeInForce!! # Market orders should not send timeInForce!!
assert "timeInForce" not in api_mock.create_order.call_args[0][5] assert "timeInForce" not in api_mock.create_order.call_args[0][5]