mirror of
https://github.com/Radiquum/YAMPD.git
synced 2025-05-20 07:39:35 +05:00
feat: multiple mod deletion
This commit is contained in:
parent
34df17d4dd
commit
01cef9a6ea
3 changed files with 96 additions and 3 deletions
|
@ -15,6 +15,7 @@ type _PACKS_ENDPOINT = {
|
||||||
type _MOD_ENDPOINT = {
|
type _MOD_ENDPOINT = {
|
||||||
addMod: string;
|
addMod: string;
|
||||||
deleteMod: string;
|
deleteMod: string;
|
||||||
|
deleteModBulk: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const PACK_ENDPOINT = (endpoint: keyof _PACK_ENDPOINT, id: string) => {
|
export const PACK_ENDPOINT = (endpoint: keyof _PACK_ENDPOINT, id: string) => {
|
||||||
|
@ -68,6 +69,7 @@ export const MOD_ENDPOINT = (
|
||||||
const _endpoints = {
|
const _endpoints = {
|
||||||
addMod: `${API}/pack/${id}/mod/add`,
|
addMod: `${API}/pack/${id}/mod/add`,
|
||||||
deleteMod: `${API}/pack/${id}/mod/${slug}/delete`,
|
deleteMod: `${API}/pack/${id}/mod/${slug}/delete`,
|
||||||
|
deleteModBulk: `${API}/pack/${id}/mods/delete`,
|
||||||
};
|
};
|
||||||
return _endpoints[endpoint];
|
return _endpoints[endpoint];
|
||||||
};
|
};
|
||||||
|
|
|
@ -10,6 +10,7 @@ import {
|
||||||
TableHeadCell,
|
TableHeadCell,
|
||||||
TableRow,
|
TableRow,
|
||||||
} from "flowbite-react";
|
} from "flowbite-react";
|
||||||
|
import { useState } from "react";
|
||||||
import { HiDownload, HiTrash } from "react-icons/hi";
|
import { HiDownload, HiTrash } from "react-icons/hi";
|
||||||
import { toast } from "react-toastify";
|
import { toast } from "react-toastify";
|
||||||
|
|
||||||
|
@ -18,6 +19,8 @@ export const ModTable = (props: {
|
||||||
updatePack: () => void;
|
updatePack: () => void;
|
||||||
packID: string;
|
packID: string;
|
||||||
}) => {
|
}) => {
|
||||||
|
const [selectedMods, setSelectedMods] = useState<string[]>([]);
|
||||||
|
|
||||||
async function deleteMod(slug: string, title: string) {
|
async function deleteMod(slug: string, title: string) {
|
||||||
if (!window) return;
|
if (!window) return;
|
||||||
if (window.confirm(`Delete mod ${title}?`)) {
|
if (window.confirm(`Delete mod ${title}?`)) {
|
||||||
|
@ -37,13 +40,54 @@ export const ModTable = (props: {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function selectAll() {
|
||||||
|
const deselect = selectedMods.length == props.mods.length;
|
||||||
|
console.log(selectedMods.length, props.mods.length, deselect);
|
||||||
|
if (deselect) {
|
||||||
|
setSelectedMods([]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
props.mods.forEach((item) => {
|
||||||
|
if (!selectedMods.includes(item.slug)) {
|
||||||
|
setSelectedMods((state) => [item.slug, ...state]);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleCheckbox(slug: string) {
|
||||||
|
if (!selectedMods.includes(slug)) {
|
||||||
|
setSelectedMods((state) => [slug, ...state]);
|
||||||
|
} else {
|
||||||
|
const newArray = selectedMods.map((i) => i);
|
||||||
|
const idx = newArray.findIndex((item) => item == slug);
|
||||||
|
newArray.splice(idx, 1);
|
||||||
|
setSelectedMods(newArray);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async function deleteSelectedMods() {
|
||||||
|
await fetch(MOD_ENDPOINT("deleteModBulk", props.packID), {
|
||||||
|
method: "POST",
|
||||||
|
body: JSON.stringify(selectedMods),
|
||||||
|
headers: {
|
||||||
|
"content-type": "application/json",
|
||||||
|
accept: "application/json",
|
||||||
|
},
|
||||||
|
});
|
||||||
|
setSelectedMods([]);
|
||||||
|
props.updatePack();
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="overflow-x-auto">
|
<div className="overflow-x-auto">
|
||||||
<Table hoverable>
|
<Table hoverable>
|
||||||
<TableHead>
|
<TableHead>
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableHeadCell className="p-4">
|
<TableHeadCell className="p-4">
|
||||||
<Checkbox />
|
<Checkbox
|
||||||
|
checked={selectedMods.length == props.mods.length}
|
||||||
|
onChange={() => selectAll()}
|
||||||
|
/>
|
||||||
</TableHeadCell>
|
</TableHeadCell>
|
||||||
<TableHeadCell>Icon</TableHeadCell>
|
<TableHeadCell>Icon</TableHeadCell>
|
||||||
<TableHeadCell>Title</TableHeadCell>
|
<TableHeadCell>Title</TableHeadCell>
|
||||||
|
@ -66,7 +110,12 @@ export const ModTable = (props: {
|
||||||
className="bg-white dark:border-gray-700 dark:bg-gray-800"
|
className="bg-white dark:border-gray-700 dark:bg-gray-800"
|
||||||
>
|
>
|
||||||
<TableCell className="p-4">
|
<TableCell className="p-4">
|
||||||
<Checkbox />
|
<Checkbox
|
||||||
|
checked={selectedMods.includes(mod.slug)}
|
||||||
|
onChange={() => {
|
||||||
|
handleCheckbox(mod.slug);
|
||||||
|
}}
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell>
|
<TableCell>
|
||||||
{/* eslint-disable-next-line @next/next/no-img-element */}
|
{/* eslint-disable-next-line @next/next/no-img-element */}
|
||||||
|
@ -104,7 +153,16 @@ export const ModTable = (props: {
|
||||||
<TableCell></TableCell>
|
<TableCell></TableCell>
|
||||||
<TableCell></TableCell>
|
<TableCell></TableCell>
|
||||||
<TableCell></TableCell>
|
<TableCell></TableCell>
|
||||||
<TableCell></TableCell>
|
<TableCell>
|
||||||
|
<Button
|
||||||
|
color={"red"}
|
||||||
|
size="sm"
|
||||||
|
disabled={selectedMods.length == 0}
|
||||||
|
onClick={() => deleteSelectedMods()}
|
||||||
|
>
|
||||||
|
Delete Selected <HiTrash className="ml-2 h-4 w-4" />
|
||||||
|
</Button>
|
||||||
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
</TableBody>
|
</TableBody>
|
||||||
</Table>
|
</Table>
|
||||||
|
|
|
@ -134,3 +134,36 @@ def deleteMod(id, slug):
|
||||||
"message": f"mod {slug} has been removed",
|
"message": f"mod {slug} has been removed",
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@apiPack.route("/<id>/mods/delete", methods=["POST"])
|
||||||
|
def deleteModBulk(id):
|
||||||
|
pack = {}
|
||||||
|
slugs = request.json
|
||||||
|
|
||||||
|
with open(f"{PACKS_FOLDER}/{id}/packfile.json") as fp:
|
||||||
|
pack = json.load(fp)
|
||||||
|
fp.close()
|
||||||
|
|
||||||
|
for slug in slugs:
|
||||||
|
for mod in pack.get("mods"):
|
||||||
|
if mod.get("slug") == slug:
|
||||||
|
pack["mods"].remove(mod)
|
||||||
|
pack["modpackVersion"] += 1
|
||||||
|
if os.path.exists(
|
||||||
|
f"{PACKS_FOLDER}/{id}/mods/{mod.get('file').get('filename')}"
|
||||||
|
):
|
||||||
|
os.remove(
|
||||||
|
f"{PACKS_FOLDER}/{id}/mods/{mod.get('file').get('filename')}"
|
||||||
|
)
|
||||||
|
|
||||||
|
with open(f"{PACKS_FOLDER}/{id}/packfile.json", mode="w", encoding="utf-8") as fp:
|
||||||
|
json.dump(pack, fp)
|
||||||
|
fp.close()
|
||||||
|
|
||||||
|
return jsonify(
|
||||||
|
{
|
||||||
|
"status": "ok",
|
||||||
|
"message": f"mods has been removed",
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue