diff --git a/freqtrade/analyze.py b/freqtrade/analyze.py index 493228e68..71d96264f 100644 --- a/freqtrade/analyze.py +++ b/freqtrade/analyze.py @@ -12,7 +12,7 @@ from pandas import DataFrame, to_datetime from freqtrade import constants from freqtrade.exchange import Exchange from freqtrade.persistence import Trade -from freqtrade.strategy.resolver import IStrategy, StrategyResolver +from freqtrade.strategy.resolver import IStrategy logger = logging.getLogger(__name__) @@ -30,13 +30,13 @@ class Analyze(object): Analyze class contains everything the bot need to determine if the situation is good for buying or selling. """ - def __init__(self, config: dict) -> None: + def __init__(self, config: dict, strategy: IStrategy) -> None: """ Init Analyze :param config: Bot configuration (use the one from Configuration()) """ self.config = config - self.strategy: IStrategy = StrategyResolver(self.config).strategy + self.strategy = strategy @staticmethod def parse_ticker_dataframe(ticker: list) -> DataFrame: diff --git a/freqtrade/freqtradebot.py b/freqtrade/freqtradebot.py index 72b5190b9..ad61b5533 100644 --- a/freqtrade/freqtradebot.py +++ b/freqtrade/freqtradebot.py @@ -22,6 +22,7 @@ from freqtrade.persistence import Trade from freqtrade.rpc import RPCMessageType from freqtrade.rpc import RPCManager from freqtrade.state import State +from freqtrade.strategy.resolver import IStrategy, StrategyResolver logger = logging.getLogger(__name__) @@ -49,7 +50,8 @@ class FreqtradeBot(object): # Init objects self.config = config - self.analyze = Analyze(self.config) + self.strategy: IStrategy = StrategyResolver(self.config).strategy + self.analyze = Analyze(self.config, self.strategy) self.fiat_converter = CryptoToFiatConverter() self.rpc: RPCManager = RPCManager(self) self.persistence = None @@ -293,8 +295,8 @@ class FreqtradeBot(object): return None amount_reserve_percent = 1 - 0.05 # reserve 5% + stoploss - if self.analyze.get_stoploss() is not None: - amount_reserve_percent += self.analyze.get_stoploss() + if self.strategy.stoploss is not None: + amount_reserve_percent += self.strategy.stoploss # it should not be more than 50% amount_reserve_percent = max(amount_reserve_percent, 0.5) return min(min_stake_amounts)/amount_reserve_percent @@ -305,7 +307,7 @@ class FreqtradeBot(object): if one pair triggers the buy_signal a new trade record gets created :return: True if a trade object has been created and persisted, False otherwise """ - interval = self.analyze.get_ticker_interval() + interval = self.strategy.ticker_interval stake_amount = self._get_trade_stake_amount() if not stake_amount: @@ -499,7 +501,7 @@ class FreqtradeBot(object): experimental = self.config.get('experimental', {}) if experimental.get('use_sell_signal') or experimental.get('ignore_roi_if_buy_signal'): (buy, sell) = self.analyze.get_signal(self.exchange, - trade.pair, self.analyze.get_ticker_interval()) + trade.pair, self.strategy.ticker_interval) if self.analyze.should_sell(trade, current_rate, datetime.utcnow(), buy, sell): self.execute_sell(trade, current_rate) diff --git a/freqtrade/optimize/backtesting.py b/freqtrade/optimize/backtesting.py index 05bcdf4b7..67d4bb2e9 100644 --- a/freqtrade/optimize/backtesting.py +++ b/freqtrade/optimize/backtesting.py @@ -21,6 +21,7 @@ from freqtrade.configuration import Configuration from freqtrade.exchange import Exchange from freqtrade.misc import file_dump_json from freqtrade.persistence import Trade +from freqtrade.strategy.resolver import IStrategy, StrategyResolver logger = logging.getLogger(__name__) @@ -52,7 +53,8 @@ class Backtesting(object): """ def __init__(self, config: Dict[str, Any]) -> None: self.config = config - self.analyze = Analyze(self.config) + self.strategy: IStrategy = StrategyResolver(self.config).strategy + self.analyze = Analyze(self.config, self.strategy) self.ticker_interval = self.analyze.strategy.ticker_interval self.tickerdata_to_dataframe = self.analyze.tickerdata_to_dataframe self.populate_buy_trend = self.analyze.populate_buy_trend diff --git a/freqtrade/tests/optimize/test_backtesting.py b/freqtrade/tests/optimize/test_backtesting.py index 6fbf71e40..89f5a0bb7 100644 --- a/freqtrade/tests/optimize/test_backtesting.py +++ b/freqtrade/tests/optimize/test_backtesting.py @@ -18,6 +18,7 @@ from freqtrade.arguments import Arguments, TimeRange from freqtrade.optimize.backtesting import (Backtesting, setup_configuration, start) from freqtrade.tests.conftest import log_has, patch_exchange +from freqtrade.strategy.default_strategy import DefaultStrategy def get_args(args) -> List[str]: @@ -348,7 +349,7 @@ def test_tickerdata_to_dataframe(default_conf, mocker) -> None: assert len(data['UNITTEST/BTC']) == 99 # Load Analyze to compare the result between Backtesting function and Analyze are the same - analyze = Analyze(default_conf) + analyze = Analyze(default_conf, DefaultStrategy()) data2 = analyze.tickerdata_to_dataframe(tickerlist) assert data['UNITTEST/BTC'].equals(data2['UNITTEST/BTC']) diff --git a/freqtrade/tests/test_analyze.py b/freqtrade/tests/test_analyze.py index 6e035d842..dc7410ffc 100644 --- a/freqtrade/tests/test_analyze.py +++ b/freqtrade/tests/test_analyze.py @@ -14,9 +14,10 @@ from freqtrade.analyze import Analyze, SignalType from freqtrade.arguments import TimeRange from freqtrade.optimize.__init__ import load_tickerdata_file from freqtrade.tests.conftest import get_patched_exchange, log_has +from freqtrade.strategy.default_strategy import DefaultStrategy # Avoid to reinit the same object again and again -_ANALYZE = Analyze({'strategy': 'DefaultStrategy'}) +_ANALYZE = Analyze({}, DefaultStrategy()) def test_signaltype_object() -> None: @@ -189,7 +190,7 @@ def test_tickerdata_to_dataframe(default_conf) -> None: """ Test Analyze.tickerdata_to_dataframe() method """ - analyze = Analyze(default_conf) + analyze = Analyze(default_conf, DefaultStrategy()) timerange = TimeRange(None, 'line', 0, -100) tick = load_tickerdata_file(None, 'UNITTEST/BTC', '1m', timerange=timerange) diff --git a/freqtrade/tests/test_dataframe.py b/freqtrade/tests/test_dataframe.py index fd461a503..f4b26eb1d 100644 --- a/freqtrade/tests/test_dataframe.py +++ b/freqtrade/tests/test_dataframe.py @@ -9,26 +9,26 @@ from freqtrade.strategy.resolver import StrategyResolver _pairs = ['ETH/BTC'] -def load_dataframe_pair(pairs): +def load_dataframe_pair(pairs, strategy): ld = load_data(None, ticker_interval='5m', pairs=pairs) assert isinstance(ld, dict) assert isinstance(pairs[0], str) dataframe = ld[pairs[0]] - analyze = Analyze({'strategy': 'DefaultStrategy'}) + analyze = Analyze({}, strategy) dataframe = analyze.analyze_ticker(dataframe) return dataframe def test_dataframe_load(): - StrategyResolver({'strategy': 'DefaultStrategy'}) - dataframe = load_dataframe_pair(_pairs) + strategy = StrategyResolver({'strategy': 'DefaultStrategy'}).strategy + dataframe = load_dataframe_pair(_pairs, strategy) assert isinstance(dataframe, pandas.core.frame.DataFrame) def test_dataframe_columns_exists(): - StrategyResolver({'strategy': 'DefaultStrategy'}) - dataframe = load_dataframe_pair(_pairs) + strategy = StrategyResolver({'strategy': 'DefaultStrategy'}).strategy + dataframe = load_dataframe_pair(_pairs, strategy) assert 'high' in dataframe.columns assert 'low' in dataframe.columns assert 'close' in dataframe.columns diff --git a/freqtrade/tests/test_freqtradebot.py b/freqtrade/tests/test_freqtradebot.py index 450504f57..c628a9da3 100644 --- a/freqtrade/tests/test_freqtradebot.py +++ b/freqtrade/tests/test_freqtradebot.py @@ -316,9 +316,8 @@ def test_get_min_pair_stake_amount(mocker, default_conf) -> None: patch_RPCManager(mocker) mocker.patch('freqtrade.exchange.Exchange.validate_pairs', MagicMock()) - mocker.patch('freqtrade.freqtradebot.Analyze.get_stoploss', MagicMock(return_value=-0.05)) freqtrade = FreqtradeBot(default_conf) - + freqtrade.strategy.stoploss = -0.05 # no pair found mocker.patch( 'freqtrade.exchange.Exchange.get_markets', diff --git a/freqtrade/tests/test_misc.py b/freqtrade/tests/test_misc.py index e2ba40dee..c30225132 100644 --- a/freqtrade/tests/test_misc.py +++ b/freqtrade/tests/test_misc.py @@ -11,6 +11,7 @@ from freqtrade.analyze import Analyze from freqtrade.misc import (common_datearray, datesarray_to_datetimearray, file_dump_json, format_ms_time, shorten_date) from freqtrade.optimize.__init__ import load_tickerdata_file +from freqtrade.strategy.default_strategy import DefaultStrategy def test_shorten_date() -> None: @@ -47,7 +48,7 @@ def test_common_datearray(default_conf) -> None: Test common_datearray() :return: None """ - analyze = Analyze(default_conf) + analyze = Analyze(default_conf, DefaultStrategy()) tick = load_tickerdata_file(None, 'UNITTEST/BTC', '1m') tickerlist = {'UNITTEST/BTC': tick} dataframes = analyze.tickerdata_to_dataframe(tickerlist)