Lots of improvements and changes
This commit is contained in:
parent
98d73ea593
commit
8121b9b975
@ -36,7 +36,7 @@ module.exports = {
|
||||
|
||||
});
|
||||
|
||||
await ticketChannel.send({ embeds: [createEmbed.basic(`${interaction.user} created a ticket`)]});
|
||||
await ticketChannel.send({ embeds: [createEmbed.basic(`${interaction.user} created a ticket`)] });
|
||||
|
||||
interaction.editReply({ embeds: [createEmbed.basic(`${ticketChannel} has been created`)], emphemeral: true });
|
||||
|
||||
@ -52,14 +52,14 @@ module.exports = {
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
);
|
||||
|
||||
const closeMessage = await interaction.reply({ embeds: [createEmbed.basic(`Closing ticket in 10 seconds...`)], components: [cancelRow]});
|
||||
const closeMessage = await interaction.reply({ embeds: [createEmbed.basic('Closing ticket in 10 seconds...')], components: [cancelRow] });
|
||||
const collector = closeMessage.createMessageComponentCollector();
|
||||
|
||||
const timeout = setTimeout(() => {
|
||||
|
||||
const timeout = setTimeout(() => {
|
||||
try {
|
||||
interaction.channel.delete()
|
||||
interaction.channel.delete();
|
||||
} catch {}
|
||||
}, 10000)
|
||||
}, 10000);
|
||||
|
||||
collector.on('collect', async () => {
|
||||
clearTimeout(timeout);
|
||||
|
@ -5,7 +5,8 @@
|
||||
"description": "",
|
||||
"main": "index.js",
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
"lint": "eslint .",
|
||||
"lint-fix": "eslint . --fix"
|
||||
},
|
||||
"author": "",
|
||||
"license": "ISC",
|
||||
|
@ -7,14 +7,14 @@ const router = express.Router();
|
||||
router.post('/createchannels', async (req, res) => {
|
||||
const { name, discordId } = req.body;
|
||||
|
||||
if (!name || !discordId ) return res.status(400).send({ error: 'Name en discordId zijn vereist' });
|
||||
if (!name || !discordId) return res.status(400).send({ error: 'Name en discordId zijn vereist' });
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
|
||||
|
||||
const category = await guild.channels.fetch(process.env.TEAM_CATEGORY_ID);
|
||||
|
||||
const member = await guild.members.fetch(discordId)
|
||||
const member = await guild.members.fetch(discordId);
|
||||
|
||||
const textChannel = await guild.channels.create({
|
||||
name: name,
|
||||
@ -27,9 +27,9 @@ router.post('/createchannels', async (req, res) => {
|
||||
},
|
||||
{
|
||||
id: member.id,
|
||||
allow: [PermissionsBitField.Flags.ViewChannel]
|
||||
}
|
||||
]
|
||||
allow: [PermissionsBitField.Flags.ViewChannel],
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
const voiceChannel = await guild.channels.create({
|
||||
@ -43,15 +43,15 @@ router.post('/createchannels', async (req, res) => {
|
||||
},
|
||||
{
|
||||
id: member.id,
|
||||
allow: [PermissionsBitField.Flags.ViewChannel]
|
||||
}
|
||||
]
|
||||
allow: [PermissionsBitField.Flags.ViewChannel],
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
res.send({ textChannel, voiceChannel });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijdens het maken van discord channels' })
|
||||
return res.status(500).send({ error: 'Error tijdens het maken van discord channels' });
|
||||
}
|
||||
});
|
||||
|
||||
@ -59,86 +59,86 @@ router.post('/createchannels', async (req, res) => {
|
||||
router.post('/deletechannels', async (req, res) => {
|
||||
const { textChannelId, voiceChannelId } = req.body;
|
||||
|
||||
if (!textChannelId, !voiceChannelId ) return res.status(400).send({ error: 'textChannelId en voiceChannelId zijn vereist' });
|
||||
if (!textChannelId, !voiceChannelId) return res.status(400).send({ error: 'textChannelId en voiceChannelId zijn vereist' });
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
|
||||
|
||||
const textChannel = await guild.channels.fetch(textChannelId);
|
||||
const voiceChannel = await guild.channels.fetch(voiceChannelId);
|
||||
|
||||
await textChannel.delete()
|
||||
await voiceChannel.delete()
|
||||
await textChannel.delete();
|
||||
await voiceChannel.delete();
|
||||
|
||||
res.send({ status: 'success' });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijdens het verwijderen van discord channels' })
|
||||
return res.status(500).send({ error: 'Error tijdens het verwijderen van discord channels' });
|
||||
}
|
||||
});
|
||||
|
||||
router.post('/removeteammember', async (req, res) => {
|
||||
const { textChannelId, voiceChannelId, discordId } = req.body;
|
||||
|
||||
if (!textChannelId, !voiceChannelId, !discordId ) return res.status(400).send({ error: 'textChannelId, voiceChannelId en discordId zijn vereist' });
|
||||
if (!textChannelId, !voiceChannelId, !discordId) return res.status(400).send({ error: 'textChannelId, voiceChannelId en discordId zijn vereist' });
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
const member = await guild.members.fetch(discordId)
|
||||
|
||||
const member = await guild.members.fetch(discordId);
|
||||
|
||||
const textChannel = await guild.channels.fetch(textChannelId);
|
||||
const voiceChannel = await guild.channels.fetch(voiceChannelId);
|
||||
|
||||
await textChannel.permissionOverwrites.delete(member)
|
||||
await voiceChannel.permissionOverwrites.delete(member)
|
||||
await textChannel.permissionOverwrites.delete(member);
|
||||
await voiceChannel.permissionOverwrites.delete(member);
|
||||
|
||||
res.send({ status: 'success' });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijdens het verwijderen van een team member' })
|
||||
return res.status(500).send({ error: 'Error tijdens het verwijderen van een team member' });
|
||||
}
|
||||
});
|
||||
|
||||
router.post('/addteammember', async (req, res) => {
|
||||
const { textChannelId, voiceChannelId, discordId } = req.body;
|
||||
|
||||
if (!textChannelId, !voiceChannelId, !discordId ) return res.status(400).send({ error: 'textChannelId, voiceChannelId en discordId zijn vereist' });
|
||||
if (!textChannelId, !voiceChannelId, !discordId) return res.status(400).send({ error: 'textChannelId, voiceChannelId en discordId zijn vereist' });
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
const member = await guild.members.fetch(discordId)
|
||||
|
||||
const member = await guild.members.fetch(discordId);
|
||||
|
||||
const textChannel = await guild.channels.fetch(textChannelId);
|
||||
const voiceChannel = await guild.channels.fetch(voiceChannelId);
|
||||
|
||||
await textChannel.permissionOverwrites.edit(member, { ViewChannel: true })
|
||||
await voiceChannel.permissionOverwrites.edit(member, { ViewChannel: true })
|
||||
await textChannel.permissionOverwrites.edit(member, { ViewChannel: true });
|
||||
await voiceChannel.permissionOverwrites.edit(member, { ViewChannel: true });
|
||||
|
||||
res.send({ status: 'success' });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijdens het toevoegen van team member' })
|
||||
return res.status(500).send({ error: 'Error tijdens het toevoegen van team member' });
|
||||
}
|
||||
});
|
||||
|
||||
router.post('/edit', async (req, res) => {
|
||||
const { textChannelId, voiceChannelId, name } = req.body;
|
||||
|
||||
if (!textChannelId, !voiceChannelId, !name ) return res.status(400).send({ error: 'textChannelId, voiceChannelId en name zijn vereist' });
|
||||
if (!textChannelId, !voiceChannelId, !name) return res.status(400).send({ error: 'textChannelId, voiceChannelId en name zijn vereist' });
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
|
||||
|
||||
const textChannel = await guild.channels.fetch(textChannelId);
|
||||
const voiceChannel = await guild.channels.fetch(voiceChannelId);
|
||||
|
||||
await textChannel.edit({ name: name })
|
||||
await voiceChannel.edit({ name: name })
|
||||
await textChannel.edit({ name: name });
|
||||
await voiceChannel.edit({ name: name });
|
||||
|
||||
res.send({ status: 'success' });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijds het veranderen van Discord channel naam' })
|
||||
return res.status(500).send({ error: 'Error tijds het veranderen van Discord channel naam' });
|
||||
}
|
||||
});
|
||||
|
||||
|
@ -1,27 +1,47 @@
|
||||
const express = require('express');
|
||||
const index = require('../index')
|
||||
const index = require('../index');
|
||||
|
||||
const router = express.Router();
|
||||
|
||||
router.post('/changenickname', async (req, res) => {
|
||||
const { nickname, discordId } = req.body;
|
||||
|
||||
if (!nickname || !discordId ) return res.status(400).send({ error: 'Nickname en discordId zijn vereist' });
|
||||
if (!nickname || !discordId) return res.status(400).send({ error: 'Nickname en discordId zijn vereist' });
|
||||
|
||||
const nick = nickname.length > 32 ? nickname.slice(0, 32) : nickname;
|
||||
|
||||
const nick = nickname.length > 32 ? nickname.slice(0, 32) : nickname
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
|
||||
const member = await guild.members.fetch(discordId)
|
||||
|
||||
await member.edit({ nick: nick })
|
||||
|
||||
const member = await guild.members.fetch(discordId);
|
||||
|
||||
await member.edit({ nick: nick });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijds het veranderen van de nickname' })
|
||||
return res.status(500).send({ error: 'Error tijds het veranderen van de nickname' });
|
||||
}
|
||||
|
||||
res.send({ status: 'success' });
|
||||
});
|
||||
|
||||
router.post('/ban', async (req, res) => {
|
||||
const { discordId, reason } = req.body;
|
||||
|
||||
if (!reason || !discordId) return res.status(400).send({ error: 'Reason en discordId zijn vereist' });
|
||||
|
||||
try {
|
||||
const guild = await index.client.guilds.fetch(process.env.GUILD_ID);
|
||||
|
||||
const member = await guild.members.fetch(discordId);
|
||||
|
||||
await member.ban({ deleteMessageSeconds: 24 * 3600, reason: reason });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
return res.status(500).send({ error: 'Error tijds het bannen van gebruiker' });
|
||||
}
|
||||
|
||||
res.send({ status: 'success' });
|
||||
});
|
||||
|
||||
|
||||
module.exports = router;
|
||||
|
@ -7,7 +7,7 @@
|
||||
te zien, vul deze code hieronder in.
|
||||
</p>
|
||||
<div class="flex gap-2">
|
||||
<Input v-model:value="code">Code</Input>
|
||||
<Input v-model="code">Code</Input>
|
||||
<Button @click="submitCode">Submit</Button>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -16,12 +16,16 @@
|
||||
<Icon size="1.5em" name="ph:map-trifold" class="mr-3" />
|
||||
Map
|
||||
</NuxtLink>
|
||||
<div v-if="user && user.admin" class="mt-auto">
|
||||
<h2 class="ml-2 text-gray-400">Adminstration</h2>
|
||||
<NuxtLink to="/admin/users" class="sidebar-item">
|
||||
<div v-if="user && user.role.admin" class="mt-auto space-y-1">
|
||||
<h2 class="ml-2 text-gray-400">Moderation</h2>
|
||||
<NuxtLink to="/mod/users" class="sidebar-item">
|
||||
<Icon size="1.5em" name="ph:users-three" class="mr-3" />
|
||||
Users
|
||||
</NuxtLink>
|
||||
<NuxtLink to="/mod/server" class="sidebar-item">
|
||||
<Icon size="1.5em" name="ph:cpu" class="mr-3" />
|
||||
Server Control
|
||||
</NuxtLink>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
@ -12,8 +12,8 @@
|
||||
</div>
|
||||
</Modal>
|
||||
<Modal v-if="editTeamModal.open" title="Edit team" @close="editTeamModal.open = false" @submit="editTeam">
|
||||
<Input v-model:value="editTeamModal.name" background-class="bg-neutral-800" class="w-full max-w-sm">Naam / Prefix</Input>
|
||||
<Colorpicker v-model:value="editTeamModal.color" input-background-class="bg-neutral-800" class="w-full max-w-sm" />
|
||||
<Input v-model="editTeamModal.name" background-class="bg-neutral-800" class="w-full max-w-sm">Naam / Prefix</Input>
|
||||
<Colorpicker v-model="editTeamModal.color" input-background-class="bg-neutral-800" class="w-full max-w-sm" />
|
||||
</Modal>
|
||||
<div class="mx-auto my-10 max-w-2xl">
|
||||
<h2 class="mb-2 text-xl font-bold text-primary">Team Information</h2>
|
||||
|
@ -28,8 +28,8 @@
|
||||
</div>
|
||||
</div>
|
||||
<div v-else class="flex w-full flex-col items-center gap-5">
|
||||
<Input v-model:value="createTeam.name" class="w-full max-w-sm">Naam</Input>
|
||||
<Colorpicker v-model:value="createTeam.color" class="w-full max-w-sm" />
|
||||
<Input v-model="createTeam.name" class="w-full max-w-sm">Naam</Input>
|
||||
<Colorpicker v-model="createTeam.color" class="w-full max-w-sm" />
|
||||
<Button @click="handleCreateTeam">Create Team</Button>
|
||||
</div>
|
||||
</template>
|
||||
|
@ -5,7 +5,7 @@ export default defineNuxtRouteMiddleware(async (to) => {
|
||||
const user = await $fetch('/api/auth/user')
|
||||
useState('user', () => user)
|
||||
|
||||
if (to.meta.admin && !user.admin) return navigateTo('/')
|
||||
if (to.meta.moderator && !user.role.moderator) return navigateTo('/')
|
||||
|
||||
} catch (err) {
|
||||
console.log(err)
|
||||
|
4249
web/package-lock.json
generated
4249
web/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -11,18 +11,18 @@
|
||||
"lint-fix": "eslint . --fix"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@nuxt/devtools": "^0.4.2",
|
||||
"@nuxt/devtools": "^0.5.0",
|
||||
"@nuxt/image-edge": "^1.0.0-28059208.2abef1b",
|
||||
"@nuxtjs/eslint-module": "^4.0.2",
|
||||
"@nuxtjs/tailwindcss": "^6.6.6",
|
||||
"@types/node": "^18",
|
||||
"@vueuse/components": "^10.1.0",
|
||||
"@vueuse/core": "^10.1.0",
|
||||
"@vueuse/nuxt": "^10.1.0",
|
||||
"eslint": "^8.39.0",
|
||||
"eslint-plugin-tailwindcss": "^3.11.0",
|
||||
"nuxt": "^3.4.2",
|
||||
"nuxt-icon": "^0.3.3"
|
||||
"@nuxtjs/eslint-module": "^4.1.0",
|
||||
"@nuxtjs/tailwindcss": "^6.7.0",
|
||||
"@types/node": "^20",
|
||||
"@vueuse/components": "^10.1.2",
|
||||
"@vueuse/core": "^10.1.2",
|
||||
"@vueuse/nuxt": "^10.1.2",
|
||||
"eslint": "^8.41.0",
|
||||
"eslint-plugin-tailwindcss": "^3.12.0",
|
||||
"nuxt": "^3.5.0",
|
||||
"nuxt-icon": "^0.4.1"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nuxt/eslint-config": "^0.1.1",
|
||||
@ -30,8 +30,7 @@
|
||||
"@xeovalyte/nuxt-xvui": "git+https://gitea.xeovalyte.dev/xeovalyte/nuxt-xvui.git",
|
||||
"jsonwebtoken": "^9.0.0",
|
||||
"minecraft-server-util": "^5.4.2",
|
||||
"mongodb": "^5.3.0",
|
||||
"socket.io-client": "^4.6.1",
|
||||
"surrealdb.js": "^0.6.0"
|
||||
"mongodb": "^5.5.0",
|
||||
"socket.io-client": "^4.6.1"
|
||||
}
|
||||
}
|
||||
|
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>
|
||||
|
13
web/server/api/auth/getusers.js
Normal file
13
web/server/api/auth/getusers.js
Normal file
@ -0,0 +1,13 @@
|
||||
export default defineEventHandler(async (event) => {
|
||||
const user = await getAuth(event)
|
||||
|
||||
if (!user.role.moderator) return createError({ statusCode: 403, statusMessage: 'Gebruiker heeft geen toegang tot alle gebruikers' })
|
||||
|
||||
const usersColl = db.collection('users');
|
||||
|
||||
const cursor = usersColl.find()
|
||||
|
||||
const users = await cursor.toArray()
|
||||
|
||||
return users
|
||||
});
|
@ -37,7 +37,7 @@ export default defineEventHandler(async (event) => {
|
||||
},
|
||||
}
|
||||
|
||||
await coll.updateOne({ 'discord.id': userResult.id }, { $set: doc, $setOnInsert: { minecraft: { uuid: null, username: null }, teamInvites: [] } }, { upsert: true })
|
||||
await coll.updateOne({ 'discord.id': userResult.id }, { $set: doc, $setOnInsert: { minecraft: { uuid: null, username: null }, teamInvites: [], role: {} } }, { upsert: true })
|
||||
|
||||
const token = createToken(tokenResponseData.access_token, tokenResponseData.refresh_token, tokenResponseData.expires_in, userResult.id )
|
||||
|
||||
|
25
web/server/api/auth/user/[id]/ban.js
Normal file
25
web/server/api/auth/user/[id]/ban.js
Normal file
@ -0,0 +1,25 @@
|
||||
import { ObjectId } from "mongodb";
|
||||
|
||||
export default defineEventHandler(async (event) => {
|
||||
const { reason } = await readBody(event)
|
||||
|
||||
const currentUser = await getAuth(event)
|
||||
const userId = event.context.params.id;
|
||||
|
||||
if (!reason) return createError({ statusCode: 400, statusMessage: 'Reason is vereist' })
|
||||
if (!currentUser.role.admin) return createError({ statusCode: 403, statusMessage: 'Geen toegang om gebruiker te bannen' })
|
||||
|
||||
const usersColl = db.collection('users')
|
||||
const user = usersColl.findOneAndUpdate({ _id: new ObjectId(userId)}, { $set: { banned: { reason: reason, date: new Date() } } })
|
||||
|
||||
if (!user.value) return createError({ statusCode: 500, statusMessage: 'Error tijdens het updaten van de gebruiker' })
|
||||
|
||||
await $fetch(config.discordHost + '/user/ban', {
|
||||
method: 'POST',
|
||||
body: { reason: reason, discordId: user.discord.id }
|
||||
})
|
||||
|
||||
await sendRconCommand(`ban ${user.value.minecraft.uuid} ${reason}`)
|
||||
|
||||
return user
|
||||
});
|
@ -1,5 +1,3 @@
|
||||
import { applyUsername } from "~/server/utils/auth";
|
||||
|
||||
export default defineEventHandler(async (event) => {
|
||||
const user = await getAuth(event)
|
||||
|
||||
|
17
web/server/api/store/index.delete.js
Normal file
17
web/server/api/store/index.delete.js
Normal file
@ -0,0 +1,17 @@
|
||||
import { ObjectId } from "mongodb";
|
||||
|
||||
export default defineEventHandler(async (event) => {
|
||||
const { id } = await readBody(event)
|
||||
|
||||
const user = await getAuth(event)
|
||||
|
||||
const storesColl = db.collection('stores');
|
||||
|
||||
const result = await storesColl.deleteOne({ _id: new ObjectId(id) })
|
||||
|
||||
if (result.deletedCount === 1) {
|
||||
return result
|
||||
} else {
|
||||
throw createError({ statusCode: 500, statusMessage: 'Error tijdens het verwijderen van de store' })
|
||||
}
|
||||
});
|
21
web/server/api/store/index.get.js
Normal file
21
web/server/api/store/index.get.js
Normal file
@ -0,0 +1,21 @@
|
||||
export default defineEventHandler(async () => {
|
||||
|
||||
const storesColl = db.collection('stores');
|
||||
|
||||
const cursor = storesColl.aggregate([
|
||||
{
|
||||
$lookup:
|
||||
{
|
||||
from: "users",
|
||||
localField: "ownerId",
|
||||
foreignField: "_id",
|
||||
as: "owner",
|
||||
},
|
||||
},
|
||||
{
|
||||
$unwind: "$owner",
|
||||
},
|
||||
])
|
||||
|
||||
return await cursor.toArray()
|
||||
});
|
13
web/server/api/store/index.post.js
Normal file
13
web/server/api/store/index.post.js
Normal file
@ -0,0 +1,13 @@
|
||||
import { ObjectId } from "mongodb";
|
||||
|
||||
export default defineEventHandler(async (event) => {
|
||||
const { coords, name, items, id } = await readBody(event)
|
||||
|
||||
const user = await getAuth(event)
|
||||
|
||||
const storesColl = db.collection('stores');
|
||||
|
||||
const { value: store } = await storesColl.findOneAndUpdate({ _id: id ? new ObjectId(id) : new ObjectId() }, { $set: { coords: coords, name: name, items: items, ownerId: user._id, } }, { returnDocument: 'after', upsert: true })
|
||||
|
||||
return store
|
||||
});
|
Loading…
Reference in New Issue
Block a user