mirror of
https://github.com/NebulaServices/Nebula.git
synced 2025-05-16 21:10:02 -04:00
InstalledPlugins
This commit is contained in:
parent
4fe4efd95a
commit
ddca0f3038
3 changed files with 84 additions and 71 deletions
|
@ -73,6 +73,17 @@ async function setupDB(db: ModelStatic<CatalogModel>) {
|
|||
tags: ["Theme", "Simple", "Dark", "Retro"],
|
||||
payload: "retro.css",
|
||||
type: "theme"
|
||||
},
|
||||
{
|
||||
package_name: 'gyatt',
|
||||
title: 'gyatt',
|
||||
image: 'gyatt',
|
||||
author: "nebuka",
|
||||
version: "2",
|
||||
description: "e",
|
||||
tags: [ "e" ],
|
||||
payload: "gyatt.js",
|
||||
type: "plugin-page"
|
||||
}
|
||||
//To add plugins: plugin types consist of plugin-sw (workerware) & plugin-page (uv.config.inject)
|
||||
];
|
||||
|
|
|
@ -2,10 +2,11 @@
|
|||
</div>
|
||||
<div class="w-0 h-0 visibility-none hidden"> <asset-loader1 /> </div>
|
||||
<script>
|
||||
import { SettingsVals } from "@utils/values";
|
||||
import { Elements } from "@utils/index";
|
||||
import { Marketplace } from "@utils/marketplace";
|
||||
const mp = Marketplace.getInstances().next().value as Marketplace;
|
||||
type Assets = {
|
||||
import { SettingsVals } from "@utils/values";
|
||||
|
||||
type Item = {
|
||||
description: string,
|
||||
image: string,
|
||||
package_name: string,
|
||||
|
@ -17,11 +18,12 @@
|
|||
type: string,
|
||||
version: string
|
||||
}
|
||||
async function getItem(item: any) {
|
||||
|
||||
const getItem = async (item: any) => {
|
||||
try {
|
||||
const res = await fetch(new URL(`/api/packages/${item}`, window.location.origin));
|
||||
const res = await fetch(new URL(`/api/packages/${item.name}`, window.location.origin));
|
||||
const data = await res.json();
|
||||
return { ...data, package_name: item }
|
||||
return { ...data, package_name: item.name }
|
||||
}
|
||||
catch (err: any) {
|
||||
console.log(`Err in themes: ${err}`);
|
||||
|
@ -29,77 +31,77 @@
|
|||
}
|
||||
}
|
||||
|
||||
async function getAssets(mp: Marketplace) {
|
||||
const items = JSON.parse(await mp.getValueFromStore(SettingsVals.marketPlace.plugins)) || [];
|
||||
const promises = items.map(getItem);
|
||||
const dataArray = await Promise.all(promises);
|
||||
const accumulatedData = dataArray.filter((data) => data !== null);
|
||||
return accumulatedData;
|
||||
}
|
||||
const constructElements = async (item: Item, parent: HTMLDivElement, marketplace: Marketplace) => {
|
||||
const main = document.createElement("div");
|
||||
main.classList.add("rounded-3xl", "bg-navbar-color", "w-64", "flex", "flex-col", "cursor-pointer", "border-text-color");
|
||||
main.dataset.name = item.package_name
|
||||
|
||||
const attachDeleteEvent = (elem: HTMLElement, mainElem: HTMLElement, parentElem: HTMLElement, asset: Assets) => {
|
||||
elem.addEventListener("click", async () => {
|
||||
await mp.uninstallPlugin({ name: asset.package_name, type: asset.type === "page" ? "page" : "serviceWorker" })
|
||||
parentElem.removeChild(mainElem);
|
||||
});
|
||||
}
|
||||
|
||||
const createElem = (asset: Assets) => {
|
||||
const parent = document.getElementById("parent");
|
||||
const mainDiv = document.createElement("div");
|
||||
mainDiv.classList.add("rounded-3xl", "bg-navbar-color", "w-64", "flex", "flex-col", "cursor-pointer");
|
||||
const click = document.createElement("div");
|
||||
click.classList.add("w-full");
|
||||
|
||||
const clickDiv = document.createElement("div");
|
||||
clickDiv.classList.add("w-full");
|
||||
const imgDiv = document.createElement("img");
|
||||
imgDiv.classList.add("aspect-[16/9]", "rounded-t-3xl");
|
||||
imgDiv.src = `/packages/${asset.package_name}/${asset.image}`;
|
||||
imgDiv.alt = `${asset.type}-${asset.title}`;
|
||||
clickDiv.appendChild(imgDiv);
|
||||
const img = document.createElement("img");
|
||||
img.classList.add("aspect-[16/9]", "rounded-t-3xl");
|
||||
img.src = `/packages/${item.package_name}/${item.image}`;
|
||||
img.alt = `${item.type}-${item.package_name}`;
|
||||
img.loading = "lazy";
|
||||
|
||||
const info = document.createElement("div");
|
||||
info.classList.add("h-2/6", "text-center", "content-center", "p-3", "font-semibold", "items-center", "flex", "flex-col");
|
||||
|
||||
const infoDiv = document.createElement("div");
|
||||
infoDiv.classList.add("h-2/6", "text-center", "content-center", "p-3", "font-semibold", "items-center", "flex", "flex-col");
|
||||
const infoTitle = document.createElement("p");
|
||||
infoTitle.classList.add("text-2xl");
|
||||
infoTitle.innerHTML = asset.title;
|
||||
infoTitle.innerHTML = item.title;
|
||||
|
||||
const elemInfoMain = document.createElement("div");
|
||||
elemInfoMain.classList.add("flex", "flex-row");
|
||||
const deleteButton = document.createElement("div");
|
||||
deleteButton.classList.add("h-8", "w-8", "cursor-pointer");
|
||||
attachDeleteEvent(deleteButton, mainDiv, parent!, asset);
|
||||
//FUCK SVG's
|
||||
const deleteButtonSVG = `<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%" viewBox="0 0 256 256"><path fill="currentColor" d="M216 48h-40v-8a24 24 0 0 0-24-24h-48a24 24 0 0 0-24 24v8H40a8 8 0 0 0 0 16h8v144a16 16 0 0 0 16 16h128a16 16 0 0 0 16-16V64h8a8 8 0 0 0 0-16M112 168a8 8 0 0 1-16 0v-64a8 8 0 0 1 16 0Zm48 0a8 8 0 0 1-16 0v-64a8 8 0 0 1 16 0Zm0-120H96v-8a8 8 0 0 1 8-8h48a8 8 0 0 1 8 8Z" /></svg>`
|
||||
deleteButton.innerHTML= deleteButtonSVG;
|
||||
elemInfoMain.appendChild(deleteButton);
|
||||
const infoInner = document.createElement("div");
|
||||
infoInner.classList.add("flex", "flex-row");
|
||||
|
||||
const openButton = document.createElement("a");
|
||||
openButton.classList.add("h-8", "w-8", "cursor-pointer");
|
||||
openButton.href = `../catalog/package/${asset.package_name}`
|
||||
const openButtonSVG = `<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%" viewBox="0 0 256 256"><path fill="currentColor" d="M192 136v72a16 16 0 0 1-16 16H48a16 16 0 0 1-16-16V80a16 16 0 0 1 16-16h72a8 8 0 0 1 0 16H48v128h128v-72a8 8 0 0 1 16 0m32-96a8 8 0 0 0-8-8h-64a8 8 0 0 0-5.66 13.66L172.69 72l-42.35 42.34a8 8 0 0 0 11.32 11.32L184 83.31l26.34 26.35A8 8 0 0 0 224 104Z" /></svg>`
|
||||
openButton.innerHTML = openButtonSVG;
|
||||
elemInfoMain.appendChild(openButton);
|
||||
const infoInnerDelete = document.createElement("div");
|
||||
infoInnerDelete.classList.add("h-8", "w-8", "cursor-pointer");
|
||||
// This is cursed yes. SVG's SUUUCK
|
||||
infoInnerDelete.innerHTML = `<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%" viewBox="0 0 256 256"><path fill="currentColor" d="M216 48h-40v-8a24 24 0 0 0-24-24h-48a24 24 0 0 0-24 24v8H40a8 8 0 0 0 0 16h8v144a16 16 0 0 0 16 16h128a16 16 0 0 0 16-16V64h8a8 8 0 0 0 0-16M112 168a8 8 0 0 1-16 0v-64a8 8 0 0 1 16 0Zm48 0a8 8 0 0 1-16 0v-64a8 8 0 0 1 16 0Zm0-120H96v-8a8 8 0 0 1 8-8h48a8 8 0 0 1 8 8Z" /></svg>`;
|
||||
|
||||
infoDiv.appendChild(elemInfoMain);
|
||||
infoDiv.appendChild(infoTitle);
|
||||
const infoInnerOpen = document.createElement("a");
|
||||
infoInnerOpen.classList.add("h-8", "w-8", "cursor-pointer");
|
||||
infoInnerOpen.href = `../catalog/package/${item.package_name}`;
|
||||
infoInnerOpen.innerHTML = `<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%" viewBox="0 0 256 256"><path fill="currentColor" d="M192 136v72a16 16 0 0 1-16 16H48a16 16 0 0 1-16-16V80a16 16 0 0 1 16-16h72a8 8 0 0 1 0 16H48v128h128v-72a8 8 0 0 1 16 0m32-96a8 8 0 0 0-8-8h-64a8 8 0 0 0-5.66 13.66L172.69 72l-42.35 42.34a8 8 0 0 0 11.32 11.32L184 83.31l26.34 26.35A8 8 0 0 0 224 104Z" /></svg>`;
|
||||
|
||||
click.appendChild(img);
|
||||
infoInner.appendChild(infoInnerDelete);
|
||||
infoInner.appendChild(infoInnerOpen);
|
||||
info.appendChild(infoTitle);
|
||||
info.appendChild(infoInner);
|
||||
main.appendChild(click);
|
||||
main.appendChild(info);
|
||||
parent.appendChild(main);
|
||||
|
||||
|
||||
mainDiv.appendChild(clickDiv);
|
||||
mainDiv.appendChild(infoDiv);
|
||||
parent?.appendChild(mainDiv);
|
||||
console.log(mainDiv);
|
||||
Elements.attachEvent(infoInnerDelete, "click", async () => {
|
||||
await marketplace.uninstallPlugin({ name: item.package_name, type: item.type as "page" | "serviceWorker" })
|
||||
parent.removeChild(main);
|
||||
});
|
||||
}
|
||||
|
||||
//I don't actually want this to run on every page but defining a custom component is an easy way around it.
|
||||
class AssetLoader extends HTMLElement {
|
||||
constructor() {
|
||||
super();
|
||||
(async function() {
|
||||
const assets = await getAssets(Marketplace.getInstances().next().value as Marketplace);
|
||||
console.log(assets);
|
||||
assets.map((asset) => { createElem(asset); });
|
||||
})();
|
||||
|
||||
const init = async () => {
|
||||
await Marketplace.ready();
|
||||
const mp = Marketplace.getInstances().next().value!;
|
||||
const els = Elements.select([
|
||||
{ type: 'id', val: 'parent' }
|
||||
]);
|
||||
const itemsJSON = JSON.parse(await mp.getValueFromStore(SettingsVals.marketPlace.plugins)) || [];
|
||||
const filteredItems = itemsJSON.filter((dat: any) => dat.remove !== true);
|
||||
const itemPromises = filteredItems.map(getItem);
|
||||
const itemsArray = await Promise.all(itemPromises);
|
||||
return {
|
||||
items: itemsArray.filter((data) => data !== null),
|
||||
elements: els,
|
||||
marketplace: mp
|
||||
}
|
||||
}
|
||||
customElements.define('asset-loader1', AssetLoader);
|
||||
|
||||
Elements.createCustomElement("asset-loader1", async () => {
|
||||
const { items, elements, marketplace } = await init();
|
||||
const parentElem = Elements.exists<HTMLDivElement>(await elements.next());
|
||||
const promises = items.map(item => constructElements(item, parentElem, marketplace));
|
||||
await Promise.all(promises);
|
||||
});
|
||||
</script>
|
||||
|
|
|
@ -157,7 +157,7 @@ class Marketplace {
|
|||
|
||||
async uninstallPlugin(plug: Omit<Plug, "src">) {
|
||||
const items = JSON.parse(this.#storage.getVal(SettingsVals.marketPlace.plugins)) || [];
|
||||
const plugin = items.find(({ name }: { name: string }) => name === plug.name.toLowerCase());
|
||||
const plugin = items.find(({ name }: { name: string }) => name === plug.name);
|
||||
if (!plugin) return log({ type: 'error', bg: false, prefix: false, throw: true }, `Plugin: ${plug.name} is not installed!`);
|
||||
plugin.remove = true;
|
||||
this.#storage.setVal(SettingsVals.marketPlace.plugins, JSON.stringify(items));
|
||||
|
@ -170,7 +170,7 @@ class Marketplace {
|
|||
if (plugins.length === 0) return log({ type: 'info', bg: false, prefix: true }, 'No plugins to add! Exiting.');
|
||||
plugins.map(async (plugin: Plug) => {
|
||||
if (plugin.type === "page") {
|
||||
const script = await fetch(`/packages/${plugin.name.toLowerCase()}/${plugin.src}`);
|
||||
const script = await fetch(`/packages/${plugin.name}/${plugin.src}`);
|
||||
const scriptRes = await script.text();
|
||||
const evaledScript = eval(scriptRes);
|
||||
const inject = (await evaledScript()) as unknown as SWPagePlugin;
|
||||
|
@ -183,7 +183,7 @@ class Marketplace {
|
|||
});
|
||||
}
|
||||
else {
|
||||
plugins = plugins.filter(({ name }: { name: string }) => name !== plugin.name.toLowerCase());
|
||||
plugins = plugins.filter(({ name }: { name: string }) => name !== plugin.name);
|
||||
pagePlugins.push({
|
||||
remove: true,
|
||||
host: inject.host,
|
||||
|
@ -196,7 +196,7 @@ class Marketplace {
|
|||
}
|
||||
|
||||
if (plugin.type === "serviceWorker") {
|
||||
const s = await fetch(`/packages/${plugin.name.toLowerCase()}/${plugin.src}`);
|
||||
const s = await fetch(`/packages/${plugin.name}/${plugin.src}`);
|
||||
const sRes = await s.text();
|
||||
const eScript = eval(sRes);
|
||||
const inject = (await eScript()) as unknown as SWPlugin;
|
||||
|
@ -209,7 +209,7 @@ class Marketplace {
|
|||
});
|
||||
}
|
||||
else {
|
||||
plugins = plugins.filter(({ name }: { name: string }) => name !== plugin.name.toLowerCase());
|
||||
plugins = plugins.filter(({ name }: { name: string }) => name !== plugin.name);
|
||||
swPlugins.push({
|
||||
remove: true,
|
||||
function: inject.function.toString(),
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue