From fbbde9de2518a1f3bfc5b9fbcd239e1a2a2f1bdb Mon Sep 17 00:00:00 2001 From: Janne Sinivirta Date: Tue, 7 Nov 2017 17:18:29 +0200 Subject: [PATCH 1/2] put shared fixtures to conftest.py --- freqtrade/tests/conftest.py | 18 ++++++++++++++++++ freqtrade/tests/test_backtesting.py | 19 ------------------- freqtrade/tests/test_hyperopt.py | 19 ------------------- 3 files changed, 18 insertions(+), 38 deletions(-) create mode 100644 freqtrade/tests/conftest.py diff --git a/freqtrade/tests/conftest.py b/freqtrade/tests/conftest.py new file mode 100644 index 000000000..5da31413a --- /dev/null +++ b/freqtrade/tests/conftest.py @@ -0,0 +1,18 @@ +import pytest + +@pytest.fixture(scope="module") +def pairs(): + return ['btc-neo', 'btc-eth', 'btc-omg', 'btc-edg', 'btc-pay', + 'btc-pivx', 'btc-qtum', 'btc-mtl', 'btc-etc', 'btc-ltc'] + +@pytest.fixture(scope="module") +def conf(): + return { + "minimal_roi": { + "40": 0.0, + "30": 0.01, + "20": 0.02, + "0": 0.04 + }, + "stoploss": -0.05 + } diff --git a/freqtrade/tests/test_backtesting.py b/freqtrade/tests/test_backtesting.py index fc7c699d6..7eb8fd981 100644 --- a/freqtrade/tests/test_backtesting.py +++ b/freqtrade/tests/test_backtesting.py @@ -26,25 +26,6 @@ def print_pair_results(pair, results): print(format_results(results[results.currency == pair])) -@pytest.fixture -def pairs(): - return ['btc-neo', 'btc-eth', 'btc-omg', 'btc-edg', 'btc-pay', - 'btc-pivx', 'btc-qtum', 'btc-mtl', 'btc-etc', 'btc-ltc'] - - -@pytest.fixture -def conf(): - return { - "minimal_roi": { - "50": 0.0, - "40": 0.01, - "30": 0.02, - "0": 0.045 - }, - "stoploss": -0.40 - } - - def backtest(conf, pairs, mocker): trades = [] exchange._API = Bittrex({'key': '', 'secret': ''}) diff --git a/freqtrade/tests/test_hyperopt.py b/freqtrade/tests/test_hyperopt.py index 5a8143269..1660ed8a2 100644 --- a/freqtrade/tests/test_hyperopt.py +++ b/freqtrade/tests/test_hyperopt.py @@ -18,25 +18,6 @@ logging.disable(logging.DEBUG) # disable debug logs that slow backtesting a lot TARGET_TRADES = 1200 -@pytest.fixture -def pairs(): - return ['btc-neo', 'btc-eth', 'btc-omg', 'btc-edg', 'btc-pay', - 'btc-pivx', 'btc-qtum', 'btc-mtl', 'btc-etc', 'btc-ltc'] - - -@pytest.fixture -def conf(): - return { - "minimal_roi": { - "40": 0.0, - "30": 0.01, - "20": 0.02, - "0": 0.04 - }, - "stoploss": -0.05 - } - - def buy_strategy_generator(params): print(params) From 0395c9226078d74ee86bcfcc01bd020fb7641dbb Mon Sep 17 00:00:00 2001 From: Janne Sinivirta Date: Tue, 7 Nov 2017 19:24:51 +0200 Subject: [PATCH 2/2] move testdata file loading to pytest fixture --- freqtrade/tests/conftest.py | 16 ++++++++--- freqtrade/tests/test_backtesting.py | 43 ++++++++++++++--------------- freqtrade/tests/test_hyperopt.py | 6 ++-- 3 files changed, 36 insertions(+), 29 deletions(-) diff --git a/freqtrade/tests/conftest.py b/freqtrade/tests/conftest.py index 5da31413a..6fc9650d2 100644 --- a/freqtrade/tests/conftest.py +++ b/freqtrade/tests/conftest.py @@ -1,9 +1,7 @@ +# pragma pylint: disable=missing-docstring +import json import pytest -@pytest.fixture(scope="module") -def pairs(): - return ['btc-neo', 'btc-eth', 'btc-omg', 'btc-edg', 'btc-pay', - 'btc-pivx', 'btc-qtum', 'btc-mtl', 'btc-etc', 'btc-ltc'] @pytest.fixture(scope="module") def conf(): @@ -16,3 +14,13 @@ def conf(): }, "stoploss": -0.05 } + + +@pytest.fixture(scope="module") +def backdata(): + result = {} + for pair in ['btc-neo', 'btc-eth', 'btc-omg', 'btc-edg', 'btc-pay', + 'btc-pivx', 'btc-qtum', 'btc-mtl', 'btc-etc', 'btc-ltc']: + with open('freqtrade/tests/testdata/' + pair + '.json') as data_file: + result[pair] = json.load(data_file) + return result diff --git a/freqtrade/tests/test_backtesting.py b/freqtrade/tests/test_backtesting.py index 7eb8fd981..6cc49c991 100644 --- a/freqtrade/tests/test_backtesting.py +++ b/freqtrade/tests/test_backtesting.py @@ -26,42 +26,41 @@ def print_pair_results(pair, results): print(format_results(results[results.currency == pair])) -def backtest(conf, pairs, mocker): +def backtest(conf, backdata, mocker): trades = [] exchange._API = Bittrex({'key': '', 'secret': ''}) mocked_history = mocker.patch('freqtrade.analyze.get_ticker_history') mocker.patch.dict('freqtrade.main._CONF', conf) mocker.patch('arrow.utcnow', return_value=arrow.get('2017-08-20T14:50:00')) - for pair in pairs: - with open('freqtrade/tests/testdata/' + pair + '.json') as data_file: - mocked_history.return_value = json.load(data_file) - ticker = analyze_ticker(pair)[['close', 'date', 'buy']].copy() - # for each buy point - for row in ticker[ticker.buy == 1].itertuples(index=True): - trade = Trade( - open_rate=row.close, - open_date=row.date, - amount=1, - fee=exchange.get_fee() * 2 - ) - # calculate win/lose forwards from buy point - for row2 in ticker[row.Index:].itertuples(index=True): - if should_sell(trade, row2.close, row2.date): - current_profit = trade.calc_profit(row2.close) + for pair, pair_data in backdata.items(): + mocked_history.return_value = pair_data + ticker = analyze_ticker(pair)[['close', 'date', 'buy']].copy() + # for each buy point + for row in ticker[ticker.buy == 1].itertuples(index=True): + trade = Trade( + open_rate=row.close, + open_date=row.date, + amount=1, + fee=exchange.get_fee() * 2 + ) + # calculate win/lose forwards from buy point + for row2 in ticker[row.Index:].itertuples(index=True): + if should_sell(trade, row2.close, row2.date): + current_profit = trade.calc_profit(row2.close) - trades.append((pair, current_profit, row2.Index - row.Index)) - break + trades.append((pair, current_profit, row2.Index - row.Index)) + break labels = ['currency', 'profit', 'duration'] results = DataFrame.from_records(trades, columns=labels) return results @pytest.mark.skipif(not os.environ.get('BACKTEST', False), reason="BACKTEST not set") -def test_backtest(conf, pairs, mocker, report=True): - results = backtest(conf, pairs, mocker) +def test_backtest(conf, backdata, mocker, report=True): + results = backtest(conf, backdata, mocker) print('====================== BACKTESTING REPORT ================================') - for pair in pairs: + for pair in backdata: print_pair_results(pair, results) print('TOTAL OVER ALL TRADES:') print(format_results(results)) diff --git a/freqtrade/tests/test_hyperopt.py b/freqtrade/tests/test_hyperopt.py index 1660ed8a2..ed8a4a0e6 100644 --- a/freqtrade/tests/test_hyperopt.py +++ b/freqtrade/tests/test_hyperopt.py @@ -63,13 +63,13 @@ def buy_strategy_generator(params): @pytest.mark.skipif(not os.environ.get('BACKTEST', False), reason="BACKTEST not set") -def test_hyperopt(conf, pairs, mocker): +def test_hyperopt(conf, backdata, mocker): mocked_buy_trend = mocker.patch('freqtrade.analyze.populate_buy_trend') def optimizer(params): mocked_buy_trend.side_effect = buy_strategy_generator(params) - results = backtest(conf, pairs, mocker) + results = backtest(conf, backdata, mocker) result = format_results(results) print(result) @@ -129,7 +129,7 @@ def test_hyperopt(conf, pairs, mocker): } trials = Trials() best = fmin(fn=optimizer, space=space, algo=tpe.suggest, max_evals=4, trials=trials) - print('\n\n\n\n====================== HYPEROPT BACKTESTING REPORT ================================') + print('\n\n\n\n==================== HYPEROPT BACKTESTING REPORT ==============================') print('Best parameters {}'.format(best)) newlist = sorted(trials.results, key=itemgetter('loss')) print('Result: {}'.format(newlist[0]['result']))