Profile schema and discord hook
This commit is contained in:
89
profiles/discord/cog.py
Normal file
89
profiles/discord/cog.py
Normal file
@@ -0,0 +1,89 @@
|
||||
from typing import Optional
|
||||
import asyncio
|
||||
|
||||
import discord
|
||||
from discord.ext import commands as cmds
|
||||
from discord import app_commands as appcmds
|
||||
|
||||
from meta import LionBot, LionCog, LionContext
|
||||
from meta.logger import log_wrap
|
||||
from utils.lib import utc_now
|
||||
|
||||
from ..data import ProfilesData, UserProfile, DiscordProfileLink, Community, DiscordCommunityLink
|
||||
from ..profiles import ProfilesRegistry
|
||||
|
||||
class ProfilesCog(LionCog):
|
||||
def __init__(self, bot: LionBot):
|
||||
self.bot = bot
|
||||
|
||||
self.data = bot.db.load_registry(ProfilesData())
|
||||
self.profiles = ProfilesRegistry(self.data)
|
||||
|
||||
async def cog_load(self):
|
||||
await self.data.init()
|
||||
await self.bot.version_check(*self.data.VERSION)
|
||||
await self.profiles.init()
|
||||
|
||||
async def bot_check_once(self, ctx: LionContext):
|
||||
profile = await self.fetch_profile(ctx.author, interaction=ctx.interaction, touch=True)
|
||||
ctx.profile = profile
|
||||
if ctx.guild:
|
||||
community = await self.fetch_community(ctx.guild, interaction=ctx.interaction, touch=True)
|
||||
ctx.community = community
|
||||
else:
|
||||
ctx.community = None
|
||||
return True
|
||||
|
||||
@log_wrap(isolate=True, action="Fetch Profile")
|
||||
async def fetch_profile(
|
||||
self,
|
||||
user: discord.User | discord.Member,
|
||||
interaction: Optional[discord.Interaction] = None,
|
||||
touch: bool = False,
|
||||
) -> UserProfile:
|
||||
"""
|
||||
Fetch or create the profile for the given user.
|
||||
"""
|
||||
async with self.bot.db.connection() as conn:
|
||||
self.bot.db.conn = conn
|
||||
async with conn.transaction():
|
||||
profile = await self.profiles.get_profile_discord(user.id)
|
||||
if profile is None:
|
||||
# Create a new profile
|
||||
# Then link with discord
|
||||
args = {
|
||||
'nickname': user.display_name,
|
||||
}
|
||||
if interaction:
|
||||
if interaction.locale:
|
||||
args['locale_hint'] = interaction.locale.language_code
|
||||
if user.avatar:
|
||||
args['avatar'] = user.avatar.url
|
||||
profile = await UserProfile.create(**args)
|
||||
await DiscordProfileLink.create(profileid=profile.profileid, userid=user.id)
|
||||
elif touch:
|
||||
await profile.update(last_seen=utc_now())
|
||||
|
||||
return profile
|
||||
|
||||
@log_wrap(isolate=True, action="Fetch Community")
|
||||
async def fetch_community(
|
||||
self,
|
||||
guild: discord.Guild,
|
||||
interaction: Optional[discord.Interaction] = None,
|
||||
touch: bool = False,
|
||||
) -> Community:
|
||||
"""
|
||||
Fetch or create the community for the given guild.
|
||||
"""
|
||||
async with self.bot.db.connection() as conn:
|
||||
self.bot.db.conn = conn
|
||||
async with conn.transaction():
|
||||
comm = await self.profiles.get_community_discord(guild.id)
|
||||
if comm is None:
|
||||
# Create a new Community and link to Discord
|
||||
comm = await Community.create()
|
||||
await DiscordCommunityLink.create(guildid=guild.id, communityid=comm.communityid)
|
||||
elif touch:
|
||||
await comm.update(last_seen=utc_now())
|
||||
return comm
|
||||
Reference in New Issue
Block a user