github.com/siglens/siglens@v0.0.0-20240328180423-f7ce9ae441ed/static/component/download/download.js (about)

     1  (function ($) {
     2    $.fn.download = function (options) {
     3      var defaults = {
     4        data: [],
     5        downloadMethod: ".cvs"
     6      };
     7      let setting = $.extend(defaults, options || {});
     8      this.html(``);
     9      let curMethod = setting.downloadMethod.replace(".", "");
    10      this
    11        .append(`<div id="download-info-${curMethod}" title="Download" class="download-result"><p class="validateTips" id="validateTips"></p>
    12              <form>
    13                  <fieldset>
    14                      <input type="text" name="qnameDL" id="qnameDL-${curMethod}" placeholder="Name"
    15                          class="text ui-widget-content ui-corner-all name-info">
    16                      <input type="submit" tabindex="-1" style="position:absolute; top:-1000px">
    17                  </fieldset>
    18              </form></div>
    19              <div class="pop-download" id="pop-box">
    20              <div class="pop-text">Downloading...</div>
    21              <button class="btn cancel-loading" id="cancel-loading">Cancel</button>
    22          </div>
    23              `);
    24  
    25  
    26  let curChoose = setting.downloadMethod;
    27  let interval = null;
    28  var progressBar = $("#progressbar");
    29  var progressLabel = $(".progress-label");
    30  let confirmDownload = true;
    31  if (typeof interval != "undefined") {
    32    doClearInterval();
    33  } else {
    34    interval = null;
    35  }
    36  var progressWidth = 0;
    37  function beginProgress(t) {
    38    progressWidth = 1;
    39    interval = setInterval("doProgress()", t * 10);
    40  }
    41  function cancelDownload() {
    42    confirmDownload = false;
    43    var popBox = document.getElementById("pop-box");
    44    var popLayer = document.getElementById("pop-layer");
    45    popLayer.style.display = "none";
    46    popBox.style.display = "none";
    47    $("#progressbar").hide();
    48  }
    49  function setProgress(node, width) {
    50    if (node) {
    51      progressBar.progressbar({
    52        value: width,
    53      });
    54      progressLabel.text(width + "%");
    55    }
    56  }
    57  function doProgress() {
    58    if (progressWidth == 98) {
    59      doClearInterval();
    60    }
    61    setProgress(progressBar, progressWidth);
    62    progressWidth++;
    63  }
    64  function doClearInterval() {
    65    clearInterval(interval);
    66  }
    67  $("#cancel-loading").on("click", cancelDownload);
    68    let dialog = null;
    69    let form = null;
    70    let qname = $(`#qnameDL-${curMethod}`);
    71    let description = $("#descriptionR");
    72    let allFields = $([]).add(qname).add(description);
    73    let tips = $("#validateTips");
    74  
    75    function updateTips(t) {
    76      tips.addClass("active");
    77      $("#validateTips").show();
    78      tips.text(t).addClass("ui-state-highlight");
    79    }
    80      function checkLength(o, n, min, max) {
    81      if (o.val().length > max || o.val().length < min) {
    82        o.addClass("ui-state-error");
    83        updateTips(
    84          "Length of " + n + " must be between " + min + " and " + max + "."
    85        );
    86        return false;
    87      } else {
    88        return true;
    89      }
    90    }
    91  
    92    function checkRegexp(o, regexp, n) {
    93      if (!regexp.test(o.val())) {
    94        o.addClass("ui-state-error");
    95        updateTips(n);
    96        return false;
    97      } else {
    98        return true;
    99      }
   100    }
   101      function downloadJson(fileName, json) {
   102      const jsonStr = json instanceof Object ? JSON.stringify(json) : json;
   103      const url = window.URL || window.webkitURL || window;
   104      const blob = new Blob([jsonStr]);
   105      const saveLink = document.createElementNS(
   106        "http://www.w3.org/1999/xhtml",
   107        "a"
   108      );
   109      saveLink.href = url.createObjectURL(blob);
   110      saveLink.download = fileName;
   111      saveLink.click();
   112    }
   113    function convertToCSV(json) {
   114      const items = JSON.parse(json);
   115  
   116      // Get column headers from first item in JSON array
   117      const headers = Object.keys(items[0]);
   118  
   119      // Build CSV header row
   120      const csvHeader = headers.join(",");
   121  
   122      // Build CSV body rows
   123      const csvBody = items
   124        .map((item) => {
   125          return headers
   126            .map((header) => {
   127              let col = item[header];
   128              return typeof col !== "string" ? col : `"${col.replace(/"/g, '""')}"`;
   129            })
   130            .join(",");
   131        })
   132        .join("\n");
   133  
   134      // Combine header and body into single CSV string
   135      const csv = `${csvHeader}\n${csvBody}`;
   136  
   137      return csv;
   138    }
   139    function downloadCsv(csvData, fileName) {
   140      const blob = new Blob([csvData], { type: "text/csv" });
   141      const url = URL.createObjectURL(blob);
   142      const downloadLink = document.createElement("a");
   143      downloadLink.href = url;
   144      downloadLink.download = fileName;
   145      document.body.appendChild(downloadLink);
   146      downloadLink.click();
   147      document.body.removeChild(downloadLink);
   148    }
   149      function download() {
   150        confirmDownload = true;
   151        let valid = true;
   152        allFields.removeClass("ui-state-error");
   153        tips.removeClass("ui-state-highlight");
   154        tips.text("");
   155        valid = valid && checkLength(qname, "download name", 3, 16);
   156        valid =
   157          valid &&
   158          checkRegexp(
   159            qname,
   160            /^[a-zA-Z0-9_.-]+$/i,
   161            "Download name may consist of a-z, 0-9, period, dash, underscores."
   162          );
   163      let enteredName = $(`#qnameDL-${curMethod}`).val();
   164      let extension = curChoose;
   165      let name = enteredName;
   166    
   167      if (!enteredName.endsWith(extension)) {
   168        name += extension;
   169      }
   170        if (valid) {
   171          dialog.dialog("close");
   172          $("#progressbar").show();
   173          //show progress box
   174          var popBox = document.getElementById("pop-box");
   175          var popLayer = document.getElementById("pop-layer");
   176          popLayer.style.width = document.body.scrollWidth + "px";
   177          popLayer.style.height = document.body.scrollHeight + "px";
   178          popLayer.style.display = "block";
   179          popBox.style.display = "block";
   180  
   181          //close progress box
   182          var popBox = document.getElementById("pop-box");
   183          var popLayer = document.getElementById("pop-layer");
   184          popLayer.style.display = "none";
   185          popBox.style.display = "none";
   186          //set progress finished
   187          doClearInterval();
   188          $("#progressbar").hide();
   189          setProgress(progressBar, 100);
   190          if (!confirmDownload) return;
   191          if (
   192            setting.data.length > 0
   193          ) {
   194            let json = JSON.stringify(setting.data);
   195            if (setting.downloadMethod == ".json") downloadJson(name, json);
   196            else {
   197              const csvData = convertToCSV(json);
   198              downloadCsv(csvData, name);
   199            }
   200          } else {
   201            alert("no data available");
   202          }
   203        }
   204      }
   205      dialog = $(`#download-info-${curMethod}`).dialog({
   206        autoOpen: false,
   207        resizable: false,
   208        width: 460,
   209        modal: true,
   210        position: {
   211          my: "center",
   212          at: "center",
   213          of: window,
   214        },
   215        buttons: {
   216          Cancel: {
   217            class: "cancelqButton",
   218            text: "Cancel",
   219            click: function () {
   220              dialog.dialog("close");
   221            },
   222          },
   223          Save: {
   224            class: "saveqButton",
   225            text: "Save",
   226            click: download,
   227          },
   228        },
   229        close: function () {
   230          form[0].reset();
   231          allFields.removeClass("ui-state-error");
   232        },
   233      });
   234      form = dialog.find("form").on("submit", function (event) {
   235        event.preventDefault();
   236        download();
   237      });
   238      $("#validateTips").hide();
   239      $(`#download-info-${curMethod}`).dialog("open");
   240      $(".ui-widget-overlay").addClass("opacity-75");
   241      return this;
   242    };
   243  })(jQuery);