diff options
Diffstat (limited to 'dist/js/messaging.js')
-rw-r--r-- | dist/js/messaging.js | 615 |
1 files changed, 0 insertions, 615 deletions
diff --git a/dist/js/messaging.js b/dist/js/messaging.js deleted file mode 100644 index c548965..0000000 --- a/dist/js/messaging.js +++ /dev/null @@ -1,615 +0,0 @@ -const API_ENDPOINT = "https://gimb.tk/test.php"; -const DIRECTORY_URL = "/directory.json"; - -const ENCRYPTED_MESSAGE_REGEX = /<!-- ba-e2eemsg-(\d{4}) -->(\S+?)<!-- end-msg -->/; - -// "Global" object for name directory and messages -var directory = null; -var messages = { - "0": [], - "1": [], - "2": [] -} -var current_tab = 0; - -async function checkLogin() { - localforage.getItem("logged_in").then(function (value) { - // This code runs once the value has been loaded - // from the offline store. - if (value !== true) { - window.location.replace("/index.html"); - } - }).catch(function (err) { - // This code runs if there were any errors - console.log(err); - }); -} - -// -----------HTML HELPERS----------- -function htmlEncode(value) { - // Create a in-memory element, set its inner text (which is automatically encoded) - // Then grab the encoded contents back out. The element never exists on the DOM. - return $("<textarea/>").text(value).html(); -} - -function htmlDecode(value) { - return $("<textarea/>").html(value).text(); -} -// --------------------------------- - -// Try to fetch name:id directory -function loadDirectory() { - $.ajax({ - url: DIRECTORY_URL, - crossDomain: true, - - dataType: "json", - cache: false, - type: "GET", - - success: (data) => { - // If we were able to retrieve it, update the saved directory - localforage.setItem("directory", data); - directory = data; - // Populate autocomplete - populateAutocomplete(); - }, - - error: () => { - // Otherwise, try to retrieve stored directory - localforage.getItem("directory").then((stored_directory) => { - if (stored_directory === null) { - // If unable, set directory to null (so other functions know that we don't have it) - UIAlert( D("nameDirectoryNotSet"), "loadDirectory(): stored_directory === null" ); - directory = null; - // Disable send button - document.getElementById("msg-send").disabled = true; - } else { - directory = stored_directory; - // Populate autocomplete - populateAutocomplete(); - } - }); - } - }); -} - -function populateAutocomplete() { - let elems = document.querySelectorAll(".autocomplete-fullname"); - // če se uporablja globalna var directory, ki je shranjena kot objekt (vedno shranjen kot reference), bo pri let x=y x le pointer na object y - // in se bo spremenil z spremembo "originala". spodnja stvar itak ni preveč efficent, loop čez vseh 7000 ljudi bi lahko delal težave... - // kakšen Object.keys bi bila boljša varianta ampak raje napišem tale komentar... idk, to se mi je zdelo uporabno ampak sedaj obžalujem - // samo guglal sem "copying an object js" - let autocomplete_entries = Object.assign({}, directory); - for (let variableKey in autocomplete_entries) { - autocomplete_entries[variableKey] = null; - } - - M.Autocomplete.init(elems, { - data: autocomplete_entries, - onAutocomplete: validateName, - minLength: 0 - }); - - if (window.location.hash.length > 1 && !window.location.hash.substring(1).startsWith("beziapp")) { - $("#full-name").val(decodeURIComponent(window.location.hash.substring(1))); - } - - M.updateTextFields(); - validateName(); -} - -// Function to toggle loading bar -function setLoading(state) { - if (state) { - $("#loading-bar").removeClass("hidden"); - } else { - $("#loading-bar").addClass("hidden"); - } -} - -// Function, responsible for fetching and displaying data -async function loadMessages(force_refresh = true, messageType = 0) { - setLoading(true); - // Load required data - let promises_to_run = [ - localforage.getItem("username").then((value) => { - username = value; - }), - localforage.getItem("password").then((value) => { - password = value; - }), - localforage.getItem("messages").then((value) => { - messages = value; - }) - ]; - - Promise.all(promises_to_run).then(() => { - - if (messages[messageType] == null || messages[messageType].length === 0 || force_refresh) { - $.ajax({ - url: API_ENDPOINT, - crossDomain: true, - data: { - "u": username, - "p": password, - "m": "fetchsporocilaseznam", - "a": messageType // Message type, see API doc for details - }, - dataType: "json", - cache: false, - type: "GET", - - success: (data) => { - // If data is null, the request failed - if (data === null) { - UIAlert( D("requestFailed") ); - setLoading(false); - } else { - // Save messages & populate view - // console.log(data); // debug - messages[messageType.toString()] = data; - localforage.setItem("messages", messages).then((value) => { - displayData(messageType); - setLoading(false); - }); - } - }, - - error: () => { - UIAlert( D("errorFetchingMessages") ); - setLoading(false); - } - }) - } else { - displayData(messageType); - setLoading(false); - } - }); -} - -async function loadMsg(id) { - - setLoading(true); - // Load required data - let promises_to_run = [ - localforage.getItem("username").then((value) => { - username = value; - }), - localforage.getItem("password").then((value) => { - password = value; - }), - ]; - - Promise.all(promises_to_run).then(() => { - $.ajax({ - url: API_ENDPOINT, - crossDomain: true, - data: { - "u": username, - "p": password, - "m": "fetchsporocilo", - "a": id.replace(/_/g, "|") - }, - dataType: "json", - cache: false, - type: "GET", - success: (data) => { - // If data is null, the request failed - if (data === null) { - UIAlert( `${D("unableToReceiveTheMessage")} ${D("requestFailed")}` ); - } else { - displayMessage(id, data); - } - setLoading(false); - }, - - error: () => { - UIAlert( `${D("unableToReceiveTheMessage")} ${D("noInternetConnection")}` ); - setLoading(false); - } - - }) - }); -} - - -async function deleteMsg(id) { - setLoading(true); - // Load required data - let promises_to_run = [ - localforage.getItem("username").then((value) => { - username = value; - }), localforage.getItem("password").then((value) => { - password = value; - }), - ]; - Promise.all(promises_to_run).then(() => { - $.ajax({ - url: API_ENDPOINT, - crossDomain: true, - data: { - "u": username, - "p": password, - "m": "izbrisisporocilo", - "a": id - }, - dataType: "json", - cache: false, - type: "GET", - success: (data) => { - // If data is null, the request failed - if (data === null) { - UIAlert( `${D("unableToDeleteTheMessage")} ${D("requestFailed")}` ); - } else { - document.getElementById("msg_box-" + id).remove(); - } - setLoading(false); - }, - - error: () => { - UIAlert( `${D("unableToDeleteTheMessage")} ${D("noInternetConnection")}` ); - setLoading(false); - } - - }) - }); -} - -function displayMessage(id, data) { - let regex_results = ENCRYPTED_MESSAGE_REGEX.exec(data["telo"]); - if (regex_results != null) { - var datatodecrypt = regex_results[2]; - var randomencdivid = Math.floor(Math.random() * 9999).toString().padStart(4, "0"); - - var msgcontent = ` - <div id='ba-msg-e2ee-form-${randomencdivid}'> - ${D("thisMessageWasEncrypted")} - <input type="password" autocomplete="new-password" id="ba-msg-e2ee-password-${randomencdivid}" placeholder="${S("password")} ..."> - <button - type="button" - value="Decrypt" - class="btn waves-effect waves-light" - onclick=" - try { - $('#ba-msg-e2ee-content-${randomencdivid}').html( - filterXSS( - sjcl.decrypt( - $('#ba-msg-e2ee-password-${randomencdivid}').val(), - $('#ba-msg-e2ee-content-${randomencdivid}').html() - ) - ) - ); - $('#ba-msg-e2ee-content-${randomencdivid}').show(); - $('#ba-msg-e2ee-form-${randomencdivid}').hide(); - } catch (err) { - alert('${D("incorrectPassword")}'); - } - " - > - ${S("decrypt")} - </button> - </div> - <div id="ba-msg-e2ee-content-${randomencdivid}" hidden> - ${datatodecrypt} - </div> - ` - $(`#msg_body-${id.replace(/\|/g, "_")}`).html(msgcontent); - } else { - $(`#msg_body-${id.replace(/\|/g, "_")}`).html(filterXSS(data["telo"])); - } -} - -// Function for displaying data -function displayData(messageType) { - let div_selector = ""; - switch (messageType) { - case 0: - div_selector = "#beziapp-received"; - break; - case 1: - div_selector = "#beziapp-sent"; - break; - case 2: - div_selector = "#beziapp-deleted"; - break; - } - - // $("#storage-bar").show(); - $("#storage-progressbar").width(Number(Number(getNumMessages(messageType) / 120) * 100).toFixed(2) + "%"); - $("#storage-stats").text(`${getNumMessages(messageType)}/120`); - - let msg_list = $(div_selector); - msg_list.html(""); - messages[messageType.toString()].forEach(element => { - if (!element["zadeva"].startsWith("ba-ctlmsg")) { - - msg_list.append(` - <div class="col s12 m12" id="msg_box-${filterXSS(element["id"])}"> - <div class="card blue-grey darken-1"> - <div class="card-content white-text"> - <span class="card-title"> - ${filterXSS(element["zadeva"])} - </span> - <p id="msg_body-${filterXSS(element["id"]).replace(/\|/g, "_")}"> - <button - class="btn waves-effect waves-light" - onclick="loadMsg('${filterXSS(element["id"])}')" - type="submit" - > - Load message - <i class="material-icons right">move_to_inbox</i> - </button> - <p> - </div> - <div class="card-action"> - <a onclick="deleteMsg('${filterXSS(element["id"])}')"> - <i class="material-icons">delete</i> - </a> - <a onclick=" - $('#full_name').val('${filterXSS(element["posiljatelj"])}'); - $('#msg_subject').val('Re: ${filterXSS(element["zadeva"])}'); - M.updateTextFields(); - $('#navigation-main').scrollIntoView(); - " - > - <i class="material-icons">reply</i> - </a> - ${filterXSS(element["posiljatelj"])} » ${filterXSS(element["datum"]["dan"])}. ${filterXSS(element["datum"]["mesec"])}. ${filterXSS(element["datum"]["leto"])} at ${filterXSS(element["cas"]["ura"]).padStart(2, "0")}:${filterXSS(element["cas"]["minuta"]).padStart(2, "0")} - </div> - </div> - </div> - `); - } - }); -} - -// -1 = cumulative -function getNumMessages(messageType = -1) { - if (messageType === -1) { - let sum = 0; - for (const [messageType, messageList] of Object.entries(messages)) { - sum += messageList.length; - } - return sum; - } else { - return (messages[messageType].length ?? 0); - } -} - -async function sendMessage(recipient_number, subject, body) { - setLoading(true); - let promises_to_run = [ - localforage.getItem("username").then((value) => { - username = value; - }), - localforage.getItem("password").then((value) => { - password = value; - }), - ]; - Promise.all(promises_to_run).then(() => { - $.ajax({ - url: API_ENDPOINT, - crossDomain: true, - data: { - "u": username, - "p": password, - "m": "posljisporocilo", - "a": recipient_number, - "b": subject, - "c": body - }, - - dataType: "json", - cache: false, - - type: "POST", - success: () => { - // we CAN'T know wether the message was delievered - UIAlert(D("messageWasProbablySent")); - setLoading(false); - }, - error: () => { - UIAlert(D("errorSendingMessage"), D("noInternetConnection")); - setLoading(false); - } - }) - }); -} - -async function validateName() { - if (directory !== null) { - if ($("#full-name").val() in directory) { - $("#full-name").addClass("valid"); - $("#full-name").removeClass("invalid"); - $("#msg-send").removeAttr("disabled"); - } else { - $("#full-name").addClass("invalid"); - $("#full-name").removeClass("valid"); - $("#msg-send").attr("disabled", "disabled"); - } - } -} - -// Setup event listeners for buttons -function setupEventListeners() { - // Button to add a photo - $("#msg-add-photo").click(() => { - let input = document.createElement("input"); - input.type = "file"; - input.onchange = (e) => { - // getting a hold of the file reference - let file = e.target.files[0]; - // setting up the reader - let reader = new FileReader(); - reader.readAsDataURL(file); // this is reading as data url - - // here we tell the reader what to do when it's done reading... - reader.onload = readerEvent => { - additionalstufftoaddtomessage += `<br><img src="${readerEvent.target.result}" />`; // this is the content! - if ($("#msg-added-image").html().length > 1) { - $("#msg-added-image").append(`<img style="width: 20mm" src="${readerEvent.target.result}" />`); - } else { - $("#msg-added-image").html(` - <input - type="button" - value="${S("removeImages")}" - class="btn waves-effect waves-light" - onclick=" - additionalstufftoaddtomessage = ''; - $('#msg-added-image').html(''); - " - /> - <br> - ${D("largeImagesNote")} - <br> - ${S("attachedImages")}: - <br> - <img style="width:20mm" src="${readerEvent.target.result}" /> - `); - // ravno obratni narekovaji - } - UIAlert(D("imageAddedAsAnAttachment")); - } - } - input.click(); - }); - - // Verify recipient when input loses focus - $("#full-name").on("blur", validateName); - - // Setup refresh icon - $("#refresh-icon").click(() => { - loadMessages(true, current_tab); - }); - - // Setup checkbox handler - $("#encrypt-checkbox").change(function() { - if (this.checked) { - $("#encryption-key-input").prop("hidden", false); - } else { - $("#encryption-key-input").prop("hidden", true); - } - }); - - // Button to send message - $("#msg-send").click(() => { - localforage.getItem("directory").then(function (value) { - var msgcontent = $("#msg-body").val() + additionalstufftoaddtomessage; - var msgsubject = $("#msg-subject").val(); - if ($("#encryption-key-input").prop("hidden") !== true) { - var randomencdivid = Math.floor(Math.random() * 9999).toString().padStart(4, "0"); - var addrparts = window.location.href.split("/"); // engleski - - var encrypted_message = sjcl.encrypt($("#msg-e2ee-pass-input").val(), msgcontent); - msgcontent = ` - <script src="${addrparts[0]}//${addrparts[2]}/js/lib/sjcl.js"></script> - <div id="ba-msg-e2ee-form-${randomencdivid}"> - This message was encrypted by BežiApp. - <input type="password" autocomplete="new-password" id="ba-msg-e2ee-password-${randomencdivid}" placeholder="Enter password ..."> - <input type="button" value="Decrypt" onclick=" - try { - console.log($('ba-msg-e2ee-content-${randomencdivid}').text()); - $('#ba-msg-e2ee-content-${randomencdivid}').html( - sjcl.decrypt( - $('#ba-msg-e2ee-password-${randomencdivid}').val(), - $('#ba-msg-e2ee-content-${randomencdivid}').text() - ) - ); - $('#ba-msg-e2ee-content-${randomencdivid}').show(); - $('#ba-msg-e2ee-form-${randomencdivid}').hide(); - } catch(err) { - alert('${D("incorrectPassword")}'); - } - "> - </div> - <div id="ba-msg-e2ee-content-${randomencdivid}" hidden> - <!-- ba-e2eemsg-${msgcontent.length.toString().padStart(4, "0")} -->${encrypted_message}<!-- end-msg --> - </div> - ` - } - - console.log(msgcontent); - console.log(encrypted_message); - - sendMessage(value[$("#full-name").val()], msgsubject, htmlEncode(msgcontent)); - $("#msg-body").val(""); - $("#full-name").val(""); - $("#msg-subject").val(""); - // $("#msg-send").prop("disabled", true); - $("#msg-send").attr("disabled", "disabled"); - additionalstufftoaddtomessage = ""; - - $("#msg-added-image").html(""); - $("#msg-e2ee-pass").hide(); - - }).catch(function (err) { - UIAlert( `${D("unableToReadDirectory")} ${D("messageCouldNotBeSend")}`, "45245" ); - console.log(err); - }); - }); -} - -function getUrlParameter(sParam) { - const url_params = new URLSearchParams(window.location.search); - const found_param = url_params.get(sParam); - return found_param -} - -var additionalstufftoaddtomessage = ""; -document.addEventListener("DOMContentLoaded", () => { - - checkLogin(); - loadDirectory(); - setupEventListeners(); - - // Setup tabs - const tabs = document.querySelectorAll(".tabs"); - const tab_options = { - // swipeable: true, // TODO: figure out how to fix height when it's enabled (it's good for UX to have it enabled) - onShow: (tab) => { - if ($(tab).hasClass("active")) { - switch (tab.id) { - case "beziapp-received": - current_tab = 0; - loadMessages(false, 0); - break; - case "beziapp-sent": - current_tab = 1; - loadMessages(false, 1); - break; - case "beziapp-deleted": - current_tab = 2; - loadMessages(false, 2); - break; - } - } - } - }; - M.Tabs.init(tabs, tab_options); - - // Setup floating action button - const fab_options = { - hoverEnabled: false, - toolbarEnabled: false - } - const fab_elem = document.querySelectorAll(".fixed-action-btn"); - M.FloatingActionButton.init(fab_elem, fab_options); - - // Setup modals - const modal_elems = document.querySelectorAll('.modal'); - const modal_options = { - onOpenStart: () => { $("#fab-new").hide() }, - onCloseEnd: () => { $("#fab-new").show() }, - dismissible: false - }; - M.Modal.init(modal_elems, modal_options); - - var receivedmessages = null; - loadMessages(true, 0); - M.updateTextFields(); - - // Setup side menu - const menus = document.querySelectorAll(".side-menu"); - M.Sidenav.init(menus, { edge: "right", draggable: true }); -}); |