191 lines
No EOL
7.7 KiB
TypeScript
191 lines
No EOL
7.7 KiB
TypeScript
import {ServerConnectionInfo, ServerEntry} from "../../tree/Server";
|
|
import {createModal, Modal} from "../../ui/elements/Modal";
|
|
import {CommandResult} from "../../connection/ServerConnectionDeclaration";
|
|
import {Graph} from "../../ui/elements/NetGraph";
|
|
import * as tooltip from "../../ui/elements/Tooltip";
|
|
import {network} from "../../ui/frames/chat";
|
|
import {ErrorCode} from "../../connection/ErrorCode";
|
|
import { tr } from "tc-shared/i18n/localize";
|
|
|
|
export enum RequestInfoStatus {
|
|
SUCCESS,
|
|
UNKNOWN,
|
|
NO_PERMISSION
|
|
}
|
|
export type ServerBandwidthInfoUpdateCallback = (status: RequestInfoStatus, info?: ServerConnectionInfo) => any;
|
|
export function openServerInfoBandwidth(server: ServerEntry, update_callbacks?: ServerBandwidthInfoUpdateCallback[]) : Modal {
|
|
let modal: Modal;
|
|
let own_callbacks = !update_callbacks;
|
|
update_callbacks = update_callbacks || [];
|
|
|
|
modal = createModal({
|
|
header: tr("Server bandwidth data"),
|
|
body: () => {
|
|
const template = $("#tmpl_server_info_bandwidth").renderTag();
|
|
|
|
const children = template.children();
|
|
initialize_current_bandwidth(modal, children.find(".statistic-bandwidth"), update_callbacks);
|
|
initialize_ft_bandwidth(modal, children.find(".statistic-ft-bandwidth"), update_callbacks);
|
|
initialize_general(template.find(".top"), update_callbacks);
|
|
|
|
tooltip.initialize(template);
|
|
return template.children();
|
|
},
|
|
footer: null,
|
|
min_width: "25em"
|
|
});
|
|
|
|
if(own_callbacks) {
|
|
const updater = setInterval(() => {
|
|
server.request_connection_info().then(info => update_callbacks.forEach(e => e(RequestInfoStatus.SUCCESS, info))).catch(error => {
|
|
if(error instanceof CommandResult && error.id == ErrorCode.SERVER_INSUFFICIENT_PERMISSIONS) {
|
|
update_callbacks.forEach(e => e(RequestInfoStatus.NO_PERMISSION));
|
|
return;
|
|
}
|
|
update_callbacks.forEach(e => e(RequestInfoStatus.UNKNOWN));
|
|
});
|
|
}, 1000);
|
|
modal.close_listener.push(() => clearInterval(updater));
|
|
}
|
|
|
|
|
|
modal.htmlTag.find(".button-close").on('click', event => modal.close());
|
|
modal.htmlTag.find(".modal-body").addClass("modal-server-info-bandwidth");
|
|
modal.open();
|
|
return modal;
|
|
}
|
|
|
|
function initialize_graph(modal: Modal, tag: JQuery, callbacks: ServerBandwidthInfoUpdateCallback[], fields: {uplaod: string, download: string}) {
|
|
const canvas = tag.find("canvas")[0] as HTMLCanvasElement;
|
|
const label_upload = tag.find(".upload");
|
|
const label_download = tag.find(".download");
|
|
let last_info: { status: RequestInfoStatus, info: ServerConnectionInfo };
|
|
let custom_info = false;
|
|
|
|
const show_info = (upload: number | undefined, download: number | undefined) => {
|
|
let fallback_text = last_info && last_info.status === RequestInfoStatus.NO_PERMISSION ? tr("No permission") : tr("receiving...");
|
|
|
|
if(typeof upload !== "number")
|
|
upload = last_info ? last_info[fields.uplaod] : undefined;
|
|
|
|
if(typeof download !== "number")
|
|
download = last_info ? last_info[fields.download] : undefined;
|
|
|
|
if(typeof upload !== "number")
|
|
label_upload.text(fallback_text);
|
|
else
|
|
label_upload.text(network.format_bytes(upload, {unit: "Bytes", time: "s", exact: false}));
|
|
|
|
if(typeof download !== "number")
|
|
label_download.text(fallback_text);
|
|
else
|
|
label_download.text(network.format_bytes(download, {unit: "Bytes", time: "s", exact: false}));
|
|
};
|
|
show_info(undefined, undefined);
|
|
|
|
const graph = new Graph(canvas);
|
|
graph.insert_entry({ timestamp: Date.now(), upload: undefined, download: undefined});
|
|
callbacks.push((status, values) => {
|
|
last_info = {status: status, info: values};
|
|
|
|
if(!values) {
|
|
graph.insert_entry({ timestamp: Date.now(), upload: undefined, download: undefined});
|
|
} else {
|
|
graph.insert_entry({
|
|
timestamp: Date.now(),
|
|
download: values[fields.download], //values.connection_bandwidth_received_last_second_total,
|
|
upload: values[fields.uplaod], //values.connection_bandwidth_sent_last_second_total
|
|
});
|
|
}
|
|
|
|
/* set set that we want to show the entry within one second */
|
|
graph._time_span.origin = Object.assign(graph.calculate_time_span(), { time: Date.now() });
|
|
graph._time_span.target = {
|
|
begin: Date.now() - 120 * 1000,
|
|
end: Date.now(),
|
|
time: Date.now() + 200
|
|
};
|
|
|
|
graph.cleanup();
|
|
if(!custom_info) {
|
|
show_info(undefined, undefined);
|
|
graph.resize(); /* just to ensure (we have to rethink this maybe; cause it causes a recalculates the style */
|
|
}
|
|
});
|
|
|
|
graph.max_gap_size(0);
|
|
graph.initialize();
|
|
|
|
graph.callback_detailed_hide = () => {
|
|
custom_info = false;
|
|
show_info(undefined, undefined);
|
|
};
|
|
|
|
graph.callback_detailed_info = (upload, download, timestamp, event) => {
|
|
custom_info = true;
|
|
show_info(upload, download);
|
|
};
|
|
|
|
modal.close_listener.push(() => graph.terminate());
|
|
modal.open_listener.push(() => graph.resize());
|
|
|
|
tag.addClass("window-resize-listener").on('resize', event => graph.resize());
|
|
}
|
|
|
|
function initialize_current_bandwidth(modal: Modal, tag: JQuery, callbacks: ServerBandwidthInfoUpdateCallback[]) {
|
|
initialize_graph(modal, tag, callbacks, {
|
|
uplaod: "connection_bandwidth_sent_last_second_total",
|
|
download: "connection_bandwidth_received_last_second_total"
|
|
});
|
|
}
|
|
|
|
function initialize_ft_bandwidth(modal: Modal, tag: JQuery, callbacks: ServerBandwidthInfoUpdateCallback[]) {
|
|
initialize_graph(modal, tag, callbacks, {
|
|
uplaod: "connection_filetransfer_bandwidth_sent",
|
|
download: "connection_filetransfer_bandwidth_received"
|
|
});
|
|
}
|
|
|
|
function initialize_general(tag: JQuery, callbacks: ServerBandwidthInfoUpdateCallback[]) {
|
|
const tag_packets_upload = tag.find(".statistic-packets .upload");
|
|
const tag_packets_download = tag.find(".statistic-packets .download");
|
|
|
|
const tag_bytes_upload = tag.find(".statistic-bytes .upload");
|
|
const tag_bytes_download = tag.find(".statistic-bytes .download");
|
|
|
|
const tag_ft_bytes_upload = tag.find(".statistic-ft-bytes .upload");
|
|
const tag_ft_bytes_download = tag.find(".statistic-ft-bytes .download");
|
|
|
|
const update = (tag, value: undefined | null | number) => {
|
|
if(typeof value === "undefined")
|
|
tag.text(tr("receiving..."));
|
|
else if(value === null)
|
|
tag.text(tr("no permissions"));
|
|
else
|
|
tag.text(network.format_bytes(value, {unit: "Bytes", exact: false}));
|
|
};
|
|
|
|
const props = [
|
|
{tag: tag_packets_download, property: "connection_packets_received_total"},
|
|
{tag: tag_packets_upload, property: "connection_packets_sent_total"},
|
|
|
|
{tag: tag_bytes_download, property: "connection_bytes_received_total"},
|
|
{tag: tag_bytes_upload, property: "connection_bytes_sent_total"},
|
|
|
|
{tag: tag_ft_bytes_upload, property: "connection_filetransfer_bytes_received_total"},
|
|
{tag: tag_ft_bytes_download, property: "connection_filetransfer_bytes_sent_total"},
|
|
];
|
|
|
|
callbacks.push((status, info) => {
|
|
if(status === RequestInfoStatus.SUCCESS) {
|
|
for(const entry of props)
|
|
update(entry.tag, info[entry.property]);
|
|
} else if(status === RequestInfoStatus.NO_PERMISSION) {
|
|
for(const entry of props)
|
|
update(entry.tag, null);
|
|
} else {
|
|
for(const entry of props)
|
|
update(entry.tag, undefined);
|
|
}
|
|
});
|
|
} |