Replace inline styles and mixed jQuery methods with consistent helper functions and `d-none` class for better maintainability and performance.
---------
Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
Co-authored-by: moisseev <2275981+moisseev@users.noreply.github.com>
<li role="presentation" class="nav-item"><a id="configuration_nav" aria-controls="configuration" role="tab" href="#configuration" data-bs-toggle="tab" class="nav-link">Configuration</a></li>
<li role="presentation" class="nav-item"><a id="symbols_nav" aria-controls="symbols" role="tab" href="#symbols" data-bs-toggle="tab" class="nav-link">Symbols</a></li>
- <li role="presentation" class="nav-item"><a id="scan_nav" aria-controls="scan" role="tab" href="#scan" data-bs-toggle="tab" class="nav-link">Scan<span class="ro-hide" style="display: none;">/Learn</span></a></li>
- <li role="presentation" class="nav-item"><a id="selectors_nav" aria-controls="selectors" role="tab" href="#selectors" data-bs-toggle="tab" class="nav-link ro-hide" style="display: none;">Test selectors</a></li>
+ <li role="presentation" class="nav-item"><a id="scan_nav" aria-controls="scan" role="tab" href="#scan" data-bs-toggle="tab" class="nav-link">Scan<span class="ro-hide d-none">/Learn</span></a></li>
+ <li role="presentation" class="nav-item"><a id="selectors_nav" aria-controls="selectors" role="tab" href="#selectors" data-bs-toggle="tab" class="nav-link ro-hide d-none">Test selectors</a></li>
<li role="presentation" class="nav-item"><a id="history_nav" aria-controls="history" role="tab" href="#history" data-bs-toggle="tab" class="nav-link">History</a></li>
</ul>
</div>
<div class="tab-content">
<div class="tab-pane" id="status">
<div class="row">
- <div id="statWidgets" class="col-lg-12 stat-boxes fw-bold text-secondary" style="display: none;">
+ <div id="statWidgets" class="col-lg-12 stat-boxes fw-bold text-secondary d-none">
</div>
</div>
<div class="row">
</div>
</div>
</div>
- <div class="card ro-hide" style="display: none;">
+ <div class="card ro-hide d-none">
<div class="card-header text-secondary py-1 d-flex align-items-center">
<span class="icon me-3"><i class="fas fa-graduation-cap"></i></span>
<span class="h6 fw-bolder my-auto">Learn Rspamd</span>
</div>
</div>
- <div id="hash-card" class="card bg-light shadow my-3" style="display: none;">
+ <div id="hash-card" class="card bg-light shadow my-3 d-none">
<div class="card-header text-secondary py-2 d-flex align-items-center">
<span class="icon me-3"><i class="fas fa-hashtag"></i></span>
<span class="h6 fw-bolder my-auto">Fuzzy hashes</span>
<span class="h6 fw-bolder my-auto ms-0">History</span>
<a href="https://rspamd.com/doc/modules/history_redis.html" target="_blank" rel="noopener noreferrer"
title="If you'd like to use the modern version of History, please enable History redis module."
- id="legacy-history-badge" class="my-2 ms-2 badge text-bg-info" style="display: none;">Legacy version</a>
+ id="legacy-history-badge" class="my-2 ms-2 badge text-bg-info d-none">Legacy version</a>
<div class="d-flex input-group-sm align-items-center text-nowrap ms-auto me-1">
<label for="selSymOrder_history">Symbols order:</label>
<select id="selSymOrder_history" class="form-select ms-1">
Browser detects passwords by form.elements[n].type == "password" and then detects
the username field by searching backwards through form elements for the text field
immediately before the password fields. -->
- <input value="Rspamd controller password" style="display: none;"/>
+ <input value="Rspamd controller password" class="d-none"/>
<div class="input-group">
<input class="form-control"
type="password"
return String(string).replace(htmlEscaper, (match) => htmlEscapes[match]);
};
+ /**
+ * Hide one or more elements using Bootstrap's d-none class
+ * @param {string|jQuery} selector - CSS selector or jQuery object
+ * @param {boolean} anim - Whether to use animation (slideUp)
+ */
+ ui.hide = function (selector, anim = false) {
+ const $el = (typeof selector === "string") ? $(selector) : selector;
+ if (anim) {
+ $el.slideUp(400, function () {
+ $(this).addClass("d-none");
+ });
+ } else {
+ $el.addClass("d-none");
+ }
+ };
+
+ /**
+ * Show one or more elements using Bootstrap's d-none class
+ * @param {string|jQuery} selector - CSS selector or jQuery object
+ * @param {boolean} anim - Whether to use animation (slideDown)
+ */
+ ui.show = function (selector, anim = false) {
+ const $el = (typeof selector === "string") ? $(selector) : selector;
+ if (anim) {
+ $el.removeClass("d-none").hide().slideDown(400);
+ } else {
+ $el.removeClass("d-none");
+ }
+ };
+
+ /**
+ * Toggle visibility of one or more elements using Bootstrap's d-none class
+ * @param {string|jQuery} selector - CSS selector or jQuery object
+ * @param {boolean} anim - Whether to use animation
+ */
+ ui.toggle = function (selector, anim = false) {
+ const $el = (typeof selector === "string") ? $(selector) : selector;
+ if ($el.hasClass("d-none")) {
+ ui.show($el, anim);
+ } else {
+ ui.hide($el, anim);
+ }
+ };
+
ui.appendButtonsToFtFilterDropdown = (ftFilter) => {
function button(text, classes, check) {
return $("<button/>", {
ui.getMaps = function () {
const $listmaps = $("#listMaps");
- $listmaps.closest(".card").hide();
+ common.hide($listmaps.closest(".card"));
common.query("maps", {
success: function (json) {
const [{data}] = json;
$("<td>" + item.description + "</td>").appendTo($tr);
$tr.appendTo($tbody);
});
- $listmaps.closest(".card").show();
+ common.show($listmaps.closest(".card"));
},
server: common.getServer()
});
if (item.editable === false || common.read_only) {
$("#editor").attr(editor[mode].readonly_attr);
icon = "fa-eye";
- $("#modalSaveGroup").hide();
+ common.hide("#modalSaveGroup");
} else {
- $("#modalSaveGroup").show();
+ common.show("#modalSaveGroup");
}
$("#modalDialog .modal-header").find("[data-fa-i2svg]").addClass(icon);
$("#modalTitle").html(item.uri);
function compare(e1, e2) { return e1.name.localeCompare(e2.name); }
- $("#selSymOrder_history, label[for='selSymOrder_history']").hide();
+ common.hide("#selSymOrder_history, label[for='selSymOrder_history']");
$.each(data, (i, item) => {
item.time = libft.unix_time_format(item.unix_time);
data.rows = [].concat.apply([], neighbours_data
.map((e) => e.rows));
data.version = version;
- $("#legacy-history-badge").hide();
+ common.hide("#legacy-history-badge");
} else {
// Legacy version
data = [].concat.apply([], neighbours_data);
- $("#legacy-history-badge").show();
+ common.show("#legacy-history-badge");
}
const o = process_history_data(data);
const {items} = o;
const unsorted_symbols = [];
const compare_function = get_compare_function(table);
- $("#selSymOrder_" + table + ", label[for='selSymOrder_" + table + "']").show();
+ common.show("#selSymOrder_" + table + ", label[for='selSymOrder_" + table + "]");
$.each(data.rows,
(i, item) => {
() => module.statWidgets(graphs, checked_server));
if (id !== "#autoRefresh") module.statWidgets(graphs, checked_server);
- $(".preset").show();
- $(".history").hide();
- $(".dynamic").hide();
+ common.show(".preset");
+ common.hide(".history");
+ common.hide(".dynamic");
});
break;
case "#throughput_nav":
() => module.draw(graphs, common.neighbours, checked_server, selData));
if (id !== "#autoRefresh") module.draw(graphs, common.neighbours, checked_server, selData);
- $(".preset").hide();
- $(".history").hide();
- $(".dynamic").show();
+ common.hide(".preset");
+ common.hide(".history");
+ common.show(".dynamic");
});
break;
case "#configuration_nav":
() => getHistoryAndErrors());
if (id !== "#autoRefresh") getHistoryAndErrors();
- $(".preset").hide();
- $(".history").show();
- $(".dynamic").hide();
+ common.hide(".preset");
+ common.show(".history");
+ common.hide(".dynamic");
module.updateHistoryControlsState();
});
if (common.read_only) {
$(".ro-disable").attr("disabled", true);
- $(".ro-hide").hide();
+ common.hide(".ro-hide");
} else {
$(".ro-disable").removeAttr("disabled", true);
- $(".ro-hide").show();
+ common.show(".ro-hide");
}
$("#preloader").addClass("d-none");
error: function () {
function clearFeedback() {
$("#connectPassword").off("input").removeClass("is-invalid");
- $("#authInvalidCharFeedback,#authUnauthorizedFeedback").hide();
+ common.hide("#authInvalidCharFeedback,#authUnauthorizedFeedback");
}
$("#connectDialog")
$("#connectPassword")
.addClass("is-invalid")
.off("input").on("input", () => clearFeedback());
- $(tooltip).show();
+ common.show(tooltip);
}
if (!(/^[\u0020-\u007e]*$/).test(password)) {
}
const stat_w = [];
- $("#statWidgets").empty().hide();
+ $("#statWidgets").empty();
+ common.hide("#statWidgets");
$.each(data, (i, item) => {
const widgetsOrder = ["scanned", "no action", "greylist", "add header", "rewrite subject", "reject", "learned"];
.wrapAll('<div class="card stat-box text-center shadow-sm float-end">' +
'<div class="widget overflow-hidden p-2 text-capitalize"></div></div>');
$("#statWidgets").find("div.float-end").appendTo("#statWidgets");
- $("#statWidgets").show();
+ common.show("#statWidgets");
$("#clusterTable tbody").empty();
$("#selSrv").empty();
"<td>" + hash + "</td></tr>");
});
}
- $("#hash-card").slideDown();
+ common.show("#hash-card", true);
}
common.query("plugins/fuzzy/hashes?flag=" + $("#fuzzy-flag").val(), {
});
$(".card-close-btn").on("click", function () {
- $(this).closest(".card").slideUp();
+ common.hide($(this).closest(".card"), true);
});
function getScanTextHeaders() {
function toggleWidgets(showPicker, showInput) {
fuzzyWidgets.forEach(({picker, input}) => {
- $(picker)[showPicker ? "show" : "hide"]();
- $(input)[showInput ? "show" : "hide"]();
+ (showPicker ? common.show : common.hide)(picker);
+ (showInput ? common.show : common.hide)(input);
});
}
const $picker = $(picker);
$picker
.empty()
- .append($("<option>", {value: "", text: "fuzzy_check disabled"}))
- .show();
+ .append($("<option>", {value: "", text: "fuzzy_check disabled"}));
+ common.show($picker);
container($picker)
.attr("title", "fuzzy_check module is not enabled in server configuration.");
});