Add a new function for parsing time from a string
This commit is contained in:
@ -1,4 +1,6 @@
|
|||||||
|
import dataclasses
|
||||||
import logging
|
import logging
|
||||||
|
from datetime import datetime
|
||||||
from typing import List
|
from typing import List
|
||||||
|
|
||||||
import dateparser
|
import dateparser
|
||||||
@ -6,7 +8,7 @@ import interactions
|
|||||||
from apscheduler.jobstores.base import JobLookupError
|
from apscheduler.jobstores.base import JobLookupError
|
||||||
from apscheduler.triggers.date import DateTrigger
|
from apscheduler.triggers.date import DateTrigger
|
||||||
from dateparser.conf import SettingValidationError
|
from dateparser.conf import SettingValidationError
|
||||||
from interactions import CommandContext, Embed, Option, OptionType, autodefer
|
from interactions import CommandContext, Embed, Option, OptionType
|
||||||
from interactions.ext.paginator import Paginator
|
from interactions.ext.paginator import Paginator
|
||||||
|
|
||||||
from discord_reminder_bot.countdown import calculate
|
from discord_reminder_bot.countdown import calculate
|
||||||
@ -30,6 +32,55 @@ async def base_command(ctx: interactions.CommandContext):
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
@dataclasses.dataclass
|
||||||
|
class ParsedTime:
|
||||||
|
"""
|
||||||
|
This is used when parsing a time or date from a string.
|
||||||
|
|
||||||
|
We use this when adding a job with /reminder add.
|
||||||
|
|
||||||
|
Attributes:
|
||||||
|
date_to_parse: The string we parsed the time from.
|
||||||
|
err: True if an error was raised when parsing the time.
|
||||||
|
err_msg: The error message.
|
||||||
|
parsed_time: The parsed time we got from the string.
|
||||||
|
"""
|
||||||
|
date_to_parse: str = None
|
||||||
|
err: bool = False
|
||||||
|
err_msg: str = ""
|
||||||
|
parsed_time: datetime = None
|
||||||
|
|
||||||
|
|
||||||
|
def parse_time(date_to_parse: str, timezone: str = config_timezone) -> ParsedTime:
|
||||||
|
"""Parse the datetime from a string.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
date_to_parse: The string we want to parse.
|
||||||
|
timezone: The timezone to use when parsing. This will be used when typing things like "22:00".
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
ParsedTime
|
||||||
|
"""
|
||||||
|
try:
|
||||||
|
parsed_date = dateparser.parse(
|
||||||
|
f"{date_to_parse}",
|
||||||
|
settings={
|
||||||
|
"PREFER_DATES_FROM": "future",
|
||||||
|
"TIMEZONE": f"{timezone}",
|
||||||
|
"TO_TIMEZONE": f"{timezone}",
|
||||||
|
},
|
||||||
|
)
|
||||||
|
except SettingValidationError as e:
|
||||||
|
return ParsedTime(err=True, err_msg=f"Timezone is possible wrong?: {e}", date_to_parse=date_to_parse)
|
||||||
|
except ValueError as e:
|
||||||
|
return ParsedTime(err=True, err_msg=f"Failed to parse date. Unknown language: {e}", date_to_parse=date_to_parse)
|
||||||
|
|
||||||
|
if not parsed_date:
|
||||||
|
return ParsedTime(err=True, err_msg=f"Could not parse the date.", date_to_parse=date_to_parse)
|
||||||
|
|
||||||
|
return ParsedTime(parsed_time=parsed_date, date_to_parse=date_to_parse)
|
||||||
|
|
||||||
|
|
||||||
@bot.modal("edit_modal")
|
@bot.modal("edit_modal")
|
||||||
async def modal_response_edit(ctx: CommandContext, *response: str):
|
async def modal_response_edit(ctx: CommandContext, *response: str):
|
||||||
"""This is what gets triggerd when the user clicks the Edit button in /reminder list.
|
"""This is what gets triggerd when the user clicks the Edit button in /reminder list.
|
||||||
@ -84,34 +135,22 @@ async def modal_response_edit(ctx: CommandContext, *response: str):
|
|||||||
msg = f"Modified job {job_id}.\n"
|
msg = f"Modified job {job_id}.\n"
|
||||||
if old_date is not None:
|
if old_date is not None:
|
||||||
if new_date:
|
if new_date:
|
||||||
try:
|
# Parse the time/date we got from the command.
|
||||||
parsed_date = dateparser.parse(
|
parsed = parse_time(date_to_parse=new_date)
|
||||||
f"{new_date}",
|
if parsed.err:
|
||||||
settings={
|
return await ctx.send(parsed.err_msg)
|
||||||
"PREFER_DATES_FROM": "future",
|
parsed_date = parsed.parsed_time
|
||||||
"TIMEZONE": f"{config_timezone}",
|
|
||||||
"TO_TIMEZONE": f"{config_timezone}",
|
|
||||||
},
|
|
||||||
)
|
|
||||||
except SettingValidationError as e:
|
|
||||||
return await ctx.send(
|
|
||||||
f"Timezone is possible wrong?: {e}", ephemeral=True
|
|
||||||
)
|
|
||||||
except ValueError as e:
|
|
||||||
return await ctx.send(
|
|
||||||
f"Failed to parse date. Unknown language: {e}", ephemeral=True
|
|
||||||
)
|
|
||||||
|
|
||||||
if not parsed_date:
|
|
||||||
return await ctx.send("Could not parse the date.", ephemeral=True)
|
|
||||||
|
|
||||||
date_new = parsed_date.strftime("%Y-%m-%d %H:%M:%S")
|
date_new = parsed_date.strftime("%Y-%m-%d %H:%M:%S")
|
||||||
|
|
||||||
new_job = scheduler.reschedule_job(job.id, run_date=date_new)
|
new_job = scheduler.reschedule_job(job.id, run_date=date_new)
|
||||||
new_time = calculate(new_job)
|
new_time = calculate(new_job)
|
||||||
|
|
||||||
|
# TODO: old_date and date_new has different precision.
|
||||||
|
# Old date: 2032-09-18 00:07
|
||||||
|
# New date: 2032-09-18 00:07:13
|
||||||
msg += (
|
msg += (
|
||||||
f"**Old date**: {old_date}\n**New date**: {date_new} (in {new_time})\n"
|
f"**Old date**: {old_date}\n"
|
||||||
|
f"**New date**: {date_new} (in {new_time})\n"
|
||||||
)
|
)
|
||||||
|
|
||||||
if old_message is not None:
|
if old_message is not None:
|
||||||
@ -205,31 +244,17 @@ async def command_add(
|
|||||||
message_reason: The message the bot should write when the reminder is triggered.
|
message_reason: The message the bot should write when the reminder is triggered.
|
||||||
different_channel: The channel the reminder should be sent to.
|
different_channel: The channel the reminder should be sent to.
|
||||||
"""
|
"""
|
||||||
try:
|
# Parse the time/date we got from the command.
|
||||||
parsed_date = dateparser.parse(
|
parsed = parse_time(date_to_parse=message_date)
|
||||||
f"{message_date}",
|
if parsed.err:
|
||||||
settings={
|
return await ctx.send(parsed.err_msg)
|
||||||
"PREFER_DATES_FROM": "future",
|
parsed_date = parsed.parsed_time
|
||||||
"TIMEZONE": f"{config_timezone}",
|
run_date = parsed_date.strftime("%Y-%m-%d %H:%M:%S")
|
||||||
"TO_TIMEZONE": f"{config_timezone}",
|
|
||||||
},
|
|
||||||
)
|
|
||||||
except SettingValidationError as e:
|
|
||||||
return await ctx.send(f"Timezone is possible wrong?: {e}", ephemeral=True)
|
|
||||||
except ValueError as e:
|
|
||||||
return await ctx.send(
|
|
||||||
f"Failed to parse date. Unknown language: {e}", ephemeral=True
|
|
||||||
)
|
|
||||||
if not parsed_date:
|
|
||||||
return await ctx.send("Could not parse the date.", ephemeral=True)
|
|
||||||
|
|
||||||
channel_id = int(ctx.channel_id)
|
|
||||||
|
|
||||||
# If we should send the message to a different channel
|
# If we should send the message to a different channel
|
||||||
|
channel_id = int(ctx.channel_id)
|
||||||
if different_channel:
|
if different_channel:
|
||||||
channel_id = int(different_channel.id)
|
channel_id = int(different_channel.id)
|
||||||
|
|
||||||
run_date = parsed_date.strftime("%Y-%m-%d %H:%M:%S")
|
|
||||||
try:
|
try:
|
||||||
reminder = scheduler.add_job(
|
reminder = scheduler.add_job(
|
||||||
send_to_discord,
|
send_to_discord,
|
||||||
@ -497,7 +522,6 @@ async def remind_cron(
|
|||||||
),
|
),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
@autodefer()
|
|
||||||
async def remind_interval(
|
async def remind_interval(
|
||||||
ctx: interactions.CommandContext,
|
ctx: interactions.CommandContext,
|
||||||
message_reason: str,
|
message_reason: str,
|
||||||
|
Reference in New Issue
Block a user