diff --git a/vnpy/__init__.py b/vnpy/__init__.py index e69de29b..1b483f37 100644 --- a/vnpy/__init__.py +++ b/vnpy/__init__.py @@ -0,0 +1 @@ +__version__ == "2.0" diff --git a/vnpy/app/cta_strategy/backtesting.py b/vnpy/app/cta_strategy/backtesting.py index 5e7224ea..aebc78ff 100644 --- a/vnpy/app/cta_strategy/backtesting.py +++ b/vnpy/app/cta_strategy/backtesting.py @@ -201,10 +201,10 @@ class BacktestingEngine: s = ( DbBarData.select() .where( - (DbBarData.vt_symbol == self.vt_symbol) & - (DbBarData.interval == self.interval) & - (DbBarData.datetime >= self.start) & - (DbBarData.datetime <= self.end) + (DbBarData.vt_symbol == self.vt_symbol) + & (DbBarData.interval == self.interval) + & (DbBarData.datetime >= self.start) + & (DbBarData.datetime <= self.end) ) .order_by(DbBarData.datetime) ) @@ -213,9 +213,9 @@ class BacktestingEngine: s = ( DbTickData.select() .where( - (DbTickData.vt_symbol == self.vt_symbol) & - (DbTickData.datetime >= self.start) & - (DbTickData.datetime <= self.end) + (DbTickData.vt_symbol == self.vt_symbol) + & (DbTickData.datetime >= self.start) + & (DbTickData.datetime <= self.end) ) .order_by(DbTickData.datetime) ) @@ -567,15 +567,15 @@ class BacktestingEngine: # Check whether limit orders can be filled. long_cross = ( - order.direction == Direction.LONG and - order.price >= long_cross_price and - long_cross_price > 0 + order.direction == Direction.LONG + and order.price >= long_cross_price + and long_cross_price > 0 ) short_cross = ( - order.direction == Direction.SHORT and - order.price <= short_cross_price and - short_cross_price > 0 + order.direction == Direction.SHORT + and order.price <= short_cross_price + and short_cross_price > 0 ) if not long_cross and not short_cross: @@ -635,13 +635,13 @@ class BacktestingEngine: for stop_order in list(self.active_stop_orders.values()): # Check whether stop order can be triggered. long_cross = ( - stop_order.direction == Direction.LONG and - stop_order.price <= long_cross_price + stop_order.direction == Direction.LONG + and stop_order.price <= long_cross_price ) short_cross = ( - stop_order.direction == Direction.SHORT and - stop_order.price >= short_cross_price + stop_order.direction == Direction.SHORT + and stop_order.price >= short_cross_price ) if not long_cross and not short_cross: diff --git a/vnpy/app/cta_strategy/engine.py b/vnpy/app/cta_strategy/engine.py index d09d8b2e..01c3d7c8 100644 --- a/vnpy/app/cta_strategy/engine.py +++ b/vnpy/app/cta_strategy/engine.py @@ -405,10 +405,10 @@ class CtaEngine(BaseEngine): s = ( DbBarData.select() .where( - (DbBarData.vt_symbol == vt_symbol) & - (DbBarData.interval == interval) & - (DbBarData.datetime >= start) & - (DbBarData.datetime <= end) + (DbBarData.vt_symbol == vt_symbol) + & (DbBarData.interval == interval) + & (DbBarData.datetime >= start) + & (DbBarData.datetime <= end) ) .order_by(DbBarData.datetime) ) @@ -425,9 +425,9 @@ class CtaEngine(BaseEngine): s = ( DbTickData.select() .where( - (DbBarData.vt_symbol == vt_symbol) & - (DbBarData.datetime >= start) & - (DbBarData.datetime <= end) + (DbBarData.vt_symbol == vt_symbol) + & (DbBarData.datetime >= start) + & (DbBarData.datetime <= end) ) .order_by(DbBarData.datetime) ) diff --git a/vnpy/app/cta_strategy/strategies/atr_rsi_strategy.py b/vnpy/app/cta_strategy/strategies/atr_rsi_strategy.py index 7a7de013..d0b8d4cf 100644 --- a/vnpy/app/cta_strategy/strategies/atr_rsi_strategy.py +++ b/vnpy/app/cta_strategy/strategies/atr_rsi_strategy.py @@ -1,13 +1,12 @@ from vnpy.app.cta_strategy import ( CtaTemplate, StopOrder, - Direction, TickData, BarData, TradeData, OrderData, BarGenerator, - ArrayManager, + ArrayManager, ) @@ -16,33 +15,33 @@ class AtrRsiStrategy(CtaTemplate): author = '用Python的交易员' - atr_length = 22 - atr_ma_length = 10 - rsi_length = 5 - rsi_entry = 16 - trailing_percent = 0.8 - fixed_size = 1 + atr_length = 22 + atr_ma_length = 10 + rsi_length = 5 + rsi_entry = 16 + trailing_percent = 0.8 + fixed_size = 1 - atr_value = 0 - atr_ma = 0 - rsi_value = 0 - rsi_buy = 0 - rsi_sell = 0 - intra_trade_high = 0 - intra_trade_low = 0 + atr_value = 0 + atr_ma = 0 + rsi_value = 0 + rsi_buy = 0 + rsi_sell = 0 + intra_trade_high = 0 + intra_trade_low = 0 - parameters= [ 'atr_length', 'atr_ma_length', 'rsi_length', 'rsi_entry', 'trailing_percent','fixed_size'] - variables= ['atr_value','atr_ma','rsi_value','rsi_buy','rsi_sell'] - + parameters = ['atr_length', 'atr_ma_length', 'rsi_length', + 'rsi_entry', 'trailing_percent', 'fixed_size'] + variables = ['atr_value', 'atr_ma', 'rsi_value', 'rsi_buy', 'rsi_sell'] def __init__(self, cta_engine, strategy_name, vt_symbol, setting): """""" super(AtrRsiStrategy, self).__init__( cta_engine, strategy_name, vt_symbol, setting - ) + ) self.bg = BarGenerator(self.on_bar) self.am = ArrayManager() - + def on_init(self): """ Callback when strategy is inited. @@ -59,7 +58,7 @@ class AtrRsiStrategy(CtaTemplate): Callback when strategy is started. """ self.write_log("策略启动") - + def on_stop(self): """ Callback when strategy is stopped. @@ -85,7 +84,7 @@ class AtrRsiStrategy(CtaTemplate): atr_array = am.atr(self.atr_length, array=True) self.atr_value = atr_array[-1] - self.atr_ma = atr_array[-self.atr_ma_length:].mean() + self.atr_ma = atr_array[-self.atr_ma_length:].mean() self.rsi_value = am.rsi(self.rsi_length) if self.pos == 0: @@ -94,26 +93,28 @@ class AtrRsiStrategy(CtaTemplate): if self.atr_value > self.atr_ma: if self.rsi_value > self.rsi_buy: - self.buy(bar.close_price+5, self.fixed_size) + self.buy(bar.close_price + 5, self.fixed_size) elif self.rsi_value < self.rsi_sell: - self.short(bar.close_price-5, self.fixed_size) + self.short(bar.close_price - 5, self.fixed_size) elif self.pos > 0: self.intra_trade_high = max(self.intra_trade_high, bar.high_price) self.intra_trade_low = bar.low_price - - long_stop = self.intra_trade_high * (1-self.trailing_percent/100) + + long_stop = self.intra_trade_high * \ + (1 - self.trailing_percent / 100) self.sell(long_stop, abs(self.pos), stop=True) - + elif self.pos < 0: self.intra_trade_low = min(self.intra_trade_low, bar.low_price) self.intra_trade_high = bar.high_price - short_stop = self.intra_trade_low * (1+self.trailing_percent/100) + short_stop = self.intra_trade_low * \ + (1 + self.trailing_percent / 100) self.cover(short_stop, abs(self.pos), stop=True) self.put_event() - + def on_order(self, order: OrderData): """ Callback of new order data update. @@ -130,4 +131,4 @@ class AtrRsiStrategy(CtaTemplate): """ Callback of stop order update. """ - pass \ No newline at end of file + pass diff --git a/vnpy/app/cta_strategy/strategies/boll_channel_strategy.py b/vnpy/app/cta_strategy/strategies/boll_channel_strategy.py index 1a947b35..137d6b1d 100644 --- a/vnpy/app/cta_strategy/strategies/boll_channel_strategy.py +++ b/vnpy/app/cta_strategy/strategies/boll_channel_strategy.py @@ -1,7 +1,6 @@ from vnpy.app.cta_strategy import ( CtaTemplate, StopOrder, - Direction, TickData, BarData, TradeData, @@ -13,38 +12,40 @@ from vnpy.app.cta_strategy import ( class BollChannelStrategy(CtaTemplate): """""" - + author = '用Python的交易员' - - boll_window = 18 - boll_dev = 3.4 - cci_window = 10 - atr_window = 30 - sl_multiplier = 5.2 - fixed_size = 1 - - boll_up = 0 - boll_down = 0 - cci_value = 0 - atr_value = 0 - - intra_trade_high = 0 - intra_trade_low = 0 - long_stop = 0 - short_stop = 0 - - parameters = [ 'boll_window', 'boll_dev', 'cci_window', 'atr_window', 'sl_multiplier', 'fixed_size'] - variables = ['boll_up', 'boll_down', 'cci_value', 'atr_value', 'intra_trade_high', 'intra_trade_low', 'long_stop', 'short_stop'] + + boll_window = 18 + boll_dev = 3.4 + cci_window = 10 + atr_window = 30 + sl_multiplier = 5.2 + fixed_size = 1 + + boll_up = 0 + boll_down = 0 + cci_value = 0 + atr_value = 0 + + intra_trade_high = 0 + intra_trade_low = 0 + long_stop = 0 + short_stop = 0 + + parameters = ['boll_window', 'boll_dev', 'cci_window', + 'atr_window', 'sl_multiplier', 'fixed_size'] + variables = ['boll_up', 'boll_down', 'cci_value', 'atr_value', + 'intra_trade_high', 'intra_trade_low', 'long_stop', 'short_stop'] def __init__(self, cta_engine, strategy_name, vt_symbol, setting): """""" super(BollChannelStrategy, self).__init__( cta_engine, strategy_name, vt_symbol, setting ) - - self.bg = BarGenerator(self.on_bar,15, self.on_15min_bar) + + self.bg = BarGenerator(self.on_bar, 15, self.on_15min_bar) self.am = ArrayManager() - + def on_init(self): """ Callback when strategy is inited. @@ -70,49 +71,49 @@ class BollChannelStrategy(CtaTemplate): """ self.bg.update_tick(tick) - def on_bar(self, bar:BarData): + def on_bar(self, bar: BarData): """ Callback of new bar data update. - """ + """ self.bg.update_bar(bar) - - def on_15min_bar(self, bar:BarData): + + def on_15min_bar(self, bar: BarData): """""" self.cancel_all() - - am = self.am - am.update_bar(bar) + + am = self.am + am.update_bar(bar) if not am.inited: return - + self.boll_up, self.boll_down = am.boll(self.boll_window, self.boll_dev) self.cci_value = am.cci(self.cci_window) self.atr_value = am.atr(self.atr_window) - + if self.pos == 0: self.intra_trade_high = bar.high_price - self.intra_trade_low = bar.low_price - + self.intra_trade_low = bar.low_price + if self.cci_value > 0: - self.buy(self.boll_up, self.fixed_size, True) + self.buy(self.boll_up, self.fixed_size, True) elif self.cci_value < 0: self.short(self.boll_down, self.fixed_size, True) - + elif self.pos > 0: self.intra_trade_high = max(self.intra_trade_high, bar.high_price) self.intra_trade_low = bar.low_price - self.long_stop = self.intra_trade_high - self.atr_value * self.sl_multiplier + self.long_stop = self.intra_trade_high - self.atr_value * self.sl_multiplier self.sell(self.long_stop, abs(self.pos), True) - + elif self.pos < 0: self.intra_trade_high = bar.high_price self.intra_trade_low = min(self.intra_trade_low, bar.low_price) - - self.short_stop = self.intra_trade_low + self.atr_value * self.sl_multiplier + + self.short_stop = self.intra_trade_low + self.atr_value * self.sl_multiplier self.cover(self.short_stop, abs(self.pos), True) - - self.put_event() + + self.put_event() def on_order(self, order: OrderData): """ @@ -131,4 +132,3 @@ class BollChannelStrategy(CtaTemplate): Callback of stop order update. """ pass - diff --git a/vnpy/app/cta_strategy/strategies/double_ma_strategy.py b/vnpy/app/cta_strategy/strategies/double_ma_strategy.py index 5baa1223..cff6f518 100644 --- a/vnpy/app/cta_strategy/strategies/double_ma_strategy.py +++ b/vnpy/app/cta_strategy/strategies/double_ma_strategy.py @@ -1,7 +1,6 @@ from vnpy.app.cta_strategy import ( CtaTemplate, StopOrder, - Direction, TickData, BarData, TradeData, @@ -13,19 +12,19 @@ from vnpy.app.cta_strategy import ( class DoubleMaStrategy(CtaTemplate): author = '用Python的交易员' - - fast_window = 10 - slow_window = 20 - fast_ma0 = 0.0 - fast_ma1 = 0.0 + fast_window = 10 + slow_window = 20 + + fast_ma0 = 0.0 + fast_ma1 = 0.0 slow_ma0 = 0.0 slow_ma1 = 0.0 - - parameters = [ 'fast_window', 'slow_window'] - variables = ['fast_ma0','fast_ma1','slow_ma0','slow_ma1'] - + + parameters = ['fast_window', 'slow_window'] + variables = ['fast_ma0', 'fast_ma1', 'slow_ma0', 'slow_ma1'] + def __init__(self, cta_engine, strategy_name, vt_symbol, setting): """""" super(DoubleMaStrategy, self).__init__( @@ -34,7 +33,7 @@ class DoubleMaStrategy(CtaTemplate): self.bg = BarGenerator(self.on_bar) self.am = ArrayManager() - + def on_init(self): """ Callback when strategy is inited. @@ -62,28 +61,28 @@ class DoubleMaStrategy(CtaTemplate): Callback of new tick data update. """ self.bg.update_tick(tick) - + def on_bar(self, bar: BarData): """ Callback of new bar data update. """ - am = self.am + am = self.am am.update_bar(bar) if not am.inited: return - + fast_ma = am.sma(self.fast_window, array=True) self.fast_ma0 = fast_ma[-1] self.fast_ma1 = fast_ma[-2] - + slow_ma = am.sma(self.slow_window, array=True) self.slow_ma0 = slow_ma[-1] self.slow_ma1 = slow_ma[-2] - cross_over = self.fast_ma0>self.slow_ma0 and self.fast_ma1self.slow_ma1 - + cross_over = self.fast_ma0 > self.slow_ma0 and self.fast_ma1 < self.slow_ma1 + cross_below = self.fast_ma0 < self.slow_ma0 and self.fast_ma1 > self.slow_ma1 + if cross_over: if self.pos == 0: self.buy(bar.close_price, 1) @@ -97,7 +96,7 @@ class DoubleMaStrategy(CtaTemplate): elif self.pos > 0: self.sell(bar.close_price, 1) self.short(bar.close_price, 1) - + self.put_event() def on_order(self, order: OrderData): @@ -116,4 +115,4 @@ class DoubleMaStrategy(CtaTemplate): """ Callback of stop order update. """ - pass \ No newline at end of file + pass diff --git a/vnpy/app/cta_strategy/strategies/dual_thrust_strategy.py b/vnpy/app/cta_strategy/strategies/dual_thrust_strategy.py index eb640fcf..75cdd3df 100644 --- a/vnpy/app/cta_strategy/strategies/dual_thrust_strategy.py +++ b/vnpy/app/cta_strategy/strategies/dual_thrust_strategy.py @@ -2,7 +2,6 @@ from datetime import time from vnpy.app.cta_strategy import ( CtaTemplate, StopOrder, - Direction, TickData, BarData, TradeData, @@ -14,19 +13,19 @@ from vnpy.app.cta_strategy import ( class DualThrustStrategy(CtaTemplate): """""" - + author = u'用Python的交易员' fixed_size = 1 k1 = 0.4 k2 = 0.6 - barList = [] - + barList = [] + day_open = 0 day_high = 0 day_low = 0 - + range = 0 long_entry = 0 short_entry = 0 @@ -35,10 +34,9 @@ class DualThrustStrategy(CtaTemplate): long_entered = False short_entered = False + parameters = ['k1', 'k2', "fixed_size"] + variables = ['range', 'long_entry', 'short_entry', 'exit_time'] - parameters = [ 'k1', 'k2', "fixed_size"] - variables = ['range','long_entry','short_entry','exit_time'] - def __init__(self, cta_engine, strategy_name, vt_symbol, setting): """""" super(DualThrustStrategy, self).__init__( @@ -61,7 +59,7 @@ class DualThrustStrategy(CtaTemplate): Callback when strategy is started. """ self.write_log("策略启动") - + def on_stop(self): """ Callback when strategy is stopped. @@ -73,26 +71,26 @@ class DualThrustStrategy(CtaTemplate): Callback of new tick data update. """ self.bg.update_tick(tick) - + def on_bar(self, bar: BarData): """ Callback of new bar data update. """ self.cancel_all() - self.barList.append(bar) + self.barList.append(bar) if len(self.barList) <= 2: return else: self.barList.pop(0) last_bar = self.barList[-2] - + if last_bar.datetime.date() != bar.datetime.date(): if self.day_high: self.range = self.day_high - self.day_low self.long_entry = bar.open_price + self.k1 * self.range - self.short_entry = bar.open_price - self.k2 * self.range - + self.short_entry = bar.open_price - self.k2 * self.range + self.day_open = bar.open_price self.day_high = bar.high_price self.day_low = bar.low_price @@ -113,30 +111,31 @@ class DualThrustStrategy(CtaTemplate): self.buy(self.long_entry, self.fixed_size, stop=True) else: if not self.short_entered: - self.short(self.short_entry, self.fixed_size, stop=True) - + self.short(self.short_entry, + self.fixed_size, stop=True) + elif self.pos > 0: self.long_entered = True self.sell(self.short_entry, self.fixed_size, stop=True) - + if not self.short_entered: self.short(self.short_entry, self.fixed_size, stop=True) - + elif self.pos < 0: self.short_entered = True self.cover(self.long_entry, self.fixed_size, stop=True) - + if not self.long_entered: self.buy(self.long_entry, self.fixed_size, stop=True) - + else: if self.pos > 0: self.sell(bar.close_price * 0.99, abs(self.pos)) elif self.pos < 0: self.cover(bar.close_price * 1.01, abs(self.pos)) - + self.put_event() def on_order(self, order: OrderData): @@ -155,4 +154,4 @@ class DualThrustStrategy(CtaTemplate): """ Callback of stop order update. """ - pass \ No newline at end of file + pass diff --git a/vnpy/app/cta_strategy/strategies/king_keltner_strategy.py b/vnpy/app/cta_strategy/strategies/king_keltner_strategy.py index e1b7d964..326f669f 100644 --- a/vnpy/app/cta_strategy/strategies/king_keltner_strategy.py +++ b/vnpy/app/cta_strategy/strategies/king_keltner_strategy.py @@ -1,7 +1,6 @@ from vnpy.app.cta_strategy import ( CtaTemplate, StopOrder, - Direction, TickData, BarData, TradeData, @@ -10,41 +9,38 @@ from vnpy.app.cta_strategy import ( ArrayManager, ) + class KingKeltnerStrategy(CtaTemplate): """""" author = '用Python的交易员' - kk_length = 11 - kk_dev = 1.6 - trailing_percent = 0.8 - fixed_size = 1 + kk_length = 11 + kk_dev = 1.6 + trailing_percent = 0.8 + fixed_size = 1 - kk_up = 0 - kk_down = 0 - intra_trade_high = 0 - intra_trade_low = 0 + kk_up = 0 + kk_down = 0 + intra_trade_high = 0 + intra_trade_low = 0 - buy_orderidList = [] - short_orderidList = [] - orderList = [] + buy_orderidList = [] + short_orderidList = [] + orderList = [] + + parameters = ['kk_length', 'kk_dev', 'fixed_size'] + variables = ['kk_up', 'kk_down'] - parameters = [ 'kk_length', 'kk_dev','fixed_size'] - variables = ['kk_up','kk_down'] - def __init__(self, cta_engine, strategy_name, vt_symbol, setting): """""" super(KingKeltnerStrategy, self).__init__( cta_engine, strategy_name, vt_symbol, setting ) - - self.bg = BarGenerator(self.on_bar,5 ,self.on_5min_bar) + + self.bg = BarGenerator(self.on_bar, 5, self.on_5min_bar) self.am = ArrayManager() - - buy_orderidList = [] - short_orderidList = [] - orderList = [] - + def on_init(self): """ Callback when strategy is inited. @@ -57,7 +53,7 @@ class KingKeltnerStrategy(CtaTemplate): Callback when strategy is started. """ self.write_log("策略启动") - + def on_stop(self): """ Callback when strategy is stopped. @@ -75,42 +71,42 @@ class KingKeltnerStrategy(CtaTemplate): Callback of new bar data update. """ self.bg.update_bar(bar) - - def on_5min_bar(self, bar:BarData): + + def on_5min_bar(self, bar: BarData): """""" - for orderid in self.orderList: + for orderid in self.orderList: self.cancel_order(orderid) self.orderList = [] - + am = self.am am.update_bar(bar) if not am.inited: return - + self.kk_up, self.kk_down = am.keltner(self.kk_length, self.kk_dev) - + if self.pos == 0: self.intra_trade_high = bar.high_price - self.intra_trade_low = bar.low_price + self.intra_trade_low = bar.low_price self.send_oco_order(self.kk_up, self.kk_down, self.fixed_size) - + elif self.pos > 0: self.intra_trade_high = max(self.intra_trade_high, bar.high_price) self.intra_trade_low = bar.low_price - - vt_orderid = self.sell(self.intra_trade_high*(1-self.trailing_percent/100), - abs(self.pos), True) + + vt_orderid = self.sell(self.intra_trade_high * (1 - self.trailing_percent / 100), + abs(self.pos), True) self.orderList.append(vt_orderid) - + elif self.pos < 0: self.intra_trade_high = bar.high_price self.intra_trade_low = min(self.intra_trade_low, bar.low_price) - - vt_orderid = self.cover(self.intra_trade_low*(1+self.trailing_percent/100), - abs(self.pos), True) + + vt_orderid = self.cover(self.intra_trade_low * (1 + self.trailing_percent / 100), + abs(self.pos), True) self.orderList.append(vt_orderid) - - self.put_event() + + self.put_event() def on_order(self, order: OrderData): """ @@ -130,18 +126,18 @@ class KingKeltnerStrategy(CtaTemplate): elif self.pos < 0: for buy_orderid in self.buy_orderidList: self.cancel_order(buy_orderid) - + for orderid in (self.buy_orderidList + self.short_orderidList): if orderid in self.orderList: self.orderList.remove(orderid) - + self.put_event() - + def send_oco_order(self, buy_price, short_price, volume): """""" self.buy_orderidList = self.buy(buy_price, volume, True) self.short_orderidList = self.short(short_price, volume, True) - + self.orderList.append(self.buy_orderidList) self.orderList.append(self.short_orderidList) @@ -149,4 +145,4 @@ class KingKeltnerStrategy(CtaTemplate): """ Callback of stop order update. """ - pass \ No newline at end of file + pass diff --git a/vnpy/app/cta_strategy/strategies/multi_signal_strategy.py b/vnpy/app/cta_strategy/strategies/multi_signal_strategy.py index 15e6dd41..62b32090 100644 --- a/vnpy/app/cta_strategy/strategies/multi_signal_strategy.py +++ b/vnpy/app/cta_strategy/strategies/multi_signal_strategy.py @@ -1,7 +1,5 @@ from vnpy.app.cta_strategy import ( - CtaTemplate, StopOrder, - Direction, TickData, BarData, TradeData, @@ -16,7 +14,7 @@ from vnpy.app.cta_strategy import ( class RsiSignal(CtaSignal): """""" - def __init__(self, rsi_window , rsi_level): + def __init__(self, rsi_window: int, rsi_level: float): """Constructor""" super(RsiSignal, self).__init__() @@ -27,7 +25,7 @@ class RsiSignal(CtaSignal): self.bg = BarGenerator(self.on_bar) self.am = ArrayManager() - + def on_tick(self, tick: TickData): """ Callback of new tick data update. @@ -38,12 +36,12 @@ class RsiSignal(CtaSignal): """ Callback of new bar data update. """ - self.am.update_bar(bar) + self.am.update_bar(bar) if not self.am.inited: self.set_signal_pos(0) - + rsi_value = self.am.rsi(self.rsi_window) - + if rsi_value >= self.rsi_long: self.set_signal_pos(1) elif rsi_value <= self.rsi_short: @@ -51,10 +49,11 @@ class RsiSignal(CtaSignal): else: self.set_signal_pos(0) + class CciSignal(CtaSignal): """""" - def __init__(self, cci_window, cci_level): + def __init__(self, cci_window: int, cci_level: float): """""" super(CciSignal, self).__init__() @@ -64,8 +63,8 @@ class CciSignal(CtaSignal): self.cci_short = -self.cci_level self.bg = BarGenerator(self.on_bar) - self.am = ArrayManager() - + self.am = ArrayManager() + def on_tick(self, tick: TickData): """ Callback of new tick data update. @@ -76,32 +75,33 @@ class CciSignal(CtaSignal): """ Callback of new bar data update. """ - self.am.update_bar(bar) + self.am.update_bar(bar) if not self.am.inited: self.set_signal_pos(0) - + cci_value = self.am.cci(self.cci_window) - + if cci_value >= self.cci_long: self.set_signal_pos(1) - elif cci_value<= self.cci_short: - self.set_signal_pos(-1) + elif cci_value <= self.cci_short: + self.set_signal_pos(-1) else: self.set_signal_pos(0) - + + class MaSignal(CtaSignal): """""" - def __init__(self, fast_window, slow_window): + def __init__(self, fast_window: int, slow_window: int): """""" super(MaSignal, self).__init__() self.fast_window = fast_window self.slow_window = slow_window - + self.bg = BarGenerator(self.on_bar, 5, self.on_5min_bar) - self.am = ArrayManager() - + self.am = ArrayManager() + def on_tick(self, tick: TickData): """ Callback of new tick data update. @@ -113,16 +113,16 @@ class MaSignal(CtaSignal): Callback of new bar data update. """ self.bg.update_bar(bar) - - def on_5min_bar(self, bar:BarData): + + def on_5min_bar(self, bar: BarData): """""" - self.am.update_bar(bar) + self.am.update_bar(bar) if not self.am.inited: self.set_signal_pos(0) - + fast_ma = self.am.sma(self.fast_window) slow_ma = self.am.sma(self.slow_window) - + if fast_ma > slow_ma: self.set_signal_pos(1) elif fast_ma < slow_ma: @@ -133,20 +133,21 @@ class MaSignal(CtaSignal): class MultiSignalStrategy(TargetPosTemplate): """""" - - author ='用Python的交易员' - rsi_window= 14 + author = '用Python的交易员' + + rsi_window = 14 rsi_level = 20 cci_window = 30 cci_level = 10 fast_window = 5 slow_window = 20 - signal_pos = {} - - parameters = ['rsi_window','rsi_level','cci_window','cci_level','fast_window','slow_window'] - variables = ['signal_pos','target_pos'] + signal_pos = {} + + parameters = ['rsi_window', 'rsi_level', 'cci_window', + 'cci_level', 'fast_window', 'slow_window'] + variables = ['signal_pos', 'target_pos'] def __init__(self, cta_engine, strategy_name, vt_symbol, setting): """""" @@ -157,13 +158,13 @@ class MultiSignalStrategy(TargetPosTemplate): self.rsi_signal = RsiSignal(self.rsi_window, self.rsi_level) self.cci_signal = CciSignal(self.cci_window, self.cci_level) self.ma_signal = MaSignal(self.fast_window, self.slow_window) - + self.signal_pos = { "rsi": 0, "cci": 0, "ma": 0 } - + def on_init(self): """ Callback when strategy is inited. @@ -176,7 +177,7 @@ class MultiSignalStrategy(TargetPosTemplate): Callback when strategy is started. """ self.write_log("策略启动") - + def on_stop(self): """ Callback when strategy is stopped. @@ -188,37 +189,37 @@ class MultiSignalStrategy(TargetPosTemplate): Callback of new tick data update. """ super(MultiSignalStrategy, self).on_tick(tick) - + self.rsi_signal.on_tick(tick) self.cci_signal.on_tick(tick) self.ma_signal.on_tick(tick) - + self.calculate_target_pos() - + def on_bar(self, bar: BarData): """ Callback of new bar data update. """ super(MultiSignalStrategy, self).on_bar(bar) - + self.rsi_signal.on_bar(bar) self.cci_signal.on_bar(bar) self.ma_signal.on_bar(bar) - + self.calculate_target_pos() - + def calculate_target_pos(self): """""" self.signal_pos['rsi'] = self.rsi_signal.get_signal_pos() self.signal_pos['cci'] = self.cci_signal.get_signal_pos() self.signal_pos['ma'] = self.ma_signal.get_signal_pos() - + target_pos = 0 for v in self.signal_pos.values(): target_pos += v - + self.set_target_pos(target_pos) - + def on_order(self, order: OrderData): """ Callback of new order data update. @@ -235,4 +236,4 @@ class MultiSignalStrategy(TargetPosTemplate): """ Callback of stop order update. """ - pass \ No newline at end of file + pass diff --git a/vnpy/app/cta_strategy/template.py b/vnpy/app/cta_strategy/template.py index d1d2b9dc..c3804286 100644 --- a/vnpy/app/cta_strategy/template.py +++ b/vnpy/app/cta_strategy/template.py @@ -2,10 +2,10 @@ from abc import ABC from typing import Any, Callable -from vnpy.trader.constant import Interval +from vnpy.trader.constant import Interval, Status from vnpy.trader.object import BarData, TickData, OrderData, TradeData -from .base import CtaOrderType, StopOrder +from .base import CtaOrderType, StopOrder, EngineType class CtaTemplate(ABC): @@ -246,8 +246,8 @@ class CtaSignal(ABC): def __init__(self): """""" - self.signal_pos = 0 - + self.signal_pos = 0 + def on_tick(self, tick: TickData): """ Callback of new tick data update. @@ -260,26 +260,25 @@ class CtaSignal(ABC): """ pass - def set_signal_pos(self, pos): """""" self.signal_pos = pos - + def get_signal_pos(self): """""" return self.signal_pos - + class TargetPosTemplate(CtaTemplate): """""" - + author = '量衍投资' - - tick_add = 1 - last_tick = None - last_bar = None - target_pos = 0 - orderList = [] + + tick_add = 1 + last_tick = None + last_bar = None + target_pos = 0 + orderList = [] variables = ['target_pos'] @@ -287,74 +286,74 @@ class TargetPosTemplate(CtaTemplate): """""" super(TargetPosTemplate, self).__init__( cta_engine, strategy_name, vt_symbol, setting - ) + ) - def on_tick(self, tick:TickData): + def on_tick(self, tick: TickData): """ Callback of new tick data update. """ self.last_tick = tick - + if self.trading: self.trade() - + def on_bar(self, bar: BarData): """ Callback of new bar data update. """ self.last_bar = bar - + def on_order(self, order: OrderData): """ Callback of new order data update. """ - if order.status == Status.ALLTRADED or order.status == Status.CANCELLED: + if order.status == Status.ALLTRADED or order.status == Status.CANCELLED: if order.vt_orderid in self.orderList: self.orderList.remove(order.vt_orderid) - + def set_target_pos(self, target_pos): """""" - self.target_pos = target_pos + self.target_pos = target_pos self.trade() - + def trade(self): """""" self.cancel_all() - + pos_change = self.target_pos - self.pos if not pos_change: return - + long_price = 0 short_price = 0 - + if self.last_tick: if pos_change > 0: long_price = self.last_tick.ask_price_1 + self.tick_add if self.last_tick.limit_up: - long_price = min(long_price, self.last_tick.limit_up) + long_price = min(long_price, self.last_tick.limit_up) else: short_price = self.last_tick.bid_price_1 - self.tick_add if self.last_tick.limit_down: - short_price = max(short_price, self.last_tick.limit_down) - + short_price = max(short_price, self.last_tick.limit_down) + else: if pos_change > 0: long_price = self.last_bar.close_price + self.tick_add else: short_price = self.last_bar.close_price - self.tick_add - + if self.get_engine_type() == EngineType.BACKTESTING: if pos_change > 0: vt_orderid = self.buy(long_price, abs(pos_change)) else: vt_orderid = self.short(short_price, abs(pos_change)) self.orderList.append(vt_orderid) - + else: if self.orderList: return - + if pos_change > 0: if self.pos < 0: if pos_change < abs(self.pos): @@ -371,4 +370,4 @@ class TargetPosTemplate(CtaTemplate): vt_orderid = self.sell(short_price, abs(self.pos)) else: vt_orderid = self.short(short_price, abs(pos_change)) - self.orderList.append(vt_orderid) \ No newline at end of file + self.orderList.append(vt_orderid) diff --git a/vnpy/gateway/ctp/ctp_gateway.py b/vnpy/gateway/ctp/ctp_gateway.py index 29e4b2f7..d0030f62 100644 --- a/vnpy/gateway/ctp/ctp_gateway.py +++ b/vnpy/gateway/ctp/ctp_gateway.py @@ -4,7 +4,39 @@ from datetime import datetime -from vnpy.api.ctp import * +from vnpy.api.ctp import ( + MdApi, + TdApi, + THOST_FTDC_OAS_Submitted, + THOST_FTDC_OAS_Accepted, + THOST_FTDC_OAS_Rejected, + THOST_FTDC_OST_NoTradeQueueing, + THOST_FTDC_OST_PartTradedQueueing, + THOST_FTDC_OST_AllTraded, + THOST_FTDC_OST_Canceled, + THOST_FTDC_D_Buy, + THOST_FTDC_D_Sell, + THOST_FTDC_PD_Long, + THOST_FTDC_PD_Short, + THOST_FTDC_OPT_LimitPrice, + THOST_FTDC_OPT_AnyPrice, + THOST_FTDC_OF_Open, + THOST_FTDC_OFEN_Close, + THOST_FTDC_OFEN_CloseYesterday, + THOST_FTDC_OFEN_CloseToday, + THOST_FTDC_PC_Futures, + THOST_FTDC_PC_Options, + THOST_FTDC_CP_CallOptions, + THOST_FTDC_CP_PutOptions, + THOST_FTDC_HF_Speculation, + THOST_FTDC_CC_Immediately, + THOST_FTDC_FCC_NotForceClose, + THOST_FTDC_TC_GFD, + THOST_FTDC_VC_AV, + THOST_FTDC_TC_IOC, + THOST_FTDC_VC_CV, + THOST_FTDC_AF_Delete +) from vnpy.trader.constant import ( Direction, Offset, @@ -84,6 +116,7 @@ symbol_exchange_map = {} symbol_name_map = {} symbol_size_map = {} + class CtpGateway(BaseGateway): """ VN Trader Gateway for CTP . @@ -489,7 +522,7 @@ class CtpTdApi(TdApi): account = AccountData( accountid=data["AccountID"], balance=data["Balance"], - frozen=data["FrozenMargin"]+data["FrozenCash"]+data["FrozenCommission"], + frozen=data["FrozenMargin"] + data["FrozenCash"] + data["FrozenCommission"], gateway_name=self.gateway_name ) account.available = data["Available"] @@ -734,7 +767,4 @@ class CtpTdApi(TdApi): def close(self): """""" if self.connect_status: - self.exit() - - - \ No newline at end of file + self.exit() \ No newline at end of file diff --git a/vnpy/gateway/futu/futu_gateway.py b/vnpy/gateway/futu/futu_gateway.py index 194a550d..5a875236 100644 --- a/vnpy/gateway/futu/futu_gateway.py +++ b/vnpy/gateway/futu/futu_gateway.py @@ -322,8 +322,7 @@ class FutuGateway(BaseGateway): account = AccountData( accountid=f"{self.gateway_name}_{self.market}", balance=float(row["total_assets"]), - frozen=(float(row["total_assets"]) - - float(row["avl_withdrawal_cash"])), + frozen=(float(row["total_assets"]) - float(row["avl_withdrawal_cash"])), gateway_name=self.gateway_name, ) self.on_account(account)