Repository: freqtrade/freqtrade

Issue:
Minimal ROI value is not really optional, Bot Crash if minimal_roi have no 0 value
## The problem:
### The "minimal_roi" configuration object is suposed to be optionnal as explained in the doc:

> Most of the strategy files already include the optimal minimal_roi value. This parameter is optional. If you use it in the configuration file, it will take over the minimal_roi value from the strategy file.

Exemple:

>     minimal_roi = {
>         "40": 0.0,
>         "30": 0.01,
>         "20": 0.02,
>         "0": 0.04
>     }

**However, If I remove this parameter in the strategy and config I get this error:**

> 2019-03-06 21:56:56,768 - freqtrade - ERROR - Fatal exception!
> Traceback (most recent call last):
>   File "./freqtrade/main.py", line 45, in main
>     freqtrade = FreqtradeBot(config)
>   File "/home/axel/dev/shatta/framework-dev/private/freqtrade/freqtrade/freqtradebot.py", line 54, in __init__
>     self.strategy: IStrategy = StrategyResolver(self.config).strategy
>   File "/home/axel/dev/shatta/framework-dev/private/freqtrade/freqtrade/resolvers/strategy_resolver.py", line 77, in __init__
>     {int(key): value for (key, value) in self.strategy.minimal_roi.items()}.items(),
> AttributeError: 'ShattaStrategy' object has no attribute 'minimal_roi'

 **Also, If I remove the 0 value key like that:**

>     minimal_roi = {
>         "40": 0.0,
>         "30": 0.01,
>         "20": 0.02,
>     }

**The bot start but crash when trying to check ROI with this error:**
>   File "/freqtrade/freqtrade/freqtradebot.py", line 699, in check_sell
>     should_sell = self.strategy.should_sell(trade, sell_rate, datetime.utcnow(), buy, sell)
>   File "/framework-dev/private/freqtrade/freqtrade/strategy/interface.py", line 273, in should_sell
>     if self.min_roi_reached(trade=trade, current_profit=current_profit, current_time=date):
>   File "/framework-dev/private/freqtrade/freqtrade/strategy/**interface.py", line 349**, in min_roi_reached
>     **roi_entry = max(list(filter(lambda x: trade_dur >= x, self.minimal_roi.keys())))**

### Standalone Python test to reproduce:

> minimal_roi_keys = [0, 20, 30, 40, 50] ## Remove the 0 to trigger error
> trade_dur = 0.3486263354619344
> roi_entry = max(list(filter(lambda x: trade_dur >= x, minimal_roi_keys)))
> print(str(roi_entry))


### Solutions

1. The quick easy solution to temporaly deal with that issue is to make the minimal_roi parameter mandatory and make the "min_roi_reached" work with missing 0. Users who don't want to use ROI can simply put an unrealistic hight value.

2. The other is to make this parameter truly optionnal.


Minimal ROI value is not really optional, Bot Crash if minimal_roi have no 0 value
## The problem:
### The "minimal_roi" configuration object is suposed to be optionnal as explained in the doc:

> Most of the strategy files already include the optimal minimal_roi value. This parameter is optional. If you use it in the configuration file, it will take over the minimal_roi value from the strategy file.

Exemple:

>     minimal_roi = {
>         "40": 0.0,
>         "30": 0.01,
>         "20": 0.02,
>         "0": 0.04
>     }

**However, If I remove this parameter in the strategy and config I get this error:**

> 2019-03-06 21:56:56,768 - freqtrade - ERROR - Fatal exception!
> Traceback (most recent call last):
>   File "./freqtrade/main.py", line 45, in main
>     freqtrade = FreqtradeBot(config)
>   File "/home/axel/dev/shatta/framework-dev/private/freqtrade/freqtrade/freqtradebot.py", line 54, in __init__
>     self.strategy: IStrategy = StrategyResolver(self.config).strategy
>   File "/home/axel/dev/shatta/framework-dev/private/freqtrade/freqtrade/resolvers/strategy_resolver.py", line 77, in __init__
>     {int(key): value for (key, value) in self.strategy.minimal_roi.items()}.items(),
> AttributeError: 'ShattaStrategy' object has no attribute 'minimal_roi'

 **Also, If I remove the 0 value key like that:**

>     minimal_roi = {
>         "40": 0.0,
>         "30": 0.01,
>         "20": 0.02,
>     }

**The bot start but crash when trying to check ROI with this error:**
>   File "/freqtrade/freqtrade/freqtradebot.py", line 699, in check_sell
>     should_sell = self.strategy.should_sell(trade, sell_rate, datetime.utcnow(), buy, sell)
>   File "/framework-dev/private/freqtrade/freqtrade/strategy/interface.py", line 273, in should_sell
>     if self.min_roi_reached(trade=trade, current_profit=current_profit, current_time=date):
>   File "/framework-dev/private/freqtrade/freqtrade/strategy/**interface.py", line 349**, in min_roi_reached
>     **roi_entry = max(list(filter(lambda x: trade_dur >= x, self.minimal_roi.keys())))**

### Standalone Python test to reproduce:

> minimal_roi_keys = [0, 20, 30, 40, 50] ## Remove the 0 to trigger error
> trade_dur = 0.3486263354619344
> roi_entry = max(list(filter(lambda x: trade_dur >= x, minimal_roi_keys)))
> print(str(roi_entry))


### Solutions

1. The quick easy solution to temporaly deal with that issue is to make the minimal_roi parameter mandatory and make the "min_roi_reached" work with missing 0. Users who don't want to use ROI can simply put an unrealistic hight value.

2. The other is to make this parameter truly optionnal.




Discussion:
`minimal_roi` is optional in the configuration and strategy - but it needs to be in one of the 2 - so you're right, the documentation in configuration.md is wrong.
We also could / should check for this.

Here however, we document how to "deactivate" it...
https://www.freqtrade.io/en/latest/bot-optimization/#minimal-roi
Add a default value which will be used in the case when this parameter is missing in both strategy and config and you can simply state it in the docs.
`minimal_roi` is optional in the configuration and strategy - but it needs to be in one of the 2 - so you're right, the documentation in configuration.md is wrong.
We also could / should check for this.

Here however, we document how to "deactivate" it...
https://www.freqtrade.io/en/latest/bot-optimization/#minimal-roi
Add a default value which will be used in the case when this parameter is missing in both strategy and config and you can simply state it in the docs.

Resolving patch:
diff --git a/freqtrade/resolvers/strategy_resolver.py b/freqtrade/resolvers/strategy_resolver.py
--- a/freqtrade/resolvers/strategy_resolver.py
+++ b/freqtrade/resolvers/strategy_resolver.py
@@ -46,18 +46,18 @@ def __init__(self, config: Optional[Dict] = None) -> None:
         # Set attributes
         # Check if we need to override configuration
         # (Attribute name,                              default, experimental)
-        attributes = [("minimal_roi",                   None,    False),
-                      ("ticker_interval",               None,    False),
-                      ("stoploss",                      None,    False),
-                      ("trailing_stop",                 None,    False),
-                      ("trailing_stop_positive",        None,    False),
-                      ("trailing_stop_positive_offset", 0.0,     False),
-                      ("process_only_new_candles",      None,    False),
-                      ("order_types",                   None,    False),
-                      ("order_time_in_force",           None,    False),
-                      ("use_sell_signal",               False,   True),
-                      ("sell_profit_only",              False,   True),
-                      ("ignore_roi_if_buy_signal",      False,   True),
+        attributes = [("minimal_roi",                   {"0": 10.0}, False),
+                      ("ticker_interval",               None,        False),
+                      ("stoploss",                      None,        False),
+                      ("trailing_stop",                 None,        False),
+                      ("trailing_stop_positive",        None,        False),
+                      ("trailing_stop_positive_offset", 0.0,         False),
+                      ("process_only_new_candles",      None,        False),
+                      ("order_types",                   None,        False),
+                      ("order_time_in_force",           None,        False),
+                      ("use_sell_signal",               False,       True),
+                      ("sell_profit_only",              False,       True),
+                      ("ignore_roi_if_buy_signal",      False,       True),
                       ]
         for attribute, default, experimental in attributes:
             if experimental:


Test patch: