let setsimulations = null;
let storedsimulation = null;
// Initialize the variable with the default template
let templateVariable = template;
// Get the switch element
const switchElement = document.getElementById('flexSwitchColors');
// Add an event listener for the 'change' event
if (switchElement !== null){
switchElement.addEventListener('change', function () {
if (this.checked) {
templateVariable = template2;
} else {
templateVariable = template;
}
console.log('Current template:', templateVariable);
});
}
let page_ccy;
//REFCHECK: Builder for database boards.
function init_currency_dd() {
const d = {"requestId":null,"status":"success","data":{"name":["PLN","CHF","KRW","USD","EUR","GBP","CAD","NOK","AUD","CNY","JPY","NONE","CCY","CLP","CZK"]}};
let ccylist = ['EUR'];
if (d.status == 'success')
ccylist = d.data["name"];
const dd = document.getElementById("simulations_list");
if (dd == null)
return;
while(dd.childNodes.firstChild) dd.childNodes.removeChild(dd.childNodes.lastChild)
let isInitialized = false;
ccylist.forEach(ccy => {
const li = document.createElement("li");
li.appendChild(document.createTextNode(ccy));
li.className = "dropdown-item";
li.addEventListener('click', _ => { onclick_ccy(ccy); });
dd.appendChild(li);
if (!isInitialized){
onclick_ccy(ccy);
isInitialized = true;
}
});
onclick_ccy('EUR');
}
// REFCHECK: called from init_currency_dd.
function onclick_ccy(ccy){
page_ccy = ccy;
const lbl = document.getElementById("sim_dd_label");
if (lbl)
lbl.textContent = page_ccy;
}
// REFCHECK: Builder.
function get_graph_and_tab_for_topic(html_id, topic, asset, topmost, refdate, ccy = page_ccy, topcount = 0, simulation = "", storedsim = "", onclick = null) {
fetch("/regrph", {
method: "POST",
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify({
topic: topic,
asset: asset,
root: topmost,
referencedate: refdate,
currency: ccy,
topcount: topcount,
setsimulation: simulation,
storedsim: storedsim
})
})
.then(r => r.text())
.then(d => {
dj = JSON.parse(d);
dj.plot.layout["template"] = templateVariable;
update_plot_and_table(html_id, dj, onclick)
});
}
// REFCHECK: Builder.
function get_data_for_topic(kpi_id, topic, asset, topmost, refdate, ccy = page_ccy, simulation = "", dict = null) {
fetch("/rerest", {
method: "POST",
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify({
topic: topic,
asset: asset,
root: topmost,
referencedate: refdate,
currency: ccy,
setsimulation: simulation
})
})
.then(r => r.text())
.then(d => {
const dj = JSON.parse(d);
if (dj.status == "success") {
dj["data"].forEach(_ => insert_kpi_values_to_card(kpi_id, _, dict));
}
});
}
// REFCHECK: Builder.
function get_and_insert_table(tableid, requestdata, asset) {
requestdata['setsimulation'] = setsimulations;
requestdata['asset'] = asset;
fetch("/retbll", {
method: 'POST',
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify(requestdata)
})
.then(r => r.text())
.then(d => {
const dj = JSON.parse(d);
const tab = document.getElementById(tableid);
if (tab)
{
tab.replaceChildren();
tab.insertAdjacentHTML("afterbegin", dj.table);
}
}
);
}
// Card drag and drop handlers
// REFCHECK: Builder.
function dragStart(event) {
event.dataTransfer.setData("text", event.target.id);
}
// REFCHECK: Builder.
function dragOver(event) {
event.preventDefault();
}
// REFCHECK: Builder.
function drop(event) {
event.preventDefault();
let droptarget = event.target;
while (droptarget != null) {
if (droptarget.parentNode.classList.contains("card_column_dyn") || droptarget.parentNode.classList.contains("card_row_dyn") || droptarget.parentNode.classList.contains("card-row")) {
droptarget.parentNode.insertBefore(document.getElementById(event.dataTransfer.getData("text")), droptarget);
break;
}
droptarget = droptarget.parentNode;
}
}
//
// Number formatting.
//
// REFCHECK: format_by_symbol.
function scale_million(num) {
if (num === null) {
return null;
}
return ((num / 1e6).toLocaleString("en", {
minimumFractionDigits: 2,
maximumFractionDigits: 2,
useGrouping: true
}) + "m");
}
// REFCHECK: format_by_symbol.
function scale_thousand(num) {
if (num === null) {
return null;
}
return ((num / 1e3).toLocaleString("en", {
minimumFractionDigits: 2,
maximumFractionDigits: 2,
useGrouping: true
}) + "t");
}
// REFCHECK: format_by_symbol.
function as_decimal(num) {
if (num === null) {
return null;
}
return ((num).toLocaleString("en", {
minimumFractionDigits: 2,
maximumFractionDigits: 2,
useGrouping: true
}));
}
// REFCHECK: format_by_symbol.
function as_integer(num) {
if (num === null) {
return null;
}
return ((num).toLocaleString("en", {
minimumFractionDigits: 0,
maximumFractionDigits: 0,
useGrouping: true
}));
}
// REFCHECK: format_by_symbol.
function as_percent(num) {
if (num === null) {
return null;
}
return (num.toLocaleString("en", {
style: "percent",
minimumFractionDigits: 2,
maximumFractionDigits: 2
}));
}
// REFCHECK: format_by_symbol.
function as_isodate(num) {
if (num === null) {
return null;
}
return ((new Date(Date.parse(num))).toLocaleDateString("en-CA"));
}
// REFCHECK: format_by_symbol.
function as_year_month(num) {
if (num === null)
return null;
const asdate = new Date(Date.parse(num));
if (!isNaN(asdate))
return ((asdate).toLocaleDateString("en-CA",
{ year: "numeric", month: "short" }));
return num;
}
// REFCHECK: insert_kpi_values_to_card.
function format_by_symbol(val_fmt, format) {
switch (format) {
case "none":
break;
case "m":
val_fmt = scale_million(val_fmt);
break;
case "t":
val_fmt = scale_thousand(val_fmt);
break;
case "d":
val_fmt = as_decimal(val_fmt);
break;
case "i":
val_fmt = as_integer(val_fmt);
break;
case "%":
val_fmt = as_percent(val_fmt);
break;
case "D":
val_fmt = as_isodate(val_fmt);
break;
case "ym":
val_fmt = as_year_month(val_fmt);
break;
}
return val_fmt;
};
// REFCHECK: Builder.
function request_simulation_quantities(quantities, asset, simulation, storedsimulation)
{
fetch("/rerest", {
method: "POST",
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify({
topic: "single_quant",
quantity: quantities,
asset: asset,
setsimulation: simulation,
storedsim: storedsimulation
})
}).then(r => r.text())
.then(d => {
const dj = JSON.parse(d);
if (dj.status == "success") {
if (simulation != null)
dj["data"].forEach(_ => insert_kpi_values_to_card(_["id"], _));
else
insert_kpi_table_to_cards(dj['data']);
}
})
}
const KPI_SUFFIXES = { quantity: '_value', unit: '_unit', trendvalue: '_trendvalue', trendsymbol: '_trendsym' };
function insert_kpi_table_to_cards(djdata) {
i = 0;
djdata['SGROUP'].forEach(card => {
if (card != null) {
let comp = djdata['COMPONENT'][i];
let parent = document.getElementById(card + KPI_SUFFIXES[comp]);
let q = djdata['DoubleValue'][i];
if (q == null)
q = djdata['DateValue'][i];
if (q == null)
q = djdata['StringValue'][i];
if (q == null)
q = djdata['QuantityName'][i];
if (parent) {
while(parent.firstChild) parent.removeChild(parent.lastChild);
if (q != null)
parent.appendChild(document.createTextNode(format_by_symbol(q, parent.dataset.format)));
}
}
i++;
});
}
// REFCHECK: get_data_for_topic, request_simulation_quantities.
function insert_kpi_values_to_card(kpi_id, kpiresult, dict = null)
{
if (dict == null)
dict = { quantity: 'quantity', unit: 'unit', trendvalue: 'trendvalue', trendsymbol: 'trendsymbol' };
const q = kpiresult[dict["quantity"]];
let parent = document.getElementById(kpi_id + "_value");
if (parent) {
while(parent.firstChild) parent.removeChild(parent.lastChild);
if (q != null) {
parent.appendChild(document.createTextNode(format_by_symbol(q, parent.dataset.format)));
}
else
parent.appendChild(document.createTextNode(format_by_symbol(0, parent.dataset.format)));
}
const ukey = dict["unit"];
const u = kpiresult[ukey];
parent = document.getElementById(kpi_id + "_unit");
if (parent) {
while(parent.firstChild) parent.removeChild(parent.lastChild);
if (u != null) {
parent.insertAdjacentHTML("afterbegin", u);
}
else
if (ukey != undefined && ukey != "unit")
parent.insertAdjacentHTML("afterbegin", ukey);
}
const tv = kpiresult[dict["trendvalue"]];
parent = document.getElementById(kpi_id + "_trendvalue");
if (parent) {
while(parent.firstChild) parent.removeChild(parent.lastChild);
if (tv != null) {
parent.appendChild(document.createTextNode(format_by_symbol(tv, parent.dataset.format)));
}
}
const ts = kpiresult[dict["trendsymbol"]];
parent = document.getElementById(kpi_id + "_trendsym");
if (parent) {
while(parent.firstChild) parent.removeChild(parent.lastChild);
if (ts != null) {
parent.appendChild(document.createTextNode(ts));
}
}
}
//REFCHECK: from get_graph_and_tab_for_topic.
function update_plot_and_table(element_id, plotdef, onclick = null) {
const chart = document.getElementById(`${element_id}_graph`);
const chart_big = document.getElementById(`card_${element_id}_graph_big`);
const chart_tab = document.getElementById(`card_${element_id}_tab`);
if (chart != null) {
if (chart.childNodes.length == 0) {
Plotly.newPlot(chart, plotdef["plot"]);
if (onclick)
chart.on('plotly_click', onclick);
}
else
Plotly.react(chart, plotdef["plot"]);
}
if (chart_big != null) {
if(chart_big.childNodes.length == 0)
Plotly.newPlot(chart_big, plotdef["plot"]);
else
Plotly.react(chart_big, plotdef["plot"]);
}
if (chart_tab) {
chart_tab.replaceChildren();
chart_tab.insertAdjacentHTML("afterbegin", plotdef["table"]);
}
}
//REFCHECK: used in Builder.
function init_asset_tree_search(treefilter = null) {
const content = {
method: 'POST',
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify({ 'topic': 'fulltree', 'topicparameters': treefilter })
};
fetch("/rerest", content)
.then(r => r.text())
.then(d => {
dj = JSON.parse(d);
if (dj.status == "success") {
// Extract the flat list
const flatList = extractFlatUniqueList(dj.data);
populateDatalist(flatList);
// Build the asset tree
build_asset_tree(dj.data);
setTimeout(initializeTreeCollapse, 1000);
}
else {
alert(dj.status + ": " + dj.message);
}
});
}
//REFCHECK: used in init_asset_tree_search.
function extractFlatUniqueList(hierarchy) {
const uniqueItems = new Set();
function addItem(item) {
uniqueItems.add(item.name);
if (item.children && item.children.length > 0) {
item.children.forEach(addItem);
}
}
hierarchy.forEach(addItem);
return Array.from(uniqueItems);
}
//REFCHECK: datalistOptions used in asset search, initialized in Builder.
function populateDatalist(flatList) {
const datalist = document.getElementById('datalistOptions');
if (datalist) {
flatList.forEach(item => {
const option = document.createElement('option');
option.value = item;
datalist.appendChild(option);
});
}
}
// REFCHECK: used in build_asset_tree.
function insert_asset_tree_node(node, parentElement, treenodes) {
let nodeElement = document.createElement('div');
nodeElement.className = 'tree-node';
nodeElement.dataset.node = JSON.stringify(node); // Store the entire node object as JSON
nodeElement.dataset.name = node.name; // Add a separate data attribute for the name
nodeElement.dataset.type = node.type; // Add a data attribute for the type
//node.AssetType = node.type;
let nodeoccurrence = 0;
while (treenodes.has(node.id + "_" + node.type + "_" + nodeoccurrence)) {
nodeoccurrence++;
}
// Create a span for the name to separate it from potential child elements
let nameSpan = document.createElement('span');
nameSpan.className = 'node-name';
nameSpan.textContent = node.name;
nodeElement.appendChild(nameSpan);
nodeElement.addEventListener('click', (event) => {
event.stopPropagation();
document.querySelectorAll('.tree-node').forEach(el => el.classList.remove('selected'));
nodeElement.classList.add('selected');
updateBreadcrumbs();
const pselector = document.getElementById("rlstt")
if (pselector != null) pselector.value = node.name;
switch_tab_visibility(node);
storeLastSelectedObject(node.name);
});
treenodes.set(node.id + "_" + node.type + "_" + nodeoccurrence, nodeElement);
parentElement.appendChild(nodeElement);
}
//REFCHECK: used in init_asset_tree_search.
function build_asset_tree(hierarchy) {
const treenodes = new Map();
const treeContainer = document.getElementById('tree-container');
let parentnode = treeContainer;
let current = hierarchy;
while (current.length > 0) {
let delayed = [];
while (current.length > 0) {
let item = current.shift();
if (item.parent_id == null) {
insert_asset_tree_node(item, treeContainer, treenodes);
continue;
}
let ptrn = new RegExp("^" + item.parent_id + "_(-1|[1-9][0-9]*)");
// hack: wrap into Array.from(...), otherwise firefox throws exception.
if (Array.from(treenodes.keys()).some(k => ptrn.test(k.toString()))) {
for (let pkey of Array.from(treenodes.keys()).filter(k => ptrn.test(k.toString()))) {
parentnode = treenodes.get(pkey);
insert_asset_tree_node(item, parentnode, treenodes);
}
continue;
}
delayed.push(item);
}
current = delayed;
}
treeContainer.firstChild.classList.add('selected');
}
//
// Get list of known simulations.
//
//REFCHECK: Builder for simulations based boards.
function get_simulations_list(portfoliofilter = null) {
d = {"requestId":"Not found","status":"error","message":"Die RealEstimate Oberfl\u00E4che muss ge\u00F6ffnet sein um den transformation-Endpunkt der REST-Api zu verwenden. \u00D6ffne die Oberfl\u00E4che mit dem Kommandozeilenparameter: SimulationsEndpoint"};
if (d.status == "success")
update_simulations_dd(d.data, portfoliofilter);
}
// REFCHECK: used in get_simulations_list.
function update_simulations_dd(simlist, portfoliofilter = null) {
const sims = document.getElementById("simulations_list");
if (sims == null)
return;
let isSimInitialized = false;
let isFirst = true;
while(sims.childNodes.firstChild) sims.childNodes.removeChild(sims.childNodes.lastChild)
simlist.forEach(sim => {
if (portfoliofilter == null || (portfoliofilter != null && sim.name && sim.name.startsWith(portfoliofilter))) {
const li = document.createElement("li");
li.appendChild(document.createTextNode(sim.tree.Name + " - " + sim.ccy + " - " + sim.refdate.substring(0, 10)));
li.className = "dropdown-item";
li.addEventListener('click', _ => {
onclick_simlist(sim);
});
sims.appendChild(li);
if (isFirst)
onclick_simlist(sim, false)
}
});
}
// REFCHECK: used in update_simulations_dd. Called there with doUpdate=false for first simulation.
function onclick_simlist(sim, doUpdate = true) {
const refdate = document.getElementById("refdate");
if (refdate)
refdate.value = sim.refdate.substring(0, 10);
setsimulations = sim.name;
const lbl = document.getElementById("sim_dd_label");
if (lbl)
lbl.textContent = sim.ccy;
if (doUpdate) update_asset_tree();
}
//
// Stored simulations.
//
function get_stored_simulations_list(portfoliofilter = null) {
d = {"requestId":null,"status":"success","data":[{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"049E7399620A39F037D6530070D34B9E"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"0733C29EBCCDA187BDB100C63B21B074"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"0B09330DD1BF569985519B5A7BCD8BA6"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"0C1D954B3FF61AC779A4CE9DBA8C8F26"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"0F1D4BF2353A7BDE449219A73F2EDF20"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"1768BE6955DBEF75C53B01851E947B5B"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"177AF213AA1E7819A3169E3EF3A4F48F"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"28A711C7447AB794DAFCA8AFB5646074"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"2D16BBFA34848D5250DDFF85AEF970CA"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"32C45774DF9AB6202A921D73B53C8B65"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"32EDA67616FBBFA31D699CDFFE8F62D9"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"3BBC9AE51F81396C87A059B2BA13B676"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"482B9E37EE82D1D539C23E7102FAFFED"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"48A775933C36D0961D7B5B0BB3D5805F"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"4A28CBB10A51AE73345195A112D1BDFA"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"55C685824DB77D79E601206D78CA623B"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"5A7ABD2088A6373E0461F93B2DB62D60"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"5E9028A20FF1240BC96031B40BF93FB7"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"5FBE4354D3555BE38189132A8953A36A"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"67A7E2FF6413BE180D4237CC886F54E5"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"67F2A885BFD48D99674E3F91EA9D4484"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"684A7A247339CD66BA3BC5A40500B8FD"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"68DDF4679A72B029EFCCF370418C833C"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"6F56E01B0049B911381E9F6F078D1D41"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"71B5D79F37F490306ED110C01F06CBA7"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"72E4A670FCFBEAD1D8E4CA9C85517BC0"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"7485BDC93CD92CC499F55F6D26FA4FA3"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"846560FE7091991BCEF5CD15134C5C58"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"84F805B3E491E2E7710D414432B77913"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"88F34E9EF5167C0F177F784DA721E17F"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"8A78FD8FEEF619AE2F00E6726A9AE3B0"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"927E662FD8C49B8931D4E9947CC588D8"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"95B54A45094D212A062AF8CE8C7A659B"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"9D7AFA6576D70D027442C822BBBF6357"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"9F5DF80EF4670E13FDF9105B2C3C1416"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"AFDD34098712CE6CCD872E6FAC91996B"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"BCF05ACC4928D4B7527F8B65CEC96DCB"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"C4B6DEE793044B11720A4DC42269356B"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"CBB3423678678FBF66DD3AF4B6332E73"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"DA92C3BABD75551F145EFACB857FFABB"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"DCF1BBB9BA4B0903E0D09F259301A2A3"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"E656E8E7120A663F0AB4BFCFFAACBE60"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"F203B79818744DF9C063A1317607A920"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"FB3A36DFB53C3EFDEF777C14D7AC0C97"},{"Portfolio":"","Currency":"","ReferenceDate":"1900-01-01T00:00:00.0000000","Info":"","Nsim":0,"ProductVersion":"","SqlInstance":"","Database":"","Schema":"","CreationTime":"1900-01-01T00:00:00.0000000","Hash":"FDC397E7F7C0238F1D0079849589D56B"}]};
if (d.status == "success")
update_stored_simulations_dd(d.data, portfoliofilter);
}
function update_stored_simulations_dd(simlist, portfoliofilter = null) {
const sims = document.getElementById("simulations_list");
if (sims == null)
return;
let isSimInitialized = false;
let isFirst = true;
while(sims.childNodes.firstChild) sims.childNodes.removeChild(sims.childNodes.lastChild)
//// FIX INITIALIZATION ISSUE!!!
//simlist.forEach(sim => {
// if (portfoliofilter == null || (portfoliofilter != null && sim.Portfolio && sim.Portfolio.startsWith(portfoliofilter))) {
// if (sim.Hash.startsWith('34D84')) {
// isFirst = false;
// }
// }
//});
simlist.forEach(sim => {
if (portfoliofilter == null || (portfoliofilter != null && sim.Portfolio && sim.Portfolio.startsWith(portfoliofilter))) {
const li = document.createElement("li");
li.appendChild(document.createTextNode(sim.Portfolio + " - " + sim.ReferenceDate.substring(0, 10) + " - " + sim.Currency + " - " + sim.Hash.substring(0,5) + " - " + sim.Info));
li.title = sim.Hash.substring(0,5) + " - " + sim.Info + " - " + sim.Currency + " - " + sim.Portfolio + " - " + sim.ReferenceDate.substring(0, 10);
li.className = "dropdown-item";
li.addEventListener('click', _ => {
onclick_simlist_stored(sim);
_.target.classList.add('selected');
});
sims.appendChild(li);
if (isFirst) {
onclick_simlist_stored(sim, false);
li.classList.add('selected');
}
//if (sim.Hash.startsWith('34D84')) {
// onclick_simlist_stored(sim, false);
// li.classList.add('selected');
//}
}
});
}
function onclick_simlist_stored(sim, doUpdate = true) {
const sims = document.getElementById("simulations_list");
if (sims) sims.childNodes.forEach(el => el.classList.remove('selected'));
const refdate = document.getElementById("refdate");
if (refdate)
refdate.value = sim.ReferenceDate.substring(0, 10);
storedsimulation = sim.Hash;
const lbl = document.getElementById("sim_dd_label");
if (lbl)
lbl.textContent = sim.Currency;
if (doUpdate) update_asset_tree_stored();
}
function update_asset_tree_stored() {
var topic = "stored_simulation_tree";
fetch("/rerest", {
method: "POST",
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify({
topic: topic,
storedsim: storedsimulation
})
}).then(r => r.text())
.then(d => {
const dj = JSON.parse(d);
if (dj.status == "success") {
var treeContainer = document.getElementById('tree-container');
if (treeContainer) {
while(treeContainer.firstChild) treeContainer.removeChild(treeContainer.lastChild);
var flatList = extractFlatUniqueList(dj.data);
populateDatalist(flatList);
build_asset_tree(dj.data);
setTimeout(initializeTreeCollapse, 1000);
}
}
});
}
//
// Tree from simulation file
//
// REFCHECK: used in onclick_simlist and in Builder.
function update_asset_tree() {
var topic = "simulation_tree";
fetch("/rerest", {
method: "POST",
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` },
body: JSON.stringify({
topic: topic,
setsimulation: setsimulations
})
}).then(r => r.text())
.then(d => {
const dj = JSON.parse(d);
if (dj.status == "success") {
var treeContainer = document.getElementById('tree-container');
if (treeContainer) {
while(treeContainer.firstChild) treeContainer.removeChild(treeContainer.lastChild);
createTreeNode(dj.data, treeContainer);
var flatList = extractFlatUniqueList(dj.data.SubAssets);
populateDatalist(flatList);
setTimeout(initializeTreeCollapse, 1000);
}
}
});
}
//REFCHECK: used in update_asset_tree. called recursively.
function createTreeNode(node, parentElement) {
const nodeElement = document.createElement('div');
nodeElement.className = 'tree-node';
nodeElement.textContent = node.Name;
nodeElement.dataset.node = node;
nodeElement.dataset.name = node.Name; // Add a separate data attribute for the name
node.name = node.Name;
nodeElement.addEventListener('click', (event) => {
event.stopPropagation();
document.querySelectorAll('.tree-node').forEach(el => el.classList.remove('selected'));
nodeElement.classList.add('selected');
updateForSelectedAsset(node);
storeLastSelectedObject(node.name);
});
parentElement.appendChild(nodeElement);
if (node.SubAssets && node.SubAssets.length > 0) {
node.SubAssets.forEach(childNode => {
createTreeNode(childNode, nodeElement);
});
}
}
// REFCHECK: used in click handler in createTreeNode.
function updateForSelectedAsset(node) {
const sel = document.getElementById('selected-node');
if (sel)
sel.textContent = node.Name;
updateBreadcrumbs();
switch_tab_visibility(node);
//if (node.AssetType == 'Immobilie' || node.AssetType == 'RealEstate')
// refresh_dashboard_realestate(node);
//else
// refresh_dashboard_portfolio(node);
const pselector = document.getElementById("rlstt");
if (pselector)
pselector.value = node.Name;
}
//REFCHECK: init_asset_tree_search and update_asset_tree.
// tree view in left navigation
function initializeTreeCollapse() {
const treeContainer = document.getElementById('tree-container');
if (!treeContainer) {
console.error('Tree container not found');
return;
}
const lastSelected = getLastSelectedObject();
// Add collapse icons to all nodes that have children
const nodes = treeContainer.querySelectorAll('.tree-node');
let nodeToClick = null;
let firstnode = null;
nodes.forEach(node => {
if (firstnode == null)
firstnode = node;
if (node.dataset.name == lastSelected)
nodeToClick = node;
if (node.querySelector('.tree-node')) {
//if (isFirst) { node.click(); isFirst = false; }
const icon = document.createElement('span');
icon.className = 'collapse-icon';
icon.addEventListener('click', function (event) {
event.stopPropagation(); // Prevent the click from bubbling up
toggleNode(node);
});
node.insertBefore(icon, node.firstChild);
}
});
function toggleNode(node) {
node.classList.toggle('collapsed');
}
// Initially collapse all nodes, including root nodes
nodes.forEach(node => {
if (node.querySelector('.tree-node')) {
if (node.dataset['name'] != lastSelected)
node.classList.add('collapsed');
}
});
if (nodeToClick != null) {
let prnt = nodeToClick.parentNode;
while (prnt != null && prnt != treeContainer) {
prnt.classList.toggle('collapsed');
prnt = prnt.parentNode;
}
nodeToClick.click();
}
else
firstnode.click();
console.log('Tree collapse/expand functionality initialized');
}
//
// Breadcrumbs
//
// REFCHECK: used in updateBreadcrumbs.
function generateBreadcrumbs() {
const selectedNode = document.querySelector('.tree-node.selected');
if (!selectedNode) return '';
const breadcrumbs = [];
let currentNode = selectedNode;
// Add the selected node's text
breadcrumbs.unshift(currentNode.dataset.name);
// Find the parent nodes
while (currentNode.parentElement) {
currentNode = currentNode.parentElement.closest('.tree-node');
if (currentNode) {
breadcrumbs.unshift(currentNode.dataset.name);
} else {
break; // Exit if we've reached the top level
}
}
// Generate HTML structure
const breadcrumbsHTML = breadcrumbs.map((crumb, index) => {
if (index === breadcrumbs.length - 1) {
// Last element
return `${crumb}`;
} else {
// Other elements
return `${crumb}`;
}
}).join(' / ');
return breadcrumbsHTML;
}
// REFCHECK: used in insert_asset_tree_node and updateForSelectedAsset (click handlers).
function updateBreadcrumbs() {
const breadcrumbsContainer = document.getElementById('breadcrumbs');
if (!breadcrumbsContainer) {
console.error('Breadcrumbs container not found');
return;
}
const breadcrumbHTML = generateBreadcrumbs();
breadcrumbsContainer.innerHTML = breadcrumbHTML || 'Select Asset';
if (breadcrumbsContainer.childNodes.length > 1) {
breadcrumbsContainer.childNodes.forEach(add_onclick_on_breadcrumb);
}
}
//REFCHECK: used in updateBreadcrumbs.
function add_onclick_on_breadcrumb(nodeElement) {
if (nodeElement.classList.contains('breadcrumb-item')) {
nodeElement.addEventListener('click', function () {
onSelectOption(this.dataset.name);
});
}
}
// REFCHECK: used in onSelectOption.
function expandParents(node) {
let currentNode = node;
while (currentNode && currentNode !== document) {
if (currentNode.classList.contains('tree-node')) {
currentNode.classList.remove('collapsed');
}
currentNode = currentNode.parentElement;
}
}
function onSelectOption(selectedValue) {
console.log('Selected value:', selectedValue);
const matchingNode = document.querySelector(`#tree-container .tree-node[data-name="${selectedValue}"]`);
if (matchingNode) {
expandParents(matchingNode);
matchingNode.scrollIntoView({ behavior: 'smooth', block: 'center' });
matchingNode.click();
}
}
function map_onClick(data) {
onSelectOption(data.points[0].text)
}
//
// Selected object storage for page switch.
//
function storeLastSelectedObject(objectname) {
sessionStorage.setItem('lastSelectedObjectName', objectname);
}
function getLastSelectedObject() {
return sessionStorage.getItem('lastSelectedObjectName');
}
//
// Selected date storage for page switch.
//
function storeLastSelectedDate(date) {
sessionStorage.setItem('lastSelectedDate', date);
}
function onBlurRefDate(eventdata) {
storeLastSelectedDate(eventdata.srcElement.value);
}
function getLastSelectedDate() {
return sessionStorage.getItem('lastSelectedDate');
}
function loadLastSelectedRefDate() {
const refdate = document.getElementById("refdate");
if (refdate) {
const storedDate = sessionStorage.getItem('lastSelectedDate');
if (storedDate)
refdate.value = storedDate;
}
}
document.addEventListener('DOMContentLoaded', () => {
const input = document.getElementById('rlstt');
if (input) {
// Listen for input changes
input.addEventListener('input', function () {
onSelectOption(this.value);
});
// Optional: Listen for the datalist option selection
input.addEventListener('select', function () {
onSelectOption(this.value);
});
}
});