add simple /help and !help command handling

This commit is contained in:
Andreas Köpf
2022-12-22 16:12:00 +01:00
parent 3205491166
commit cad6a450c0
5 changed files with 118 additions and 49 deletions
+45 -13
View File
@@ -84,7 +84,8 @@ class OpenAssistantBot(BotBase):
@self.tree.command()
async def help(interaction: discord.Interaction):
"""Sends the user a list of all available commands"""
await interaction.response.send_message(f"help command by {interaction.user.name}")
await self.post_help(interaction.user)
await interaction.response.send_message(f"@{interaction.user.display_name}, I've sent you a PM.")
@self.tree.command()
async def work(interaction: discord.Interaction):
@@ -95,6 +96,10 @@ class OpenAssistantBot(BotBase):
q = task_handlers.Questionnaire()
await interaction.response.send_modal(q)
async def post_help(self, user: discord.abc.User) -> discord.Message:
is_bot_owner = user.id == self.owner_id
return await self.post_template("help.msg", channel=user, is_bot_owner=is_bot_owner)
async def post_boot_message(self) -> discord.Message:
return await self.post_template(
"boot.msg", bot_name=BOT_NAME, version=__version__, git_hash=get_git_head_hash(), debug=self.debug
@@ -104,7 +109,13 @@ class OpenAssistantBot(BotBase):
return await self.post_template("welcome.msg")
async def delete_all_old_bot_messages(self) -> None:
logger.info("Begin deleting old bot messages.")
logger.info("Deleting old threads...")
for thread in self.bot_channel.threads:
if thread.owner_id == self.client.user.id:
await thread.delete()
logger.info("Completed deleting old theards.")
logger.info("Deleting old bot messages...")
look_until = utcnow() - timedelta(days=365)
async for msg in self.bot_channel.history(limit=None):
msg: discord.Message
@@ -119,7 +130,7 @@ class OpenAssistantBot(BotBase):
return msg
async def next_task(self):
task_type = protocol_schema.TaskRequestType.rate_summary
task_type = protocol_schema.TaskRequestType.random
task = self.backend.fetch_task(task_type, user=None)
await self.print_separtor("New Task")
@@ -199,22 +210,47 @@ class OpenAssistantBot(BotBase):
command_text: str = message.content
command_text = command_text[1:]
match command_text:
case "sync" | "sync.guild" | "sync.copy_global" | "sync.clear_guild" | "sync.clear_guild":
case "help" | "?":
await self.post_help(user=message.author)
case "sync" | "sync.guild" | "sync.copy_global" | "sync.clear_guild":
if is_owner:
await self._sync(command_text, message)
case _:
await message.reply(f"unknown command: {command_text}")
def recipient_filter(self, message: discord.Message) -> bool:
channel = message.channel
if (
message.channel.type == discord.ChannelType.private
or message.channel.type == discord.ChannelType.private_thread
):
return True
if (
message.channel.type == discord.ChannelType.text
or message.channel.type == discord.ChannelType.public_thread
):
while channel:
if self.bot_channel and channel.id == self.bot_channel.id:
return True
channel = channel.parent
return False
async def handle_message(self, message: discord.Message):
if not self.recipient_filter(message):
return
user_id = message.author.id
user_display_name = message.author.name
logger.debug(
f"{message.type} {message.channel.type} from ({user_display_name}) {user_id}: {message.content} ({type(message.content)})"
)
command_prefix = "!"
if (
message.channel.type == discord.ChannelType.private
and message.type == discord.MessageType.default
and message.content.startswith(command_prefix)
):
if message.type == discord.MessageType.default and message.content.startswith(command_prefix):
is_owner = self.owner_id and user_id == self.owner_id
await self.handle_command(message, is_owner)
@@ -228,10 +264,6 @@ class OpenAssistantBot(BotBase):
if handler and not handler.handler.completed:
handler.handler.on_reply(message)
logger.debug(
f"{message.type} {message.channel.type} from ({user_display_name}) {user_id}: {message.content} ({type(message.content)})"
)
async def remove_completed_handlers(self):
completed = [k for k, v in self.reply_handlers.items() if v.handler is None or v.handler.completed]
if len(completed) == 0:
+11 -5
View File
@@ -36,14 +36,20 @@ class BotBase(ABC):
if self.bot_channel is None:
raise RuntimeError(f"bot channel '{self.bot_channel_name}' not found")
async def post(self, content: str, view: discord.ui.View = None) -> discord.Message:
self.ensure_bot_channel()
return await self.bot_channel.send(content=content, view=view)
async def post(
self, content: str, *, view: discord.ui.View = None, channel: discord.abc.Messageable = None
) -> discord.Message:
if channel is None:
self.ensure_bot_channel()
channel = self.bot_channel
return await channel.send(content=content, view=view)
async def post_template(self, name: str, *, view: discord.ui.View = None, **kwargs: Any) -> discord.Message:
async def post_template(
self, name: str, *, view: discord.ui.View = None, channel: discord.abc.Messageable = None, **kwargs: Any
) -> discord.Message:
logger.debug(f"rendering {name}")
text = self.templates.render(name, **kwargs)
return await self.post(text, view)
return await self.post(text, view=view, channel=channel)
def register_reply_handler(self, msg_id: int, handler: ChannelHandlerBase):
if msg_id in self.reply_handlers:
+3 -3
View File
@@ -66,15 +66,15 @@ class AutoDestructThreadHandler(ChannelHandlerBase):
return await super().read()
except ChannelExpiredException:
await self.cleanup()
raise
async def cleanup(self):
logger.debug("AutoDestructThreadHandler.cleanup")
if self.thread:
logger.debug(f"[expired] deleting thread: {self.thread.name}")
logger.debug(f"deleting thread: {self.thread.name}")
await self.thread.delete()
self.thread = None
if self.first_message:
logger.debug(f"[expired] deleting first_message: {self.first_message.content}")
logger.debug(f"deleting first_message: {self.first_message.content}")
await self.first_message.delete()
self.first_message = None
+44 -28
View File
@@ -30,10 +30,14 @@ class ChannelTaskBase(AutoDestructThreadHandler):
msg = await self.send_first_message()
self.first_message = msg
self.thread = await bot.bot_channel.create_thread(message=discord.Object(msg.id), name=self.thread_name)
await self.on_thread_created(self.thread)
self.expiry_date = utcnow() + self.expires_after if self.expires_after else None
bot.register_reply_handler(msg_id=msg.id, handler=self)
return msg
async def on_thread_created(self, thread: discord.Thread) -> None:
pass
@abstractmethod
async def send_first_message(self) -> discord.message:
...
@@ -47,10 +51,11 @@ class SummarizeStoryHandler(ChannelTaskBase):
return await self.bot.post_template("task_summarize_story.msg", task=self.task)
async def handler_loop(self):
msg = await self.read()
print("received: ", msg, type(msg))
logger.info("on_summarize_story_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
print("received: ", msg, type(msg))
logger.info("on_summarize_story_reply")
await msg.add_reaction("")
class InitialPromptHandler(ChannelTaskBase):
@@ -61,9 +66,10 @@ class InitialPromptHandler(ChannelTaskBase):
return await self.bot.post_template("task_initial_prompt.msg", task=self.task)
async def handler_loop(self):
msg = await self.read()
logger.info("on_initial_prompt_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
logger.info("on_initial_prompt_reply")
await msg.add_reaction("")
class UserReplyHandler(ChannelTaskBase):
@@ -74,9 +80,10 @@ class UserReplyHandler(ChannelTaskBase):
return await self.bot.post_template("task_user_reply.msg", task=self.task)
async def handler_loop(self):
msg = await self.read()
logger.info("on_user_reply_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
logger.info("on_user_reply_reply")
await msg.add_reaction("")
class AssistantReplyHandler(ChannelTaskBase):
@@ -87,9 +94,10 @@ class AssistantReplyHandler(ChannelTaskBase):
return await self.bot.post_template("task_assistant_reply.msg", task=self.task)
async def handler_loop(self):
msg = await self.read()
logger.info("on_assistant_reply_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
logger.info("on_assistant_reply_reply")
await msg.add_reaction("")
class RankInitialPromptsHandler(ChannelTaskBase):
@@ -100,9 +108,10 @@ class RankInitialPromptsHandler(ChannelTaskBase):
return await self.bot.post_template("task_rank_initial_prompts.msg", task=self.task)
async def handler_loop(self):
msg = await self.read()
logger.info("on_rank_initial_prompts_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
logger.info("on_rank_initial_prompts_reply")
await msg.add_reaction("")
class RankConversationsHandler(ChannelTaskBase):
@@ -113,9 +122,10 @@ class RankConversationsHandler(ChannelTaskBase):
return await self.bot.post_template("task_rank_conversation_replies.msg", task=self.task)
async def handler_loop(self):
msg = await self.read()
logger.info("on_rank_conversation_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
logger.info("on_rank_conversation_reply")
await msg.add_reaction("")
class RatingButton(discord.ui.Button):
@@ -139,15 +149,21 @@ class RateSummaryHandler(ChannelTaskBase):
task: protocol_schema.RateSummaryTask
thread_name: str = "Rate"
async def send_first_message(self) -> discord.message:
async def rating_response_handler(score, interaction: discord.Interaction):
logger.info("rating_response_handler", score)
await interaction.response.send_message(f"got your feedback: {score}")
async def _rating_response_handler(self, score, interaction: discord.Interaction):
logger.info("rating_response_handler", score)
if self.thread:
await self.thread.send(f"{interaction.user.name} got your feedback: {score}")
await interaction.response.send_message(f"got your feedback: {score}")
view = generate_rating_view(self.task.scale.min, self.task.scale.max, rating_response_handler)
return await self.bot.post_template("task_rate_summary.msg", view=view, task=self.task)
async def send_first_message(self) -> discord.message:
return await self.bot.post("first message")
async def on_thread_created(self, thread: discord.Thread) -> None:
view = generate_rating_view(self.task.scale.min, self.task.scale.max, self._rating_response_handler)
return await self.bot.post_template("task_rate_summary.msg", view=view, channel=thread, task=self.task)
async def handler_loop(self):
msg = await self.read()
logger.info("on_rate_summary_reply")
await msg.add_reaction("")
while True:
msg = await self.read()
logger.info("on_rate_summary_reply")
await msg.add_reaction("")
+15
View File
@@ -0,0 +1,15 @@
**Open-Assistant Bot Help**
Available slash-commands:
`/work` Requests a new personalized human feedback task
`/help` Show this message
{% if is_bot_owner %}
Commands for bot owners:
`!sync`
`!sync.guild`
`!sync.copy_global`
`!sync.clear_guild`
{% endif %}