9 Commits

22 changed files with 123 additions and 85 deletions

View File

@@ -16,22 +16,22 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core==2022.10.0.post9",
"cpl-core==2022.12.0",
"cpl-translation==2022.10.0.post2",
"cpl-query==2022.10.0.post2",
"cpl-discord==2022.10.0.post6",
"cpl-query==2022.12.2",
"cpl-discord==2022.12.0",
"Flask==2.2.2",
"Flask-Classful==0.14.2",
"Flask-Cors==3.0.10",
"PyJWT==2.6.0",
"waitress==2.1.2",
"Flask-SocketIO==5.3.1",
"eventlet==0.33.1",
"Flask-SocketIO==5.3.2",
"eventlet==0.33.2",
"requests-oauthlib==1.3.1",
"icmplib==3.0.3"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -160,20 +160,27 @@
"removed": "Presence wurde entfernt.",
"max_char_count_exceeded": "Der Text darf nicht mehr als 128 Zeichen lang sein!"
},
"user_info": {
"fields": {
"id": "Id",
"name": "Name",
"discord_join": "Discord beigetreten am",
"last_join": "Server beigetreten am",
"xp": "XP",
"ontime": "Ontime",
"roles": "Rollen",
"joins": "Beitritte",
"lefts": "Abgänge",
"warnings": "Verwarnungen"
"user": {
"info": {
"fields": {
"id": "Id",
"name": "Name",
"discord_join": "Discord beigetreten am",
"last_join": "Server beigetreten am",
"xp": "XP",
"ontime": "Ontime",
"roles": "Rollen",
"joins": "Beitritte",
"lefts": "Abgänge",
"warnings": "Verwarnungen"
},
"footer": ""
},
"footer": ""
"get": {
"atr_not_found": "Das Attribut {} konnte nicht gefunden werden :(",
"xp": "{} hat {} xp",
"ontime": "{} war insgesamt {} Stunden aktiv in einem Sprachkanal"
}
}
},
"boot_log": {

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core==2022.10.0.post7"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -46,14 +46,14 @@ class AuthController:
@Route.authorize(role=AuthRoleEnum.admin)
async def get_all_users(self) -> Response:
result = await self._auth_service.get_all_auth_users_async()
return jsonify(result.select(lambda x: x.to_dict()))
return jsonify(result.select(lambda x: x.to_dict()).to_list())
@Route.post(f'{BasePath}/users/get/filtered')
@Route.authorize(role=AuthRoleEnum.admin)
async def get_filtered_users(self) -> Response:
dto: AuthUserSelectCriteria = JSONProcessor.process(AuthUserSelectCriteria, request.get_json(force=True, silent=True))
result = await self._auth_service.get_filtered_auth_users_async(dto)
result.result = result.result.select(lambda x: x.to_dict())
result.result = result.result.select(lambda x: x.to_dict()).to_list()
return jsonify(result.to_dict())
@Route.get(f'{BasePath}/users/get/<email>')

View File

@@ -40,14 +40,14 @@ class ServerController:
@Route.authorize(role=AuthRoleEnum.admin)
async def get_all_servers(self) -> Response:
result = await self._discord_service.get_all_servers()
result = result.select(lambda x: x.to_dict())
result = result.select(lambda x: x.to_dict()).to_list()
return jsonify(result)
@Route.get(f'{BasePath}/get/servers-by-user')
@Route.authorize
async def get_all_servers_by_user(self) -> Response:
result = await self._discord_service.get_all_servers_by_user()
result = result.select(lambda x: x.to_dict())
result = result.select(lambda x: x.to_dict()).to_list()
return jsonify(result)
@Route.post(f'{BasePath}/get/filtered')
@@ -55,11 +55,11 @@ class ServerController:
async def get_filtered_servers(self) -> Response:
dto: ServerSelectCriteria = JSONProcessor.process(ServerSelectCriteria, request.get_json(force=True, silent=True))
result = await self._discord_service.get_filtered_servers_async(dto)
result.result = result.result.select(lambda x: x.to_dict())
result.result = result.result.select(lambda x: x.to_dict()).to_list()
return jsonify(result.to_dict())
@Route.get(f'{BasePath}/get/<id>')
@Route.authorize
async def get_server_by_id(self, id: int) -> Response:
result = await self._discord_service.get_server_by_id_async(id)
result = await self._discord_service.get_server_by_id_async(id).to_list()
return jsonify(result.to_dict())

View File

@@ -16,10 +16,10 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core>=0.3.dev70"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core>=0.3.dev70"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post5"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post2"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -1,10 +1,11 @@
from typing import Optional
from typing import Optional, List
import discord
from cpl_core.configuration import ConfigurationABC
from cpl_discord.command import DiscordCommandABC
from cpl_discord.service import DiscordBotServiceABC
from cpl_translation import TranslatePipe
from discord import app_commands
from discord.ext import commands
from discord.ext.commands import Context
@@ -83,26 +84,28 @@ class UserGroup(DiscordCommandABC):
color=int('ef9d0d', 16)
)
ujvs = self._user_joined_voice_channel.get_user_joined_voice_channels_by_user_id(user.user_id)
ontime = ujvs.sum(lambda join: round((join.leaved_on - join.joined_on).total_seconds() / 3600, 2))
ontime = self._user_joined_voice_channel.get_user_joined_voice_channels_by_user_id(user.user_id).sum(
lambda join: round((join.leaved_on - join.joined_on).total_seconds() / 3600, 2))
embed.add_field(name=self._t.transform('modules.base.user_info.fields.id'), value=member.id)
embed.add_field(name=self._t.transform('modules.base.user_info.fields.name'), value=member.name)
embed.add_field(name=self._t.transform('modules.base.user_info.fields.discord_join'), value=self._date.transform(member.created_at), inline=False)
embed.add_field(name=self._t.transform('modules.base.user_info.fields.last_join'), value=self._date.transform(member.joined_at), inline=False)
embed.add_field(name=self._t.transform('modules.base.user_info.fields.xp'), value=str(user.xp))
embed.add_field(name=self._t.transform('modules.base.user_info.fields.ontime'), value=str(ontime))
embed.add_field(name=self._t.transform('modules.base.user.info.fields.id'), value=member.id)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.name'), value=member.name)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.discord_join'),
value=self._date.transform(member.created_at), inline=False)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.last_join'),
value=self._date.transform(member.joined_at), inline=False)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.xp'), value=str(user.xp))
embed.add_field(name=self._t.transform('modules.base.user.info.fields.ontime'), value=str(ontime))
roles = ''
for role in member.roles:
roles += f'{role.name}\n'
embed.add_field(name=self._t.transform('modules.base.user_info.fields.roles'), value=roles, inline=False)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.roles'), value=roles, inline=False)
if is_mod or member == ctx.author:
joins_string = ''
for join in joins:
joins_string += f'{self._date.transform(join.joined_on)}\n'
embed.add_field(name=self._t.transform('modules.base.user_info.fields.joins'), value=joins_string)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.joins'), value=joins_string)
if is_mod or member == ctx.author:
lefts_string = ''
@@ -113,11 +116,54 @@ class UserGroup(DiscordCommandABC):
continue
lefts_string += f'{self._date.transform(join.leaved_on)}\n'
embed.add_field(name=self._t.transform('modules.base.user_info.fields.lefts'), value=lefts_string)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.lefts'), value=lefts_string)
if is_mod or member == ctx.author:
embed.add_field(name=self._t.transform('modules.base.user_info.fields.warnings'), value=self._t.transform('common.not_implemented_yet'), inline=False)
embed.add_field(name=self._t.transform('modules.base.user.info.fields.warnings'),
value=self._t.transform('common.not_implemented_yet'), inline=False)
# send to interaction because of sensitive data
await self._message_service.send_interaction_msg(ctx.interaction, embed, wait_before_delete=wait)
self._logger.trace(__name__, f'Finished user-info command')
@user.command()
@commands.guild_only()
@CommandChecks.check_is_ready()
async def get(self, ctx: Context, atr: str, member: discord.Member = None):
self._logger.debug(__name__, f'Received command user-info {ctx}:{member}')
is_mod = self._permissions.is_member_moderator(ctx.author)
if member is not None and not is_mod:
await self._message_service.send_ctx_msg(ctx, self._t.transform('common.no_permission_message'))
return
if member is None or not isinstance(member, discord.Member):
member = ctx.author
server = self._servers.find_server_by_discord_id(ctx.guild.id)
user = self._users.find_user_by_discord_id_and_server_id(member.id, server.server_id)
match atr:
case 'xp':
value = str(user.xp)
case 'ontime':
value = str(round(
self._user_joined_voice_channel.get_user_joined_voice_channels_by_user_id(user.user_id)
.sum(lambda join: (join.leaved_on - join.joined_on).total_seconds() / 3600),
2
))
case other:
await self._message_service.send_interaction_msg(ctx.interaction, self._t.transform('modules.base.user.get.atr_not_found').format(atr))
return
await self._message_service.send_interaction_msg(
ctx.interaction,
self._t.transform(f'modules.base.user.get.{atr}').format(member.mention, value)
)
@get.autocomplete('atr')
async def get_autocomplete(self, interaction: discord.Interaction, current: str) -> List[app_commands.Choice[str]]:
atr_list = ['xp', 'ontime']
return [app_commands.Choice(name=atr, value=atr) for atr in atr_list]

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post2"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core>=2022.10.0.post2"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post7"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli>=2022.10.1"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -88,7 +88,7 @@ class LevelSeeder(DataSeederABC):
if levels.where(lambda l: l.name == role.name).count() == 0:
continue
new_position = position_above_levels - (levels.index(levels.where(lambda l: l.name == role.name).single()) + 1)
new_position = position_above_levels - (levels.index_of(levels.where(lambda l: l.name == role.name).single()) + 1)
if new_position <= 0:
new_position = 1
try:

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post2"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post7"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli>=2022.10.1"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core>=2022.10.0.post7"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli>=2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.6",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core==2022.10.0.post7"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,10 +16,10 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core>=2022.10.0.post7"
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli>=2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -16,11 +16,11 @@
"LicenseName": "MIT",
"LicenseDescription": "MIT, see LICENSE for more details.",
"Dependencies": [
"cpl-core==2022.10.0.post7",
"cpl-core==2022.12.0"
"GitPython==3.1.27"
],
"DevDependencies": [
"cpl-cli==2022.10.0"
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},

View File

@@ -1,13 +0,0 @@
import { NgModule } from "@angular/core";
import { RouterModule, Routes } from "@angular/router";
import { MembersComponent } from "./component/members/members.component";
const routes: Routes = [
{ path: '', component: MembersComponent },
];
@NgModule({
imports: [RouterModule.forChild(routes)],
exports: [RouterModule]
})
export class MembersRoutingModule { }

View File

@@ -1,11 +1,9 @@
import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { ServerDashboardComponent } from './server-dashboard/server-dashboard.component';
import { AuthGuard } from "../../shared/guards/auth/auth.guard";
import { NgModule } from "@angular/core";
import { RouterModule, Routes } from "@angular/router";
import { ServerDashboardComponent } from "./server-dashboard/server-dashboard.component";
const routes: Routes = [
{ path: '', component: ServerDashboardComponent },
{ path: 'members', loadChildren: () => import('./members/members.module').then(m => m.MembersModule), canActivate: [AuthGuard] },
];
@NgModule({