From 5fd6da7f5923d3cd16020a60a027f05c20e3f484 Mon Sep 17 00:00:00 2001 From: David Brazda Date: Tue, 13 Jun 2023 11:34:32 +0200 Subject: [PATCH] docasne ulozeni sec indikatoru pred smazanim --- v2realbot/ENTRY_Vykladaci_RSI_MYSELL.py | 43 ++++++++--- v2realbot/controller/services.py | 10 +++ v2realbot/static/js/utils.js | 4 +- .../strategy/__pycache__/base.cpython-310.pyc | Bin 14208 -> 15792 bytes v2realbot/strategy/base.py | 70 ++++++++++++++++-- .../utils/__pycache__/utils.cpython-310.pyc | Bin 10166 -> 10291 bytes v2realbot/utils/utils.py | 3 + 7 files changed, 110 insertions(+), 20 deletions(-) diff --git a/v2realbot/ENTRY_Vykladaci_RSI_MYSELL.py b/v2realbot/ENTRY_Vykladaci_RSI_MYSELL.py index eca1f9f..4cc2973 100644 --- a/v2realbot/ENTRY_Vykladaci_RSI_MYSELL.py +++ b/v2realbot/ENTRY_Vykladaci_RSI_MYSELL.py @@ -396,17 +396,30 @@ def next(data, state: StrategyState): state.ilog(e=f"RSI {rsi_length=} necháváme 0", message=str(e)+format_exc()) #state.indicators.RSI14[-1]=0 - def populate_cbar_rsi_indicator(): - #CBAR RSI indicator + # def populate_cbar_rsi_indicator(): + # #CBAR RSI indicator + # try: + # crsi_length = int(safe_get(state.vars, "crsi_length",14)) + # source = state.cbar_indicators.tick_price #[-rsi_length:] #state.bars.vwap + # crsi_res = rsi(source, crsi_length) + # crsi_value = trunc(crsi_res[-1],3) + # state.cbar_indicators.CRSI[-1]=crsi_value + # #state.ilog(e=f"RSI {rsi_length=} {rsi_value=} {rsi_dont_buy=} {rsi_buy_signal=}", rsi_indicator=state.indicators.RSI14[-5:]) + # except Exception as e: + # state.ilog(e=f"CRSI {crsi_length=} necháváme 0", message=str(e)+format_exc()) + # #state.indicators.RSI14[-1]=0 + + def populate_secondary_rsi_indicator(): + #SBAR RSI indicator try: - crsi_length = int(safe_get(state.vars, "crsi_length",14)) - source = state.cbar_indicators.tick_price #[-rsi_length:] #state.bars.vwap - crsi_res = rsi(source, crsi_length) - crsi_value = trunc(crsi_res[-1],3) - state.cbar_indicators.CRSI[-1]=crsi_value + srsi_length = int(safe_get(state.vars, "srsi_length",14)) + source = state.secondary_indicators.sec_price #[-rsi_length:] #state.bars.vwap + srsi_res = rsi(source, srsi_length) + srsi_value = trunc(srsi_res[-1],3) + state.secondary_indicators.SRSI[-1]=srsi_value #state.ilog(e=f"RSI {rsi_length=} {rsi_value=} {rsi_dont_buy=} {rsi_buy_signal=}", rsi_indicator=state.indicators.RSI14[-5:]) except Exception as e: - state.ilog(e=f"CRSI {crsi_length=} necháváme 0", message=str(e)+format_exc()) + state.ilog(e=f"SRSI {srsi_length=} necháváme 0", message=str(e)+format_exc()) #state.indicators.RSI14[-1]=0 def slope_too_low(): @@ -573,7 +586,12 @@ def next(data, state: StrategyState): for key in state.cbar_indicators: if key != 'time': - last_ind_vals[key] = state.cbar_indicators[key][-5:] + last_ind_vals[key] = state.cbar_indicators[key][-5:] + + for key in state.secondary_indicators: + if key != 'time': + last_ind_vals[key] = state.secondary_indicators[key][-5:] + return last_ind_vals conf_bar = data['confirmed'] @@ -591,11 +609,14 @@ def next(data, state: StrategyState): state.vars.last_tick_volume = 0 state.vars.next_new = 1 + #SRSI + populate_secondary_rsi_indicator() + #kroky pro CONTINOUS TICKS only else: #CBAR INDICATOR pro tick price a deltu VOLUME populate_cbar_tick_price_indicator() - populate_cbar_rsi_indicator() + #SPOLECNA LOGIKA - bar indikatory muzeme populovat kazdy tick (dobre pro RT GUI), ale uklada se stejne az pri confirmu @@ -628,7 +649,7 @@ def init(state: StrategyState): #state.cbar_indicators['ivwap'] = [] state.cbar_indicators['tick_price'] = [] state.cbar_indicators['tick_volume'] = [] - state.cbar_indicators['CRSI'] = [] + state.secondary_indicators['SRSI'] = [] state.indicators['ema'] = [] state.indicators['slope'] = [] state.indicators['slopeMA'] = [] diff --git a/v2realbot/controller/services.py b/v2realbot/controller/services.py index c99ca90..af1f360 100644 --- a/v2realbot/controller/services.py +++ b/v2realbot/controller/services.py @@ -527,6 +527,16 @@ def archive_runner(runner: Runner, strat: StrategyInstance): #print("is not numpy", key, value) flattened_indicators[key]= value flattened_indicators_list.append(flattened_indicators) + flattened_indicators = {} + for key, value in strat.state.secondary_indicators.items(): + if isinstance(value, ndarray): + #print("is numpy", key,value) + flattened_indicators[key]= value.tolist() + #print("changed numpy:",value.tolist()) + else: + #print("is not numpy", key, value) + flattened_indicators[key]= value + flattened_indicators_list.append(flattened_indicators) runArchiveDetail: RunArchiveDetail = RunArchiveDetail(id = runner.id, name=runner.run_name, diff --git a/v2realbot/static/js/utils.js b/v2realbot/static/js/utils.js index 020c5ae..5e91300 100644 --- a/v2realbot/static/js/utils.js +++ b/v2realbot/static/js/utils.js @@ -30,12 +30,12 @@ indConfig = [ {name: "ema", titlevisible: false, embed: true, display: true, pri {name: "emaSlow", titlevisible: true, embed: true, display: true, priceScaleId: "right", lastValueVisible: false}, {name: "emaFast", titlevisible: true, embed: true, display: true, priceScaleId: "right", lastValueVisible: false}, {name: "RSI14", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, - {name: "CRSI", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, + {name: "SRSI", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, {name: "aroon", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, {name: "apo", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, {name: "ppo", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, {name: "stoch2", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false}, - {name: "stoch1", titlevisible: true, embed: true, display: true, priceScaleId: "left", lastValueVisible: false},] + {name: "sec_price", titlevisible: true, embed: true, display: true, priceScaleId: "right", lastValueVisible: false},] function initialize_statusheader() { diff --git a/v2realbot/strategy/__pycache__/base.cpython-310.pyc b/v2realbot/strategy/__pycache__/base.cpython-310.pyc index d06bc3795377c5c30343417cdcf474c9ccaeae84..a087840d17a9fb011b1d0117f1cc1fd919532b44 100644 GIT binary patch delta 6983 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 XW1`|52GHP49*~oVc56zxe(1jd=tyxN delta 5343 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 BvBLlW diff --git a/v2realbot/strategy/base.py b/v2realbot/strategy/base.py index f05c2e4..16955e9 100644 --- a/v2realbot/strategy/base.py +++ b/v2realbot/strategy/base.py @@ -2,7 +2,7 @@ Strategy base class """ from datetime import datetime -from v2realbot.utils.utils import AttributeDict, zoneNY, is_open_rush, is_close_rush, json_serial, print +from v2realbot.utils.utils import AttributeDict, zoneNY, is_open_rush, is_close_rush, json_serial, print, safe_get, Average from v2realbot.utils.tlog import tlog from v2realbot.utils.ilog import insert_log, insert_log_multiple from v2realbot.enums.enums import RecordType, StartBarAlign, Mode, Order, Account @@ -55,7 +55,8 @@ class Strategy: self.rtqueue = None self.runner_id = runner_id self.ilog_save = ilog_save - + self.secondary_res_start_time = dict() + self.secondary_res_start_index = dict() #TODO predelat na dynamické queues self.q1 = queue.Queue() @@ -189,11 +190,57 @@ class Strategy: #pokud je potvrzeny, pak nenese nikdy zmenu ceny, nepridavame zaznam nic self.nextnew = 1 - #TODO potvrzeny CBAR by mohl triggerovat populaci indikatoru se sekundarnim rozlisenim (tbd co BAR?) - #zatim to udelat tak, ze secondary bude jen priceline nikoli ohlcv (pro RSI, MA a slope bude snad dostatecne) - #prvni iterace nastavi 0 (inicializace) - #kazdy potvrzeny bar updatne hodnotu, DOMYSLET tento algoritmus (co bude zde a co v NEXT) - #self.state.secondary_indicators + #pokud jsou nastaveny secondary - zatím skrz stratvars - pripadne do do API + #zatim jedno, predelat pak na list + if safe_get(self.state.vars, "secondary_timeframe",None): + self.process_secondary_indicators(item) + + + #tady jsem skoncil + def process_secondary_indicators(self, item): + #toto je voláno každý potvrzený CBAR + resolution = int(safe_get(self.state.vars, "secondary_timeframe",10)) + if int(item['resolution']) >= int(resolution) or int(resolution) % int(item['resolution']) != 0: + self.state.ilog(e=f"Secondary res {resolution} must be higher than main resolution {item['resolution']} a jejim delitelem") + + #prvni vytvori pocatecni + if safe_get(self.secondary_res_start_time, resolution, None) is None: + self.secondary_res_start_time[resolution] = item['time'] + self.secondary_res_start_index[resolution] = int(item['index']) + self.state.ilog(e=f"INIT SECINDS {self.secondary_res_start_time[resolution]=} {self.secondary_res_start_index[resolution]=}") + + start_timestamp = datetime.timestamp(self.secondary_res_start_time[resolution]) + self.state.ilog(e=f"SECINDS EVAL", start_time=start_timestamp,start_time_plus=start_timestamp + resolution, aktual=datetime.timestamp(item['time'])) + #pokud uz jsme prekrocili okno, ukladame hodnotu + if start_timestamp + resolution <= datetime.timestamp(item['time']): + self.state.ilog(e=f"SECINDS okno prekroceno") + + index_from = self.secondary_res_start_index[resolution] - int(item['index']) -1 + + #vytvorime cas a vyplnime data + for key in self.state.secondary_indicators: + if key == 'time': + #nastavujeme aktualni cas + self.state.secondary_indicators['time'].append(item['time']) + #self.state.secondary_indicators['time'].append(self.secondary_res_start_time[resolution] ) + + #pro cenu vyplnime aktualni cenou, pro ostatni 0 + elif key == 'sec_price': + #do ceny dame ceny v tomto okne + + source = self.state.bars['vwap'] + #source = self.state.bars['close'] + + self.state.ilog(e=f"SECINDS pocitame z hodnot", hodnty=source[index_from:]) + self.state.secondary_indicators[key].append(Average(self.state.bars['close'][index_from:])) + else: + self.state.secondary_indicators[key].append(0) + + self.state.ilog(e="SECIND populated", sec_price=self.state.secondary_indicators['sec_price'][-5:]) + + #priprava start hodnot pro dalsi iteraci + self.secondary_res_start_time[resolution] = item['time'] + self.secondary_res_start_index[resolution] = int(item['index']) """"refresh positions and avgp - for CBAR once per confirmed, for BARS each time""" @@ -445,6 +492,13 @@ class Strategy: rt_out["indicators"][key]= value[-1] except IndexError: pass + #secondaries + if len(self.state.secondary_indicators) > 0 and item['confirmed'] == 1: + for key, value in self.state.secondary_indicators.items(): + try: + rt_out["indicators"][key]= value[-1] + except IndexError: + pass #same for static indicators if len(self.state.statinds) > 0: @@ -580,6 +634,8 @@ class StrategyState: self.trades = AttributeDict(trades) self.indicators = AttributeDict(time=[]) self.cbar_indicators = AttributeDict(time=[]) + #secondary timeframe indicators + self.secondary_indicators = AttributeDict(time=[], sec_price=[]) self.statinds = AttributeDict() #these methods can be overrided by StrategyType (to add or alter its functionality) self.buy = self.interface.buy diff --git a/v2realbot/utils/__pycache__/utils.cpython-310.pyc b/v2realbot/utils/__pycache__/utils.cpython-310.pyc index b762a4692e1353ff1204c044df58a0c55fdee981..a899d3f8a082fb30d187e1e1d060e0656c4c4276 100644 GIT binary patch delta 2184 zcmZ{kdu-EH6vun|TKDKEd$6rt+1jle-Pph}V2)SEU}KEEA4)|_+5G_>-CAzD@$iAN zi9|q#Co!PJfKg#8OdRt`q6iu!k_a*W@eBF~e_%-T4>Ud!4SLRR2@a!c_W7Orz2}_Y zJ@?$-eYa)2)f%x{lXUbq@%u67mi`@FA}-J zNy=g|Q{>TeiO5%~HtK~-xQC7YrS&>dAPR?dqHsv>U#1v`bbgC=$gK zlPcB{BHRQ<2Bm0+~nWcJjocvOS!%9hPIh? z&MfO461C=MfIN-8PG52ly9tJZ6Ha&L7@0tAiJ8f;=!{?iIYw>Icz)&z*v5&{O>sHU z-(zAY{^;x=&yH`I`6ra{q4XM6Q*0orNI5~H$rHVjb%T7Eh0Tl*9?Ex^__U|tnf&6M zDT^RYO$Y=;q$d!N0lb~>%zKYR+zd`>nYy@)L^*+Ft{>`ZIL^r5t!&ZEa3~g6)0p>u z$g-9baqnd+!%Fa)5OPZ#(-+G`T0yv9Kes=hy}S~ki^Unovn zdJ4-5muFT1?L1!#8IVFh3!kK`7*2NI4ijA-YzwSP&I@(Q|&({U`< zgx3qLJ|Ab|9;Sf2Mi06qa@k8;3uxa3N&L-vyZy<1u}#rn&z5p!dt7pmJcC|OgLxC1 z61RIw%zWX=ZanE(0!?_+0P=B1R#ZH=!uv3_^opFG1ka3uywfO{Fqm0vxF~(VjcCfY9YbW6Aj6wwBADVdmM@S?RQ4`U`h@$7*!Nfmoaz8!4@9&&* z&$++Hbl1sFbJ%P)Y4A6-X@uv#V9sMFrpikh>w{jlV00bN2lS8ftPaExZbmpRLoVz%Q06IpN~H2a^rxGFBs(&C^hqSd?8Gc%`i8 zRqFJ8yc)w-|3_QG??-J7Ml6-9G3f)m2FESDR(A7cYE&Js$DFPAD9d>RDs6m)%rK&n zuf$P1w$#MsX6&gMd+Ok;_-gE-6Xi9$1=SY0dQ9u-O4M+-+{IhvrC4(p_SDAPF}$01 z;0tF|H>#by3)LRp&3iD*TE3R|;(srf)@oc2PT!DD>tSBvkM#m$$^6Mh>Aru{t4@X2hjn~8O zIhpJgI6S9ikt)n3)k0ntuh$m}g=4;0ARLN%y`qDrtOO6?VX&uWX0@UDJU&s{W+sgl z+cB|ZgJ^@E)OPIz>wtr)OW1z+CiN;Cgwt~~*kSl;?kVE{y1SSNz}_^c`4}aT5Sa!s z1n1MD(+U8>J6$T}z+} z#s9s;rB#fZWqFAEwnW8Kx8!ms^6@$Vhlt@AQ}h_{zj8;6AnRr-ec??n8+(L-$Fs%7iml! z#q*H{zvj(PdW77(gh!#==18AJ^EP?Xr!s1E%*ezf^xHPDD12zkGE3}EmTV@brmxuk zWNvD~rBn3LctjTBIF4oxMg!?uv4I3mkP#D1N%VUCL0^=P(roc+gau0MC0X}Wg#Jo` z*UQ6x^!31?Jum+RB~rf)y+}{h+^sY%Q5=T@_8ZB|C{D)%{+MvXK8G#0o`PtXh!lbu z;WCI1$UX&MI_!EknptqmQOMkoU$}ErZ7D%eB5{UrmT;Otu7VOO245s1hd6GqPe?mO zI7j%HP(x7r`?txnsJW=*G&JbbnsBSkJXZB4RNv!g;412Ksx>6uQ$r30DN-n+7zadn zI1s~+eFP2^HKtcnO1gK_FiA3|#l3e4{wS)*P;+Q!a-2s8ae?qTEO!<()KQd#<76f- z;~!orxiqWBF!d;*MCaYr=Sdol4n}G8OtACzOUt?GTCXak{` z$fxNcO(&A>PZ1;RAgK4$9 tuple[bool, str]: return False, None +def Average(lst): + return sum(lst) / len(lst) + def safe_get(collection, key, default=None): """Get values from a collection without raising errors"""