mirror of
https://github.com/arcan1s/ahriman.git
synced 2025-04-24 23:37:18 +00:00
add support of table filter controls (#101)
This commit is contained in:
parent
ad570aae0f
commit
9f2fe219c8
@ -63,6 +63,8 @@
|
|||||||
|
|
||||||
<table id="packages" class="table table-striped table-hover"
|
<table id="packages" class="table table-striped table-hover"
|
||||||
data-export-options='{"fileName": "packages"}'
|
data-export-options='{"fileName": "packages"}'
|
||||||
|
data-filter-control="true"
|
||||||
|
data-filter-control-visible="false"
|
||||||
data-page-list="[10, 25, 50, 100, all]"
|
data-page-list="[10, 25, 50, 100, all]"
|
||||||
data-page-size="10"
|
data-page-size="10"
|
||||||
data-pagination="true"
|
data-pagination="true"
|
||||||
@ -72,6 +74,7 @@
|
|||||||
data-show-columns-search="true"
|
data-show-columns-search="true"
|
||||||
data-show-columns-toggle-all="true"
|
data-show-columns-toggle-all="true"
|
||||||
data-show-export="true"
|
data-show-export="true"
|
||||||
|
data-show-filter-control-switch="true"
|
||||||
data-show-fullscreen="true"
|
data-show-fullscreen="true"
|
||||||
data-show-search-clear-button="true"
|
data-show-search-clear-button="true"
|
||||||
data-sortable="true"
|
data-sortable="true"
|
||||||
@ -82,14 +85,14 @@
|
|||||||
<thead class="table-primary">
|
<thead class="table-primary">
|
||||||
<tr>
|
<tr>
|
||||||
<th data-checkbox="true"></th>
|
<th data-checkbox="true"></th>
|
||||||
<th data-sortable="true" data-switchable="false" data-field="base">package base</th>
|
<th data-sortable="true" data-switchable="false" data-field="base" data-filter-control="input" data-filter-control-placeholder="(any base)">package base</th>
|
||||||
<th data-sortable="true" data-field="version">version</th>
|
<th data-sortable="true" data-field="version" data-filter-control="input" data-filter-control-placeholder="(any version)">version</th>
|
||||||
<th data-sortable="true" data-field="packages">packages</th>
|
<th data-sortable="true" data-field="packages" data-filter-control="input" data-filter-control-placeholder="(any package)">packages</th>
|
||||||
<th data-sortable="true" data-visible="false" data-field="groups">groups</th>
|
<th data-sortable="true" data-visible="false" data-field="groups" data-filter-control="select" data-filter-data="func:filterListGroups" data-filter-custom-search="filterList" data-filter-control-placeholder="(any group)">groups</th>
|
||||||
<th data-sortable="true" data-visible="false" data-field="licenses">licenses</th>
|
<th data-sortable="true" data-visible="false" data-field="licenses" data-filter-control="select" data-filter-data="func:filterListLicenses" data-filter-custom-search="filterList" data-filter-control-placeholder="(any license)">licenses</th>
|
||||||
<th data-sortable="true" data-visible="false" data-field="packager">packager</th>
|
<th data-sortable="true" data-visible="false" data-field="packager" data-filter-control="select" data-filter-custom-search="filterContains" data-filter-control-placeholder="(any packager)">packager</th>
|
||||||
<th data-sortable="true" data-field="timestamp">last update</th>
|
<th data-sortable="true" data-field="timestamp" data-filter-control="input" data-filter-custom-search="filterDateRange" data-filter-control-placeholder="(any date)">last update</th>
|
||||||
<th data-sortable="true" data-cell-style="statusFormat" data-field="status">status</th>
|
<th data-sortable="true" data-cell-style="statusFormat" data-field="status" data-filter-control="select" data-filter-control-placeholder="(any status)">status</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
</table>
|
</table>
|
||||||
|
@ -84,7 +84,7 @@
|
|||||||
showSuccess("Success", `Key ${key} has been imported`);
|
showSuccess("Success", `Key ${key} has been imported`);
|
||||||
},
|
},
|
||||||
error: (jqXHR, _, errorThrown) => {
|
error: (jqXHR, _, errorThrown) => {
|
||||||
const message = _ => { return `Could not import key ${key} from ${server}`; };
|
const message = _ => `Could not import key ${key} from ${server}`;
|
||||||
showFailure("Action failed", message, jqXHR, errorThrown);
|
showFailure("Action failed", message, jqXHR, errorThrown);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
@ -60,8 +60,8 @@
|
|||||||
const packages = packageInput.val();
|
const packages = packageInput.val();
|
||||||
if (packages) {
|
if (packages) {
|
||||||
packageAddModal.modal("hide");
|
packageAddModal.modal("hide");
|
||||||
const onSuccess = update => { return `Packages ${update} have been added`; };
|
const onSuccess = update => `Packages ${update} have been added`;
|
||||||
const onFailure = error => { return `Package addition failed: ${error}`; };
|
const onFailure = error => `Package addition failed: ${error}`;
|
||||||
doPackageAction("/api/v1/service/add", [packages], onSuccess, onFailure);
|
doPackageAction("/api/v1/service/add", [packages], onSuccess, onFailure);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -70,8 +70,8 @@
|
|||||||
const packages = packageInput.val();
|
const packages = packageInput.val();
|
||||||
if (packages) {
|
if (packages) {
|
||||||
packageAddModal.modal("hide");
|
packageAddModal.modal("hide");
|
||||||
const onSuccess = update => { return `Packages ${update} have been requested`; };
|
const onSuccess = update => `Packages ${update} have been requested`;
|
||||||
const onFailure = error => { return `Package request failed: ${error}`; };
|
const onFailure = error => `Package request failed: ${error}`;
|
||||||
doPackageAction("/api/v1/service/request", [packages], onSuccess, onFailure);
|
doPackageAction("/api/v1/service/request", [packages], onSuccess, onFailure);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -61,7 +61,7 @@
|
|||||||
error: (jqXHR, _, errorThrown) => {
|
error: (jqXHR, _, errorThrown) => {
|
||||||
// show failed modal in case if first time loading
|
// show failed modal in case if first time loading
|
||||||
if (isPackageBaseSet) {
|
if (isPackageBaseSet) {
|
||||||
const message = error => { return `Could not load package ${packageBase} logs: ${error}`; };
|
const message = error => `Could not load package ${packageBase} logs: ${error}`;
|
||||||
showFailure("Load failure", message, jqXHR, errorThrown);
|
showFailure("Load failure", message, jqXHR, errorThrown);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -33,8 +33,8 @@
|
|||||||
const packages = dependencyInput.val();
|
const packages = dependencyInput.val();
|
||||||
if (packages) {
|
if (packages) {
|
||||||
packageRebuildModal.modal("hide");
|
packageRebuildModal.modal("hide");
|
||||||
const onSuccess = update => { return `Repository rebuild has been run for packages which depend on ${update}`; };
|
const onSuccess = update => `Repository rebuild has been run for packages which depend on ${update}`;
|
||||||
const onFailure = error => { return `Repository rebuild failed: ${error}`; };
|
const onFailure = error => `Repository rebuild failed: ${error}`;
|
||||||
doPackageAction("/api/v1/service/rebuild", [packages], onSuccess, onFailure);
|
doPackageAction("/api/v1/service/rebuild", [packages], onSuccess, onFailure);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -15,6 +15,25 @@
|
|||||||
table.bootstrapTable(method, {field: "id", values: [data.id]});
|
table.bootstrapTable(method, {field: "id", values: [data.id]});
|
||||||
} else showLogs(data.id);
|
} else showLogs(data.id);
|
||||||
});
|
});
|
||||||
|
table.on("created-controls.bs.table", () => {
|
||||||
|
const pickerInput = $(".bootstrap-table-filter-control-timestamp");
|
||||||
|
pickerInput.daterangepicker({
|
||||||
|
autoUpdateInput: false,
|
||||||
|
locale: {
|
||||||
|
cancelLabel: "Clear",
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
pickerInput.on("apply.daterangepicker", (event, picker) => {
|
||||||
|
pickerInput.val(`${picker.startDate.format("YYYY-MM-DD")} - ${picker.endDate.format("YYYY-MM-DD")}`);
|
||||||
|
table.bootstrapTable("triggerSearch");
|
||||||
|
});
|
||||||
|
|
||||||
|
pickerInput.on("cancel.daterangepicker", () => {
|
||||||
|
pickerInput.val("");
|
||||||
|
table.bootstrapTable("triggerSearch");
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
const repositoryBadge = $("#badge-repository");
|
const repositoryBadge = $("#badge-repository");
|
||||||
const statusBadge = $("#badge-status");
|
const statusBadge = $("#badge-status");
|
||||||
@ -37,21 +56,21 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
function getSelection() {
|
function getSelection() {
|
||||||
return table.bootstrapTable("getSelections").map(row => { return row.id; });
|
return table.bootstrapTable("getSelections").map(row => row.id);
|
||||||
}
|
}
|
||||||
|
|
||||||
function removePackages() {
|
function removePackages() {
|
||||||
const onSuccess = update => { return `Packages ${update} have been removed`; };
|
const onSuccess = update => `Packages ${update} have been removed`;
|
||||||
const onFailure = error => { return `Could not remove packages: ${error}`; };
|
const onFailure = error => `Could not remove packages: ${error}`;
|
||||||
doPackageAction("/api/v1/service/remove", getSelection(), onSuccess, onFailure);
|
doPackageAction("/api/v1/service/remove", getSelection(), onSuccess, onFailure);
|
||||||
}
|
}
|
||||||
|
|
||||||
function updatePackages() {
|
function updatePackages() {
|
||||||
const currentSelection = getSelection();
|
const currentSelection = getSelection();
|
||||||
const [url, onSuccess] = currentSelection.length === 0
|
const [url, onSuccess] = currentSelection.length === 0
|
||||||
? ["/api/v1/service/update", _ => { return "Repository update has been run"; }]
|
? ["/api/v1/service/update", _ => "Repository update has been run"]
|
||||||
: ["/api/v1/service/add", update => { return `Run update for packages ${update}`; }];
|
: ["/api/v1/service/add", update => `Run update for packages ${update}`];
|
||||||
const onFailure = error => { return `Packages update failed: ${error}`; };
|
const onFailure = error => `Packages update failed: ${error}`;
|
||||||
doPackageAction(url, currentSelection, onSuccess, onFailure);
|
doPackageAction(url, currentSelection, onSuccess, onFailure);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -81,13 +100,13 @@
|
|||||||
success: response => {
|
success: response => {
|
||||||
const extractListProperties = (description, property) => {
|
const extractListProperties = (description, property) => {
|
||||||
return Object.values(description.packages)
|
return Object.values(description.packages)
|
||||||
.map(pkg => { return pkg[property]; })
|
.map(pkg => pkg[property])
|
||||||
.reduce((left, right) => { return left.concat(right); }, []);
|
.reduce((left, right) => left.concat(right), []);
|
||||||
};
|
};
|
||||||
const listToTable = data => {
|
const listToTable = data => {
|
||||||
return Array.from(new Set(data))
|
return Array.from(new Set(data))
|
||||||
.sort()
|
.sort()
|
||||||
.map(entry => { return safe(entry); })
|
.map(entry => safe(entry))
|
||||||
.join("<br>");
|
.join("<br>");
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -121,7 +140,7 @@
|
|||||||
table.bootstrapTable("hideLoading");
|
table.bootstrapTable("hideLoading");
|
||||||
} else {
|
} else {
|
||||||
// other errors
|
// other errors
|
||||||
const message = error => { return `Could not load list of packages: ${error}`; };
|
const message = error => `Could not load list of packages: ${error}`;
|
||||||
showFailure("Load failure", message, jqXHR, errorThrown);
|
showFailure("Load failure", message, jqXHR, errorThrown);
|
||||||
}
|
}
|
||||||
hideControls(true);
|
hideControls(true);
|
||||||
@ -158,6 +177,18 @@
|
|||||||
return {classes: cellClass(value)};
|
return {classes: cellClass(value)};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function filterListGroups() {
|
||||||
|
return extractDataList(table.bootstrapTable("getData"), "groups");
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterListLicenses() {
|
||||||
|
return extractDataList(table.bootstrapTable("getData"), "licenses");
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterListPackagers() {
|
||||||
|
return extractDataList(table.bootstrapTable("getData"), "packager");
|
||||||
|
}
|
||||||
|
|
||||||
$(() => {
|
$(() => {
|
||||||
table.bootstrapTable({});
|
table.bootstrapTable({});
|
||||||
statusBadge.popover();
|
statusBadge.popover();
|
||||||
|
@ -31,6 +31,8 @@ SigLevel = Database{% if has_repo_signed %}Required{% else %}Never{% endif %} Pa
|
|||||||
<div class="container">
|
<div class="container">
|
||||||
<table id="packages" class="table table-striped table-hover"
|
<table id="packages" class="table table-striped table-hover"
|
||||||
data-export-options='{"fileName": "packages"}'
|
data-export-options='{"fileName": "packages"}'
|
||||||
|
data-filter-control="true"
|
||||||
|
data-filter-control-visible="false"
|
||||||
data-page-list="[10, 25, 50, 100, all]"
|
data-page-list="[10, 25, 50, 100, all]"
|
||||||
data-page-size="10"
|
data-page-size="10"
|
||||||
data-pagination="true"
|
data-pagination="true"
|
||||||
@ -40,6 +42,7 @@ SigLevel = Database{% if has_repo_signed %}Required{% else %}Never{% endif %} Pa
|
|||||||
data-show-columns-search="true"
|
data-show-columns-search="true"
|
||||||
data-show-columns-toggle-all="true"
|
data-show-columns-toggle-all="true"
|
||||||
data-show-export="true"
|
data-show-export="true"
|
||||||
|
data-show-filter-control-switch="true"
|
||||||
data-show-fullscreen="true"
|
data-show-fullscreen="true"
|
||||||
data-show-search-clear-button="true"
|
data-show-search-clear-button="true"
|
||||||
data-sortable="true"
|
data-sortable="true"
|
||||||
@ -48,17 +51,17 @@ SigLevel = Database{% if has_repo_signed %}Required{% else %}Never{% endif %} Pa
|
|||||||
data-toggle="table">
|
data-toggle="table">
|
||||||
<thead class="table-primary">
|
<thead class="table-primary">
|
||||||
<tr>
|
<tr>
|
||||||
<th data-sortable="true" data-switchable="false">package</th>
|
<th data-sortable="true" data-switchable="false" data-field="name" data-filter-control="input" data-filter-control-placeholder="(any package)">package</th>
|
||||||
<th data-sortable="true">version</th>
|
<th data-sortable="true" data-field="version" data-filter-control="input" data-filter-control-placeholder="(any version)">version</th>
|
||||||
<th data-sortable="true" data-visible="false">architecture</th>
|
<th data-sortable="true" data-visible="false" data-field="architecture" data-filter-control="select" data-filter-control-placeholder="(any arch)">architecture</th>
|
||||||
<th data-sortable="true" data-visible="false">description</th>
|
<th data-sortable="true" data-visible="false" data-field="description" data-filter-control="input" data-filter-control-placeholder="(any description)">description</th>
|
||||||
<th data-sortable="true" data-visible="false">upstream url</th>
|
<th data-sortable="true" data-visible="false" data-field="url">upstream url</th>
|
||||||
<th data-sortable="true" data-visible="false">licenses</th>
|
<th data-sortable="true" data-visible="false" data-field="licenses" data-filter-control="select" data-filter-data="func:filterListLicenses" data-filter-custom-search="filterList" data-filter-control-placeholder="(any license)">licenses</th>
|
||||||
<th data-sortable="true" data-visible="false">groups</th>
|
<th data-sortable="true" data-visible="false" data-field="groups" data-filter-control="select" data-filter-data="func:filterListGroups" data-filter-custom-search="filterList" data-filter-control-placeholder="(any group)">groups</th>
|
||||||
<th data-sortable="true" data-visible="false">depends</th>
|
<th data-sortable="true" data-visible="false" data-field="depends" data-filter-control="select" data-filter-data="func:filterListDepends" data-filter-custom-search="filterList" data-filter-control-placeholder="(any depends)">depends</th>
|
||||||
<th data-sortable="true">archive size</th>
|
<th data-sortable="true" data-field="archive_size">archive size</th>
|
||||||
<th data-sortable="true">installed size</th>
|
<th data-sortable="true" data-field="installed_size">installed size</th>
|
||||||
<th data-sortable="true">build date</th>
|
<th data-sortable="true" data-field="timestamp" data-filter-control="input" data-filter-custom-search="filterDateRange" data-filter-control-placeholder="(any date)">build date</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
|
|
||||||
@ -96,6 +99,27 @@ SigLevel = Database{% if has_repo_signed %}Required{% else %}Never{% endif %} Pa
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
|
const table = $("#packages");
|
||||||
|
table.on("created-controls.bs.table", () => {
|
||||||
|
const pickerInput = $(".bootstrap-table-filter-control-timestamp");
|
||||||
|
pickerInput.daterangepicker({
|
||||||
|
autoUpdateInput: false,
|
||||||
|
locale: {
|
||||||
|
cancelLabel: "Clear",
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
pickerInput.on("apply.daterangepicker", (event, picker) => {
|
||||||
|
pickerInput.val(`${picker.startDate.format("YYYY-MM-DD")} - ${picker.endDate.format("YYYY-MM-DD")}`);
|
||||||
|
table.bootstrapTable("triggerSearch");
|
||||||
|
});
|
||||||
|
|
||||||
|
pickerInput.on("cancel.daterangepicker", () => {
|
||||||
|
pickerInput.val("");
|
||||||
|
table.bootstrapTable("triggerSearch");
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
const pacmanConf = $("#pacman-conf");
|
const pacmanConf = $("#pacman-conf");
|
||||||
const pacmanConfCopyButton = $("#copy-btn");
|
const pacmanConfCopyButton = $("#copy-btn");
|
||||||
|
|
||||||
@ -103,6 +127,18 @@ SigLevel = Database{% if has_repo_signed %}Required{% else %}Never{% endif %} Pa
|
|||||||
const conf = pacmanConf.text();
|
const conf = pacmanConf.text();
|
||||||
await copyToClipboard(conf, pacmanConfCopyButton);
|
await copyToClipboard(conf, pacmanConfCopyButton);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function filterListDepends() {
|
||||||
|
return extractDataList(table.bootstrapTable("getData"), "depends");
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterListGroups() {
|
||||||
|
return extractDataList(table.bootstrapTable("getData"), "groups");
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterListLicenses() {
|
||||||
|
return extractDataList(table.bootstrapTable("getData"), "licenses");
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
</body>
|
</body>
|
||||||
|
@ -1,16 +1,21 @@
|
|||||||
<script src="https://cdn.jsdelivr.net/npm/jquery/dist/jquery.min.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/jquery@3.7.0/dist/jquery.min.js" integrity="sha384-NXgwF8Kv9SSAr+jemKKcbvQsz+teULH/a5UNJvZc6kP47hZgl62M1vGnw6gHQhb1" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
<script src="https://unpkg.com/tableexport.jquery.plugin/tableExport.min.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/moment@2.29.4/moment.min.js" integrity="sha384-8hHkOkbWN1TLWwet/jpbJ0zbx3FJDeYJgQ8dX1mRrv/vfCfHCqFSFZYCgaMML3z9" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/daterangepicker@3.1.0/daterangepicker.min.js" integrity="sha384-u4eJN1VWrTf/FnYYQJo2kqJyVxEQf5UmWY4iUcNAoLenOEtEuCkfwc5bKvZOWBi5" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
<script src="https://unpkg.com/jquery-resizable-columns@0.2.3/dist/jquery.resizableColumns.min.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/tableexport.jquery.plugin@1.28.0/tableExport.min.js" integrity="sha384-1Rz4Kz/y1rSWw+ZsjTcxB684XgofbO8iizY+UFIzCwFeQ+QUyhBNWBMh/STOyomI" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
<script src="https://cdn.jsdelivr.net/npm/@popperjs/core@2.11.6/dist/umd/popper.min.js" integrity="sha384-oBqDVmMz9ATKxIep9tiCxS/Z9fNfEXiDAYTujMAeBAsjFuCZSmKbSSUnQlmh/jp3" crossorigin="anonymous"></script>
|
<script src="https://cdn.jsdelivr.net/npm/jquery-resizable-columns@0.2.3/dist/jquery.resizableColumns.min.js" integrity="sha384-IazMVNyYoUNx6357fWJoqtHYUWWCNHIXxFVtbpVgvImQNWuRP2WbHPaIb3QF8j97" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.2.2/dist/js/bootstrap.min.js" integrity="sha384-IDwe1+LCz02ROU9k972gdyvl+AESN10+x7tBKgc9I5HFtuNz0wWnPclzo6p9vxnk" crossorigin="anonymous"></script>
|
|
||||||
<script src="https://unpkg.com/bootstrap-table@1.21.1/dist/bootstrap-table.min.js"></script>
|
|
||||||
|
|
||||||
<script src="https://unpkg.com/bootstrap-table@1.21.1/dist/extensions/export/bootstrap-table-export.min.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/@popperjs/core@2.11.8/dist/umd/popper.min.js" integrity="sha384-I7E8VVD/ismYTF4hNIPjVp/Zjvgyol6VFvRkX/vR+Vc4jQkC+hVqc2pM8ODewa9r" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.2.3/dist/js/bootstrap.min.js" integrity="sha384-cuYeSxntonz0PPNlHhBs68uyIAVpIIOZZ5JqeqvYYIcEL727kskC66kF92t6Xl2V" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap-table@1.22.1/dist/bootstrap-table.min.js" integrity="sha384-GVLHfbEvuGA/RFiQ3MK2ClEJkWYJXABg55t9LpoDPZFGIsSq8xhFlQydm5poV2jW" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
<script src="https://unpkg.com/bootstrap-table@1.21.1/dist/extensions/resizable/bootstrap-table-resizable.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap-table@1.21.4/dist/extensions/export/bootstrap-table-export.min.js" integrity="sha384-jeldDadm+qM2RwGER3qVqxFgWVpAEJ7Jie+0rlYj8ni3KkQA654T8TSXDtol022X" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap-table@1.21.4/dist/extensions/resizable/bootstrap-table-resizable.js" integrity="sha384-wd8Vc6Febikdnsnk9vthRWRvMwffw246vhqiqNO3aSNe1maTEA07Vh3zAQiSyDji" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap-table@1.21.4/dist/extensions/filter-control/bootstrap-table-filter-control.js" integrity="sha384-B6xNXlSOaOFxjlKo9OW3htbox+9/DcaEcjPPEi1+pTMwH5Tzc/s2wNTYriHz7Tb8" crossorigin="anonymous" type="application/javascript"></script>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
async function copyToClipboard(text, button) {
|
async function copyToClipboard(text, button) {
|
||||||
@ -38,4 +43,28 @@
|
|||||||
.replace(/>/g, ">")
|
.replace(/>/g, ">")
|
||||||
.replace(/"/g, """);
|
.replace(/"/g, """);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function extractDataList(data, column) {
|
||||||
|
const elements = data.flatMap(row => row[column].split("<br>")).filter(v => v); // remove empty elements from array
|
||||||
|
return Array.from(new Set(elements)).sort();
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterContains(text, value) {
|
||||||
|
return value.includes(text.toLowerCase().trim());
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterDateRange(text, value) {
|
||||||
|
const asOfStartOfDay = date => date.setUTCHours(0, 0, 0, 0);
|
||||||
|
|
||||||
|
const [minDate, maxDate] = text.split(" - ");
|
||||||
|
const buildDate = asOfStartOfDay(new Date(value));
|
||||||
|
|
||||||
|
return (buildDate >= asOfStartOfDay(new Date(minDate))) && (buildDate <= asOfStartOfDay(new Date(maxDate)));
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterList(index, value, field, data) {
|
||||||
|
const dataList = extractDataList(data, field);
|
||||||
|
// the library removes all symbols from string, so it is just string
|
||||||
|
return value.includes(dataList[index].toLowerCase());
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
@ -1,11 +1,15 @@
|
|||||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@5.2.2/dist/css/bootstrap.min.css" integrity="sha384-Zenh87qX5JnK2Jl0vWa8Ck2rdkQ2Bzep5IDxbcnCeuOxjzrPF/et3URy9Bv1WTRi" crossorigin="anonymous" type="text/css">
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@5.2.3/dist/css/bootstrap.min.css" integrity="sha384-rbsA2VBKQhggwzxH7pPCaAqO46MgnOM80zW1RWuH61DGLwZJEdK2Kadq2F9CUG65" crossorigin="anonymous" type="text/css">
|
||||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.10.2/font/bootstrap-icons.css" type="text/css">
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.10.4/font/bootstrap-icons.css" integrity="sha384-LrVLJJYk9OiJmjNDakUBU7kS9qCT8wk1j2OU7ncpsfB3QS37UPdkCuq3ZD1MugNY" crossorigin="anonymous" type="text/css">
|
||||||
|
|
||||||
<link rel="stylesheet" href="https://unpkg.com/bootstrap-table@1.21.1/dist/bootstrap-table.min.css" type="text/css">
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-table@1.21.4/dist/bootstrap-table.min.css" integrity="sha384-pTEAhytv7JmEG2D7qiW5gY0lI5EKZ9n3CNmj6Qp+U3qhnmH2qnnN9KJbVwbtMHN0" crossorigin="anonymous" type="text/css">
|
||||||
|
|
||||||
<link rel="stylesheet" href="https://unpkg.com/jquery-resizable-columns@0.2.3/dist/jquery.resizableColumns.css" type="text/css">
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/jquery-resizable-columns@0.2.3/dist/jquery.resizableColumns.css" integrity="sha384-1sLxvR8mXzjhvFY9f8mzXl97DNLepeZ0PnRiMMdm/rQsKjsrPZPJxYle2wwT2PMg" crossorigin="anonymous" type="text/css">
|
||||||
|
|
||||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootswatch@5.2.2/dist/cosmo/bootstrap.min.css" integrity="sha256-5t++JZpgVLzo9vF7snO5Qw0y3fA5/NkoJENWB7kpg0E=" crossorigin="anonymous" type="text/css">
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-table@1.21.4/dist/extensions/filter-control/bootstrap-table-filter-control.css" integrity="sha384-4Glx18jZ0Un+yDG6KUpYJ/af8hkssJ02jRASuFv23gfCl0mTXaVMPI9cB4cn3GvE" crossorigin="anonymous" type="text/css">
|
||||||
|
|
||||||
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootswatch@5.2.3/dist/cosmo/bootstrap.min.css" integrity="sha384-P1PBFVifKf1Ww0gS5B8A0siIeDpcFd4uU7S68LA1XMdE0R+y1WN3DR4HcLc9csRC" crossorigin="anonymous" type="text/css">
|
||||||
|
|
||||||
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/daterangepicker@3.1.0/daterangepicker.css" integrity="sha384-zLkQsiLfAQqGeIJeKLC+rcCR1YoYaQFLCL7cLDUoKE1ajKJzySpjzWGfYS2vjSG+" crossorigin="anonymous" type="text/css">
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
.pre-scrollable {
|
.pre-scrollable {
|
||||||
|
Loading…
Reference in New Issue
Block a user