rozpracovane zmeny
This commit is contained in:
7
testy/asyncioRun.py
Normal file
7
testy/asyncioRun.py
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
import asyncio
|
||||||
|
|
||||||
|
async def vysledek():
|
||||||
|
return 100
|
||||||
|
|
||||||
|
a = asyncio.run(vysledek())
|
||||||
|
print(a)
|
||||||
@ -40,6 +40,7 @@ stratvars = AttributeDict(maxpozic = 250,
|
|||||||
lastbuyindex=-6,
|
lastbuyindex=-6,
|
||||||
pendingbuys={},
|
pendingbuys={},
|
||||||
limitka = None,
|
limitka = None,
|
||||||
|
limitka_price = None,
|
||||||
jevylozeno=0,
|
jevylozeno=0,
|
||||||
vykladka=5,
|
vykladka=5,
|
||||||
curve = [0.01, 0.01, 0.01, 0, 0.02, 0.02, 0.01,0.01, 0.01,0.03, 0.01, 0.01, 0.01,0.04, 0.01,0.01, 0.01,0.05, 0.01,0.01, 0.01,0.01, 0.06,0.01, 0.01,0.01, 0.01],
|
curve = [0.01, 0.01, 0.01, 0, 0.02, 0.02, 0.01,0.01, 0.01,0.03, 0.01, 0.01, 0.01,0.04, 0.01,0.01, 0.01,0.05, 0.01,0.01, 0.01,0.01, 0.06,0.01, 0.01,0.01, 0.01],
|
||||||
@ -155,10 +156,10 @@ def next(data, state: StrategyState):
|
|||||||
slope_lookback = int(state.vars.slope_lookback)
|
slope_lookback = int(state.vars.slope_lookback)
|
||||||
minimum_slope = float(state.vars.minimum_slope)
|
minimum_slope = float(state.vars.minimum_slope)
|
||||||
|
|
||||||
if len(state.indicators.ema) > slope_lookback:
|
if len(state.bars.close) > slope_lookback:
|
||||||
#slope = ((state.indicators.ema[-1] - state.indicators.ema[-slope_lookback])/slope_lookback)*100
|
#slope = ((state.indicators.ema[-1] - state.indicators.ema[-slope_lookback])/slope_lookback)*100
|
||||||
#PUVODNI slope = ((state.bars.close[-1] - state.bars.close[-slope_lookback])/slope_lookback)*100
|
#PUVODNI slope = ((state.bars.close[-1] - state.bars.close[-slope_lookback])/slope_lookback)*100
|
||||||
slope = ((state.bars.close[-1] - state.indicators.ema[-slope_lookback])/state.indicators.ema[-slope_lookback])*100
|
slope = ((state.bars.close[-1] - state.bars.close[-slope_lookback])/state.bars.close[-slope_lookback])*100
|
||||||
#roc = ((state.indicators.ema[-1] - state.indicators.ema[-roc_lookback])/state.indicators.ema[-roc_lookback])*100
|
#roc = ((state.indicators.ema[-1] - state.indicators.ema[-roc_lookback])/state.indicators.ema[-roc_lookback])*100
|
||||||
state.indicators.slope.append(slope)
|
state.indicators.slope.append(slope)
|
||||||
#state.indicators.roc.append(roc)
|
#state.indicators.roc.append(roc)
|
||||||
@ -166,6 +167,7 @@ def next(data, state: StrategyState):
|
|||||||
#ic(state.indicators.roc[-5:])
|
#ic(state.indicators.roc[-5:])
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print("Exception in NEXT Indicator section", str(e))
|
print("Exception in NEXT Indicator section", str(e))
|
||||||
|
state.ilog(e="EXCEPTION", msg="Exception in NEXT Indicator section" + str(e))
|
||||||
|
|
||||||
print("is falling",isfalling(state.indicators.ema,state.vars.Trend))
|
print("is falling",isfalling(state.indicators.ema,state.vars.Trend))
|
||||||
print("is rising",isrising(state.indicators.ema,state.vars.Trend))
|
print("is rising",isrising(state.indicators.ema,state.vars.Trend))
|
||||||
@ -175,34 +177,54 @@ def next(data, state: StrategyState):
|
|||||||
##CONSOLIDATION PART kazdy Nty bar dle nastaveni
|
##CONSOLIDATION PART kazdy Nty bar dle nastaveni
|
||||||
if int(data["index"])%int(state.vars.consolidation_bar_count) == 0:
|
if int(data["index"])%int(state.vars.consolidation_bar_count) == 0:
|
||||||
print("***Consolidation ENTRY***")
|
print("***Consolidation ENTRY***")
|
||||||
|
state.ilog(e="Konzolidujeme")
|
||||||
|
|
||||||
orderlist = state.interface.get_open_orders(symbol=state.symbol, side=None)
|
orderlist = state.interface.get_open_orders(symbol=state.symbol, side=None)
|
||||||
#print(orderlist)
|
#print(orderlist)
|
||||||
pendingbuys_new = {}
|
pendingbuys_new = {}
|
||||||
limitka_old = state.vars.limitka
|
limitka_old = state.vars.limitka
|
||||||
print("Puvodni LIMITKA", limitka_old)
|
print("Puvodni LIMITKA", limitka_old)
|
||||||
|
#zaciname s cistym stitem
|
||||||
state.vars.limitka = None
|
state.vars.limitka = None
|
||||||
|
state.vars.limitka_price = None
|
||||||
|
limitka_found = False
|
||||||
for o in orderlist:
|
for o in orderlist:
|
||||||
if o.side == OrderSide.SELL:
|
if o.side == OrderSide.SELL:
|
||||||
print("Nalezena LIMITKA")
|
print("Nalezena LIMITKA")
|
||||||
|
limitka_found = True
|
||||||
state.vars.limitka = o.id
|
state.vars.limitka = o.id
|
||||||
|
state.vars.limitka_price = o.limit_price
|
||||||
|
##TODO sem pridat upravu ceny
|
||||||
if o.side == OrderSide.BUY:
|
if o.side == OrderSide.BUY:
|
||||||
pendingbuys_new[str(o.id)]=float(o.limit_price)
|
pendingbuys_new[str(o.id)]=float(o.limit_price)
|
||||||
|
|
||||||
print("Nová LIMITKA", state.vars.limitka)
|
state.ilog(e="Konzolidace", limitka_old=str(limitka_old), limitka_new=str(state.vars.limitka), limitka_new_price=state.vars.limitka_price)
|
||||||
|
|
||||||
|
#neni limitka, ale mela by byt - vytváříme ji
|
||||||
|
if state.positions > 0 and state.vars.limitka is None:
|
||||||
|
state.ilog(e="Neni limitka, ale mela by být.")
|
||||||
|
price=price2dec(float(state.avgp)+state.vars.profit)
|
||||||
|
state.vars.limitka = asyncio.run(state.interface.sell_l(price=price, size=state.positions))
|
||||||
|
state.vars.limitka_price = price
|
||||||
|
state.ilog(e="Vytvořena nová limitka", limitka=str(state.vars.limitka), limtka_price=state.vars.limitka_price)
|
||||||
|
|
||||||
|
|
||||||
if pendingbuys_new != state.vars.pendingbuys:
|
if pendingbuys_new != state.vars.pendingbuys:
|
||||||
|
state.ilog(e="Rozdilna PB prepsana", pb_new=pendingbuys_new, pb_old = state.vars.pendingbuys)
|
||||||
print("ROZDILNA PENDINGBUYS přepsána")
|
print("ROZDILNA PENDINGBUYS přepsána")
|
||||||
print("OLD",state.vars.pendingbuys)
|
print("OLD",state.vars.pendingbuys)
|
||||||
state.vars.pendingbuys = unpackb(packb(pendingbuys_new))
|
state.vars.pendingbuys = unpackb(packb(pendingbuys_new))
|
||||||
print("NEW", state.vars.pendingbuys)
|
print("NEW", state.vars.pendingbuys)
|
||||||
else:
|
else:
|
||||||
print("PENDINGBUYS sedí - necháváme", state.vars.pendingbuys)
|
print("PENDINGBUYS sedí - necháváme", state.vars.pendingbuys)
|
||||||
|
state.ilog(e="PB sedi nechavame", pb_new=pendingbuys_new, pb_old = state.vars.pendingbuys)
|
||||||
print("OLD jevylozeno", state.vars.jevylozeno)
|
print("OLD jevylozeno", state.vars.jevylozeno)
|
||||||
if len(state.vars.pendingbuys) > 0:
|
if len(state.vars.pendingbuys) > 0:
|
||||||
state.vars.jevylozeno = 1
|
state.vars.jevylozeno = 1
|
||||||
else:
|
else:
|
||||||
state.vars.jevylozeno = 0
|
state.vars.jevylozeno = 0
|
||||||
print("NEW jevylozeno", state.vars.jevylozeno)
|
print("NEW jevylozeno", state.vars.jevylozeno)
|
||||||
|
state.ilog(e="Nove jevyloze", jevylozeno=state.vars.jevylozeno)
|
||||||
|
|
||||||
#print(limitka)
|
#print(limitka)
|
||||||
#print(pendingbuys_new)
|
#print(pendingbuys_new)
|
||||||
@ -215,14 +237,21 @@ def next(data, state: StrategyState):
|
|||||||
else:
|
else:
|
||||||
print("no time for consolidation", data["index"])
|
print("no time for consolidation", data["index"])
|
||||||
|
|
||||||
|
#HLAVNI ITERACNI LOG JESTE PRED AKCI - obsahuje aktualni hodnoty vetsiny parametru
|
||||||
|
lp = state.interface.get_last_price(symbol=state.symbol)
|
||||||
|
state.ilog(e="ITER_ENTRY", last_price=lp, stratvars=state.vars)
|
||||||
|
|
||||||
#SLOPE ANGLE PROTECTION
|
#SLOPE ANGLE PROTECTION
|
||||||
|
state.ilog(e="SLOPE", curr_slope=slope, minimum_slope=minimum_slope, last_slopes=state.indicators.slope[-5:])
|
||||||
if slope < minimum_slope:
|
if slope < minimum_slope:
|
||||||
print("OCHRANA SLOPE TOO HIGH")
|
print("OCHRANA SLOPE TOO HIGH")
|
||||||
|
state.ilog(e="SLOPE_EXCEEDED")
|
||||||
if len(state.vars.pendingbuys)>0:
|
if len(state.vars.pendingbuys)>0:
|
||||||
print("CANCEL PENDINGBUYS")
|
print("CANCEL PENDINGBUYS")
|
||||||
ic(state.vars.pendingbuys)
|
ic(state.vars.pendingbuys)
|
||||||
res = asyncio.run(state.cancel_pending_buys())
|
res = asyncio.run(state.cancel_pending_buys())
|
||||||
ic(state.vars.pendingbuys)
|
ic(state.vars.pendingbuys)
|
||||||
|
state.ilog(e="Rusime pendingbuyes", pb=state.vars.pendingbuys)
|
||||||
print("slope", slope)
|
print("slope", slope)
|
||||||
print("min slope", minimum_slope)
|
print("min slope", minimum_slope)
|
||||||
|
|
||||||
@ -235,6 +264,7 @@ def next(data, state: StrategyState):
|
|||||||
ic(state.time)
|
ic(state.time)
|
||||||
#zatim vykladame full
|
#zatim vykladame full
|
||||||
#positions = int(int(state.vars.maxpozic)/int(state.vars.chunk))
|
#positions = int(int(state.vars.maxpozic)/int(state.vars.chunk))
|
||||||
|
state.ilog(e="BUY SIGNAL", ema=state.indicators.ema[-1], trend=state.vars.Trend)
|
||||||
vyloz()
|
vyloz()
|
||||||
|
|
||||||
## testuje aktualni cenu od nejvyssi visici limitky
|
## testuje aktualni cenu od nejvyssi visici limitky
|
||||||
@ -252,6 +282,7 @@ def next(data, state: StrategyState):
|
|||||||
print("max cena v orderbuys", maxprice)
|
print("max cena v orderbuys", maxprice)
|
||||||
if state.interface.get_last_price(state.symbol) > float(maxprice) + state.vars.ticks2reset:
|
if state.interface.get_last_price(state.symbol) > float(maxprice) + state.vars.ticks2reset:
|
||||||
print("ujelo to vice nez o " + str(state.vars.ticks2reset) + ", rusime limit buye")
|
print("ujelo to vice nez o " + str(state.vars.ticks2reset) + ", rusime limit buye")
|
||||||
|
state.ilog(e="Ujelo to o více " + str(state.vars.ticks2reset), msg="rusime PB buye")
|
||||||
##TODO toto nejak vymyslet - duplikovat?
|
##TODO toto nejak vymyslet - duplikovat?
|
||||||
res = asyncio.run(state.cancel_pending_buys())
|
res = asyncio.run(state.cancel_pending_buys())
|
||||||
|
|
||||||
@ -268,6 +299,7 @@ def next(data, state: StrategyState):
|
|||||||
if len(state.vars.pendingbuys) == 0:
|
if len(state.vars.pendingbuys) == 0:
|
||||||
state.vars.blockbuy = 0
|
state.vars.blockbuy = 0
|
||||||
state.vars.jevylozeno = 0
|
state.vars.jevylozeno = 0
|
||||||
|
state.ilog(e="PB se vyklepaly nastavujeme: neni vylozeno", jevylozeno=state.vars.jevylozeno)
|
||||||
|
|
||||||
#TODO toto dodelat konzolidaci a mozna lock na limitku a pendingbuys a jevylozeno ??
|
#TODO toto dodelat konzolidaci a mozna lock na limitku a pendingbuys a jevylozeno ??
|
||||||
|
|
||||||
@ -305,6 +337,7 @@ def init(state: StrategyState):
|
|||||||
state.indicators['ema'] = []
|
state.indicators['ema'] = []
|
||||||
state.indicators['slope'] = []
|
state.indicators['slope'] = []
|
||||||
#state.indicators['roc'] = []
|
#state.indicators['roc'] = []
|
||||||
|
#state.ilog(e="INIT", stratvars=state.vars)
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
|
|
||||||
|
|||||||
@ -113,7 +113,7 @@ async def websocket_endpoint(
|
|||||||
if data=="break":
|
if data=="break":
|
||||||
break
|
break
|
||||||
await ws.send_text(data)
|
await ws.send_text(data)
|
||||||
print("WSTX thread received data", data)
|
print("WSTX thread received data") #,data)
|
||||||
except Empty:
|
except Empty:
|
||||||
print("WSTX thread Heartbeat. No data received from queue.")
|
print("WSTX thread Heartbeat. No data received from queue.")
|
||||||
continue
|
continue
|
||||||
|
|||||||
@ -16,6 +16,30 @@
|
|||||||
<body>
|
<body>
|
||||||
<div id="main" class="mainConteiner flex-container">
|
<div id="main" class="mainConteiner flex-container">
|
||||||
<div id="chartContainer" class="flex-items">
|
<div id="chartContainer" class="flex-items">
|
||||||
|
|
||||||
|
|
||||||
|
<div class="line">
|
||||||
|
<div data-toggle="collapse" data-target="#rec1">12233 <strong>Event</strong></div>
|
||||||
|
<div id="rec1" class="collapse">
|
||||||
|
Detaila mozna structured
|
||||||
|
Lorem ipsum dolor sit amet, consectetur adipisicing elit,
|
||||||
|
sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,
|
||||||
|
quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="line">
|
||||||
|
<div data-toggle="collapse" data-target="#rec2">12233 <strong>Event</strong></div>
|
||||||
|
<div id="rec2" class="collapse">
|
||||||
|
Detaila mozna structured
|
||||||
|
Lorem ipsum dolor sit amet, consectetur adipisicing elit,
|
||||||
|
sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,
|
||||||
|
quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<h4>Status: <span id="status">Not connected</span></h4>
|
<h4>Status: <span id="status">Not connected</span></h4>
|
||||||
<div id="formular">
|
<div id="formular">
|
||||||
<form action="">
|
<form action="">
|
||||||
@ -26,11 +50,16 @@
|
|||||||
<button onclick="sendMessage(event)" id="bt.send" class="btn btn-success">Send</button>
|
<button onclick="sendMessage(event)" id="bt.send" class="btn btn-success">Send</button>
|
||||||
</form>
|
</form>
|
||||||
</div>
|
</div>
|
||||||
<ul id='messages'>
|
<div id="chart" style="display: None; float: left; "></div>
|
||||||
</ul>
|
|
||||||
<div id="chart" style="display: None"></div>
|
|
||||||
<div class="legend" id="legend"></div>
|
<div class="legend" id="legend"></div>
|
||||||
|
<div id="msgContainer">
|
||||||
|
<div class="msgContainerInner">
|
||||||
|
<div id="lines">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div id="runner-table" class="flex-items">
|
<div id="runner-table" class="flex-items">
|
||||||
<div id="controls">
|
<div id="controls">
|
||||||
<label>API-KEY: <input type="password" id="api-key" autocomplete="off"/></label>
|
<label>API-KEY: <input type="password" id="api-key" autocomplete="off"/></label>
|
||||||
|
|||||||
@ -1,16 +1,18 @@
|
|||||||
//const chartOptions = { layout: { textColor: 'black', background: { type: 'solid', color: 'white' } } };
|
//const chartOptions = { layout: { textColor: 'black', background: { type: 'solid', color: 'white' } } };
|
||||||
const chartOptions = { width: 1200, height: 600, leftPriceScale: {visible: true}}
|
const chartOptions = { width: 1045, height: 600, leftPriceScale: {visible: true}}
|
||||||
const chart = LightweightCharts.createChart(document.getElementById('chart'), chartOptions);
|
const chart = LightweightCharts.createChart(document.getElementById('chart'), chartOptions);
|
||||||
chart.applyOptions({ timeScale: { visible: true, timeVisible: true, secondsVisible: true }, crosshair: {
|
chart.applyOptions({ timeScale: { visible: true, timeVisible: true, secondsVisible: true }, crosshair: {
|
||||||
mode: LightweightCharts.CrosshairMode.Normal, labelVisible: true
|
mode: LightweightCharts.CrosshairMode.Normal, labelVisible: true
|
||||||
}})
|
}})
|
||||||
const candlestickSeries = chart.addCandlestickSeries();
|
const candlestickSeries = chart.addCandlestickSeries({ lastValueVisible: true, priceLineWidth:2, priceLineColor: "red", priceFormat: { type: 'price', precision: 2, minMove: 0.01 }});
|
||||||
candlestickSeries.priceScale().applyOptions({
|
candlestickSeries.priceScale().applyOptions({
|
||||||
scaleMargins: {
|
scaleMargins: {
|
||||||
top: 0.1, // highest point of the series will be 10% away from the top
|
top: 0.1, // highest point of the series will be 10% away from the top
|
||||||
bottom: 0.4, // lowest point will be 40% away from the bottom
|
bottom: 0.4, // lowest point will be 40% away from the bottom
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
const volumeSeries = chart.addHistogramSeries({title: "Volume", color: '#26a69a', priceFormat: {type: 'volume'}, priceScaleId: ''});
|
const volumeSeries = chart.addHistogramSeries({title: "Volume", color: '#26a69a', priceFormat: {type: 'volume'}, priceScaleId: ''});
|
||||||
volumeSeries.priceScale().applyOptions({
|
volumeSeries.priceScale().applyOptions({
|
||||||
// set the positioning of the volume series
|
// set the positioning of the volume series
|
||||||
@ -21,11 +23,13 @@ volumeSeries.priceScale().applyOptions({
|
|||||||
});
|
});
|
||||||
|
|
||||||
const vwapSeries = chart.addLineSeries({
|
const vwapSeries = chart.addLineSeries({
|
||||||
title: "vwap",
|
// title: "vwap",
|
||||||
color: '#2962FF',
|
color: '#2962FF',
|
||||||
lineWidth: 1,
|
lineWidth: 1,
|
||||||
|
lastValueVisible: false
|
||||||
})
|
})
|
||||||
|
|
||||||
|
chart.timeScale().fitContent();
|
||||||
|
|
||||||
//TBD dynamicky zobrazovat vsechny indikatory
|
//TBD dynamicky zobrazovat vsechny indikatory
|
||||||
//document.getElementById('chart').style.display = 'inline-block';
|
//document.getElementById('chart').style.display = 'inline-block';
|
||||||
@ -54,7 +58,7 @@ chart.subscribeCrosshairMove((param) => {
|
|||||||
firstRow.innerText += item.name + " " + ind.value + " ";
|
firstRow.innerText += item.name + " " + ind.value + " ";
|
||||||
});
|
});
|
||||||
|
|
||||||
firstRow.innerText += 'vwap' + ' ' + vwap.toFixed(2) + " o" + bars.open + " h" + bars.high + " l" + bars.low + " c" + bars.close + " v" + volumes.value;
|
firstRow.innerText += ' vwap' + ' ' + vwap.toFixed(2) + " O" + bars.open + " H" + bars.high + " L" + bars.low + " C" + bars.close + " V" + volumes.value + "";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
firstRow.innerText = '-';
|
firstRow.innerText = '-';
|
||||||
|
|||||||
@ -1,6 +1,9 @@
|
|||||||
const momentumIndicatorNames = ["roc", "slope"]
|
const momentumIndicatorNames = ["roc", "slope"]
|
||||||
var indList = []
|
var indList = []
|
||||||
|
var pbiList = []
|
||||||
var ws = null;
|
var ws = null;
|
||||||
|
var positionsPriceLine = null
|
||||||
|
var limitkaPriceLine = null
|
||||||
function connect(event) {
|
function connect(event) {
|
||||||
var runnerId = document.getElementById("runnerId")
|
var runnerId = document.getElementById("runnerId")
|
||||||
try {
|
try {
|
||||||
@ -16,12 +19,6 @@ function connect(event) {
|
|||||||
document.getElementById("chart").style.display = "block"
|
document.getElementById("chart").style.display = "block"
|
||||||
}
|
}
|
||||||
ws.onmessage = function(event) {
|
ws.onmessage = function(event) {
|
||||||
//var messages = document.getElementById('messages')
|
|
||||||
//var message = document.createElement('li')
|
|
||||||
//var content = document.createTextNode(event.data)
|
|
||||||
//message.appendChild(content)
|
|
||||||
//messages.appendChild(message)
|
|
||||||
|
|
||||||
var parsed_data = JSON.parse(event.data)
|
var parsed_data = JSON.parse(event.data)
|
||||||
|
|
||||||
console.log(JSON.stringify(parsed_data))
|
console.log(JSON.stringify(parsed_data))
|
||||||
@ -53,6 +50,107 @@ function connect(event) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//loglist
|
||||||
|
if (parsed_data.hasOwnProperty("iter_log")) {
|
||||||
|
iterLogList = parsed_data.iter_log
|
||||||
|
console.log("Incoming logline object")
|
||||||
|
|
||||||
|
var lines = document.getElementById('lines')
|
||||||
|
var line = document.createElement('div')
|
||||||
|
line.classList.add("line")
|
||||||
|
const newLine = document.createTextNode("-----------------NEXT ITER------------------")
|
||||||
|
line.appendChild(newLine)
|
||||||
|
lines.appendChild(line)
|
||||||
|
|
||||||
|
iterLogList.forEach((logLine) => {
|
||||||
|
console.log("logline item")
|
||||||
|
console.log(JSON.stringify(logLine,null,2))
|
||||||
|
row = logLine.time + " <strong>" + logLine.event + "</strong>:" + logLine.message;
|
||||||
|
str_row = JSON.stringify(logLine.details, null, 2)
|
||||||
|
var lines = document.getElementById('lines')
|
||||||
|
var line = document.createElement('div')
|
||||||
|
line.classList.add("line")
|
||||||
|
//const newLine = document.createTextNode(row)
|
||||||
|
line.insertAdjacentHTML( 'beforeend', row );
|
||||||
|
//line.appendChild(newLine)
|
||||||
|
var pre = document.createElement("span")
|
||||||
|
pre.classList.add("pidi")
|
||||||
|
const stLine = document.createTextNode(str_row)
|
||||||
|
pre.appendChild(stLine)
|
||||||
|
line.appendChild(pre)
|
||||||
|
lines.appendChild(line)
|
||||||
|
});
|
||||||
|
$('#messages').animate({
|
||||||
|
scrollTop: $('#lines')[0].scrollHeight}, 2000);
|
||||||
|
}
|
||||||
|
|
||||||
|
//limitka
|
||||||
|
if (parsed_data.hasOwnProperty("limitka")) {
|
||||||
|
limitka = parsed_data.limitka
|
||||||
|
const limitkaLine = {
|
||||||
|
price: limitka.price,
|
||||||
|
color: '#1ed473',
|
||||||
|
lineWidth: 1,
|
||||||
|
lineStyle: 1, // LineStyle.Dotted
|
||||||
|
axisLabelVisible: true,
|
||||||
|
title: "SELL:XX",
|
||||||
|
};
|
||||||
|
|
||||||
|
if (limitkaPriceLine !== null) {
|
||||||
|
candlestickSeries.removePriceLine(limitkaPriceLine)
|
||||||
|
}
|
||||||
|
limitkaPriceLine = candlestickSeries.createPriceLine(limitkaLine);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if (parsed_data.hasOwnProperty("pendingbuys")) {
|
||||||
|
pendingbuys = parsed_data.pendingbuys
|
||||||
|
|
||||||
|
//vymazeme vsechny predchozi instance pendingbuys
|
||||||
|
if (pbiList.length) {
|
||||||
|
console.log(pbiList)
|
||||||
|
pbiList.forEach((line) => {
|
||||||
|
candlestickSeries.removePriceLine(line)
|
||||||
|
});
|
||||||
|
pbiList = []
|
||||||
|
}
|
||||||
|
|
||||||
|
//zobrazime pendingbuys a ulozime instance do pole
|
||||||
|
console.log("pred loopem")
|
||||||
|
for (const [orderid, price] of Object.entries(pendingbuys)) {
|
||||||
|
console.log("v loopu", price)
|
||||||
|
const pbLine = {
|
||||||
|
price: parseFloat(price),
|
||||||
|
color: "#e3a059",
|
||||||
|
lineWidth: 1,
|
||||||
|
lineStyle: 1, // LineStyle.Dotted
|
||||||
|
axisLabelVisible: true,
|
||||||
|
title: "BUY:",
|
||||||
|
};
|
||||||
|
|
||||||
|
pbLineInstance = candlestickSeries.createPriceLine(pbLine);
|
||||||
|
pbiList.push(pbLineInstance)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if (parsed_data.hasOwnProperty("positions")) {
|
||||||
|
positions = parsed_data.positions
|
||||||
|
const posLine = {
|
||||||
|
price: positions.avgp,
|
||||||
|
color: 'black',
|
||||||
|
lineWidth: 1,
|
||||||
|
lineStyle: 1, // LineStyle.Dotted
|
||||||
|
axisLabelVisible: true,
|
||||||
|
title: "POS:"+positions.positions,
|
||||||
|
};
|
||||||
|
|
||||||
|
if (positionsPriceLine !== null) {
|
||||||
|
candlestickSeries.removePriceLine(positionsPriceLine)
|
||||||
|
}
|
||||||
|
positionsPriceLine = candlestickSeries.createPriceLine(posLine);
|
||||||
|
}
|
||||||
|
|
||||||
if (parsed_data.hasOwnProperty("indicators")) {
|
if (parsed_data.hasOwnProperty("indicators")) {
|
||||||
var indicators = parsed_data.indicators
|
var indicators = parsed_data.indicators
|
||||||
//if there are indicators it means there must be at least two keys (except time which is always present)
|
//if there are indicators it means there must be at least two keys (except time which is always present)
|
||||||
@ -73,8 +171,9 @@ function connect(event) {
|
|||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
obj.series = chart.addLineSeries({
|
obj.series = chart.addLineSeries({
|
||||||
title: key,
|
//title: key,
|
||||||
lineWidth: 1,
|
lineWidth: 1,
|
||||||
|
lastValueVisible: false
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
obj.series.update({
|
obj.series.update({
|
||||||
@ -95,6 +194,7 @@ function connect(event) {
|
|||||||
console.log(`${key}: ${value}`);
|
console.log(`${key}: ${value}`);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
//chart.timeScale().fitContent();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ws.onclose = function(event) {
|
ws.onclose = function(event) {
|
||||||
|
|||||||
@ -15,6 +15,7 @@
|
|||||||
align-self: auto;
|
align-self: auto;
|
||||||
order: 0;
|
order: 0;
|
||||||
margin-inline-start: 50px;
|
margin-inline-start: 50px;
|
||||||
|
padding-bottom: 10px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.chartContainer {
|
.chartContainer {
|
||||||
@ -30,4 +31,36 @@
|
|||||||
font-size: 16px;
|
font-size: 16px;
|
||||||
line-height: 18px;
|
line-height: 18px;
|
||||||
font-weight: 300;
|
font-weight: 300;
|
||||||
|
}
|
||||||
|
|
||||||
|
#msgContainer {
|
||||||
|
display: grid;
|
||||||
|
overflow: auto;
|
||||||
|
height: 568px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.msgContainerInner {
|
||||||
|
display: flex;
|
||||||
|
overflow: auto;
|
||||||
|
height: 568px;
|
||||||
|
flex-direction: column-reverse;
|
||||||
|
}
|
||||||
|
|
||||||
|
pre {
|
||||||
|
display: block;
|
||||||
|
/* padding: 9.5px; */
|
||||||
|
/* margin: 0 0 10px; */
|
||||||
|
font-size: 10px;
|
||||||
|
/* line-height: 2.428571; */
|
||||||
|
color: #333;
|
||||||
|
word-break: break-all;
|
||||||
|
word-wrap: break-word;
|
||||||
|
/* background-color: #f5f5f5; */
|
||||||
|
/* border: 1px solid #ccc; */
|
||||||
|
border-radius: 4px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pidi {
|
||||||
|
display: block;
|
||||||
|
font-size: smaller;
|
||||||
}
|
}
|
||||||
@ -17,11 +17,13 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
super().__init__(name, symbol, next, init, account, mode, stratvars, open_rush, close_rush, pe, se)
|
super().__init__(name, symbol, next, init, account, mode, stratvars, open_rush, close_rush, pe, se)
|
||||||
|
|
||||||
async def orderUpdateBuy(self, data: TradeUpdate):
|
async def orderUpdateBuy(self, data: TradeUpdate):
|
||||||
|
|
||||||
o: Order = data.order
|
o: Order = data.order
|
||||||
|
self.state.ilog(e="NOT:BUY_NOT_INCOMING", status=o.status, orderid=str(o.id))
|
||||||
if o.status == OrderStatus.FILLED or o.status == OrderStatus.CANCELED:
|
if o.status == OrderStatus.FILLED or o.status == OrderStatus.CANCELED:
|
||||||
|
|
||||||
#pokud existuje objednavka v pendingbuys - vyhodime ji
|
#pokud existuje objednavka v pendingbuys - vyhodime ji
|
||||||
if self.state.vars.pendingbuys.pop(str(o.id), False):
|
if self.state.vars.pendingbuys.pop(str(o.id), False):
|
||||||
|
self.state.ilog(e="NOT:BUY_NOT_DELETE_PB", msg="mazeme z pendingu", orderid=str(o.id), pb=self.state.vars.pendingbuys)
|
||||||
print("limit buy filled or cancelled. Vyhazujeme z pendingbuys.")
|
print("limit buy filled or cancelled. Vyhazujeme z pendingbuys.")
|
||||||
ic(self.state.vars.pendingbuys)
|
ic(self.state.vars.pendingbuys)
|
||||||
|
|
||||||
@ -34,13 +36,20 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
self.state.avgp = float(data.price)
|
self.state.avgp = float(data.price)
|
||||||
price=price2dec(float(o.filled_avg_price)+self.state.vars.profit)
|
price=price2dec(float(o.filled_avg_price)+self.state.vars.profit)
|
||||||
self.state.vars.limitka = await self.interface.sell_l(price=price, size=o.filled_qty)
|
self.state.vars.limitka = await self.interface.sell_l(price=price, size=o.filled_qty)
|
||||||
|
self.state.vars.limitka_price = price
|
||||||
|
self.state.ilog(e="NOT:BUY_NOT_LIMITKA_CREATE", msg="limitka neni vytvarime", orderid=str(o.id), limitka=str(self.state.vars.limitka), limtka_price=self.state.vars.limitka_price)
|
||||||
else:
|
else:
|
||||||
#avgp, pos
|
#avgp, pos
|
||||||
self.state.avgp, self.state.positions = self.state.interface.pos()
|
self.state.avgp, self.state.positions = self.state.interface.pos()
|
||||||
cena = price2dec(float(self.state.avgp) + float(self.state.vars.profit))
|
cena = price2dec(float(self.state.avgp) + float(self.state.vars.profit))
|
||||||
try:
|
try:
|
||||||
|
puvodni = self.state.vars.limitka
|
||||||
self.state.vars.limitka = await self.interface.repl(price=cena,orderid=self.state.vars.limitka,size=int(self.state.positions))
|
self.state.vars.limitka = await self.interface.repl(price=cena,orderid=self.state.vars.limitka,size=int(self.state.positions))
|
||||||
|
self.state.vars.limitka_price = cena
|
||||||
|
self.state.ilog(e="NOT:BUY_NOT_LIMITKA_REPLACE", msg="limitka existuje-replace", orderid=str(o.id), limitka=str(self.state.vars.limitka), limtka_price=self.state.vars.limitka_price, puvodni_limitka=str(puvodni))
|
||||||
except APIError as e:
|
except APIError as e:
|
||||||
|
self.state.ilog(e="NOT:BUY_NOT_LIMITKA_REPLACE_ERROR", msg=str(e), orderid=str(o.id), limitka=str(self.state.vars.limitka), limitka_price=self.state.vars.limitka_price, puvodni_limitka=str(puvodni))
|
||||||
|
|
||||||
#stejne parametry - stava se pri rychle obratce, nevadi
|
#stejne parametry - stava se pri rychle obratce, nevadi
|
||||||
if e.code == 42210000: return 0,0
|
if e.code == 42210000: return 0,0
|
||||||
else:
|
else:
|
||||||
@ -49,6 +58,7 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
|
|
||||||
async def orderUpdateSell(self, data: TradeUpdate):
|
async def orderUpdateSell(self, data: TradeUpdate):
|
||||||
if data.event == TradeEvent.PARTIAL_FILL:
|
if data.event == TradeEvent.PARTIAL_FILL:
|
||||||
|
self.state.ilog(e="NOT:SELL_PARTIAL_FILL", msg="pouze update pozic", orderid=str(data.order.id))
|
||||||
ic("partial fill jen udpatujeme pozice")
|
ic("partial fill jen udpatujeme pozice")
|
||||||
self.state.avgp, self.state.positions = self.interface.pos()
|
self.state.avgp, self.state.positions = self.interface.pos()
|
||||||
elif data.event == TradeEvent.FILL or data.event == TradeEvent.CANCELED:
|
elif data.event == TradeEvent.FILL or data.event == TradeEvent.CANCELED:
|
||||||
@ -60,9 +70,11 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
self.state.avgp, self.state.positions = self.interface.pos()
|
self.state.avgp, self.state.positions = self.interface.pos()
|
||||||
ic(self.state.avgp, self.state.positions)
|
ic(self.state.avgp, self.state.positions)
|
||||||
self.state.vars.limitka = None
|
self.state.vars.limitka = None
|
||||||
|
self.state.vars.limitka_price = None
|
||||||
self.state.vars.lastbuyindex = -5
|
self.state.vars.lastbuyindex = -5
|
||||||
self.state.vars.jevylozeno = 0
|
self.state.vars.jevylozeno = 0
|
||||||
await self.state.cancel_pending_buys()
|
await self.state.cancel_pending_buys()
|
||||||
|
self.state.ilog(e="NOT:SELL_FILL_OR_CANCEL", msg="mazeme limitku a pb", orderid=str(data.order.id), pb=self.state.vars.pendingbuys)
|
||||||
|
|
||||||
#this parent method is called by strategy just once before waiting for first data
|
#this parent method is called by strategy just once before waiting for first data
|
||||||
def strat_init(self):
|
def strat_init(self):
|
||||||
@ -77,6 +89,7 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
def buy(self, size = None, repeat: bool = False):
|
def buy(self, size = None, repeat: bool = False):
|
||||||
print("overriden method to size&check maximum ")
|
print("overriden method to size&check maximum ")
|
||||||
if int(self.state.positions) >= self.state.vars.maxpozic:
|
if int(self.state.positions) >= self.state.vars.maxpozic:
|
||||||
|
self.state.ilog(e="BUY_REQ_MAX_POS_REACHED", msg="Pozadavek na buy, max pozic", curr_positions=self.state.positions)
|
||||||
print("max mnostvi naplneno")
|
print("max mnostvi naplneno")
|
||||||
return 0
|
return 0
|
||||||
if size is None:
|
if size is None:
|
||||||
@ -92,12 +105,13 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
def buy_l(self, price: float = None, size = None, repeat: bool = False):
|
def buy_l(self, price: float = None, size = None, repeat: bool = False):
|
||||||
print("entering overriden BUY")
|
print("entering overriden BUY")
|
||||||
if int(self.state.positions) >= self.state.vars.maxpozic:
|
if int(self.state.positions) >= self.state.vars.maxpozic:
|
||||||
print("max mnostvi naplneno")
|
self.state.ilog(e="BUY_REQ_MAX_POS_REACHED", msg="Pozadavek na buy, max pozic", price=price, size=size, curr_positions=self.state.positions)
|
||||||
return 0
|
return 0
|
||||||
if size is None: size=self.state.vars.chunk
|
if size is None: size=self.state.vars.chunk
|
||||||
if price is None: price=price2dec((self.state.interface.get_last_price(self.symbol)))
|
if price is None: price=price2dec((self.state.interface.get_last_price(self.symbol)))
|
||||||
ic(price)
|
ic(price)
|
||||||
print("odesilame LIMIT s cenou/qty", price, size)
|
print("odesilame LIMIT s cenou/qty", price, size)
|
||||||
|
self.state.ilog(e="BUY_REQ_ORDER_SENDING", msg="Pozadavek na buy, odesilame do if", price=price, size=size)
|
||||||
order = self.state.interface.buy_l(price=price, size=size)
|
order = self.state.interface.buy_l(price=price, size=size)
|
||||||
print("ukladame pendingbuys")
|
print("ukladame pendingbuys")
|
||||||
self.state.vars.pendingbuys[str(order)]=price
|
self.state.vars.pendingbuys[str(order)]=price
|
||||||
@ -105,9 +119,11 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
self.state.vars.lastbuyindex = self.state.bars['index'][-1]
|
self.state.vars.lastbuyindex = self.state.bars['index'][-1]
|
||||||
ic(self.state.blockbuy)
|
ic(self.state.blockbuy)
|
||||||
ic(self.state.vars.lastbuyindex)
|
ic(self.state.vars.lastbuyindex)
|
||||||
|
self.state.ilog(e="BUY_REQ_ORDER_SENT", msg="Uloženo do pb", order=str(order), pb=self.state.vars.pendingbuys)
|
||||||
|
|
||||||
async def cancel_pending_buys(self):
|
async def cancel_pending_buys(self):
|
||||||
print("cancel pending buys called.")
|
print("cancel pending buys called.")
|
||||||
|
self.state.ilog(e="CANCEL_ALL_PB_REQUESTED", pb=self.state.vars.pendingbuys)
|
||||||
##proto v pendingbuys pridano str(), protoze UUIN nejde serializovat
|
##proto v pendingbuys pridano str(), protoze UUIN nejde serializovat
|
||||||
##padalo na variable changed during iteration, pridano
|
##padalo na variable changed during iteration, pridano
|
||||||
if len(self.state.vars.pendingbuys)>0:
|
if len(self.state.vars.pendingbuys)>0:
|
||||||
@ -117,7 +133,9 @@ class StrategyOrderLimitVykladaci(Strategy):
|
|||||||
#nejprve vyhodime z pendingbuys
|
#nejprve vyhodime z pendingbuys
|
||||||
self.state.vars.pendingbuys.pop(key, False)
|
self.state.vars.pendingbuys.pop(key, False)
|
||||||
res = self.interface.cancel(key)
|
res = self.interface.cancel(key)
|
||||||
|
self.state.ilog(e="PB_CANCELLED", orderid=key, res=str(res))
|
||||||
print("CANCEL PENDING BUYS RETURN", res)
|
print("CANCEL PENDING BUYS RETURN", res)
|
||||||
self.state.vars.pendingbuys={}
|
self.state.vars.pendingbuys={}
|
||||||
self.state.vars.jevylozeno = 0
|
self.state.vars.jevylozeno = 0
|
||||||
print("cancel pending buys end")
|
print("cancel pending buys end")
|
||||||
|
self.state.ilog(e="CANCEL_ALL_PB_FINISHED", pb=self.state.vars.pendingbuys)
|
||||||
|
|||||||
Binary file not shown.
Binary file not shown.
@ -251,6 +251,7 @@ class Strategy:
|
|||||||
elif self.pe.is_set():
|
elif self.pe.is_set():
|
||||||
print(current_thread().name, "Paused.")
|
print(current_thread().name, "Paused.")
|
||||||
continue
|
continue
|
||||||
|
#self.state.iter_log(event="INGEST",msg="New data ingested", item=item)
|
||||||
print("New data ingested")
|
print("New data ingested")
|
||||||
#calling main loop
|
#calling main loop
|
||||||
self.strat_loop(item=item)
|
self.strat_loop(item=item)
|
||||||
@ -339,7 +340,25 @@ class Strategy:
|
|||||||
rt_out["indicators"][key]= value[-1]
|
rt_out["indicators"][key]= value[-1]
|
||||||
except IndexError:
|
except IndexError:
|
||||||
pass
|
pass
|
||||||
print(rt_out)
|
|
||||||
|
#vkladame average price and positions, pokud existuji
|
||||||
|
#self.state.avgp , self.state.positions
|
||||||
|
rt_out["positions"] = dict(time=self.state.time, positions=self.state.positions, avgp=self.state.avgp)
|
||||||
|
|
||||||
|
#vkladame limitku a pendingbuys
|
||||||
|
try:
|
||||||
|
rt_out["pendingbuys"] = self.state.vars.pendingbuys
|
||||||
|
rt_out["limitka"] = dict(id=self.state.vars.limitka, price=self.state.vars.limitka_price)
|
||||||
|
|
||||||
|
except Exception as e:
|
||||||
|
print(str(e))
|
||||||
|
pass
|
||||||
|
|
||||||
|
#vkladame iteration log (do toho si muze instance vlozit cokoliv relavantniho pro danou iteraci) a po iteraci se smaze
|
||||||
|
if len(self.state.iter_log_list) > 0:
|
||||||
|
rt_out["iter_log"] = self.state.iter_log_list
|
||||||
|
|
||||||
|
#print(rt_out)
|
||||||
|
|
||||||
print("RTQUEUE INSERT")
|
print("RTQUEUE INSERT")
|
||||||
#send current values to Realtime display on frontend
|
#send current values to Realtime display on frontend
|
||||||
@ -347,6 +366,10 @@ class Strategy:
|
|||||||
self.rtqueue.put(json.dumps(rt_out, default=json_serial))
|
self.rtqueue.put(json.dumps(rt_out, default=json_serial))
|
||||||
print("RTQUEUE", self.rtqueue)
|
print("RTQUEUE", self.rtqueue)
|
||||||
|
|
||||||
|
#cleaning iterlog lsit
|
||||||
|
#TODO pridat cistku i mimo RT blok
|
||||||
|
self.state.iter_log_list = []
|
||||||
|
|
||||||
|
|
||||||
# inicializace poplatna typu strategie (např. u LIMITu dotažení existující limitky)
|
# inicializace poplatna typu strategie (např. u LIMITu dotažení existující limitky)
|
||||||
def strat_init(self):
|
def strat_init(self):
|
||||||
@ -448,4 +471,12 @@ class StrategyState:
|
|||||||
self.buy_l = self.interface.buy_l
|
self.buy_l = self.interface.buy_l
|
||||||
self.sell = self.interface.sell
|
self.sell = self.interface.sell
|
||||||
self.sell_l = self.interface.sell_l
|
self.sell_l = self.interface.sell_l
|
||||||
self.cancel_pending_buys = None
|
self.cancel_pending_buys = None
|
||||||
|
self.iter_log_list = []
|
||||||
|
|
||||||
|
def ilog(self, e: str = None, msg: str = None, **kwargs):
|
||||||
|
if e is None:
|
||||||
|
row = dict(time=self.time, message=msg, details=kwargs)
|
||||||
|
else:
|
||||||
|
row = dict(time=self.time, event=e, message=msg, details=kwargs)
|
||||||
|
self.iter_log_list.append(row)
|
||||||
Reference in New Issue
Block a user