Lots of improvements and changes
This commit is contained in:
14
web/pages/mod/server.vue
Normal file
14
web/pages/mod/server.vue
Normal file
@@ -0,0 +1,14 @@
|
||||
<template>
|
||||
<div class="mt-5">
|
||||
Server Control
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
definePageMeta({
|
||||
middleware: ["auth"],
|
||||
moderator: true
|
||||
})
|
||||
|
||||
useHead({ title: 'Server Control | Polarcraft' })
|
||||
</script>
|
77
web/pages/mod/users.vue
Normal file
77
web/pages/mod/users.vue
Normal file
@@ -0,0 +1,77 @@
|
||||
<template>
|
||||
<div class="mt-5">
|
||||
<Modal v-if="actionModal.open" :title="actionModal.title">
|
||||
WIP
|
||||
</Modal>
|
||||
<h1 class="text-2xl font-bold text-primary">
|
||||
Users
|
||||
</h1>
|
||||
<div class="mx-auto my-10 max-w-4xl">
|
||||
<h2 class="mb-2 text-xl font-bold text-primary">User Actions</h2>
|
||||
<div class="w-full rounded border-[1px] border-primary px-3 py-1 text-left">
|
||||
<table class="w-full table-auto divide-y divide-neutral-500 rounded">
|
||||
<tr class="border-b-2 border-primary text-gray-200">
|
||||
<th class="py-1">Username</th>
|
||||
<th class="py-1">Team</th>
|
||||
<th class="py-1">MC Linked</th>
|
||||
<th class="py-1">Actions</th>
|
||||
</tr>
|
||||
<tr v-for="user in users" :key="user._id" class="text-gray-200">
|
||||
<td class="py-1">{{ user.username }}</td>
|
||||
<td class="py-1">{{ user.team ? teams.filter(a => a._id === user.team.id)[0].name : '-' }}</td>
|
||||
<td class="py-1">{{ user.minecraft.uuid ? 'True ' : 'False' }}</td>
|
||||
<td class="space-x-2 py-1">
|
||||
<span v-if="currentUser.role.admin" class="rounded bg-red-700 px-2 text-red-300 hover:cursor-pointer hover:bg-red-800" @click="openModal(user, 'ban', ban(user))">Ban</span>
|
||||
<span class="rounded bg-orange-700 px-2 text-orange-300 hover:cursor-pointer hover:bg-orange-800">Suspend</span>
|
||||
<span class="rounded bg-yellow-700 px-2 text-yellow-300 hover:cursor-pointer hover:bg-yellow-800">Warn</span>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
definePageMeta({
|
||||
middleware: ["auth"],
|
||||
moderator: true
|
||||
})
|
||||
|
||||
useHead({ title: 'Users | Polarcraft' })
|
||||
|
||||
const currentUser = useState('user')
|
||||
|
||||
const { data: users } = useFetch('/api/auth/getusers')
|
||||
const { data: teams } = useFetch('/api/team/all')
|
||||
|
||||
const actionModal = ref({
|
||||
open: false,
|
||||
title: '',
|
||||
userId: '',
|
||||
func: null,
|
||||
})
|
||||
|
||||
const openModal = (user, type, func) => {
|
||||
if (type === 'ban') actionModal.value.title = 'Ban User'
|
||||
if (type === 'suspend') actionModal.value.title = 'Suspend User'
|
||||
if (type === 'warn') actionModal.value.title = 'Warn User'
|
||||
|
||||
actionModal.value.func = func
|
||||
actionModal.value.userId = user._id;
|
||||
actionModal.value.open = true
|
||||
}
|
||||
|
||||
const ban = async (user) => {
|
||||
try {
|
||||
const response = await $fetch(`/api/auth/user/${user._id}/ban`, {
|
||||
reason: "reason"
|
||||
})
|
||||
|
||||
user = response;
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
useToast().error('Error banning user')
|
||||
}
|
||||
}
|
||||
</script>
|
@@ -1,6 +1,59 @@
|
||||
<template>
|
||||
<div class="mt-5 text-primary">
|
||||
Player Store
|
||||
<Modal
|
||||
v-if="storeModal.open"
|
||||
title="Create new store"
|
||||
:delete="!storeModal.new"
|
||||
@submit="submitModal"
|
||||
@delete="deleteStore"
|
||||
@close="storeModal.open = false"
|
||||
>
|
||||
<Input v-model="storeModal.name" background-class="bg-neutral-800">Store name</Input>
|
||||
<div class="flex gap-x-5">
|
||||
<Input v-model="storeModal.coords.x" background-class="bg-neutral-800">Coordinate X</Input>
|
||||
<Input v-model="storeModal.coords.z" background-class="bg-neutral-800">Coordinate Z</Input>
|
||||
</div>
|
||||
<h2 class="font-bold">Items</h2>
|
||||
<div class="max-h-56 space-y-3 overflow-scroll">
|
||||
<div v-for="item, index in storeModal.items" :key="item.name" class="flex gap-2">
|
||||
<Input v-model="item.displayName" background-class="bg-neutral-800">Name</Input>
|
||||
<Input v-model="item.price" background-class="bg-neutral-800">Price per quantity</Input>
|
||||
<Button type="danger" @click="storeModal.items.splice(index, 1)"><Icon size="1.5em" name="ph:trash" class="-my-2" /></Button>
|
||||
</div>
|
||||
</div>
|
||||
<Button class="" @click="storeModal.items.push({ displayName: '', price: '' })">Add Item</Button>
|
||||
</Modal>
|
||||
<h1 class="pb-10 text-2xl font-bold text-primary">
|
||||
Player Stores
|
||||
</h1>
|
||||
<div class="fixed bottom-10 right-10">
|
||||
<Button class="fixed" @click="openStoreModal(true)">
|
||||
Create Store
|
||||
</Button>
|
||||
</div>
|
||||
<div class="flex flex-wrap gap-10">
|
||||
<div v-for="store in stores" :key="store._id.toString()" class="h-min w-96 rounded-lg bg-neutral-800 text-gray-200 shadow relative">
|
||||
<div v-if="store.ownerId === user._id" class="absolute right-5 top-5 hover:cursor-pointer" @click="openStoreModal(false, store)">
|
||||
<Icon name="ph:pencil-simple" size="1.6em" />
|
||||
</div>
|
||||
<div class="p-5 pb-3">
|
||||
<div class="flex items-center">
|
||||
<img :src="'https://api.mineatar.io/face/' + store.owner.minecraft.uuid + '?scale=3'" class="mr-2 aspect-square rounded">
|
||||
{{ store.owner.username }}
|
||||
</div>
|
||||
<h2 class="text-2xl font-bold text-primary">
|
||||
{{ store.name }}
|
||||
<span class="text-sm font-medium">({{ store.coords.x }}, {{ store.coords.z }})</span>
|
||||
</h2>
|
||||
</div>
|
||||
<h2 class="ml-3 text-xl font-bold">Items</h2>
|
||||
<div class="divide-y divide-neutral-600 rounded-lg bg-neutral-700 px-4 pt-2 pb-2">
|
||||
<div v-for="item in store.items" :key="item.displayname" class="py-1">
|
||||
<b>{{ item.displayName }}</b> for <b>{{ item.price }}</b>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -9,5 +62,97 @@ definePageMeta({
|
||||
middleware: ["auth"]
|
||||
})
|
||||
|
||||
const user = useState('user')
|
||||
|
||||
useHead({ title: 'Player Stores | Polarcraft' })
|
||||
|
||||
const { data: stores } = await useFetch('/api/store');
|
||||
|
||||
const storeModal = ref({
|
||||
open: false,
|
||||
name: '',
|
||||
new: false,
|
||||
id: '',
|
||||
coords: {
|
||||
x: '',
|
||||
z: '',
|
||||
},
|
||||
items: [
|
||||
{ displayName: '', price: '' }
|
||||
],
|
||||
})
|
||||
|
||||
const openStoreModal = (newStore, store) => {
|
||||
storeModal.value.open = true;
|
||||
|
||||
if (newStore === true) {
|
||||
storeModal.value.name = '';
|
||||
storeModal.value.items = [
|
||||
{ displayName: '', price: '' }
|
||||
];
|
||||
|
||||
storeModal.value.coords = { x: '', z: '' }
|
||||
|
||||
storeModal.value.new = true
|
||||
} else {
|
||||
storeModal.value.new = false
|
||||
|
||||
storeModal.value.items = []
|
||||
store.items.forEach(item => {
|
||||
storeModal.value.items.push(item);
|
||||
})
|
||||
|
||||
storeModal.value.name = store.name
|
||||
storeModal.value.id = store._id
|
||||
storeModal.value.coords.x = store.coords.x
|
||||
storeModal.value.coords.z = store.coords.z
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const submitModal = async () => {
|
||||
try {
|
||||
const store = await $fetch('/api/store', {
|
||||
method: 'POST',
|
||||
body: { name: storeModal.value.name, coords: storeModal.value.coords, items: storeModal.value.items, id: storeModal.value.id || null }
|
||||
})
|
||||
|
||||
if (storeModal.value.id) {
|
||||
const oldStore = stores.value.filter(a => a._id === storeModal.value.id)[0]
|
||||
|
||||
oldStore.name = storeModal.value.name;
|
||||
oldStore.coords = storeModal.value.coords;
|
||||
oldStore.items = storeModal.value.items;
|
||||
} else {
|
||||
store.owner = user
|
||||
stores.value.push(store)
|
||||
}
|
||||
|
||||
storeModal.value.open = false
|
||||
|
||||
useToast().success('Succesvol store aangemaakt')
|
||||
} catch (e) {
|
||||
console.log(e)
|
||||
useToast().error(e.statusMessage)
|
||||
}
|
||||
}
|
||||
|
||||
const deleteStore = async () => {
|
||||
try {
|
||||
await $fetch('/api/store', {
|
||||
method: 'DELETE',
|
||||
body: { id: storeModal.value.id }
|
||||
})
|
||||
|
||||
|
||||
|
||||
stores.value = stores.value.filter(a => a._id !== storeModal.value.id)
|
||||
|
||||
storeModal.value.open = false
|
||||
useToast().success('Succesvol store verwijderd')
|
||||
} catch (e) {
|
||||
console.log(e)
|
||||
useToast().error(e.statusMessage)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
Reference in New Issue
Block a user