Merge pull request #1828 from freqtrade/rpc/trade_tojson
Refactor trade to_json to persistence
This commit is contained in:
		| @@ -213,6 +213,27 @@ class Trade(_DECL_BASE): | |||||||
|         return (f'Trade(id={self.id}, pair={self.pair}, amount={self.amount:.8f}, ' |         return (f'Trade(id={self.id}, pair={self.pair}, amount={self.amount:.8f}, ' | ||||||
|                 f'open_rate={self.open_rate:.8f}, open_since={open_since})') |                 f'open_rate={self.open_rate:.8f}, open_since={open_since})') | ||||||
|  |  | ||||||
|  |     def to_json(self) -> Dict[str, Any]: | ||||||
|  |         return { | ||||||
|  |             'trade_id': self.id, | ||||||
|  |             'pair': self.pair, | ||||||
|  |             'open_date_hum': arrow.get(self.open_date).humanize(), | ||||||
|  |             'open_date': self.open_date.strftime("%Y-%m-%d %H:%M:%S"), | ||||||
|  |             'close_date_hum': (arrow.get(self.close_date).humanize() | ||||||
|  |                                if self.close_date else None), | ||||||
|  |             'close_date': (self.close_date.strftime("%Y-%m-%d %H:%M:%S") | ||||||
|  |                            if self.close_date else None), | ||||||
|  |             'open_rate': self.open_rate, | ||||||
|  |             'close_rate': self.close_rate, | ||||||
|  |             'amount': round(self.amount, 8), | ||||||
|  |             'stake_amount': round(self.stake_amount, 8), | ||||||
|  |             'stop_loss': self.stop_loss, | ||||||
|  |             'stop_loss_pct': (self.stop_loss_pct * 100) if self.stop_loss_pct else None, | ||||||
|  |             'initial_stop_loss': self.initial_stop_loss, | ||||||
|  |             'initial_stop_loss_pct': (self.initial_stop_loss_pct * 100 | ||||||
|  |                                       if self.initial_stop_loss_pct else None), | ||||||
|  |         } | ||||||
|  |  | ||||||
|     def adjust_min_max_rates(self, current_price: float): |     def adjust_min_max_rates(self, current_price: float): | ||||||
|         """ |         """ | ||||||
|         Adjust the max_rate and min_rate. |         Adjust the max_rate and min_rate. | ||||||
|   | |||||||
| @@ -100,28 +100,17 @@ class RPC(object): | |||||||
|                 current_profit = trade.calc_profit_percent(current_rate) |                 current_profit = trade.calc_profit_percent(current_rate) | ||||||
|                 fmt_close_profit = (f'{round(trade.close_profit * 100, 2):.2f}%' |                 fmt_close_profit = (f'{round(trade.close_profit * 100, 2):.2f}%' | ||||||
|                                     if trade.close_profit else None) |                                     if trade.close_profit else None) | ||||||
|                 results.append(dict( |                 trade_dict = trade.to_json() | ||||||
|                     trade_id=trade.id, |                 trade_dict.update(dict( | ||||||
|                     pair=trade.pair, |  | ||||||
|                     base_currency=self._freqtrade.config['stake_currency'], |                     base_currency=self._freqtrade.config['stake_currency'], | ||||||
|                     date=arrow.get(trade.open_date), |  | ||||||
|                     open_rate=trade.open_rate, |  | ||||||
|                     close_rate=trade.close_rate, |  | ||||||
|                     current_rate=current_rate, |  | ||||||
|                     amount=round(trade.amount, 8), |  | ||||||
|                     stake_amount=round(trade.stake_amount, 8), |  | ||||||
|                     close_profit=fmt_close_profit, |                     close_profit=fmt_close_profit, | ||||||
|  |                     current_rate=current_rate, | ||||||
|                     current_profit=round(current_profit * 100, 2), |                     current_profit=round(current_profit * 100, 2), | ||||||
|                     stop_loss=trade.stop_loss, |  | ||||||
|                     stop_loss_pct=(trade.stop_loss_pct * 100) |  | ||||||
|                     if trade.stop_loss_pct else None, |  | ||||||
|                     initial_stop_loss=trade.initial_stop_loss, |  | ||||||
|                     initial_stop_loss_pct=(trade.initial_stop_loss_pct * 100) |  | ||||||
|                     if trade.initial_stop_loss_pct else None, |  | ||||||
|                     open_order='({} {} rem={:.8f})'.format( |                     open_order='({} {} rem={:.8f})'.format( | ||||||
|                         order['type'], order['side'], order['remaining'] |                         order['type'], order['side'], order['remaining'] | ||||||
|                     ) if order else None, |                     ) if order else None, | ||||||
|                 )) |                 )) | ||||||
|  |                 results.append(trade_dict) | ||||||
|             return results |             return results | ||||||
|  |  | ||||||
|     def _rpc_status_table(self) -> DataFrame: |     def _rpc_status_table(self) -> DataFrame: | ||||||
|   | |||||||
| @@ -193,14 +193,11 @@ class Telegram(RPC): | |||||||
|  |  | ||||||
|         try: |         try: | ||||||
|             results = self._rpc_trade_status() |             results = self._rpc_trade_status() | ||||||
|             # pre format data |  | ||||||
|             for result in results: |  | ||||||
|                 result['date'] = result['date'].humanize() |  | ||||||
|  |  | ||||||
|             messages = [] |             messages = [] | ||||||
|             for r in results: |             for r in results: | ||||||
|                 lines = [ |                 lines = [ | ||||||
|                     "*Trade ID:* `{trade_id}` `(since {date})`", |                     "*Trade ID:* `{trade_id}` `(since {open_date_hum})`", | ||||||
|                     "*Current Pair:* {pair}", |                     "*Current Pair:* {pair}", | ||||||
|                     "*Amount:* `{amount} ({stake_amount} {base_currency})`", |                     "*Amount:* `{amount} ({stake_amount} {base_currency})`", | ||||||
|                     "*Open Rate:* `{open_rate:.8f}`", |                     "*Open Rate:* `{open_rate:.8f}`", | ||||||
|   | |||||||
| @@ -47,12 +47,14 @@ def test_rpc_trade_status(default_conf, ticker, fee, markets, mocker) -> None: | |||||||
|  |  | ||||||
|     freqtradebot.create_trade() |     freqtradebot.create_trade() | ||||||
|     results = rpc._rpc_trade_status() |     results = rpc._rpc_trade_status() | ||||||
|  |  | ||||||
|     assert { |     assert { | ||||||
|         'trade_id': 1, |         'trade_id': 1, | ||||||
|         'pair': 'ETH/BTC', |         'pair': 'ETH/BTC', | ||||||
|         'base_currency': 'BTC', |         'base_currency': 'BTC', | ||||||
|         'date': ANY, |         'open_date': ANY, | ||||||
|  |         'open_date_hum': ANY, | ||||||
|  |         'close_date': None, | ||||||
|  |         'close_date_hum': None, | ||||||
|         'open_rate': 1.099e-05, |         'open_rate': 1.099e-05, | ||||||
|         'close_rate': None, |         'close_rate': None, | ||||||
|         'current_rate': 1.098e-05, |         'current_rate': 1.098e-05, | ||||||
| @@ -78,7 +80,10 @@ def test_rpc_trade_status(default_conf, ticker, fee, markets, mocker) -> None: | |||||||
|         'trade_id': 1, |         'trade_id': 1, | ||||||
|         'pair': 'ETH/BTC', |         'pair': 'ETH/BTC', | ||||||
|         'base_currency': 'BTC', |         'base_currency': 'BTC', | ||||||
|         'date': ANY, |         'open_date': ANY, | ||||||
|  |         'open_date_hum': ANY, | ||||||
|  |         'close_date': None, | ||||||
|  |         'close_date_hum': None, | ||||||
|         'open_rate': 1.099e-05, |         'open_rate': 1.099e-05, | ||||||
|         'close_rate': None, |         'close_rate': None, | ||||||
|         'current_rate': ANY, |         'current_rate': ANY, | ||||||
|   | |||||||
| @@ -192,7 +192,10 @@ def test_status(default_conf, update, mocker, fee, ticker, markets) -> None: | |||||||
|             'trade_id': 1, |             'trade_id': 1, | ||||||
|             'pair': 'ETH/BTC', |             'pair': 'ETH/BTC', | ||||||
|             'base_currency': 'BTC', |             'base_currency': 'BTC', | ||||||
|             'date': arrow.utcnow(), |             'open_date': arrow.utcnow(), | ||||||
|  |             'open_date_hum': arrow.utcnow().humanize, | ||||||
|  |             'close_date': None, | ||||||
|  |             'close_date_hum': None, | ||||||
|             'open_rate': 1.099e-05, |             'open_rate': 1.099e-05, | ||||||
|             'close_rate': None, |             'close_rate': None, | ||||||
|             'current_rate': 1.098e-05, |             'current_rate': 1.098e-05, | ||||||
|   | |||||||
| @@ -1,7 +1,8 @@ | |||||||
| # pragma pylint: disable=missing-docstring, C0103 | # pragma pylint: disable=missing-docstring, C0103 | ||||||
| from unittest.mock import MagicMock |  | ||||||
| import logging | import logging | ||||||
|  | from unittest.mock import MagicMock | ||||||
|  |  | ||||||
|  | import arrow | ||||||
| import pytest | import pytest | ||||||
| from sqlalchemy import create_engine | from sqlalchemy import create_engine | ||||||
|  |  | ||||||
| @@ -710,3 +711,69 @@ def test_get_open(default_conf, fee): | |||||||
|     Trade.session.add(trade) |     Trade.session.add(trade) | ||||||
|  |  | ||||||
|     assert len(Trade.get_open_trades()) == 2 |     assert len(Trade.get_open_trades()) == 2 | ||||||
|  |  | ||||||
|  |  | ||||||
|  | def test_to_json(default_conf, fee): | ||||||
|  |     init(default_conf) | ||||||
|  |  | ||||||
|  |     # Simulate dry_run entries | ||||||
|  |     trade = Trade( | ||||||
|  |         pair='ETH/BTC', | ||||||
|  |         stake_amount=0.001, | ||||||
|  |         amount=123.0, | ||||||
|  |         fee_open=fee.return_value, | ||||||
|  |         fee_close=fee.return_value, | ||||||
|  |         open_date=arrow.utcnow().shift(hours=-2).datetime, | ||||||
|  |         open_rate=0.123, | ||||||
|  |         exchange='bittrex', | ||||||
|  |         open_order_id='dry_run_buy_12345' | ||||||
|  |     ) | ||||||
|  |     result = trade.to_json() | ||||||
|  |     assert isinstance(result, dict) | ||||||
|  |     print(result) | ||||||
|  |  | ||||||
|  |     assert result == {'trade_id': None, | ||||||
|  |                       'pair': 'ETH/BTC', | ||||||
|  |                       'open_date_hum': '2 hours ago', | ||||||
|  |                       'open_date': trade.open_date.strftime("%Y-%m-%d %H:%M:%S"), | ||||||
|  |                       'close_date_hum': None, | ||||||
|  |                       'close_date': None, | ||||||
|  |                       'open_rate': 0.123, | ||||||
|  |                       'close_rate': None, | ||||||
|  |                       'amount': 123.0, | ||||||
|  |                       'stake_amount': 0.001, | ||||||
|  |                       'stop_loss': None, | ||||||
|  |                       'stop_loss_pct': None, | ||||||
|  |                       'initial_stop_loss': None, | ||||||
|  |                       'initial_stop_loss_pct': None} | ||||||
|  |  | ||||||
|  |     # Simulate dry_run entries | ||||||
|  |     trade = Trade( | ||||||
|  |         pair='XRP/BTC', | ||||||
|  |         stake_amount=0.001, | ||||||
|  |         amount=100.0, | ||||||
|  |         fee_open=fee.return_value, | ||||||
|  |         fee_close=fee.return_value, | ||||||
|  |         open_date=arrow.utcnow().shift(hours=-2).datetime, | ||||||
|  |         close_date=arrow.utcnow().shift(hours=-1).datetime, | ||||||
|  |         open_rate=0.123, | ||||||
|  |         close_rate=0.125, | ||||||
|  |         exchange='bittrex', | ||||||
|  |     ) | ||||||
|  |     result = trade.to_json() | ||||||
|  |     assert isinstance(result, dict) | ||||||
|  |  | ||||||
|  |     assert result == {'trade_id': None, | ||||||
|  |                       'pair': 'XRP/BTC', | ||||||
|  |                       'open_date_hum': '2 hours ago', | ||||||
|  |                       'open_date': trade.open_date.strftime("%Y-%m-%d %H:%M:%S"), | ||||||
|  |                       'close_date_hum': 'an hour ago', | ||||||
|  |                       'close_date': trade.close_date.strftime("%Y-%m-%d %H:%M:%S"), | ||||||
|  |                       'open_rate': 0.123, | ||||||
|  |                       'close_rate': 0.125, | ||||||
|  |                       'amount': 100.0, | ||||||
|  |                       'stake_amount': 0.001, | ||||||
|  |                       'stop_loss': None, | ||||||
|  |                       'stop_loss_pct': None, | ||||||
|  |                       'initial_stop_loss': None, | ||||||
|  |                       'initial_stop_loss_pct': None} | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user