浏览代码

Early attempt at activeRPG

root 3 年之前
父节点
当前提交
9a649f6b32
共有 6 个文件被更改,包括 166 次插入8 次删除
  1. 82 1
      bot/commands/games.py
  2. 2 2
      bot/commands/general.py
  3. 1 1
      bot/common/logging.py
  4. 60 2
      bot/events/general.py
  5. 3 1
      bot/query/initialise_database.py
  6. 18 1
      bot/query/user.py

+ 82 - 1
bot/commands/games.py

@@ -3,7 +3,8 @@ import discord
 import random
 from typing import Optional
 from query.channel import get_games
-from query.user import is_ignored
+from query.user import is_ignored, get_level, get_xp, level_up
+from local_settings import COMMAND_PREFIX
 
 def setup(bot: commands.Bot):
 	bot.add_cog(Games(bot))
@@ -15,6 +16,85 @@ class Games(commands.Cog):
 		self.bot = bot
 
 
+	@commands.command(
+		description="Check the level for a player.",
+		brief="Get player level",
+		help="View game level of player."
+	)
+	async def level(self, ctx: commands.Context, user: Optional[discord.User]):
+		# Ignore user if on the ignore list.
+		if await is_ignored(self.bot.pg, ctx.author.id):
+			return
+
+		# Warn if games are off.
+		if not await get_games(self.bot.pg, ctx.channel.id):
+			ctx.author.send(f"Games are disabled in {ctx.channel}, ask an admin to enable them.")
+			return
+
+		if not user:
+			user = ctx.author
+		level = await get_level(self.bot.pg, user)
+
+		if level == 0:
+			if ctx.author == user:
+				ctx.send(f"You are not playing, join the game with {COMMAND_PREFIX}`levelup`")
+			else:
+				ctx.send(f"{user} is not playing.")
+		else:
+			xp_spent, total_xp = get_xp(user)
+			if ctx.author == user:
+				ctx.send(f"You rank at level {level}. ({xp_spent}/{total_xp})")
+			else:
+				ctx.send(f"{user} ranks at level {level}. ({xp_spent}/{total_xp})")
+
+	@commands.command(
+		description="Check the experience points for a player.",
+		brief="Get player xp",
+		help="View amount of XP a game player has."
+	)
+	async def xp(self, ctx: commands.Context, user: Optional[discord.User]):
+		# Ignore user if on the ignore list.
+		if await is_ignored(self.bot.pg, ctx.author.id):
+			return
+
+		# Warn if games are off.
+		if not await get_games(self.bot.pg, ctx.channel.id):
+			ctx.author.send(f"Games are disabled in {ctx.channel}, ask an admin to enable them.")
+			return
+
+		if not user:
+			xp_spent, total_xp = await get_xp(self.bot.pg, ctx.author.id)
+			ctx.send(f"You have spent {xp_spent} experience points of your {total_xp} total.")
+		else:
+			xp_spent, total_xp = await get_xp(self.bot.pg, user)
+			ctx.send(f"{user} has spent {xp_spent} of {total_xp} experience points.")
+
+	@commands.command(
+		description="Attempt to gain a level.",
+		brief="Level up",
+		help="Try to rank up a level in the game by spending XP."
+	)
+	async def levelup(self, ctx: commands.Context, user: Optional[discord.User]):
+		# Ignore user if on the ignore list.
+		if await is_ignored(self.bot.pg, ctx.author.id):
+			return
+
+		# Warn if games are off.
+		if not await get_games(self.bot.pg, ctx.channel.id):
+			ctx.author.send(f"Games are disabled in {ctx.channel}, ask an admin to enable them.")
+			return
+
+		xp_spent, total_xp = await get_xp(self.bot.pg, ctx.author.id)
+		xp_available = total_xp - xp_spent
+		level = await get_level(self.bot.pg, user)
+		threshold = (level + 1) * 50 + xp_spent
+		if xp_available < threshold:
+			ctx.send(f"Not yet, you require {threshold - xp_available} more XP to level up.")
+		else:
+			level_up(self.bot.pg, ctx.author.id, threshold)
+			ctx.send(f"You have climbed the ranks for {threshold} XP, leaving you {xp_available - threshold} remaining.")
+
+
 	@commands.command(
 		description="Simulate dice rolls.",
 		brief="Roll dice",
@@ -25,6 +105,7 @@ class Games(commands.Cog):
 		if await is_ignored(self.bot.pg, ctx.author.id):
 			return
 
+		# Warn if games are off.
 		if not await get_games(self.bot.pg, ctx.channel.id):
 			ctx.author.send(f"Games are disabled in {ctx.channel}, ask an admin to enable them.")
 			return

+ 2 - 2
bot/commands/general.py

@@ -69,7 +69,7 @@ class General(commands.Cog):
 		elif channel:
 			if await get_interact(self.bot.pg, channel.id):
 				await channel.send(message)
-				await report(self.bot, f"`{ctx.author}`  has sent {message} to `{channel.name}`", ctx.guild)
+				await report(self.bot, f"`{ctx.author}` @ {channel.mention}: {message}", ctx.guild)
 			else:
 				await ctx.send(f"Interactive mode for {channel} is deactivated.")
 		elif user:
@@ -77,7 +77,7 @@ class General(commands.Cog):
 			await report(self.bot, f"`{ctx.author}`  has sent {message} to `{user.name}`")
 		else:
 			await ctx.send(message)
-			await report(self.bot, f"`{ctx.author}` has sent `{message}` locally.", ctx.guild)
+			await report(self.bot, f"`{ctx.author}` has sent {message} locally.", ctx.guild)
 
 
 	@commands.command(

+ 1 - 1
bot/common/logging.py

@@ -6,7 +6,7 @@ from query.guild import get_output_channel
 async def report(bot, message, guild: Optional[discord.Guild]=None):
     channel = bot.get_channel(OUTPUT_CHANNEL)
     if guild:
-        message = f"`{guild}` | {message}"
+        message = f"**{guild}** | {message}"
         try: channel = bot.get_channel(get_output_channel(guild.id))
         except:
             pass

+ 60 - 2
bot/events/general.py

@@ -1,4 +1,5 @@
-import logging, discord, asyncpg, random
+import logging, discord, asyncpg, random, sys
+
 from discord.ext import commands
 from query.guild import update_guild, get_report_deleted, get_output_channel
 from query.channel import insert_channel, get_interact
@@ -16,17 +17,74 @@ class General(commands.Cog):
 		self.bot = bot
 		self.last_msg = None
 
+	@commands.Cog.listener()
+	async def on_raw_app_command_permissions_update(self, payload):
+		logging.info(f"Application command permissions are updated: {payload}")
+		await report(self.bot, f"Application command permissions are updated: {payload}", payload.guild)
+
+	@commands.Cog.listener()
+	async def on_app_command_completion(self, interaction, command):
+		logging.info(f"Application command completion: {interaction} - {command}")
+		await report(self.bot, f"Application command completion: {interaction} - {command}", interaction.guild)
+
+	@commands.Cog.listener()
+	async def on_connect(self):
+		logging.info("Connecting...")
+
+	@commands.Cog.listener()
+	async def on_disconnect(self):
+		logging.info("Disconnecting...")
+
+	@commands.Cog.listener()
+	async def on_shard_connect(self, shard_id):
+		logging.info(f"Connecting to chard: {shard_id}")
+
+	@commands.Cog.listener()
+	async def on_shard_disconnect(self, shard_id):
+		logging.info(f"Disconnecting from chard: {shard_id}")
+
+	@commands.Cog.listener()
+	async def on_error(self, event, *args, **kwargs):
+		logging.error(event, args, kwargs, sys.exc_info())
+		await report(self.bot, f"{event}, {args}, {kwargs}, {sys.exc_info()}")
 
 	@commands.Cog.listener()
 	async def on_ready(self):
 		logging.info("Logged in as %s - %i", self.bot.user.name, self.bot.user.id)
 		#await report(self.bot, f"Logged in as {self.bot.user.name} - {self.bot.user.id}.")
 
+	@commands.Cog.listener()
+	async def on_resumed(self):
+		logging.info("Resumed")
+
+	@commands.Cog.listener()
+	async def on_shard_ready(self, shard_id):
+		logging.info(f"Chard ready: {shard_id}")
+
+	@commands.Cog.listener()
+	async def on_shard_resumed(self, shard_id):
+		logging.info(f"Chard resumed: {shard_id}")
+
+	@commands.Cog.listener()
+	async def on_guild_available(self, guild: discord.Guild):
+		logging.info(f"Guild available: {guild}")
+		#await report(self.bot, f"Guild available: {guild}.")
+
+	@commands.Cog.listener()
+	async def on_guild_unavailable(self, guild: discord.Guild):
+		logging.info(f"Guild unavailable: {guild}")
+		await report(self.bot, f"Guild unavailable: `{guild}`.")
+
 	@commands.Cog.listener()
 	async def on_guild_join(self, guild: discord.Guild):
 		await update_guild(self.bot.pg, guild)
 		logging.info(f"Joined guild {guild}")
-		await report(self.bot, f"Joined guild {guild.name}.")
+		await report(self.bot, f"Joined guild `{guild}`.")
+
+	@commands.Cog.listener()
+	async def on_guild_remove(self, guild: discord.Guild):
+		logging.info(f"Guild removed: {guild}")
+		await report(self.bot, f"Guild removed `{guild}`.")
 
 	@commands.Cog.listener()
 	async def on_message_delete(self, message: discord.Message):

+ 3 - 1
bot/query/initialise_database.py

@@ -34,7 +34,9 @@ async def init_db(pg):
             \"user\" (\
                 id SERIAL PRIMARY KEY, \
                 user_id BIGINT UNIQUE NOT NULL, \
-                ignore BOOL DEFAULT FALSE\
+                ignore BOOL DEFAULT FALSE, \
+                level INT DEFAULT 0, \
+                xp_spent INT DEFAULT 0\
             )\
         ",
         "CREATE TABLE IF NOT EXISTS \

+ 18 - 1
bot/query/user.py

@@ -8,4 +8,21 @@ async def unignore_user(pg, user_id):
 	await pg.execute("UPDATE \"user\" SET ignore = FALSE WHERE user_id = $1", user_id)
 
 async def is_ignored(pg, user_id):
-	return await pg.fetchval("SELECT ignore FROM \"user\" WHERE user_id = $1", user_id)
+	return await pg.fetchval("SELECT ignore FROM \"user\" WHERE user_id = $1", user_id)
+
+async def get_level(pg, user_id):
+	return await pg.fetchval("SELECT level FROM \"user\" WHERE user_id = $1", user_id)
+
+async def get_xp(pg, user_id):
+	message_array = await pg.fetch("SELECT total_messages FROM channel_user WHERE user_id = $1", user_id)
+	print(message_array)
+	total_xp = 0
+	for messages in message_array:
+		print(messages)
+		total_xp += messages
+
+	xp_spent = await pg.fetchval("SELECT xp_spent FROM \"user\" WHERE user_id = $1", user_id)
+	return xp_spent, total_xp
+
+async def level_up(pg, user_id, xp):
+	await pg.execute("UPDATE \"user\" (level, xp_spent) VALUES(+ 1, $2) WHERE user_id = $1", user_id, xp)