//
// This 'server' variable we use to contact the Admin/Monitor backend is
// constructed in this example pretty much as we do in all the demos, so
// refer to the guidelines there with respect to absolute vs. relative
// paths and the like.
//
var server = null;
if (window.location.protocol === "http:")
server = "http://" + window.location.hostname + ":7088/admin";
else server = "https://" + window.location.hostname + ":7889/admin";
// If you don't want the page to prompt you for a password, insert it here
var secret = "janusoverlord";
var session = null; // Selected session
var handle = null; // Selected handle
var plugins = [],
pluginsIndex = [],
pluginRows = 0;
var transports = [],
transportsIndex = [],
transportRows = 0;
var settings = {};
var currentHandle = null;
var localSdp = null,
remoteSdp = null;
var handleInfo;
$(document).ready(function () {
$("#admintabs a").click(function (e) {
e.preventDefault();
$(this).tab("show");
});
if (!server) server = "";
if (!secret) secret = "";
if (server !== "" && secret !== "") {
updateServerInfo();
} else {
promptAccessDetails();
}
});
var prompting = false;
var alerted = false;
function promptAccessDetails() {
if (prompting) return;
prompting = true;
let serverPlaceholder = "Insert the address of the Admin API backend";
let secretPlaceholder = "Insert the Admin API secret";
bootbox.alert({
message:
"
" +
" " +
" " +
"
" +
"
" +
" " +
" " +
"
",
closeButton: false,
callback: function () {
prompting = false;
server = $("#server").val();
secret = $("#secret").val();
updateServerInfo();
},
});
}
// Helper method to create random identifiers (e.g., transaction)
function randomString(len) {
const charSet =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
let randomString = "";
for (let i = 0; i < len; i++) {
let randomPoz = Math.floor(Math.random() * charSet.length);
randomString += charSet.substring(randomPoz, randomPoz + 1);
}
return randomString;
}
// Server info
function updateServerInfo() {
plugins = [];
pluginsIndex = [];
transports = [];
transportsIndex = [];
$.ajax({
type: "GET",
url: server + "/info",
cache: false,
contentType: "application/json",
success: function (json) {
if (json["janus"] !== "server_info") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(json["error"].reason, function () {
promptAccessDetails();
alerted = false;
});
}
return;
}
console.log("Got server info:");
console.log(json);
let pluginsJson = json.plugins;
let transportsJson = json.transports;
let eventsJson = json.events;
let loggersJson = json.loggers;
delete json.janus;
delete json.transaction;
delete json.plugins;
delete json.transports;
delete json.events;
delete json.loggers;
$("#server-details").empty();
for (let k in json) {
if (k === "dependencies") {
$("#server-deps").html(
"
" + "
Library
" + "
Version
" + "
"
);
for (let ln in json[k]) {
$("#server-deps").append(
"
" +
"
" +
ln +
"
" +
"
" +
json[k][ln] +
"
" +
"
"
);
}
continue;
}
let v = json[k];
$("#server-details").append(
"
" + "
" + k + ":
" + "
" + v + "
" + "
"
);
}
$("#server-plugins").html(
"
" +
"
Name
" +
"
Author
" +
"
Description
" +
"
Version
" +
"
"
);
$("#plugins-list").empty();
for (let p in pluginsJson) {
plugins.push(p);
let v = pluginsJson[p];
$("#server-plugins").append(
"
"
);
for (let t in transportsJson) {
transports.push(t);
let v = transportsJson[t];
$("#server-transports").append(
"
" +
"
" +
v.name +
"
" +
"
" +
v.author +
"
" +
"
" +
v.description +
"
" +
"
" +
v.version_string +
"
" +
"
"
);
transportsIndex.push(t);
$("#transports-list").append(
'' +
"" +
t +
"" +
""
);
$("#transport-" + (transportsIndex.length - 1)).click(function (event) {
event.preventDefault();
let ti = parseInt($(this).attr("id").split("transport-")[1]);
let transport = transportsIndex[ti];
console.log("Selected transport:", transport);
$("#transports-list a").removeClass("active");
$("#transport-" + ti).addClass("active");
resetTransportRequest();
});
}
$("#server-handlers").html(
"
" +
"
Name
" +
"
Author
" +
"
Description
" +
"
Version
" +
"
"
);
for (let e in eventsJson) {
let v = eventsJson[e];
$("#server-handlers").append(
"
" +
"
" +
v.name +
"
" +
"
" +
v.author +
"
" +
"
" +
v.description +
"
" +
"
" +
v.version_string +
"
" +
"
"
);
}
$("#server-loggers").html(
"
" +
"
Name
" +
"
Author
" +
"
Description
" +
"
Version
" +
"
"
);
for (let e in loggersJson) {
let v = loggersJson[e];
$("#server-loggers").append(
"
" +
"
" +
v.name +
"
" +
"
" +
v.author +
"
" +
"
" +
v.description +
"
" +
"
" +
v.version_string +
"
" +
"
"
);
}
// Unlock tabs
$("#admintabs li a").removeClass("disabled");
// Refresh settings now
updateSettings();
// Refresh sessions and handles now
$("#handles").addClass("hide");
$("#info").addClass("hide");
$("#update-sessions").click(updateSessions);
$("#update-handles").click(updateHandles);
$("#update-handle").click(updateHandleInfo);
updateSessions();
$("#autorefresh").change(function () {
if (this.checked) {
updateHandleInfo(true);
}
});
$("#prettify").change(function () {
if (this.checked) {
prettyHandleInfo();
} else {
rawHandleInfo();
}
});
$("#capture").change(function () {
if (this.checked) {
// We're trying to start a new capture, show a dialog
$("#capturetext").html("Stop capture");
captureTrafficPrompt();
} else {
// We're trying to stop a capture
$("#capturetext").html("Start capture");
captureTrafficRequest(
false,
handleInfo["dump-to-text2pcap"] === true
);
}
});
// Only check tokens if the mechanism is enabled
if (!json["auth_token"]) {
$("a[href='#tokens']").addClass("disabled");
$("a[href='#tokens']")
.attr("href", "#")
.unbind("click")
.click(function (e) {
e.preventDefault();
return false;
});
} else {
updateTokens();
}
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
// Settings
function updateSettings() {
$("#update-settings").unbind("click").addClass("fa-spin");
let request = {
janus: "get_status",
transaction: randomString(12),
admin_secret: secret,
};
$.ajax({
type: "POST",
url: server,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
setTimeout(function () {
$("#update-settings").removeClass("fa-spin").click(updateSettings);
}, 1000);
return;
}
console.log("Got status:");
console.log(json);
setTimeout(function () {
$("#update-settings").removeClass("fa-spin").click(updateSettings);
}, 1000);
$("#server-settings").empty();
for (let k in json.status) {
settings[k] = json.status[k];
$("#server-settings").append(
"
" +
"
" +
k +
":
" +
"
" +
settings[k] +
"
" +
'
' +
"
"
);
if (k === "session_timeout") {
$("#" + k).append(
''
);
$("#" + k + "_button").click(function () {
bootbox.prompt(
"Set the new session timeout value (in seconds, currently " +
settings["session_timeout"] +
")",
function (result) {
if (isNaN(result)) {
bootbox.alert("Invalid session timeout value");
return;
}
result = parseInt(result);
if (result < 0) {
console.log(isNaN(result));
console.log(result < 0);
bootbox.alert("Invalid session timeout value");
return;
}
setSessionTimeoutValue(result);
}
);
});
} else if (k === "log_level") {
$("#" + k).append(
''
);
$("#" + k + "_button").click(function () {
bootbox.prompt(
"Set the new desired log level (0-7, currently " +
settings["log_level"] +
")",
function (result) {
if (isNaN(result)) {
bootbox.alert("Invalid log level (should be [0,7])");
return;
}
result = parseInt(result);
if (result < 0 || result > 7) {
console.log(isNaN(result));
console.log(result < 0);
console.log(result > 7);
bootbox.alert("Invalid log level (should be [0,7])");
return;
}
setLogLevel(result);
}
);
});
} else if (k === "min_nack_queue") {
$("#" + k).append(
''
);
$("#" + k + "_button").click(function () {
bootbox.prompt(
"Set the new desired min NACK queue (a positive integer, currently " +
settings["min_nack_queue"] +
")",
function (result) {
if (isNaN(result)) {
bootbox.alert(
"Invalid min NACK queue (should be a positive integer)"
);
return;
}
result = parseInt(result);
if (result < 0) {
bootbox.alert(
"Invalid min NACK queue (should be a positive integer)"
);
return;
}
setMinNackQueue(result);
}
);
});
} else if (k === "no_media_timer") {
$("#" + k).append(
''
);
$("#" + k + "_button").click(function () {
bootbox.prompt(
"Set the new desired no-media timer value (in seconds, currently " +
settings["no_media_timer"] +
")",
function (result) {
if (isNaN(result)) {
bootbox.alert(
"Invalid no-media timer (should be a positive integer)"
);
return;
}
result = parseInt(result);
if (result < 0) {
bootbox.alert(
"Invalid no-media timer (should be a positive integer)"
);
return;
}
setNoMediaTimer(result);
}
);
});
} else if (k === "slowlink_threshold") {
$("#" + k).append(
''
);
$("#" + k + "_button").click(function () {
bootbox.prompt(
"Set the new desired slowlink-threshold value (in lost packets per seconds, currently " +
settings["slowlink_threshold"] +
")",
function (result) {
if (isNaN(result)) {
bootbox.alert(
"Invalid slowlink-threshold timer (should be a positive integer)"
);
return;
}
result = parseInt(result);
if (result < 0) {
bootbox.alert(
"Invalid slowlink-threshold timer (should be a positive integer)"
);
return;
}
setSlowlinkThreshold(result);
}
);
});
} else if (k === "locking_debug") {
$("#" + k).append(
''
);
$("#" + k + "_button")
.addClass(!settings[k] ? "btn-success" : "btn-danger")
.html(
!settings[k] ? "Enable locking debug" : "Disable locking debug"
);
$("#" + k + "_button").click(function () {
let text = !settings["locking_debug"]
? "Are you sure you want to enable the locking debug? This will print a line on the console any time a mutex is locked/unlocked"
: "Are you sure you want to disable the locking debug?";
bootbox.confirm(text, function (result) {
if (result) setLockingDebug(!settings["locking_debug"]);
});
});
} else if (k === "refcount_debug") {
$("#" + k).append(
''
);
$("#" + k + "_button")
.addClass(!settings[k] ? "btn-success" : "btn-danger")
.html(
!settings[k]
? "Enable reference counters debug"
: "Disable reference counters debug"
);
$("#" + k + "_button").click(function () {
let text = !settings["refcount_debug"]
? "Are you sure you want to enable the reference counters debug? This will print a line on the console any time a reference counter is increased/decreased"
: "Are you sure you want to disable the reference counters debug?";
bootbox.confirm(text, function (result) {
if (result) setRefcountDebug(!settings["refcount_debug"]);
});
});
} else if (k === "log_timestamps") {
$("#" + k).append(
''
);
$("#" + k + "_button")
.addClass(!settings[k] ? "btn-success" : "btn-danger")
.html(
!settings[k] ? "Enable log timestamps" : "Disable log timestamps"
);
$("#" + k + "_button").click(function () {
let text = !settings["log_timestamps"]
? "Are you sure you want to enable the log timestamps? This will print the current date/time for each new line on the console"
: "Are you sure you want to disable the log timestamps?";
bootbox.confirm(text, function (result) {
if (result) setLogTimestamps(!settings["log_timestamps"]);
});
});
} else if (k === "log_colors") {
$("#" + k).append(
''
);
$("#" + k + "_button")
.addClass(!settings[k] ? "btn-success" : "btn-danger")
.html(!settings[k] ? "Enable log colors" : "Disable log colors");
$("#" + k + "_button").click(function () {
let text = !settings["log_colors"]
? "Are you sure you want to enable the log colors? This will strip the colors from events like warnings, errors, etc. on the console"
: "Are you sure you want to disable the log colors?";
bootbox.confirm(text, function (result) {
if (result) setLogColors(!settings["log_colors"]);
});
});
} else if (k === "libnice_debug") {
$("#" + k).append(
''
);
$("#" + k + "_button")
.addClass(!settings[k] ? "btn-success" : "btn-danger")
.html(
!settings[k] ? "Enable libnice debug" : "Disable libnice debug"
);
$("#" + k + "_button").click(function () {
let text = !settings["libnice_debug"]
? "Are you sure you want to enable the libnice debug? This will print the a very verbose debug of every libnice-related operation on the console"
: "Are you sure you want to disable the libnice debug?";
bootbox.confirm(text, function (result) {
if (result) setLibniceDebug(!settings["libnice_debug"]);
});
});
}
}
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
$("#update-settings").removeClass("fa-spin").click(updateSettings);
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
function setSessionTimeoutValue(timeout) {
let request = {
janus: "set_session_timeout",
timeout: timeout,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setLogLevel(level) {
let request = {
janus: "set_log_level",
level: level,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setLockingDebug(enable) {
let request = {
janus: "set_locking_debug",
debug: enable,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setRefcountDebug(enable) {
let request = {
janus: "set_refcount_debug",
debug: enable,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setLogTimestamps(enable) {
let request = {
janus: "set_log_timestamps",
timestamps: enable,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setLogColors(enable) {
let request = {
janus: "set_log_colors",
colors: enable,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setLibniceDebug(enable) {
let request = {
janus: "set_libnice_debug",
debug: enable,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setMinNackQueue(queue) {
let request = {
janus: "set_min_nack_queue",
min_nack_queue: queue,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setNoMediaTimer(timer) {
let request = {
janus: "set_no_media_timer",
no_media_timer: timer,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function setSlowlinkThreshold(packets) {
let request = {
janus: "set_slowlink_threshold",
slowlink_threshold: packets,
transaction: randomString(12),
admin_secret: secret,
};
sendSettingsRequest(request);
}
function sendSettingsRequest(request) {
console.log(request);
$.ajax({
type: "POST",
url: server,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
return;
}
updateSettings();
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
// Plugins
function resetPluginRequest() {
pluginRows = 0;
$("#plugin-request")
.empty()
.append(
'
' +
'
Name
' +
'
Value
' +
'
Type
' +
"
" +
"
" +
"
" +
'
' +
"
" +
"
" +
'
' +
"
"
);
$("#addattr").click(addPluginMessageAttribute).click();
$("#sendmsg").click(function () {
let message = {};
let index = 0;
for (let i = 0; i <= pluginRows; i++) {
if ($("#attrname" + i).length === 0) continue;
index++;
let name = $("#attrname" + i).val();
if (name === "") {
bootbox.alert("Missing name in attribute #" + index);
return;
}
if (message[name] !== null && message[name] !== undefined) {
bootbox.alert("Duplicate attribute '" + name + "'");
return;
}
let value = $("#attrvalue" + i).val();
if (value === "") {
bootbox.alert("Missing value in attribute #" + index);
return;
}
let type = $("#attrtype" + i).val();
if (type === "number") {
value = parseInt(value);
if (isNaN(value)) {
bootbox.alert(
"Invalid value in attribute #" + index + " (expecting a number)"
);
return;
}
} else if (type === "boolean") {
if (value.toLowerCase() === "true") {
value = true;
} else if (value.toLowerCase() === "false") {
value = false;
} else {
bootbox.alert(
"Invalid value in attribute #" + index + " (expecting a boolean)"
);
return;
}
}
console.log("Type:", type);
message[name] = value;
}
sendPluginMessage($("#plugins-list .active").text(), message);
});
$("#plugin-message").removeClass("hide");
}
function addPluginMessageAttribute() {
let num = pluginRows;
pluginRows++;
$("#addattr")
.parent()
.parent()
.before(
"
" +
'
' +
'
' +
"
" +
' " +
"
" +
'
' +
"
"
);
$("#rmattr" + num).click(function () {
$(this).parent().parent().remove();
});
}
function sendPluginMessage(plugin, message) {
console.log("Sending message to " + plugin + ":", message);
let request = {
janus: "message_plugin",
transaction: randomString(12),
admin_secret: secret,
plugin: plugin,
request: message,
};
$.ajax({
type: "POST",
url: server,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
}
$("#plugin-response").text(JSON.stringify(json, null, 4));
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
// Transports
function resetTransportRequest() {
transportRows = 0;
$("#transport-request")
.empty()
.append(
'
' +
'
Name
' +
'
Value
' +
'
Type
' +
"
" +
"
" +
"
" +
'
' +
"
" +
"
" +
'
' +
"
"
);
$("#traddattr").click(addTransportMessageAttribute).click();
$("#trsendmsg").click(function () {
let message = {};
let index = 0;
for (let i = 0; i <= transportRows; i++) {
if ($("#trattrname" + i).length === 0) continue;
index++;
let name = $("#trattrname" + i).val();
if (name === "") {
bootbox.alert("Missing name in attribute #" + index);
return;
}
if (message[name] !== null && message[name] !== undefined) {
bootbox.alert("Duplicate attribute '" + name + "'");
return;
}
let value = $("#trattrvalue" + i).val();
if (value === "") {
bootbox.alert("Missing value in attribute #" + index);
return;
}
let type = $("#trattrtype" + i).val();
if (type === "number") {
value = parseInt(value);
if (isNaN(value)) {
bootbox.alert(
"Invalid value in attribute #" + index + " (expecting a number)"
);
return;
}
} else if (type === "boolean") {
if (value.toLowerCase() === "true") {
value = true;
} else if (value.toLowerCase() === "false") {
value = false;
} else {
bootbox.alert(
"Invalid value in attribute #" + index + " (expecting a boolean)"
);
return;
}
}
console.log("Type:", type);
message[name] = value;
}
sendTransportMessage($("#transports-list .active").text(), message);
});
$("#transport-message").removeClass("hide");
}
function addTransportMessageAttribute() {
let num = transportRows;
transportRows++;
$("#traddattr")
.parent()
.parent()
.before(
"
" +
'
' +
'
' +
"
" +
' " +
"
" +
'
' +
"
"
);
$("#rmtrattr" + num).click(function () {
$(this).parent().parent().remove();
});
}
function sendTransportMessage(transport, message) {
console.log("Sending message to " + transport + ":", message);
let request = {
janus: "query_transport",
transaction: randomString(12),
admin_secret: secret,
transport: transport,
request: message,
};
$.ajax({
type: "POST",
url: server,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
}
$("#transport-response").text(JSON.stringify(json, null, 4));
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
// Handles
function updateSessions() {
$("#update-sessions").unbind("click").addClass("fa-spin");
$("#update-handles").unbind("click");
$("#update-handle").unbind("click");
let request = {
janus: "list_sessions",
transaction: randomString(12),
admin_secret: secret,
};
$.ajax({
type: "POST",
url: server,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
setTimeout(function () {
$("#update-sessions").removeClass("fa-spin").click(updateSessions);
$("#update-handles").click(updateHandles);
$("#update-handle").click(updateHandleInfo);
}, 1000);
session = null;
handle = null;
currentHandle = null;
$("#handles-list").empty();
$("#handles").addClass("hide");
$("#handle-info").empty();
$("#options").addClass("hide");
$("#info").addClass("hide");
return;
}
console.log("Got sessions:");
console.log(json);
$("#sessions-list").empty();
let sessions = json["sessions"];
$("#sessions-num").text(sessions.length);
for (let i = 0; i < sessions.length; i++) {
let s = sessions[i];
$("#sessions-list").append(
'' +
"" +
s +
"" +
""
);
$("#session-" + s).click(function () {
let sh = $(this).text();
console.log("Getting session " + sh + " handles");
session = sh;
$("#sessions-list a").removeClass("active");
$("#session-" + sh).addClass("active");
handle = null;
currentHandle = null;
$("#handles-list").empty();
$("#handles").removeClass("hide");
$("#handle-info").empty();
$("#options").addClass("hide");
$("#info").addClass("hide");
updateHandles();
});
}
if (session !== null && session !== undefined) {
if ($("#session-" + session).length) {
$("#session-" + session).addClass("active");
} else {
// The session that was selected has disappeared
session = null;
handle = null;
currentHandle = null;
$("#handles-list").empty();
$("#handles").addClass("hide");
$("#handle-info").empty();
$("#options").addClass("hide");
$("#info").addClass("hide");
}
}
setTimeout(function () {
$("#update-sessions").removeClass("fa-spin").click(updateSessions);
$("#update-handles").click(updateHandles);
$("#update-handle").click(updateHandleInfo);
}, 1000);
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
setTimeout(function () {
$("#update-sessions").removeClass("fa-spin").click(updateSessions);
$("#update-handles").click(updateHandles);
$("#update-handle").click(updateHandleInfo);
}, 1000);
session = null;
handle = null;
currentHandle = null;
$("#handles-list").empty();
$("#handles").addClass("hide");
$("#handle-info").empty();
$("#options").addClass("hide");
$("#info").addClass("hide");
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
function updateHandles() {
if (session === null || session === undefined) return;
$("#update-sessions").unbind("click");
$("#update-handles").unbind("click").addClass("fa-spin");
$("#update-handle").unbind("click");
let request = {
janus: "list_handles",
transaction: randomString(12),
admin_secret: secret,
};
$.ajax({
type: "POST",
url: server + "/" + session,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
setTimeout(function () {
$("#update-handles").removeClass("fa-spin").click(updateHandles);
$("#update-sessions").click(updateSessions);
$("#update-handle").click(updateHandleInfo);
}, 1000);
return;
}
console.log("Got handles:");
console.log(json);
$("#handles-list").empty();
let handles = json["handles"];
$("#handles-num").text(handles.length);
for (let i = 0; i < handles.length; i++) {
let h = handles[i];
$("#handles-list").append(
'' +
"" +
h +
"" +
""
);
$("#handle-" + h).click(function () {
let hi = $(this).text();
console.log("Getting handle " + hi + " info");
handle = hi;
if (handle === currentHandle) return; // The self-refresh takes care of that
$("#handles-list a").removeClass("active");
$("#handle-" + hi).addClass("active");
$("#handle-info").empty();
$("#options").addClass("hide");
$("#info").removeClass("hide");
updateHandleInfo();
});
}
if (handle !== null && handle !== undefined) {
if ($("#handle-" + handle).length) {
$("#handle-" + handle).addClass("active");
} else {
// The handle that was selected has disappeared
handle = null;
currentHandle = null;
$("#handle-info").empty();
$("#options").addClass("hide");
$("#info").addClass("hide");
}
}
setTimeout(function () {
$("#update-handles").removeClass("fa-spin").click(updateHandles);
$("#update-sessions").click(updateSessions);
$("#update-handle").click(updateHandleInfo);
}, 1000);
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
$("#update-handles").removeClass("fa-spin").click(updateHandles);
$("#update-sessions").click(updateSessions);
$("#update-handle").click(updateHandleInfo);
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
function updateHandleInfo(refresh) {
if (handle === null || handle === undefined) return;
if (refresh !== true) {
if (handle === currentHandle && $("#autorefresh")[0].checked) return; // The self-refresh takes care of that
currentHandle = handle;
}
let updateHandle = currentHandle;
$("#update-sessions").unbind("click");
$("#update-handles").unbind("click");
$("#update-handle").unbind("click").addClass("fa-spin");
$("#capture").removeAttr("checked");
$("#capturetext").html("Start capture");
let request = {
janus: "handle_info",
transaction: randomString(12),
admin_secret: secret,
};
$.ajax({
type: "POST",
url: server + "/" + session + "/" + handle,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
if (refresh !== true) {
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
}
setTimeout(function () {
$("#update-sessions").click(updateSessions);
$("#update-handles").click(updateHandles);
$("#update-handle").removeClass("fa-spin").click(updateHandleInfo);
}, 1000);
return;
}
console.log("Got info:");
console.log(json);
handleInfo = json["info"];
if ($("#prettify")[0].checked) {
prettyHandleInfo();
} else {
rawHandleInfo();
}
if (handleInfo["dump-to-pcap"] || handleInfo["dump-to-text2pcap"]) {
$("#capture").attr("checked", true);
$("#capturetext").html("Stop capture");
}
setTimeout(function () {
$("#update-sessions").click(updateSessions);
$("#update-handles").click(updateHandles);
$("#update-handle").removeClass("fa-spin").click(updateHandleInfo);
}, 1000);
// Show checkboxes
$("#options").removeClass("hide");
// If the related box is checked, autorefresh this handle info every tot seconds
if ($("#autorefresh")[0].checked) {
setTimeout(function () {
if (updateHandle !== currentHandle) {
// The handle changed in the meanwhile, don't autorefresh
return;
}
if (!$("#autorefresh")[0].checked) {
// Unchecked in the meantime
return;
}
updateHandleInfo(true);
}, 5000);
}
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
$("#update-handles").removeClass("fa-spin").click(updateHandles);
$("#update-sessions").click(updateSessions);
$("#update-handle").click(updateHandleInfo);
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
function rawHandleInfo() {
// Just use
and show the handle info as it is
$("#handle-info").html(
'
' +
JSON.stringify(handleInfo, null, 4) +
"
"
);
}
function prettyHandleInfo() {
// Prettify the handle info, processing it and turning it into tables
$("#handle-info").html(
'
'
);
$("#options").addClass("hide");
for (let k in handleInfo) {
let v = handleInfo[k];
if (k === "plugin_specific") {
$("#handle-info").append(
"
Plugin specific details
" +
'
' +
"
"
);
for (let kk in v) {
let vv = v[kk];
$("#plugin-specific").append(
"
"
);
for (let index in json.data.tokens) {
let t = json.data.tokens[index];
let tokenPlugins = t.allowed_plugins.toString().replace(/,/g, " ");
$("#auth-tokens").append(
"
" +
"
" +
t.token +
"
" +
"
" +
tokenPlugins +
"
" +
'
' +
"
"
);
$("#" + t.token).click(function () {
let token = $(this).attr("id");
bootbox.confirm(
"Are you sure you want to remove token " + token + "?",
function (result) {
if (result) removeToken(token);
}
);
});
}
$("#auth-tokens").append(
"
" +
'
' +
'
' +
'
' +
"
"
);
let pluginsCheckboxes = "";
for (let i in plugins) {
let plugin = plugins[i];
pluginsCheckboxes +=
'
' +
' ' +
' " +
"
";
}
$("#permissions").html(pluginsCheckboxes);
$("#addtoken").click(function () {
let token = $("#token").val().replace(/ /g, "");
if (token === "") {
bootbox.alert("Please insert a valid token string");
return;
}
let checked = $(":checked");
if (checked.length === 0) {
bootbox.alert("Please allow the token access to at least a plugin");
return;
}
let pluginPermissions = [];
for (let i = 0; i < checked.length; i++)
pluginPermissions.push(checked[i].value);
let text =
"Are you sure you want to add the new token " +
token +
" with access to the following plugins?" +
"
";
for (let i in pluginPermissions)
text += "
" + pluginPermissions[i] + "
";
text += "
";
bootbox.confirm(text, function (result) {
if (result) addToken(token, pluginPermissions);
});
});
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
$("#update-settings").removeClass("fa-spin").click(updateSettings);
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
function addToken(token, permissions) {
let request = {
janus: "add_token",
token: token,
plugins: permissions,
transaction: randomString(12),
admin_secret: secret,
};
sendTokenRequest(request);
}
function removeToken(token) {
let request = {
janus: "remove_token",
token: token,
transaction: randomString(12),
admin_secret: secret,
};
sendTokenRequest(request);
}
function sendTokenRequest(request) {
console.log(request);
$.ajax({
type: "POST",
url: server,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
let authenticate = json["error"].code === 403;
if (!authenticate || (authenticate && !prompting && !alerted)) {
if (authenticate) alerted = true;
bootbox.alert(json["error"].reason, function () {
if (authenticate) {
promptAccessDetails();
alerted = false;
}
});
}
return;
}
updateTokens();
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
// text2pcap and pcap requests
function captureTrafficPrompt() {
bootbox.dialog({
title: "Start capturing traffic",
message:
'
' +
' " +
"
",
buttons: [
{
label: "Start",
className: "btn btn-primary pull-left",
callback: function () {
let text = $("#type").val() === "text2pcap";
let folder =
$("#folder").val() !== "" ? $("#folder").val() : undefined;
let filename =
$("#filename").val() !== "" ? $("#filename").val() : undefined;
let truncate = parseInt($("#truncate").val());
if (!truncate || isNaN(truncate)) truncate = 0;
captureTrafficRequest(true, text, folder, filename, truncate);
},
},
{
label: "Close",
className: "btn btn-secondary pull-left",
callback: function () {
$("#capture").removeAttr("checked");
$("#capturetext").html("Start capture");
},
},
],
});
}
function captureTrafficRequest(start, text, folder, filename, truncate) {
let req = start
? text
? "start_text2pcap"
: "start_pcap"
: text
? "stop_text2pcap"
: "stop_pcap";
let request = {
janus: req,
transaction: randomString(12),
admin_secret: secret,
};
if (start) {
request["folder"] = folder;
request["filename"] = filename;
request["truncate"] = truncate;
}
$.ajax({
type: "POST",
url: server + "/" + session + "/" + handle,
cache: false,
contentType: "application/json",
data: JSON.stringify(request),
success: function (json) {
if (json["janus"] !== "success") {
console.log(
"Ooops: " + json["error"].code + " " + json["error"].reason
); // FIXME
bootbox.alert(json["error"].reason);
if (start && json["error"].reason.indexOf("already") === -1) {
$("#capture").removeAttr("checked");
$("#capturetext").html("Start capture");
}
return;
}
},
// eslint-disable-next-line no-unused-vars
error: function (XMLHttpRequest, textStatus, errorThrown) {
console.log(textStatus + ": " + errorThrown); // FIXME
if (!prompting && !alerted) {
alerted = true;
bootbox.alert(
"Couldn't contact the backend: is Janus down, or is the Admin/Monitor interface disabled?",
function () {
promptAccessDetails();
alerted = false;
}
);
}
},
dataType: "json",
});
}
// eslint-disable-next-line no-unused-vars
function checkEnter(field, event) {
let theCode = event.keyCode
? event.keyCode
: event.which
? event.which
: event.charCode;
if (theCode == 13) {
if (field.id == "token") $("#addtoken").click();
else if (field.id.indexOf("attr") !== -1) $("#sendmsg").click();
return false;
} else {
return true;
}
}