diff --git a/kdb-bot/src/bot_api/api_module.py b/kdb-bot/src/bot_api/api_module.py index 0a9446ad5d..7348388fcb 100644 --- a/kdb-bot/src/bot_api/api_module.py +++ b/kdb-bot/src/bot_api/api_module.py @@ -15,6 +15,7 @@ from bot_api.controller.discord.server_controller import ServerController from bot_api.controller.gui_controller import GuiController from bot_api.controller.auth_controller import AuthController from bot_api.event.bot_api_on_ready_event import BotApiOnReadyEvent +from bot_api.mail.mail_thread import MailThread from bot_api.service.auth_service import AuthService from bot_api.service.discord_service import DiscordService from bot_core.abc.module_abc import ModuleABC @@ -36,6 +37,7 @@ class ApiModule(ModuleABC): def configure_services(self, services: ServiceCollectionABC, env: ApplicationEnvironmentABC): services.add_singleton(EMailClientABC, EMailClient) + services.add_singleton(MailThread) services.add_singleton(ApiThread) services.add_singleton(Flask, Api) diff --git a/kdb-bot/src/bot_api/mail/__init__.py b/kdb-bot/src/bot_api/mail/__init__.py new file mode 100644 index 0000000000..425ab6c146 --- /dev/null +++ b/kdb-bot/src/bot_api/mail/__init__.py @@ -0,0 +1 @@ +# imports diff --git a/kdb-bot/src/bot_api/mail/mail_thread.py b/kdb-bot/src/bot_api/mail/mail_thread.py new file mode 100644 index 0000000000..c6ae4c0b90 --- /dev/null +++ b/kdb-bot/src/bot_api/mail/mail_thread.py @@ -0,0 +1,23 @@ +import threading +from typing import Optional + +from cpl_core.mailing import EMailClientABC, EMail + + +class MailThread(threading.Thread): + + def __init__(self, mailer: EMailClientABC): + threading.Thread.__init__(self, daemon=True) + + self._mailer = mailer + self._mail: Optional[EMail] = None + + def send_mail(self, mail: EMail): + self._mail = mail + self.start() + + def run(self) -> None: + if self._mailer is None: + return + + self._mailer.send_mail(self._mail) diff --git a/kdb-bot/src/bot_api/service/auth_service.py b/kdb-bot/src/bot_api/service/auth_service.py index 94f8830047..7e4c969bd1 100644 --- a/kdb-bot/src/bot_api/service/auth_service.py +++ b/kdb-bot/src/bot_api/service/auth_service.py @@ -20,6 +20,7 @@ from bot_api.exception.service_error_code_enum import ServiceErrorCode from bot_api.exception.service_exception import ServiceException from bot_api.filter.auth_user_select_criteria import AuthUserSelectCriteria from bot_api.logging.api_logger import ApiLogger +from bot_api.mail.mail_thread import MailThread from bot_api.model.auth_user_dto import AuthUserDTO from bot_api.model.auth_user_filtered_result_dto import AuthUserFilteredResultDTO from bot_api.model.email_string_dto import EMailStringDTO @@ -41,7 +42,7 @@ class AuthService(AuthServiceABC): logger: ApiLogger, auth_users: AuthUserRepositoryABC, db: DatabaseContextABC, - mailer: EMailClientABC, + mailer: MailThread, t: TranslatePipe, auth_settings: AuthenticationSettings, frontend_settings: FrontendSettings, @@ -132,7 +133,7 @@ class AuthService(AuthServiceABC): self._db.save_changes() return token - def _send_confirmation_id_to_user(self, user: AuthUser): + def _send_link_mail(self, email: str, subject: str, message: str): url = self._frontend_settings.url if not url.endswith('/'): url = f'{url}/' @@ -141,30 +142,34 @@ class AuthService(AuthServiceABC): mail.add_header('Mime-Version: 1.0') mail.add_header('Content-Type: text/plain; charset=utf-8') mail.add_header('Content-Transfer-Encoding: quoted-printable') - mail.add_receiver(str(user.email)) - mail.subject = self._t.transform('api.auth.confirmation.subject').format(user.first_name, user.last_name) - mail.body = textwrap.dedent(f"""{self._t.transform('api.auth.confirmation.message').format(url, user.forgot_password_id)} + mail.add_receiver(str(email)) + mail.subject = subject + mail.body = textwrap.dedent(f"""{message} {self._t.transform('api.mail.automatic_mail').format(self._environment.application_name, self._environment.environment_name, self._environment.host_name)} """) self._mailer.send_mail(mail) + def _send_confirmation_id_to_user(self, user: AuthUser): + url = self._frontend_settings.url + if not url.endswith('/'): + url = f'{url}/' + + self._send_link_mail( + user.email, + self._t.transform('api.auth.confirmation.subject').format(user.first_name, user.last_name), + self._t.transform('api.auth.confirmation.message').format(url, user.forgot_password_id) + ) + def _send_forgot_password_id_to_user(self, user: AuthUser): url = self._frontend_settings.url if not url.endswith('/'): url = f'{url}/' - # todo send mail in background task - # todo create cpl ticket to send mails async - mail = EMail() - mail.add_header('Mime-Version: 1.0') - mail.add_header('Content-Type: text/plain; charset=utf-8') - mail.add_header('Content-Transfer-Encoding: quoted-printable') - mail.add_receiver(str(user.email)) - mail.subject = self._t.transform('api.auth.forgot_password.subject').format(user.first_name, user.last_name) - mail.body = textwrap.dedent(f"""{self._t.transform('api.auth.forgot_password.message').format(url, user.forgot_password_id)} - {self._t.transform('api.mail.automatic_mail').format(self._environment.application_name, self._environment.environment_name, self._environment.host_name)} - """) - self._mailer.send_mail(mail) + self._send_link_mail( + user.email, + self._t.transform('api.auth.forgot_password.subject').format(user.first_name, user.last_name), + self._t.transform('api.auth.forgot_password.message').format(url, user.forgot_password_id) + ) async def get_all_auth_users_async(self) -> List[AuthUserDTO]: result = self._auth_users.get_all_auth_users() \