updated for PR #6653
This commit is contained in:
parent
5fa96174e1
commit
28f4a3b373
@ -129,6 +129,7 @@ Telegram is not mandatory. However, this is a great way to control your bot. Mor
|
|||||||
- `/status <trade_id>|[table]`: Lists all or specific open trades.
|
- `/status <trade_id>|[table]`: Lists all or specific open trades.
|
||||||
- `/profit [<n>]`: Lists cumulative profit from all finished trades, over the last n days.
|
- `/profit [<n>]`: Lists cumulative profit from all finished trades, over the last n days.
|
||||||
- `/force_exit <trade_id>|all`: Instantly exits the given trade (Ignoring `minimum_roi`).
|
- `/force_exit <trade_id>|all`: Instantly exits the given trade (Ignoring `minimum_roi`).
|
||||||
|
- `/fe <trade_id>|all`: Alias to `/force_exit`
|
||||||
- `/performance`: Show performance of each finished trade grouped by pair
|
- `/performance`: Show performance of each finished trade grouped by pair
|
||||||
- `/balance`: Show account balance per currency.
|
- `/balance`: Show account balance per currency.
|
||||||
- `/daily <n>`: Shows profit or loss per day, over the last n days.
|
- `/daily <n>`: Shows profit or loss per day, over the last n days.
|
||||||
|
@ -147,8 +147,8 @@ python3 scripts/rest_client.py --config rest_config.json <command> [optional par
|
|||||||
| `profit` | Display a summary of your profit/loss from close trades and some stats about your performance.
|
| `profit` | Display a summary of your profit/loss from close trades and some stats about your performance.
|
||||||
| `force_exit <trade_id>` | Instantly exits the given trade (Ignoring `minimum_roi`).
|
| `force_exit <trade_id>` | Instantly exits the given trade (Ignoring `minimum_roi`).
|
||||||
| `force_exit all` | Instantly exits all open trades (Ignoring `minimum_roi`).
|
| `force_exit all` | Instantly exits all open trades (Ignoring `minimum_roi`).
|
||||||
| `forceenter <pair> [rate]` | Instantly enters the given pair. Rate is optional. (`forcebuy_enable` must be set to True)
|
| `force_enter <pair> [rate]` | Instantly enters the given pair. Rate is optional. (`forcebuy_enable` must be set to True)
|
||||||
| `forceenter <pair> <side> [rate]` | Instantly longs or shorts the given pair. Rate is optional. (`forcebuy_enable` must be set to True)
|
| `force_enter <pair> <side> [rate]` | Instantly longs or shorts the given pair. Rate is optional. (`forcebuy_enable` must be set to True)
|
||||||
| `performance` | Show performance of each finished trade grouped by pair.
|
| `performance` | Show performance of each finished trade grouped by pair.
|
||||||
| `balance` | Show account balance per currency.
|
| `balance` | Show account balance per currency.
|
||||||
| `daily <n>` | Shows profit or loss per day, over the last n days (n defaults to 7).
|
| `daily <n>` | Shows profit or loss per day, over the last n days (n defaults to 7).
|
||||||
@ -216,7 +216,7 @@ forcebuy
|
|||||||
:param pair: Pair to buy (ETH/BTC)
|
:param pair: Pair to buy (ETH/BTC)
|
||||||
:param price: Optional - price to buy
|
:param price: Optional - price to buy
|
||||||
|
|
||||||
forceenter
|
force_enter
|
||||||
Force entering a trade
|
Force entering a trade
|
||||||
|
|
||||||
:param pair: Pair to buy (ETH/BTC)
|
:param pair: Pair to buy (ETH/BTC)
|
||||||
|
@ -9,6 +9,8 @@ You can use the quick summary as checklist. Please refer to the detailed section
|
|||||||
|
|
||||||
## Quick summary / migration checklist
|
## Quick summary / migration checklist
|
||||||
|
|
||||||
|
Note : `force_exit`, `force_enter`, `emergency_exit` are changed to `force_exit`, `force_enter`, `emergency_exit` respectively.
|
||||||
|
|
||||||
* Strategy methods:
|
* Strategy methods:
|
||||||
* [`populate_buy_trend()` -> `populate_entry_trend()`](#populate_buy_trend)
|
* [`populate_buy_trend()` -> `populate_entry_trend()`](#populate_buy_trend)
|
||||||
* [`populate_sell_trend()` -> `populate_exit_trend()`](#populate_sell_trend)
|
* [`populate_sell_trend()` -> `populate_exit_trend()`](#populate_sell_trend)
|
||||||
@ -331,6 +333,7 @@ After:
|
|||||||
#### `order_types`
|
#### `order_types`
|
||||||
|
|
||||||
`order_types` have changed all wordings from `buy` to `entry` - and `sell` to `exit`.
|
`order_types` have changed all wordings from `buy` to `entry` - and `sell` to `exit`.
|
||||||
|
And two words are joined with `_`.
|
||||||
|
|
||||||
``` python hl_lines="2-6"
|
``` python hl_lines="2-6"
|
||||||
order_types = {
|
order_types = {
|
||||||
|
@ -243,7 +243,7 @@ def _validate_time_in_force(conf: Dict[str, Any]) -> None:
|
|||||||
def _validate_order_types(conf: Dict[str, Any]) -> None:
|
def _validate_order_types(conf: Dict[str, Any]) -> None:
|
||||||
|
|
||||||
order_types = conf.get('order_types', {})
|
order_types = conf.get('order_types', {})
|
||||||
if any(x in order_types for x in ['buy', 'sell', 'emergencysell', 'forcebuy', 'forcesell']):
|
if any(x in order_types for x in ['buy', 'sell', 'emergencysell', 'forcebuy', 'forcesell', 'emergencyexit', 'forceexit', 'forceentry']):
|
||||||
if conf.get('trading_mode', TradingMode.SPOT) != TradingMode.SPOT:
|
if conf.get('trading_mode', TradingMode.SPOT) != TradingMode.SPOT:
|
||||||
raise OperationalException(
|
raise OperationalException(
|
||||||
"Please migrate your order_types settings to use the new wording.")
|
"Please migrate your order_types settings to use the new wording.")
|
||||||
@ -258,6 +258,9 @@ def _validate_order_types(conf: Dict[str, Any]) -> None:
|
|||||||
('emergencysell', 'emergency_exit'),
|
('emergencysell', 'emergency_exit'),
|
||||||
('forcesell', 'force_exit'),
|
('forcesell', 'force_exit'),
|
||||||
('forcebuy', 'force_entry'),
|
('forcebuy', 'force_entry'),
|
||||||
|
('emergencyexit', 'emergency_exit'),
|
||||||
|
('forceexit', 'force_exit'),
|
||||||
|
('forceentry', 'force_entry'),
|
||||||
]:
|
]:
|
||||||
|
|
||||||
process_deprecated_setting(conf, 'order_types', o, 'order_types', n)
|
process_deprecated_setting(conf, 'order_types', o, 'order_types', n)
|
||||||
|
@ -316,7 +316,7 @@ class ForceEnterPayload(BaseModel):
|
|||||||
entry_tag: Optional[str]
|
entry_tag: Optional[str]
|
||||||
|
|
||||||
|
|
||||||
class Force_exitPayload(BaseModel):
|
class ForceExitPayload(BaseModel):
|
||||||
tradeid: str
|
tradeid: str
|
||||||
ordertype: Optional[OrderTypeValues]
|
ordertype: Optional[OrderTypeValues]
|
||||||
|
|
||||||
|
@ -15,7 +15,7 @@ from freqtrade.rpc import RPC
|
|||||||
from freqtrade.rpc.api_server.api_schemas import (AvailablePairs, Balances, BlacklistPayload,
|
from freqtrade.rpc.api_server.api_schemas import (AvailablePairs, Balances, BlacklistPayload,
|
||||||
BlacklistResponse, Count, Daily,
|
BlacklistResponse, Count, Daily,
|
||||||
DeleteLockRequest, DeleteTrade, ForceEnterPayload,
|
DeleteLockRequest, DeleteTrade, ForceEnterPayload,
|
||||||
ForceEnterResponse, Force_exitPayload, Health,
|
ForceEnterResponse, ForceExitPayload, Health,
|
||||||
Locks, Logs, OpenTradeSchema, PairHistory,
|
Locks, Logs, OpenTradeSchema, PairHistory,
|
||||||
PerformanceEntry, Ping, PlotConfig, Profit,
|
PerformanceEntry, Ping, PlotConfig, Profit,
|
||||||
ResultMsg, ShowConfig, Stats, StatusMsg,
|
ResultMsg, ShowConfig, Stats, StatusMsg,
|
||||||
@ -136,7 +136,7 @@ def show_config(rpc: Optional[RPC] = Depends(get_rpc_optional), config=Depends(g
|
|||||||
|
|
||||||
|
|
||||||
# /forcebuy is deprecated with short addition. use Force_entry instead
|
# /forcebuy is deprecated with short addition. use Force_entry instead
|
||||||
@router.post('/forceenter', response_model=ForceEnterResponse, tags=['trading'])
|
@router.post('/force_enter', response_model=ForceEnterResponse, tags=['trading'])
|
||||||
@router.post('/forcebuy', response_model=ForceEnterResponse, tags=['trading'])
|
@router.post('/forcebuy', response_model=ForceEnterResponse, tags=['trading'])
|
||||||
def force_entry(payload: ForceEnterPayload, rpc: RPC = Depends(get_rpc)):
|
def force_entry(payload: ForceEnterPayload, rpc: RPC = Depends(get_rpc)):
|
||||||
ordertype = payload.ordertype.value if payload.ordertype else None
|
ordertype = payload.ordertype.value if payload.ordertype else None
|
||||||
@ -156,7 +156,7 @@ def force_entry(payload: ForceEnterPayload, rpc: RPC = Depends(get_rpc)):
|
|||||||
|
|
||||||
@router.post('/force_exit', response_model=ResultMsg, tags=['trading'])
|
@router.post('/force_exit', response_model=ResultMsg, tags=['trading'])
|
||||||
@router.post('/forcesell', response_model=ResultMsg, tags=['trading'])
|
@router.post('/forcesell', response_model=ResultMsg, tags=['trading'])
|
||||||
def forcesell(payload: Force_exitPayload, rpc: RPC = Depends(get_rpc)):
|
def forcesell(payload: ForceExitPayload, rpc: RPC = Depends(get_rpc)):
|
||||||
ordertype = payload.ordertype.value if payload.ordertype else None
|
ordertype = payload.ordertype.value if payload.ordertype else None
|
||||||
return rpc._rpc_force_exit(payload.tradeid, ordertype)
|
return rpc._rpc_force_exit(payload.tradeid, ordertype)
|
||||||
|
|
||||||
|
@ -115,7 +115,7 @@ class Telegram(RPCHandler):
|
|||||||
r'/stopbuy$', r'/reload_config$', r'/show_config$',
|
r'/stopbuy$', r'/reload_config$', r'/show_config$',
|
||||||
r'/logs$', r'/whitelist$', r'/blacklist$', r'/bl_delete$',
|
r'/logs$', r'/whitelist$', r'/blacklist$', r'/bl_delete$',
|
||||||
r'/weekly$', r'/weekly \d+$', r'/monthly$', r'/monthly \d+$',
|
r'/weekly$', r'/weekly \d+$', r'/monthly$', r'/monthly \d+$',
|
||||||
r'/forcebuy$', r'/forcelong$', r'/forceshort$',
|
r'/forcebuy$', r'/forcelong$', r'/forceshort$', r'/force_exit$',
|
||||||
r'/edge$', r'/health$', r'/help$', r'/version$']
|
r'/edge$', r'/health$', r'/help$', r'/version$']
|
||||||
# Create keys for generation
|
# Create keys for generation
|
||||||
valid_keys_print = [k.replace('$', '') for k in valid_keys]
|
valid_keys_print = [k.replace('$', '') for k in valid_keys]
|
||||||
@ -153,11 +153,11 @@ class Telegram(RPCHandler):
|
|||||||
CommandHandler('balance', self._balance),
|
CommandHandler('balance', self._balance),
|
||||||
CommandHandler('start', self._start),
|
CommandHandler('start', self._start),
|
||||||
CommandHandler('stop', self._stop),
|
CommandHandler('stop', self._stop),
|
||||||
CommandHandler(['forcesell', 'force_exit'], self._force_exit),
|
CommandHandler(['forcesell', 'force_exit', 'fe'], self._force_exit),
|
||||||
CommandHandler(['forcebuy', 'forcelong'], partial(
|
CommandHandler(['forcebuy', 'forcelong'], partial(
|
||||||
self._forceenter, order_side=SignalDirection.LONG)),
|
self._force_enter, order_side=SignalDirection.LONG)),
|
||||||
CommandHandler('forceshort', partial(
|
CommandHandler('forceshort', partial(
|
||||||
self._forceenter, order_side=SignalDirection.SHORT)),
|
self._force_enter, order_side=SignalDirection.SHORT)),
|
||||||
CommandHandler('trades', self._trades),
|
CommandHandler('trades', self._trades),
|
||||||
CommandHandler('delete', self._delete_trade),
|
CommandHandler('delete', self._delete_trade),
|
||||||
CommandHandler('performance', self._performance),
|
CommandHandler('performance', self._performance),
|
||||||
@ -197,7 +197,7 @@ class Telegram(RPCHandler):
|
|||||||
pattern='update_exit_reason_performance'),
|
pattern='update_exit_reason_performance'),
|
||||||
CallbackQueryHandler(self._mix_tag_performance, pattern='update_mix_tag_performance'),
|
CallbackQueryHandler(self._mix_tag_performance, pattern='update_mix_tag_performance'),
|
||||||
CallbackQueryHandler(self._count, pattern='update_count'),
|
CallbackQueryHandler(self._count, pattern='update_count'),
|
||||||
CallbackQueryHandler(self._forceenter_inline),
|
CallbackQueryHandler(self._force_enter_inline),
|
||||||
]
|
]
|
||||||
for handle in handles:
|
for handle in handles:
|
||||||
self._updater.dispatcher.add_handler(handle)
|
self._updater.dispatcher.add_handler(handle)
|
||||||
@ -946,14 +946,14 @@ class Telegram(RPCHandler):
|
|||||||
except RPCException as e:
|
except RPCException as e:
|
||||||
self._send_msg(str(e))
|
self._send_msg(str(e))
|
||||||
|
|
||||||
def _forceenter_action(self, pair, price: Optional[float], order_side: SignalDirection):
|
def _force_enter_action(self, pair, price: Optional[float], order_side: SignalDirection):
|
||||||
if pair != 'cancel':
|
if pair != 'cancel':
|
||||||
try:
|
try:
|
||||||
self._rpc._rpc_force_entry(pair, price, order_side=order_side)
|
self._rpc._rpc_force_entry(pair, price, order_side=order_side)
|
||||||
except RPCException as e:
|
except RPCException as e:
|
||||||
self._send_msg(str(e))
|
self._send_msg(str(e))
|
||||||
|
|
||||||
def _forceenter_inline(self, update: Update, _: CallbackContext) -> None:
|
def _force_enter_inline(self, update: Update, _: CallbackContext) -> None:
|
||||||
if update.callback_query:
|
if update.callback_query:
|
||||||
query = update.callback_query
|
query = update.callback_query
|
||||||
if query.data and '_||_' in query.data:
|
if query.data and '_||_' in query.data:
|
||||||
@ -961,7 +961,7 @@ class Telegram(RPCHandler):
|
|||||||
order_side = SignalDirection(side)
|
order_side = SignalDirection(side)
|
||||||
query.answer()
|
query.answer()
|
||||||
query.edit_message_text(text=f"Manually entering {order_side} for {pair}")
|
query.edit_message_text(text=f"Manually entering {order_side} for {pair}")
|
||||||
self._forceenter_action(pair, None, order_side)
|
self._force_enter_action(pair, None, order_side)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def _layout_inline_keyboard(buttons: List[InlineKeyboardButton],
|
def _layout_inline_keyboard(buttons: List[InlineKeyboardButton],
|
||||||
@ -969,7 +969,7 @@ class Telegram(RPCHandler):
|
|||||||
return [buttons[i:i + cols] for i in range(0, len(buttons), cols)]
|
return [buttons[i:i + cols] for i in range(0, len(buttons), cols)]
|
||||||
|
|
||||||
@authorized_only
|
@authorized_only
|
||||||
def _forceenter(
|
def _force_enter(
|
||||||
self, update: Update, context: CallbackContext, order_side: SignalDirection) -> None:
|
self, update: Update, context: CallbackContext, order_side: SignalDirection) -> None:
|
||||||
"""
|
"""
|
||||||
Handler for /forcelong <asset> <price> and `/forceshort <asset> <price>
|
Handler for /forcelong <asset> <price> and `/forceshort <asset> <price>
|
||||||
@ -981,7 +981,7 @@ class Telegram(RPCHandler):
|
|||||||
if context.args:
|
if context.args:
|
||||||
pair = context.args[0]
|
pair = context.args[0]
|
||||||
price = float(context.args[1]) if len(context.args) > 1 else None
|
price = float(context.args[1]) if len(context.args) > 1 else None
|
||||||
self._forceenter_action(pair, price, order_side)
|
self._force_enter_action(pair, price, order_side)
|
||||||
else:
|
else:
|
||||||
whitelist = self._rpc._rpc_whitelist()['whitelist']
|
whitelist = self._rpc._rpc_whitelist()['whitelist']
|
||||||
pair_buttons = [
|
pair_buttons = [
|
||||||
@ -1359,12 +1359,12 @@ class Telegram(RPCHandler):
|
|||||||
:param update: message update
|
:param update: message update
|
||||||
:return: None
|
:return: None
|
||||||
"""
|
"""
|
||||||
forceenter_text = ("*/forcelong <pair> [<rate>]:* `Instantly buys the given pair. "
|
force_enter_text = ("*/forcelong <pair> [<rate>]:* `Instantly buys the given pair. "
|
||||||
"Optionally takes a rate at which to buy "
|
"Optionally takes a rate at which to buy "
|
||||||
"(only applies to limit orders).` \n"
|
"(only applies to limit orders).` \n"
|
||||||
)
|
)
|
||||||
if self._rpc._freqtrade.trading_mode != TradingMode.SPOT:
|
if self._rpc._freqtrade.trading_mode != TradingMode.SPOT:
|
||||||
forceenter_text += ("*/forceshort <pair> [<rate>]:* `Instantly shorts the given pair. "
|
force_enter_text += ("*/forceshort <pair> [<rate>]:* `Instantly shorts the given pair. "
|
||||||
"Optionally takes a rate at which to sell "
|
"Optionally takes a rate at which to sell "
|
||||||
"(only applies to limit orders).` \n")
|
"(only applies to limit orders).` \n")
|
||||||
message = (
|
message = (
|
||||||
@ -1375,7 +1375,8 @@ class Telegram(RPCHandler):
|
|||||||
"*/stopbuy:* `Stops buying, but handles open trades gracefully` \n"
|
"*/stopbuy:* `Stops buying, but handles open trades gracefully` \n"
|
||||||
"*/force_exit <trade_id>|all:* `Instantly exits the given trade or all trades, "
|
"*/force_exit <trade_id>|all:* `Instantly exits the given trade or all trades, "
|
||||||
"regardless of profit`\n"
|
"regardless of profit`\n"
|
||||||
f"{forceenter_text if self._config.get('forcebuy_enable', False) else ''}"
|
"*/fe <trade_id>|all:* `Alias to /force_exit`"
|
||||||
|
f"{force_enter_text if self._config.get('forcebuy_enable', False) else ''}"
|
||||||
"*/delete <trade_id>:* `Instantly delete the given trade in the database`\n"
|
"*/delete <trade_id>:* `Instantly delete the given trade in the database`\n"
|
||||||
"*/whitelist:* `Show current whitelist` \n"
|
"*/whitelist:* `Show current whitelist` \n"
|
||||||
"*/blacklist [pair]:* `Show current blacklist, or adds one or more pairs "
|
"*/blacklist [pair]:* `Show current blacklist, or adds one or more pairs "
|
||||||
|
@ -261,7 +261,7 @@ class FtRestClient():
|
|||||||
}
|
}
|
||||||
return self._post("forcebuy", data=data)
|
return self._post("forcebuy", data=data)
|
||||||
|
|
||||||
def forceenter(self, pair, side, price=None):
|
def force_enter(self, pair, side, price=None):
|
||||||
"""Force entering a trade
|
"""Force entering a trade
|
||||||
|
|
||||||
:param pair: Pair to buy (ETH/BTC)
|
:param pair: Pair to buy (ETH/BTC)
|
||||||
@ -273,7 +273,7 @@ class FtRestClient():
|
|||||||
"side": side,
|
"side": side,
|
||||||
"price": price,
|
"price": price,
|
||||||
}
|
}
|
||||||
return self._post("forceenter", data=data)
|
return self._post("force_enter", data=data)
|
||||||
|
|
||||||
def forcesell(self, tradeid):
|
def forcesell(self, tradeid):
|
||||||
"""Force-sell a trade.
|
"""Force-sell a trade.
|
||||||
|
@ -1075,7 +1075,7 @@ def test_api_whitelist(botclient):
|
|||||||
|
|
||||||
@pytest.mark.parametrize('endpoint', [
|
@pytest.mark.parametrize('endpoint', [
|
||||||
'forcebuy',
|
'forcebuy',
|
||||||
'forceenter',
|
'force_enter',
|
||||||
])
|
])
|
||||||
def test_api_force_entry(botclient, mocker, fee, endpoint):
|
def test_api_force_entry(botclient, mocker, fee, endpoint):
|
||||||
ftbot, client = botclient
|
ftbot, client = botclient
|
||||||
|
@ -1231,7 +1231,7 @@ def test_forcesell_handle_invalid(default_conf, update, mocker) -> None:
|
|||||||
assert 'invalid argument' in msg_mock.call_args_list[0][0][0]
|
assert 'invalid argument' in msg_mock.call_args_list[0][0][0]
|
||||||
|
|
||||||
|
|
||||||
def test_forceenter_handle(default_conf, update, mocker) -> None:
|
def test_force_enter_handle(default_conf, update, mocker) -> None:
|
||||||
mocker.patch('freqtrade.rpc.rpc.CryptoToFiatConverter._find_price', return_value=15000.0)
|
mocker.patch('freqtrade.rpc.rpc.CryptoToFiatConverter._find_price', return_value=15000.0)
|
||||||
|
|
||||||
fbuy_mock = MagicMock(return_value=None)
|
fbuy_mock = MagicMock(return_value=None)
|
||||||
@ -1243,7 +1243,7 @@ def test_forceenter_handle(default_conf, update, mocker) -> None:
|
|||||||
# /forcelong ETH/BTC
|
# /forcelong ETH/BTC
|
||||||
context = MagicMock()
|
context = MagicMock()
|
||||||
context.args = ["ETH/BTC"]
|
context.args = ["ETH/BTC"]
|
||||||
telegram._forceenter(update=update, context=context, order_side=SignalDirection.LONG)
|
telegram._force_enter(update=update, context=context, order_side=SignalDirection.LONG)
|
||||||
|
|
||||||
assert fbuy_mock.call_count == 1
|
assert fbuy_mock.call_count == 1
|
||||||
assert fbuy_mock.call_args_list[0][0][0] == 'ETH/BTC'
|
assert fbuy_mock.call_args_list[0][0][0] == 'ETH/BTC'
|
||||||
@ -1256,7 +1256,7 @@ def test_forceenter_handle(default_conf, update, mocker) -> None:
|
|||||||
# /forcelong ETH/BTC 0.055
|
# /forcelong ETH/BTC 0.055
|
||||||
context = MagicMock()
|
context = MagicMock()
|
||||||
context.args = ["ETH/BTC", "0.055"]
|
context.args = ["ETH/BTC", "0.055"]
|
||||||
telegram._forceenter(update=update, context=context, order_side=SignalDirection.LONG)
|
telegram._force_enter(update=update, context=context, order_side=SignalDirection.LONG)
|
||||||
|
|
||||||
assert fbuy_mock.call_count == 1
|
assert fbuy_mock.call_count == 1
|
||||||
assert fbuy_mock.call_args_list[0][0][0] == 'ETH/BTC'
|
assert fbuy_mock.call_args_list[0][0][0] == 'ETH/BTC'
|
||||||
@ -1264,20 +1264,20 @@ def test_forceenter_handle(default_conf, update, mocker) -> None:
|
|||||||
assert fbuy_mock.call_args_list[0][0][1] == 0.055
|
assert fbuy_mock.call_args_list[0][0][1] == 0.055
|
||||||
|
|
||||||
|
|
||||||
def test_forceenter_handle_exception(default_conf, update, mocker) -> None:
|
def test_force_enter_handle_exception(default_conf, update, mocker) -> None:
|
||||||
mocker.patch('freqtrade.rpc.rpc.CryptoToFiatConverter._find_price', return_value=15000.0)
|
mocker.patch('freqtrade.rpc.rpc.CryptoToFiatConverter._find_price', return_value=15000.0)
|
||||||
|
|
||||||
telegram, freqtradebot, msg_mock = get_telegram_testobject(mocker, default_conf)
|
telegram, freqtradebot, msg_mock = get_telegram_testobject(mocker, default_conf)
|
||||||
patch_get_signal(freqtradebot)
|
patch_get_signal(freqtradebot)
|
||||||
|
|
||||||
update.message.text = '/forcebuy ETH/Nonepair'
|
update.message.text = '/forcebuy ETH/Nonepair'
|
||||||
telegram._forceenter(update=update, context=MagicMock(), order_side=SignalDirection.LONG)
|
telegram._force_enter(update=update, context=MagicMock(), order_side=SignalDirection.LONG)
|
||||||
|
|
||||||
assert msg_mock.call_count == 1
|
assert msg_mock.call_count == 1
|
||||||
assert msg_mock.call_args_list[0][0][0] == 'Force_entry not enabled.'
|
assert msg_mock.call_args_list[0][0][0] == 'Force_entry not enabled.'
|
||||||
|
|
||||||
|
|
||||||
def test_forceenter_no_pair(default_conf, update, mocker) -> None:
|
def test_force_enter_no_pair(default_conf, update, mocker) -> None:
|
||||||
mocker.patch('freqtrade.rpc.rpc.CryptoToFiatConverter._find_price', return_value=15000.0)
|
mocker.patch('freqtrade.rpc.rpc.CryptoToFiatConverter._find_price', return_value=15000.0)
|
||||||
|
|
||||||
fbuy_mock = MagicMock(return_value=None)
|
fbuy_mock = MagicMock(return_value=None)
|
||||||
@ -1289,7 +1289,7 @@ def test_forceenter_no_pair(default_conf, update, mocker) -> None:
|
|||||||
|
|
||||||
context = MagicMock()
|
context = MagicMock()
|
||||||
context.args = []
|
context.args = []
|
||||||
telegram._forceenter(update=update, context=context, order_side=SignalDirection.LONG)
|
telegram._force_enter(update=update, context=context, order_side=SignalDirection.LONG)
|
||||||
|
|
||||||
assert fbuy_mock.call_count == 0
|
assert fbuy_mock.call_count == 0
|
||||||
assert msg_mock.call_count == 1
|
assert msg_mock.call_count == 1
|
||||||
@ -1301,7 +1301,7 @@ def test_forceenter_no_pair(default_conf, update, mocker) -> None:
|
|||||||
update = MagicMock()
|
update = MagicMock()
|
||||||
update.callback_query = MagicMock()
|
update.callback_query = MagicMock()
|
||||||
update.callback_query.data = 'XRP/USDT_||_long'
|
update.callback_query.data = 'XRP/USDT_||_long'
|
||||||
telegram._forceenter_inline(update, None)
|
telegram._force_enter_inline(update, None)
|
||||||
assert fbuy_mock.call_count == 1
|
assert fbuy_mock.call_count == 1
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user