From ad5c8f601cb8455bcb16d7ae53eefab1f1d88a94 Mon Sep 17 00:00:00 2001 From: Matthias Date: Thu, 2 Dec 2021 20:19:22 +0100 Subject: [PATCH] Simplify datahandler classes by exploiting commonalities --- freqtrade/data/history/hdf5datahandler.py | 40 ++--------------------- freqtrade/data/history/idatahandler.py | 32 ++++++++++++++++-- freqtrade/data/history/jsondatahandler.py | 24 -------------- 3 files changed, 33 insertions(+), 63 deletions(-) diff --git a/freqtrade/data/history/hdf5datahandler.py b/freqtrade/data/history/hdf5datahandler.py index 1ede3de98..49fac99ea 100644 --- a/freqtrade/data/history/hdf5datahandler.py +++ b/freqtrade/data/history/hdf5datahandler.py @@ -6,7 +6,6 @@ from typing import List, Optional import numpy as np import pandas as pd -from freqtrade import misc from freqtrade.configuration import TimeRange from freqtrade.constants import (DEFAULT_DATAFRAME_COLUMNS, DEFAULT_TRADES_COLUMNS, ListPairsWithTimeframes, TradeList) @@ -99,19 +98,6 @@ class HDF5DataHandler(IDataHandler): 'low': 'float', 'close': 'float', 'volume': 'float'}) return pairdata - def ohlcv_purge(self, pair: str, timeframe: str) -> bool: - """ - Remove data for this pair - :param pair: Delete data for this pair. - :param timeframe: Timeframe (e.g. "5m") - :return: True when deleted, false if file did not exist. - """ - filename = self._pair_data_filename(self._datadir, pair, timeframe) - if filename.exists(): - filename.unlink() - return True - return False - def ohlcv_append(self, pair: str, timeframe: str, data: pd.DataFrame) -> None: """ Append data to existing data structures @@ -180,17 +166,9 @@ class HDF5DataHandler(IDataHandler): trades[['id', 'type']] = trades[['id', 'type']].replace({np.nan: None}) return trades.values.tolist() - def trades_purge(self, pair: str) -> bool: - """ - Remove data for this pair - :param pair: Delete data for this pair. - :return: True when deleted, false if file did not exist. - """ - filename = self._pair_trades_filename(self._datadir, pair) - if filename.exists(): - filename.unlink() - return True - return False + @classmethod + def _get_file_extension(cls): + return "h5" @classmethod def _pair_ohlcv_key(cls, pair: str, timeframe: str) -> str: @@ -199,15 +177,3 @@ class HDF5DataHandler(IDataHandler): @classmethod def _pair_trades_key(cls, pair: str) -> str: return f"{pair}/trades" - - @classmethod - def _pair_data_filename(cls, datadir: Path, pair: str, timeframe: str) -> Path: - pair_s = misc.pair_to_filename(pair) - filename = datadir.joinpath(f'{pair_s}-{timeframe}.h5') - return filename - - @classmethod - def _pair_trades_filename(cls, datadir: Path, pair: str) -> Path: - pair_s = misc.pair_to_filename(pair) - filename = datadir.joinpath(f'{pair_s}-trades.h5') - return filename diff --git a/freqtrade/data/history/idatahandler.py b/freqtrade/data/history/idatahandler.py index 05052b2d7..578d0b5bf 100644 --- a/freqtrade/data/history/idatahandler.py +++ b/freqtrade/data/history/idatahandler.py @@ -12,6 +12,7 @@ from typing import List, Optional, Type from pandas import DataFrame +from freqtrade import misc from freqtrade.configuration import TimeRange from freqtrade.constants import ListPairsWithTimeframes, TradeList from freqtrade.data.converter import clean_ohlcv_dataframe, trades_remove_duplicates, trim_dataframe @@ -26,6 +27,13 @@ class IDataHandler(ABC): def __init__(self, datadir: Path) -> None: self._datadir = datadir + @classmethod + def _get_file_extension(cls) -> str: + """ + Get file extension for this particular datahandler + """ + raise NotImplementedError() + @abstractclassmethod def ohlcv_get_available_data(cls, datadir: Path) -> ListPairsWithTimeframes: """ @@ -70,7 +78,6 @@ class IDataHandler(ABC): :return: DataFrame with ohlcv data, or empty DataFrame """ - @abstractmethod def ohlcv_purge(self, pair: str, timeframe: str) -> bool: """ Remove data for this pair @@ -78,6 +85,11 @@ class IDataHandler(ABC): :param timeframe: Timeframe (e.g. "5m") :return: True when deleted, false if file did not exist. """ + filename = self._pair_data_filename(self._datadir, pair, timeframe) + if filename.exists(): + filename.unlink() + return True + return False @abstractmethod def ohlcv_append(self, pair: str, timeframe: str, data: DataFrame) -> None: @@ -123,13 +135,17 @@ class IDataHandler(ABC): :return: List of trades """ - @abstractmethod def trades_purge(self, pair: str) -> bool: """ Remove data for this pair :param pair: Delete data for this pair. :return: True when deleted, false if file did not exist. """ + filename = self._pair_trades_filename(self._datadir, pair) + if filename.exists(): + filename.unlink() + return True + return False def trades_load(self, pair: str, timerange: Optional[TimeRange] = None) -> TradeList: """ @@ -141,6 +157,18 @@ class IDataHandler(ABC): """ return trades_remove_duplicates(self._trades_load(pair, timerange=timerange)) + @classmethod + def _pair_data_filename(cls, datadir: Path, pair: str, timeframe: str) -> Path: + pair_s = misc.pair_to_filename(pair) + filename = datadir.joinpath(f'{pair_s}-{timeframe}.{cls._get_file_extension()}') + return filename + + @classmethod + def _pair_trades_filename(cls, datadir: Path, pair: str) -> Path: + pair_s = misc.pair_to_filename(pair) + filename = datadir.joinpath(f'{pair_s}-trades.{cls._get_file_extension()}') + return filename + def ohlcv_load(self, pair, timeframe: str, timerange: Optional[TimeRange] = None, fill_missing: bool = True, diff --git a/freqtrade/data/history/jsondatahandler.py b/freqtrade/data/history/jsondatahandler.py index 24d6e814b..ccefc8356 100644 --- a/freqtrade/data/history/jsondatahandler.py +++ b/freqtrade/data/history/jsondatahandler.py @@ -174,34 +174,10 @@ class JsonDataHandler(IDataHandler): pass return tradesdata - def trades_purge(self, pair: str) -> bool: - """ - Remove data for this pair - :param pair: Delete data for this pair. - :return: True when deleted, false if file did not exist. - """ - filename = self._pair_trades_filename(self._datadir, pair) - if filename.exists(): - filename.unlink() - return True - return False - - @classmethod - def _pair_data_filename(cls, datadir: Path, pair: str, timeframe: str) -> Path: - pair_s = misc.pair_to_filename(pair) - filename = datadir.joinpath(f'{pair_s}-{timeframe}.{cls._get_file_extension()}') - return filename - @classmethod def _get_file_extension(cls): return "json.gz" if cls._use_zip else "json" - @classmethod - def _pair_trades_filename(cls, datadir: Path, pair: str) -> Path: - pair_s = misc.pair_to_filename(pair) - filename = datadir.joinpath(f'{pair_s}-trades.{cls._get_file_extension()}') - return filename - class JsonGzDataHandler(JsonDataHandler):