add home format for Vue.js vuilder

This commit is contained in:
Jordan Blasenhauer 2024-06-06 11:44:35 +02:00
parent 72916d2b60
commit 58b9ff2351
3 changed files with 198 additions and 36 deletions

View file

@ -614,6 +614,139 @@ def totp():
return render_template("totp.html")
def home_builder(data):
"""
It returns the home page in JSON format for the Vue.js builder
"""
version_card = {
"type": "card",
"link": "https://panel.bunkerweb.io/?utm_campaign=self&utm_source=ui#pro",
"containerColumns": {"pc": 4, "tablet": 6, "mobile": 12},
"widgets": [
{
"type": "Stat",
"data": {
"title": "home_version",
"subtitle": (
"home_all_features_available"
if data.get("is_pro_version")
else (
"home_awaiting_compliance"
if data.get("pro_status") == "active" and data.get("pro_overlapped")
else (
"home_renew_license"
if data.get("pro_status") == "expired"
else "home_talk_to_team" if data.get("pro_status") == "suspended" else "home_upgrade_to_pro"
)
)
),
"subtitleColor": "success" if data.get("is_pro_version") else "warning",
"stat": (
"home_pro"
if data.get("is_pro_version")
else (
"home_pro_locked"
if data.get("pro_status") == "active" and data.get("pro_overlapped")
else (
"home_expired"
if data.get("pro_status") == "expired"
else "home_suspended" if data.get("pro_status") == "suspended" else "home_free"
)
)
),
"iconName": "crown" if data.get("is_pro_version") else "key",
"iconColor": "amber" if data.get("is_pro_version") else "green",
},
}
],
}
version_num_card = {
"type": "card",
"link": "https://github.com/bunkerity/bunkerweb",
"containerColumns": {"pc": 4, "tablet": 6, "mobile": 12},
"widgets": [
{
"type": "Stat",
"data": {
"title": "home_version_number",
"subtitle": (
"home_couldnt_find_remote"
if not data.get("remote_version")
else "home_latest_version" if data.get("remote_version") and data.get("check_version") else "home_update_available"
),
"subtitleColor": (
"error" if not data.get("remote_version") else "success" if data.get("remote_version") and data.get("check_version") else "warning"
),
"stat": data.get("version"),
"iconName": "wire",
"iconColor": "teal",
},
}
],
}
instances_card = {
"type": "card",
"link": "/instances",
"containerColumns": {"pc": 4, "tablet": 6, "mobile": 12},
"widgets": [
{
"type": "Stat",
"data": {
"title": "home_instances",
"subtitle": "home_total_number",
"subtitleColor": "info",
"stat": data.get("instances_number"),
"iconName": "box",
"iconColor": "dark",
},
}
],
}
services_card = {
"type": "card",
"link": "/services",
"containerColumns": {"pc": 4, "tablet": 6, "mobile": 12},
"widgets": [
{
"type": "Stat",
"data": {
"title": "home_services",
"subtitle": "home_all_methods_included",
"subtitleColor": "info",
"stat": data.get("services_number"),
"iconName": "disk",
"iconColor": "orange",
},
}
],
}
plugins_card = {
"type": "card",
"link": "/plugins",
"containerColumns": {"pc": 4, "tablet": 6, "mobile": 12},
"widgets": [
{
"type": "Stat",
"data": {
"title": "home_plugins",
"subtitle": "home_errors_found" if data.get("plugins_errors") > 0 else "home_no_error",
"subtitleColor": "error" if data.get("plugins_errors") > 0 else "success",
"stat": "42",
"iconName": "puzzle",
"iconColor": "yellow",
},
}
],
}
builder = [version_card, version_num_card, instances_card, services_card, plugins_card]
return builder
@app.route("/home")
@login_required
def home():
@ -638,7 +771,8 @@ def home():
remote_version = basename(r.url).strip().replace("v", "")
config = app.config["CONFIG"].get_config(with_drafts=True)
instances = app.config["INSTANCES"].get_instances()
override_instances = config["OVERRIDE_INSTANCES"]["value"] != ""
instances = app.config["INSTANCES"].get_instances(override_instances=override_instances)
instance_health_count = 0
@ -662,6 +796,34 @@ def home():
services_autoconf_count += 1
services += 1
metadata = app.config["DB"].get_metadata()
is_pro_version = metadata["is_pro"]
pro_status = metadata["pro_status"]
pro_services = metadata["pro_services"]
pro_overlapped = metadata["pro_overlapped"]
bw_version = metadata["version"]
data = {
"check_version": not remote_version or bw_version == remote_version,
"remote_version": remote_version,
"version": bw_version,
"instances_number": len(instances),
"services_number": services,
"instance_health_count": instance_health_count,
"services_scheduler_count": services_scheduler_count,
"services_ui_count": services_ui_count,
"services_autoconf_count": services_autoconf_count,
"is_pro_version": is_pro_version,
"pro_status": pro_status,
"pro_services": pro_services,
"pro_overlapped": pro_overlapped,
"plugins_number": len(app.config["CONFIG"].get_plugins()),
"plugins_errors": app.config["DB"].get_plugins_errors(),
}
data_server_builder = home_builder(data)
return render_template(
"home.html",
check_version=not remote_version or bw_version == remote_version,

View file

@ -85,7 +85,7 @@ class News {
) {
sessionStorage.setItem(
"lastRefetch",
Math.round(new Date().getTime() / 1000) + 3600
Math.round(new Date().getTime() / 1000) + 3600,
);
sessionStorage.setItem("lastNews", JSON.stringify(lastNews));
}
@ -102,7 +102,7 @@ class News {
news.photo.url,
news.excerpt,
news.tags,
news.date
news.date,
);
const BASE_URL = this.BASE_URL;
let cleanHTML = DOMPurify.sanitize(cardHTML);
@ -114,7 +114,7 @@ class News {
slug.addEventListener("click", function () {
window.open(
`${BASE_URL}blog/post/${news.slug}?utm_campaign=self&utm_source=ui`,
"_blank"
"_blank",
);
});
});
@ -268,7 +268,7 @@ class FlashMsg {
if (Number(this.flashCount.textContent) > 0) this.animeBtn();
// display only one fixed flash message
const flashFixedEls = document.querySelectorAll(
"[data-flash-message-fixed]"
"[data-flash-message-fixed]",
);
if (flashFixedEls.length > 1) {
flashFixedEls.forEach((el, i) => {
@ -298,7 +298,7 @@ class FlashMsg {
flashEl.remove();
//update count
this.flashCount.textContent = document.querySelectorAll(
"[data-flash-message]"
"[data-flash-message]",
).length;
}
} catch (err) {}
@ -401,7 +401,7 @@ class Banner {
// Try to get data from api
if (sessionStorage.getItem("bannerNews") !== null) {
return this.updateBanner(
JSON.parse(sessionStorage.getItem("bannerNews"))
JSON.parse(sessionStorage.getItem("bannerNews")),
);
}
fetch("https://www.bunkerweb.io/api/bw-ui-news")
@ -413,7 +413,7 @@ class Banner {
// Refetch after one hour
sessionStorage.setItem(
"bannerRefetch",
Math.round(new Date().getTime() / 1000) + 3600
Math.round(new Date().getTime() / 1000) + 3600,
);
return this.updateBanner(res.data[0].data);
})
@ -446,7 +446,7 @@ class Banner {
this.bannerEl.querySelector(
`[role="listitem"][data-id="${
+visibleEl.getAttribute("data-id") + 1
}"]`
}"]`,
) || this.bannerEl.querySelector(`[role="listitem"][data-id="0"]`);
// Hide current one
@ -538,7 +538,7 @@ class Clipboard {
if (result.state === "granted" || result.state === "prompt") {
/* write to the clipboard now */
const copyEl = document.querySelector(
e.target.getAttribute("data-clipboard-target")
e.target.getAttribute("data-clipboard-target"),
);
copyEl.select();
@ -560,7 +560,7 @@ class Clipboard {
if (!this.isCopy) {
/* write to the clipboard now */
const copyEl = document.querySelector(
e.target.getAttribute("data-clipboard-target")
e.target.getAttribute("data-clipboard-target"),
);
copyEl.select();
@ -579,7 +579,7 @@ class Clipboard {
if (!this.isCopy) {
/* write to the clipboard now */
const copyEl = document.querySelector(
e.target.getAttribute("data-clipboard-target")
e.target.getAttribute("data-clipboard-target"),
);
copyEl.select();
@ -611,7 +611,7 @@ class Clipboard {
"opacity-0",
"transition-opacity",
"duration-300",
this.isCopy ? "bg-green-500" : "bg-red-500"
this.isCopy ? "bg-green-500" : "bg-red-500",
);
feedbackEl.textContent = this.isCopy ? "Copied!" : "Error!";
btn.appendChild(feedbackEl);
@ -642,13 +642,13 @@ const setMenu = new Menu();
const setNewsSidebar = new Sidebar(
"[data-sidebar-info]",
"[data-sidebar-info-open]",
"[data-sidebar-info-close]"
"[data-sidebar-info-close]",
);
const setFlashSidebar = new Sidebar(
"[data-flash-sidebar]",
"[data-flash-sidebar-open]",
"[data-flash-sidebar-close]"
"[data-flash-sidebar-close]",
);
const setClipboard = new Clipboard();

View file

@ -2,7 +2,7 @@ class FolderNav {
constructor(prefix) {
this.prefix = prefix;
this.breadContainer = document.querySelector(
`[data-${this.prefix}-breadcrumb]`
`[data-${this.prefix}-breadcrumb]`,
);
this.container = document.querySelector(`[data-${this.prefix}-container]`);
this.isReadonly =
@ -12,11 +12,11 @@ class FolderNav {
? true
: false;
this.listContainer = document.querySelector(
`[data-${this.prefix}-folders]`
`[data-${this.prefix}-folders]`,
);
this.els = document.querySelectorAll(`div[data-${this.prefix}-element]`);
this.files = document.querySelectorAll(
`div[data-${this.prefix}-element][data-_type='file']`
`div[data-${this.prefix}-element][data-_type='file']`,
);
this.addFileEl = document.querySelector(`[data-${this.prefix}-add-file]`);
this.initSorted();
@ -91,8 +91,8 @@ class FolderNav {
this.removeBreadElByLvl(+prevLvl);
const folder = document.querySelector(
`div[data-${this.prefix}-element][data-path='${item.getAttribute(
"data-path"
)}']`
"data-path",
)}']`,
);
this.updateActions(folder);
}
@ -113,7 +113,7 @@ class FolderNav {
showCurrentFolderEls(path, lvl) {
const nestedEl = document.querySelectorAll(
`div[data-path^="${path}/"][data-level="${+lvl + 1}"]`
`div[data-path^="${path}/"][data-level="${+lvl + 1}"]`,
);
for (let i = 0; i < nestedEl.length; i++) {
const el = nestedEl[i];
@ -157,7 +157,7 @@ class FolderNav {
//the clicked bread item
removeBreadElByLvl(lvl) {
const breadcrumbItem = this.breadContainer.querySelectorAll(
`[data-${this.prefix}-breadcrumb-item]`
`[data-${this.prefix}-breadcrumb-item]`,
);
breadcrumbItem.forEach((item) => {
if (
@ -216,7 +216,7 @@ class FolderDropdown {
this.prefix = prefix;
this.container = document.querySelector(`[data-${this.prefix}-container]`);
this.dropEls = document.querySelectorAll(
`[data-${this.prefix}-action-dropdown]`
`[data-${this.prefix}-action-dropdown]`,
);
this.init();
}
@ -262,7 +262,7 @@ class FolderDropdown {
.closest("button")
.getAttribute(`data-${this.prefix}-action-dropdown-btn`);
const dropEl = document.querySelector(
`[data-${this.prefix}-action-dropdown="${att}"]`
`[data-${this.prefix}-action-dropdown="${att}"]`,
);
this.hideDrop(dropEl);
}
@ -346,33 +346,33 @@ class FolderModal {
: false;
//add service/file elements
this.breadContainer = document.querySelector(
`[data-${this.prefix}-breadcrumb]`
`[data-${this.prefix}-breadcrumb]`,
);
this.addConfContainer = document.querySelector(
`[data-${this.prefix}-add-container]`
`[data-${this.prefix}-add-container]`,
);
//modal DOM elements
this.form = document.querySelector(`[data-${this.prefix}-modal-form]`);
this.modalEl = document.querySelector(`[data-${this.prefix}-modal]`);
this.modalTitle = this.modalEl.querySelector(
`[data-${this.prefix}-modal-title]`
`[data-${this.prefix}-modal-title]`,
);
this.modalPath = this.modalEl.querySelector(
`[data-${this.prefix}-modal-path]`
`[data-${this.prefix}-modal-path]`,
);
this.modalEditor = this.modalEl.querySelector(
`[data-${this.prefix}-modal-editor]`
`[data-${this.prefix}-modal-editor]`,
);
this.modalPathPrev = this.modalPath.querySelector(
`p[data-${this.prefix}-modal-path-prefix]`
`p[data-${this.prefix}-modal-path-prefix]`,
);
this.modalPathName = this.modalPath.querySelector("input");
this.modalPathSuffix = this.modalPath.querySelector(
`p[data-${this.prefix}-modal-path-suffix]`
`p[data-${this.prefix}-modal-path-suffix]`,
);
this.modalSubmit = this.modalEl.querySelector(
`[data-${this.prefix}-modal-submit]`
`[data-${this.prefix}-modal-submit]`,
);
//hidden input for backend
this.modalInpPath = this.modalEl.querySelector("#path");
@ -381,7 +381,7 @@ class FolderModal {
this.modalInpOldName = this.modalEl.querySelector("#old_name");
this.modalTxtarea = this.modalEl.querySelector("#content");
this.modalDelMsg = this.modalEl.querySelector(
`[data-${this.prefix}-modal-delete]`
`[data-${this.prefix}-modal-delete]`,
);
//HANDLERS
//modal and values logic after clicking add file/folder button
@ -411,7 +411,7 @@ class FolderModal {
"file",
"",
"",
this.getLevelFromBread()
this.getLevelFromBread(),
);
}
} catch (err) {}
@ -481,7 +481,7 @@ class FolderModal {
var element = document.createElement("a");
element.setAttribute(
"href",
"data:text/plain;charset=utf-8," + encodeURIComponent(text)
"data:text/plain;charset=utf-8," + encodeURIComponent(text),
);
element.setAttribute("download", filename);
@ -652,7 +652,7 @@ class FolderModal {
"delete-btn",
"valid-btn",
"edit-btn",
"info-btn"
"info-btn",
);
}