def notifyUnLockDuo(security): security = util.futureName(security) currentTimeString = util.getYMDHMS() a = '<a href="http://107.182.31.161:5288/">查看行情</a>' sendEmail(subject='[' + str(currentTimeString) + '] 解锁多(重新开多仓)_' + security, content='' + a)
def notifyCloseKon(security, currentTimeString=None): if currentTimeString is None: currentTimeString = util.getYMDHMS() a = '<a href="http://107.182.31.161:5288/">查看行情</a>' sendEmail(subject='[' + str(currentTimeString) + '] Kon平_' + util.futureName(security), content='' + a)
def getNowEarningRate(df, preCount=0): pricePositions = getPricePosiArray(df) indexList = df[df.EMA60 == df.EMA60].index.tolist() if preCount > 0: pricePositions = pricePositions[0:-preCount - 1] indexList = indexList[0:-preCount - 1] closes = [] for index in indexList: closes.append(df.loc[index, 'close']) i = pricePositions.__len__() - 1 nowPricePosition = pricePositions[-1] while (i - 1) > 0: pp = pricePositions[i - 1] if pp == nowPricePosition: i = i - 1 else: break closes = closes[i:] isDouing = getNearMaxClosePrice(df) is not None startPrice = closes[0] nowPrice = closes[-1] if isDouing is True: return util.getRate(startPrice, nowPrice) else: return util.getRate(nowPrice, startPrice)
def appendTreses(tmp_rates_every_step): tmp_treses = util.getProperty('tmp_treses') if tmp_treses is not None: tmp_treses.append(tmp_rates_every_step) else: tmp_treses = [tmp_rates_every_step] util.setProperty('tmp_treses', tmp_treses)
def notifyVolumeUnusual(security, volumeArrowCount=0): currentTimeString = util.getYMDHMS() content = '<div style="padding: 10px">' \ '<a href="http://107.182.31.161:5288/candle_sticks?security='+security+'" style="font-weight: bold;">查看走势</a>' \ '</div>' sendEmail(subject='[' + str(currentTimeString) + '] 成交量大增:' + str(volumeArrowCount) + '_' + util.futureName(security), content='' + content)
def notifyTrade(security, nowRate="?"): currentTimeString = util.getYMDHMS() duo = str(int(dao.readDuoPosition(security=security))) kon = str(int(dao.readKongPosition(security=security))) max = str(int(dao.readMaxPosition(security=security))) a = '<p>duo: <strong>' + duo + '</strong></p><p>kon: <strong>' + kon + '</strong></p><p>max: <strong>' + max + '</strong></p>' sendEmail(subject='[' + str(currentTimeString) + '] 触发交易动作_' + util.futureName(security), content='rate: ' + nowRate + ' duo: ' + duo + ' kon: ' + kon + ' max: ' + max)
def getDangerRate(df, preCount=0): indexList = df[df.EMA60 == df.EMA60].index.tolist() if preCount > 0: indexList = indexList[0:-preCount - 1] nowPrice = df.loc[indexList[-1], 'close'] maxClosePrice = getNearMaxClosePrice(df, preCount) minClosePrice = getNearMinClosePrice(df, preCount) if maxClosePrice is not None: rate = util.getRate(fromPrice=maxClosePrice, toPrice=nowPrice) else: rate = util.getRate(fromPrice=nowPrice, toPrice=minClosePrice) return rate
def notify10min(): # -------------------------------------------------------------------------------------------------------------------------------------------- items = dao.select( "select f_code, f_name, f_price, f_pre_close, f_createtime from t_future_tick where" " f_createtime > date_add(now(), interval - 10 minute) order by f_createtime desc", ()) code_items_rel = {} for item in items: code = item['f_code'] if code not in code_items_rel.keys(): code_items_rel.setdefault(code, [item]) else: code_items_rel[code].append(item) for code in code_items_rel.keys(): items = code_items_rel[code] if items.__len__() < 2: continue lastest = items[0] pre_close = float(lastest['f_pre_close']) price = float(lastest['f_price']) rate = round((price - pre_close) / pre_close * 100, 2) speed = getRateBetweenMaxAndMin_Speed(items) if speed < -0.7: # Ôٴη¢ËÍ֪ͨµÄCDʱ¼ä if code in coolDown_10min.keys(): now = util.getYMDHMS() coolDown_10min_starttime = coolDown_10min[code] durSec = util.timeDur_ReturnSec(coolDown_10min_starttime, now) if durSec < 60 * 30: return else: coolDown_10min.pop(code) # ·¢ËÍ֪ͨ log.log("Send Notification: " + code + " speed: " + str(speed)) url = 'http://' + SmtpClient_Host + ':' + str( SmtpClient_Port ) + '/smtpclient/sendFuture/(Rate: ' + str(rate) + ' Speed: ' + str( speed ) + ')This is ' + code + '/This is ' + code + '/[email protected]' #util.Async_req(url).start() dao.update( "insert into t_future_unusual_action(f_code, f_name, f_speed, f_rate, f_createtime)" " values(%s,%s,%s,%s,%s)", (code, code_name_rel[code], speed, rate, util.getYMDHMS())) coolDown_10min.setdefault(code, util.getYMDHMS())
def log(content): string = "[Time: " + util.getYMDHMS() + "]: " + str(content) print(string) file = open("log.out", "a") file.write(string + "\n") file.close() return string
def action(msg): ts = util.string2timestamp(str(nowTimeString)) frequencyLimitFlag = int(time.strftime('%M', time.localtime(ts))) % int( frequency[0:-1]) == 0 if frequencyLimitFlag is False: return msg if util.isFutureTradingTime(nowTimeString=nowTimeString ) is False or util.isFutureCommonTradingTime( security=security, nowTimeString=nowTimeString) is False: return msg msg = loop(security=security, frequency=frequency, nowTimeString=nowTimeString, msg=msg) return msg
def listen(): while True: if util.isOpenTime_wide() is False: time.sleep(10) continue url = getUrl(code_name_rel.keys()) ctn = requests.get(url).text strs = ctn.split("\n") values = [] count = 0 for line in strs: if line == '': continue try: code = line[line.index("str_") + 4:line.index('=') - 1].upper() except: continue if util.isOpenTime_Kind(code) is False: continue if '"' not in line: continue line = line[line.index('"') + 1:line.rindex('"')] if line.__len__() == 0: continue cols = line.split(",") name = cols[0] pre_close = float(cols[5]) price = float(cols[8]) position = float(cols[13]) settlement_price = float(cols[9]) date = cols[17] log.log("Ãû³Æ£º" + name + " ×òÊÕ£º" + str(pre_close) + " ÏÖ¼Û£º" + str(price) + " ÊÕÅ̼ۣº" + str(round((price - pre_close) / pre_close * 100, 2))) values.append((code, name, date, price, pre_close, position, settlement_price, util.getHMS(), util.getYMDHMS())) count = count + 1 dao.updatemany( "insert into" " t_future_tick(f_code, f_name, f_date, f_price, f_pre_close," " f_position, f_settlement_price, f_time, f_createtime)" " values(%s,%s,%s,%s,%s,%s,%s,%s,%s)", values) notify5min() notify10min() notify15min() print("loop next need sleep") time.sleep(25)
def get_bar_rates(df=None, len=20): bar_rates = [] closes = [float(x) for x in df['close']] opens = [float(x) for x in df['open']] i = 0 while i < len: rate = util.getRate(fromPrice=opens[-i - 1], toPrice=closes[-i - 1]) bar_rates.append(rate) i = i + 1 return bar_rates
def _handleOneTick(msg=None, nowTimeString=None): if security is None: print('请确认Security') ts = util.string2timestamp(str(nowTimeString)) frequencyLimitFlag = int(time.strftime('%M', time.localtime(ts))) % int( frequency[0:-1]) == 0 if frequencyLimitFlag is False: return msg if util.isFutureTradingTime(nowTimeString=nowTimeString ) is False or util.isFutureCommonTradingTime( security=security, nowTimeString=nowTimeString) is False: return msg msg = loop(security=security, frequency=frequency, nowTimeString=nowTimeString, msg=msg) return msg
def pushPosition(position): o = { 'available': True, 'position': position, 'createtime': util.getYMDHMS() } position_flow = util.getProperty('position_flow') if position_flow is None: util.setProperty('position_flow', [o]) else: position_flow.append(o) util.removeProperty('position_flow') util.setProperty('position_flow', position_flow)
def getOpen2CloseRates(df): opens = [float(x) for x in df['open']] closes = [float(x) for x in df['close']] arr = [] i = 0 for open in opens: close = closes[i] rate = util.getRate(open, close) i = i + 1 arr.append(rate) return arr
def loop(security=None, frequency=None, nowTimeString=None, msg=None): df = msg.get('df') position = msg.get('position') force_waiting_count = msg.get('force_waiting_count') open = msg.get('open') real_open = msg.get('real_open') clearRates = msg.get('clearRates') tmp_rates_every_step = msg.get('tmp_rates_every_step') open_after_next_change = msg.get('open_after_next_change') df = getAdvancedData(df, security=security, frequency=frequency, nowTimeString=nowTimeString) # atr = getATR(df=df, len=20) closes = [float(x) for x in df['close']] if force_waiting_count > 0: force_waiting_count = force_waiting_count - 1 print(nowTimeString + ": ForceWaiting...") return { 'df': df, 'position': position, 'force_waiting_count': force_waiting_count, 'open': open, 'clearRates': clearRates, 'tmp_rates_every_step': tmp_rates_every_step, 'open_after_next_change': open_after_next_change } status = isChangeTo(df) ADXs = [float(x) for x in df[df.ADX == df.ADX]['ADX']][-200:] cfn_count = changeFromNowCount(df) dangerRate = getDangerRate( df) # dangerRate的容忍度应该由earningRate决定,两个是正相关。能容忍利润做筹码,厌恶本金损失 earningRate = 0 pricePosis = getPricePosiArray(df) pricePosi = pricePosis[-1] if open is not None and open != 0: if pricePosis[-2] == 0: earningRate = util.getRate(open, closes[-1]) else: earningRate = util.getRate(closes[-1], open) if real_open is not None and real_open != 0: if pricePosis[-2] == 0: earningRate = util.getRate(real_open, closes[-1]) else: earningRate = util.getRate(closes[-1], real_open) # 趋势持续 if status == 'STILL': # 止损止盈平仓 if position != 0 and ( (earningRate <= cond_er and dangerRate < -cond_before_er) or (earningRate > cond_er and dangerRate < -cond_after_er)): if real_open != 0: clearRates.append(round((1 + earningRate / 100), 4)) else: clearRates.append(1) tmp_rates_every_step.append(earningRate) #print(str(tmp_rates_every_step.__len__()) + '@@@@@@@@@@tmp_rates_every_step: ' + str(tmp_rates_every_step)) appendTreses(tmp_rates_every_step) tmp_rates_every_step = [] print('!***********************# clear Position 止损止盈平仓 -> ' + str(earningRate) + ' r:' + str(reduce(lambda x, y: x * y, clearRates)) + '!!! ----- !!!') position = 0 open = 0 real_open = 0 # open_after_next_change = True open_after_next_change = False # pushPosition(0) else: # 高位回落平仓后再此处等待,或瞬间变化时ADX条件不符合正在等待机会 if position == 0: if open_after_next_change is False: # 等到adx条件符合,开空仓 if pricePosi == 1 and (ADXs[-1] > adx_edge): print( ' 平仓后再此处等待 adx条件符合,开空仓 ### ### ### ### ### ### ### ### ### ### ### ### Down Position' + ' adx:' + str(ADXs[-1])) position = -1 open = closes[-1] dangerRate = 0 # 等到adx条件符合,开多仓 elif pricePosi == 0 and (ADXs[-1] > adx_edge): print( ' 平仓后再此处等待 adx条件符合,开多仓 ### ### ### ### ### ### ### ### ### ### ### ### Up Position' + ' adx:' + str(ADXs[-1])) position = 1 open = closes[-1] dangerRate = 0 else: print(nowTimeString + ':' + " WAITING..." + ' close: ' + str(closes[-1])) else: print(nowTimeString + ':' + " WAITING..." + ' adx: ' + str(ADXs[-1])) # 持有多仓 if position > 0: print(nowTimeString + ':' + " Still Holding DUO..." + " dr:" + str(dangerRate) + ' er:' + str(earningRate) + ' adx:' + str(ADXs[-1])) tmp_rates_every_step.append(earningRate) if earningRate > real_open_rate and real_open == 0: closes = closes[-100:] real_open = closes[-1] print('!***********************#正式做多:' + str(closes[-1])) # 持有空仓 if position < 0: print(nowTimeString + ':' + " Still Holding KON..." + " dr:" + str(dangerRate) + ' er:' + str(earningRate) + ' adx:' + str(ADXs[-1])) tmp_rates_every_step.append(earningRate) if earningRate > real_open_rate and real_open == 0: real_open = closes[-1] print('!***********************#正式做空:' + str(closes[-1])) # 瞬间 Down elif status == 'DOWN': # 前个趋势还在持仓,而现在趋势反转,应该反手做空 if position != 0: position = 0 if real_open != 0: clearRates.append(round((1 + earningRate / 100), 4)) else: clearRates.append(1) tmp_rates_every_step.append(earningRate) #print(str(tmp_rates_every_step.__len__()) + '@@@@@@@@@@tmp_rates_every_step: ' + str(tmp_rates_every_step)) appendTreses(tmp_rates_every_step) tmp_rates_every_step = [] print(nowTimeString + ':!***********************# clear Position 趋势反转 ------> ' + str(earningRate) + ' r:' + str(reduce(lambda x, y: x * y, clearRates)) + '!!! ----- !!!') if ADXs[-1] < adx_edge: force_waiting_count = 5 open = 0 real_open = 0 # ------------------------------------------------------------------- # 变为Down瞬间,adx也符合要求,开空仓 elif (ADXs[-1] > adx_edge and cfn_count < 10) and position == 0: print( ' 变为Down瞬间,adx也符合要求,开空仓 ### ### ### ### ### ### ### ### ### ### ### ### Down Position' + ' adx:' + str(ADXs[-1])) position = -1 open = closes[-1] # pushPosition(1) open_after_next_change = False # 瞬间 Up elif status == 'UP': # 前个趋势还在持仓,而现在趋势反转,应该反手做多 if position != 0: position = 0 if real_open != 0: clearRates.append(round((1 + earningRate / 100), 4)) else: clearRates.append(1) print(nowTimeString + ':!***********************# clear Position 趋势反转 ------> ' + str(earningRate) + ' r:' + str(reduce(lambda x, y: x * y, clearRates)) + '!!! ----- !!!') tmp_rates_every_step.append(earningRate) #print(str(tmp_rates_every_step.__len__()) + '@@@@@@@@@@tmp_rates_every_step: ' + str(tmp_rates_every_step)) appendTreses(tmp_rates_every_step) tmp_rates_every_step = [] if ADXs[-1] < adx_edge: force_waiting_count = 5 open = 0 real_open = 0 if earningRate > 2: print() # ------------------------------------------------------------------- # 变为Up瞬间,adx也符合要求,开多仓 elif (ADXs[-1] > adx_edge and cfn_count < 10) and position == 0: print( ' 变为Up瞬间,adx也符合要求,开多仓 ### ### ### ### ### ### ### ### ### ### ### ### Up Position' + ' adx:' + str(ADXs[-1])) position = 1 open = closes[-1] open_after_next_change = False # pushPosition(-1) if clearRates.__len__() > 500: clearRates.pop(0) return { 'df': df, 'position': position, 'force_waiting_count': force_waiting_count, 'open': open, 'real_open': real_open, 'clearRates': clearRates, 'tmp_rates_every_step': tmp_rates_every_step, 'open_after_next_change': open_after_next_change }
def removeTreses(): util.removeProperty('tmp_treses')
def getNowPosition(): position_flow = util.getProperty('position_flow') if position_flow is None: return 0 else: return int(position_flow[-1].get('position'))
def notifyError(content): currentTimeString = util.getYMDHMS() sendEmail(subject='[' + str(currentTimeString) + '] 错误:' + content, content=str(content))
import StrategyBody as sb from StrategyBody import TickHandler import PyBase.Util as util th = TickHandler() sb.security = 'L8888.XDCE' timeArr = util.getTimeSerial(starttime='2019-03-15 14:15:00', count=200000, periodSec=61) for nowTimeString in timeArr: msg = th.handleOneTick(nowTimeString=nowTimeString)
import talib import jqdatasdk import numpy as np import PyBase.Util as util import time from functools import reduce cond_er = 0.8 cond_before_er = 0.8 cond_after_er = 1.2 adx_timeperiod = 4 adx_edge = 30 fast_ema = 6 slow_ema = 11 timeArr = util.getTimeSerial(starttime='2018-11-06 09:20:00', count=2000000, periodSec=61) df = None security = 'SC8888.XINE' frequency = '30m' msg = { 'df': df, 'position': 0, 'force_waiting_count': 0, 'open': 0, 'clearRates': [], 'tmp_rates_every_step': [], 'open_after_next_change': False }