Clean up mailing code

This commit is contained in:
Florine W. Dekker 2022-12-01 23:05:12 +01:00
parent ca30d9d42c
commit f67873467e
Signed by: FWDekker
GPG Key ID: D3DCFAA8A4560BE0
19 changed files with 285 additions and 236 deletions

View File

@ -1,7 +1,7 @@
{
"name": "fwdekker/death-notifier",
"description": "Get notified when a famous person dies.",
"version": "0.15.4", "_comment_version": "Also update version in `package.json`!",
"version": "0.15.5", "_comment_version": "Also update version in `package.json`!",
"type": "project",
"license": "MIT",
"homepage": "https://git.fwdekker.com/tools/death-notifier",

View File

@ -1,6 +1,6 @@
{
"name": "death-notifier",
"version": "0.15.4", "_comment_version": "Also update version in `composer.json`!",
"version": "0.15.5", "_comment_version": "Also update version in `composer.json`!",
"description": "Get notified when a famous person dies.",
"author": "Florine W. Dekker",
"browser": "dist/bundle.js",

View File

@ -4,7 +4,8 @@ use com\fwdekker\deathnotifier\ActionDispatcher;
use com\fwdekker\deathnotifier\ActionMethod;
use com\fwdekker\deathnotifier\Database;
use com\fwdekker\deathnotifier\EmulateCronCliAction;
use com\fwdekker\deathnotifier\mailer\Mailer;
use com\fwdekker\deathnotifier\LoggerUtil;
use com\fwdekker\deathnotifier\mailer\MailManager;
use com\fwdekker\deathnotifier\mailer\ProcessEmailQueueCliAction;
use com\fwdekker\deathnotifier\mediawiki\MediaWiki;
use com\fwdekker\deathnotifier\Response;
@ -36,14 +37,16 @@ require_once __DIR__ . "/.vendor/autoload.php";
// Preamble
$config = Util::read_config();
// TODO: Improve logging specificity and usefulness
$logger = Util::create_logger($config["logger"]);
$db = new Database($logger->withName("Database"), $config["database"]["filename"]);
$mailer = new Mailer($config, $logger->withName("Mailer"), $db->conn);
$mediawiki = new MediaWiki($logger->withName("Mediawiki"));
$user_manager = new UserManager($logger->withName("UserManager"), $db->conn, $mailer);
$tracking_manager = new TrackingManager($logger->withName("TrackingManager"), $db->conn);
LoggerUtil::configure($config["logger"]);
$logger = LoggerUtil::with_name();
$db = new Database($config["database"]["filename"]);
$mediawiki = new MediaWiki();
$mail_manager = new MailManager($db->conn);
$user_manager = new UserManager($db->conn, $mail_manager);
$tracking_manager = new TrackingManager($db->conn);
// Handle request
@ -53,7 +56,7 @@ try {
$_POST = Util::parse_post();
// Update database
$db->auto_install($mailer, $user_manager, $tracking_manager);
$db->auto_install($mail_manager, $user_manager, $tracking_manager);
$db->auto_migrate();
// Dispatch request
@ -79,8 +82,8 @@ try {
$dispatcher->register_action(new RemoveTrackingAction($tracking_manager));
// CLI actions
$cli_actions = [
new UpdateTrackingsCliAction($config, $db->conn, $tracking_manager, $mediawiki, $mailer),
new ProcessEmailQueueCliAction($config, $mailer),
new UpdateTrackingsCliAction($config, $db->conn, $tracking_manager, $mediawiki, $mail_manager),
new ProcessEmailQueueCliAction($config, $mail_manager),
];
$dispatcher->register_action($cli_actions[0]);
$dispatcher->register_action($cli_actions[1]);

View File

@ -11,15 +11,15 @@ use com\fwdekker\deathnotifier\validator\Rule;
abstract class CliAction extends Action
{
/**
* @var mixed the application's configuration
* @var array<string, mixed> the application's configuration
*/
private mixed $config;
protected mixed $config;
/**
* Constructs a new CLI action.
*
* @param mixed $config the application's configuration
* @param array<string, mixed> $config the application's configuration
* @param string $name the name of the action that this action handles
* @param array<string, Rule[]> $rule_lists maps input keys to {@see Rule}s that should be validated before this
* action is handled

View File

@ -2,7 +2,7 @@
namespace com\fwdekker\deathnotifier;
use com\fwdekker\deathnotifier\mailer\Mailer;
use com\fwdekker\deathnotifier\mailer\MailManager;
use com\fwdekker\deathnotifier\tracking\TrackingManager;
use com\fwdekker\deathnotifier\user\UserManager;
use Composer\Semver\Comparator;
@ -33,12 +33,11 @@ class Database
/**
* Opens a connection with the database at `filename`.
*
* @param Logger $logger the logger to use for logging
* @param string $filename the path to the database to connect to
*/
public function __construct(Logger $logger, string $filename)
public function __construct(string $filename)
{
$this->logger = $logger;
$this->logger = LoggerUtil::with_name("Database");
$this->conn = new PDO("sqlite:$filename", options: array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION));
$this->conn->exec("PRAGMA foreign_keys = ON;");
@ -48,12 +47,12 @@ class Database
/**
* Installs all necessary data structures to get the database working.
*
* @param Mailer $mailer the mailer to install
* @param MailManager $mailer the mailer to install
* @param UserManager $userManager the use manager to install
* @param TrackingManager $trackingManager the tracking manager to install
* @return void
*/
public function auto_install(Mailer $mailer, UserManager $userManager, TrackingManager $trackingManager): void
public function auto_install(MailManager $mailer, UserManager $userManager, TrackingManager $trackingManager): void
{
// TODO: Keep track of statistics, such as #users, mails sent, etc.
self::transaction($this->conn, function () use ($mailer, $userManager, $trackingManager) {

View File

@ -1,10 +1,14 @@
<?php
namespace com\fwdekker\deathnotifier;
use Error;
/**
* Thrown if something happens that should not be able to happen, and there is no way to recover.
*/
class InvalidStateException extends Error
class IllegalStateException extends Error
{
// Intentionally left empty
}

View File

@ -0,0 +1,53 @@
<?php
namespace com\fwdekker\deathnotifier;
use Monolog\ErrorHandler;
use Monolog\Handler\StreamHandler;
use Monolog\Logger;
/**
* Helps with creating loggers.
*
* Contains global state, but reduces unnecessary parameter passing and unused fields.
*/
// TODO: Improve logging specificity and usefulness
class LoggerUtil
{
/**
* @var Logger|null the main logger instance that other loggers are derived from
*/
private static ?Logger $main_logger = null;
/**
* Configures the main logger.
*
* @param array $config the logger configuration
* @return void
*/
public static function configure(array $config): void
{
if (self::$main_logger !== null)
throw new IllegalStateException("Logger has already been created.");
self::$main_logger = new Logger("main");
self::$main_logger->pushHandler(new StreamHandler($config["file"], $config["level"]));
ErrorHandler::register(self::$main_logger);
}
/**
* Returns a logger with the given name.
*
* @param string $name the name of the logger to return
* @return Logger a logger with the given name
*/
public static function with_name(string $name = "main"): Logger
{
if (self::$main_logger === null)
throw new IllegalStateException("Logger has not been created yet.");
return self::$main_logger->withName($name);
}
}

View File

@ -48,21 +48,6 @@ class Util
return $config;
}
/**
* Creates the main logger instance.
*
* @param array<string, mixed> $logger_config the logger section of the configuration
* @return Logger the main logger instance
*/
static function create_logger(array $logger_config): Logger
{
$logger = new Logger("main");
$logger->pushHandler(new StreamHandler($logger_config["file"], $logger_config["level"]));
ErrorHandler::register($logger);
return $logger;
}
/**
* Parses POST values from JSON-based inputs.
*

View File

@ -2,6 +2,7 @@
namespace com\fwdekker\deathnotifier\mailer;
use com\fwdekker\deathnotifier\IllegalStateException;
use com\fwdekker\deathnotifier\tracking\NotifyArticleDeletedEmail;
use com\fwdekker\deathnotifier\tracking\NotifyArticleUndeletedEmail;
use com\fwdekker\deathnotifier\tracking\NotifyStatusChangedEmail;
@ -10,7 +11,6 @@ use com\fwdekker\deathnotifier\user\ChangedPasswordEmail;
use com\fwdekker\deathnotifier\user\RegisterEmail;
use com\fwdekker\deathnotifier\user\ResetPasswordEmail;
use com\fwdekker\deathnotifier\user\VerifyEmailEmail;
use Exception;
/**
@ -65,7 +65,6 @@ abstract class Email
* @param string $arg1 the first argument to construct the email
* @param string $arg2 the second argument to construct the email
* @return Email a deserialized email
* @throws Exception if the `type` is not recognized
*/
public static function deserialize(string $type, string $recipient, string $arg1, string $arg2): Email
{
@ -80,7 +79,7 @@ abstract class Email
NotifyArticleDeletedEmail::TYPE => new NotifyArticleDeletedEmail($recipient, $arg1),
NotifyArticleUndeletedEmail::TYPE => new NotifyArticleUndeletedEmail($recipient, $arg1),
NotifyStatusChangedEmail::TYPE => new NotifyStatusChangedEmail($recipient, $arg1, $arg2),
default => throw new Exception("Unknown email type $type."),
default => throw new IllegalStateException("Unknown email type $type."),
};
}
}

View File

@ -0,0 +1,102 @@
<?php
namespace com\fwdekker\deathnotifier\mailer;
use PDO;
/**
* Queues up mails and sends them when appropriate.
*/
class MailManager
{
/**
* @var PDO the database connection to interact with
*/
private PDO $conn;
/**
* Constructs a new mailer.
*
* @param PDO $conn the connection to the email database
*/
public function __construct(PDO $conn)
{
$this->conn = $conn;
}
/**
* Populates the database with the necessary structures for emails.
*
* @return void
*/
public function install(): void
{
$this->conn->exec("CREATE TABLE email_tasks(type TEXT NOT NULL,
recipient TEXT NOT NULL,
arg1 TEXT NOT NULL DEFAULT(''),
arg2 TEXT NOT NULL DEFAULT(''),
PRIMARY KEY (type, recipient, arg1, arg2));");
}
/**
* Queues an email to be sent.
*
* @param Email $email the email to queue
* @return void
*/
public function queue_email(Email $email): void
{
$stmt = $this->conn->prepare("INSERT OR IGNORE INTO email_tasks (type, recipient, arg1, arg2)
VALUES (:type, :recipient, :arg1, :arg2);");
$stmt->bindValue(":type", $email->type);
$stmt->bindValue(":recipient", $email->recipient);
$stmt->bindValue(":arg1", $email->arg1);
$stmt->bindValue(":arg2", $email->arg2);
$stmt->execute();
}
/**
* Returns all queued emails.
*
* @return array<Email> the queued emails
*/
public function get_queue(): array
{
$stmt = $this->conn->prepare("SELECT type, recipient, arg1, arg2 FROM email_tasks;");
$stmt->execute();
$emails = $stmt->fetchAll(PDO::FETCH_ASSOC);
return array_map(
fn($row) => Email::deserialize($row["type"], $row["recipient"], $row["arg1"], $row["arg2"]),
$emails
);
}
/**
* Removes mails from the queue.
*
* @param array<Email> $emails the emails to remove from the queue
* @return void
*/
public function unqueue_emails(array $emails): void
{
$stmt = $this->conn->prepare("DELETE FROM email_tasks
WHERE type=:type AND recipient=:recipient AND arg1=:arg1 AND arg2=:arg2;");
$stmt->bindParam(":type", $type);
$stmt->bindParam(":recipient", $recipient);
$stmt->bindParam(":arg1", $arg1);
$stmt->bindParam(":arg2", $arg2);
foreach ($emails as $email) {
$type = $email->type;
$recipient = $email->recipient;
$arg1 = $email->arg1;
$arg2 = $email->arg2;
$stmt->execute();
}
}
}

View File

@ -1,149 +0,0 @@
<?php
namespace com\fwdekker\deathnotifier\mailer;
use com\fwdekker\deathnotifier\Response;
use Exception;
use Monolog\Logger;
use PDO;
use PHPMailer\PHPMailer\Exception as MailerException;
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\SMTP;
/**
* Queues up mails and sends them when appropriate.
*/
class Mailer
{
/**
* @var Logger the logger to use for logging
*/
private Logger $logger;
/**
* @var array<string, array<string, mixed>> the configuration to use for mailing
*/
private array $config;
/**
* @var PDO the database connection to interact with
*/
private PDO $conn;
/**
* Constructs a new mailer.
*
* @param array<string, array<string, mixed>> $config the configuration to use for mailing
* @param Logger $logger the logger to use for logging
* @param PDO $conn the connection to the email database
*/
public function __construct(array $config, Logger $logger, PDO $conn)
{
$this->logger = $logger;
$this->config = $config;
$this->conn = $conn;
}
/**
* Populates the database with the necessary structures for emails.
*
* @return void
*/
public function install(): void
{
$this->conn->exec("CREATE TABLE email_tasks(type TEXT NOT NULL,
recipient TEXT NOT NULL,
arg1 TEXT NOT NULL DEFAULT(''),
arg2 TEXT NOT NULL DEFAULT(''),
PRIMARY KEY (type, recipient, arg1, arg2));");
}
/**
* Queues an email to be sent.
*
* @param Email $email the email to queue
* @return Response a satisfied `Response` if the email was queued, or an unsatisfied `Response` otherwise
*/
public function queue_email(Email $email): Response
{
$stmt = $this->conn->prepare("INSERT OR IGNORE INTO email_tasks (type, recipient, arg1, arg2)
VALUES (:type, :recipient, :arg1, :arg2);");
$stmt->bindValue(":type", $email->type);
$stmt->bindValue(":recipient", $email->recipient);
$stmt->bindValue(":arg1", $email->arg1);
$stmt->bindValue(":arg2", $email->arg2);
return $stmt->execute() ? Response::satisfied() : Response::unsatisfied(null);
}
/**
* Sends all emails in the queue.
*
* @return void
*/
public function process_queue(): void
{
// Open mailer
$mailer = new PHPMailer();
$mailer->IsSMTP();
$mailer->CharSet = "UTF-8";
$mailer->SMTPAuth = true;
$mailer->SMTPDebug = SMTP::DEBUG_OFF;
$mailer->SMTPKeepAlive = true;
$mailer->SMTPSecure = PHPMailer::ENCRYPTION_SMTPS;
$mailer->Host = $this->config["mail"]["host"];
$mailer->Port = $this->config["mail"]["port"];
$mailer->Username = $this->config["mail"]["username"];
$mailer->Password = $this->config["mail"]["password"];
try {
$mailer->setFrom($this->config["mail"]["username"], $this->config["mail"]["from_name"]);
} catch (MailerException $exception) {
$this->logger->error("Failed to set 'from' address while processing queue.", ["cause" => $exception]);
$mailer->smtpClose();
}
// Get queue
$stmt = $this->conn->prepare("SELECT type, recipient, arg1, arg2 FROM email_tasks;");
$stmt->execute();
$email_tasks = $stmt->fetchAll(PDO::FETCH_ASSOC);
// Process queue
$stmt = $this->conn->prepare("DELETE FROM email_tasks
WHERE type=:type AND recipient=:recipient AND arg1=:arg1 AND arg2=:arg2;");
$stmt->bindParam(":type", $type);
$stmt->bindParam(":recipient", $recipient);
$stmt->bindParam(":arg1", $arg1);
$stmt->bindParam(":arg2", $arg2);
foreach ($email_tasks as ["type" => $type, "recipient" => $recipient, "arg1" => $arg1, "arg2" => $arg2]) {
try {
$email = Email::deserialize($type, $recipient, $arg1, $arg2);
$mailer->Subject = $email->getSubject();
$mailer->Body = $email->getBody($this->config);
try {
$mailer->addAddress($recipient);
$mailer->send();
} catch (MailerException $exception) {
$this->logger->error(
"Failed to send mail.",
["cause" => $exception, "email" => $email]
);
$mailer->getSMTPInstance()->reset();
}
$mailer->clearAddresses();
} catch (Exception $exception) {
$this->logger->error(
"Failed to send mail.",
["cause" => $exception]
);
$mailer->getSMTPInstance()->reset();
}
$stmt->execute();
}
}
}

View File

@ -2,7 +2,13 @@
namespace com\fwdekker\deathnotifier\mailer;
use com\fwdekker\deathnotifier\ActionException;
use com\fwdekker\deathnotifier\CliAction;
use com\fwdekker\deathnotifier\LoggerUtil;
use Monolog\Logger;
use PHPMailer\PHPMailer\Exception as PHPMailerException;
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\SMTP;
/**
@ -11,22 +17,27 @@ use com\fwdekker\deathnotifier\CliAction;
class ProcessEmailQueueCliAction extends CliAction
{
/**
* @var Mailer the mailer to process the queue with
* @var Logger the logger to log with
*/
private readonly Mailer $mailer;
private readonly Logger $logger;
/**
* @var MailManager the manager to process the queue with
*/
private readonly MailManager $mail_manager;
/**
* Constructs a new `ProcessEmailQueueAction`.
*
* @param mixed $config the application's configuration
* @param Mailer $mailer the mailer to process the queue with
* @param MailManager $mail_manager the manager to process the queue with
*/
public function __construct(mixed $config, Mailer $mailer)
public function __construct(mixed $config, MailManager $mail_manager)
{
parent::__construct($config, "process-email-queue");
$this->mailer = $mailer;
$this->logger = LoggerUtil::with_name("ProcessEmailQueueCliAction");
$this->mail_manager = $mail_manager;
}
@ -34,11 +45,64 @@ class ProcessEmailQueueCliAction extends CliAction
* Processes the queue.
*
* @return mixed `null`
* @throws ActionException if the mailer could not be created or if an email could not be sent
*/
public function handle(): mixed
{
$this->mailer->process_queue();
$emails = $this->mail_manager->get_queue();
$mailer = $this->create_mailer();
foreach ($emails as $email) {
$mailer->Subject = $email->getSubject();
$mailer->Body = $email->getBody($this->config);
try {
$mailer->addAddress($email->recipient);
$mailer->send();
} catch (PHPMailerException $exception) {
$mailer->getSMTPInstance()->reset();
$this->logger->error("Failed to send email.", ["cause" => $exception]);
throw new ActionException("Failed to send mail.");
}
$mailer->clearAddresses();
}
$this->mail_manager->unqueue_emails($emails);
return null;
}
/**
* Creates a mailer object to send emails with.
*
* @throws ActionException if the mailer could not be created
*/
private function create_mailer(): PHPMailer
{
$mailer = new PHPMailer();
$mailer->IsSMTP();
$mailer->CharSet = "UTF-8";
$mailer->SMTPAuth = true;
$mailer->SMTPDebug = SMTP::DEBUG_OFF;
$mailer->SMTPKeepAlive = true;
$mailer->SMTPSecure = PHPMailer::ENCRYPTION_SMTPS;
$mailer->Host = $this->config["mail"]["host"];
$mailer->Port = $this->config["mail"]["port"];
$mailer->Username = $this->config["mail"]["username"];
$mailer->Password = $this->config["mail"]["password"];
try {
$mailer->setFrom($this->config["mail"]["username"], $this->config["mail"]["from_name"]);
} catch (PHPMailerException $exception) {
$mailer->smtpClose();
$this->logger->error("Failed to set 'from' address while processing email queue.", ["cause" => $exception]);
throw new ActionException("Failed to set 'from' address while processing queue.");
}
return $mailer;
}
}

View File

@ -2,6 +2,7 @@
namespace com\fwdekker\deathnotifier\mediawiki;
use com\fwdekker\deathnotifier\LoggerUtil;
use Monolog\Logger;
@ -40,12 +41,10 @@ class MediaWiki
/**
* Creates a new Mediawiki instance.
*
* @param Logger $logger the logger to use for logging
*/
public function __construct(Logger $logger)
public function __construct()
{
$this->logger = $logger;
$this->logger = LoggerUtil::with_name("MediaWiki");
}

View File

@ -5,16 +5,13 @@ namespace com\fwdekker\deathnotifier\tracking;
use com\fwdekker\deathnotifier\Action;
use com\fwdekker\deathnotifier\ActionException;
use com\fwdekker\deathnotifier\ActionMethod;
use com\fwdekker\deathnotifier\mediawiki\ArticleType;
use com\fwdekker\deathnotifier\IllegalStateException;
use com\fwdekker\deathnotifier\mediawiki\IsPersonPageRule;
use com\fwdekker\deathnotifier\mediawiki\MediaWiki;
use com\fwdekker\deathnotifier\mediawiki\MediaWikiException;
use com\fwdekker\deathnotifier\Response;
use com\fwdekker\deathnotifier\ValidationException;
use com\fwdekker\deathnotifier\validator\HasLengthRule;
use com\fwdekker\deathnotifier\validator\IsNotBlankRule;
use Exception;
use InvalidStateException;
/**
@ -83,7 +80,7 @@ class AddTrackingAction extends Action
$normalized_name = $info->redirects[$person_name];
$status = $info->results[$normalized_name]["status"];
if ($status === null)
throw new InvalidStateException("Article is about person, but person has no status.");
throw new IllegalStateException("Article is about person, but person has no status.");
// Add tracking (Transaction is not necessary)
if ($this->tracking_manager->has_tracking($user_uuid, $normalized_name))

View File

@ -3,6 +3,7 @@
namespace com\fwdekker\deathnotifier\tracking;
use com\fwdekker\deathnotifier\Database;
use com\fwdekker\deathnotifier\LoggerUtil;
use com\fwdekker\deathnotifier\mediawiki\ArticleType;
use com\fwdekker\deathnotifier\mediawiki\PersonStatus;
use Monolog\Logger;
@ -36,12 +37,11 @@ class TrackingManager
/**
* Constructs a new tracking manager.
*
* @param Logger $logger the logger to log with
* @param PDO $conn the database connection to interact with
*/
public function __construct(Logger $logger, PDO $conn)
public function __construct(PDO $conn)
{
$this->logger = $logger;
$this->logger = LoggerUtil::with_name("TrackingManager");
$this->conn = $conn;
}

View File

@ -5,7 +5,7 @@ namespace com\fwdekker\deathnotifier\tracking;
use com\fwdekker\deathnotifier\ActionException;
use com\fwdekker\deathnotifier\CliAction;
use com\fwdekker\deathnotifier\Database;
use com\fwdekker\deathnotifier\mailer\Mailer;
use com\fwdekker\deathnotifier\mailer\MailManager;
use com\fwdekker\deathnotifier\mediawiki\MediaWiki;
use com\fwdekker\deathnotifier\mediawiki\MediaWikiException;
use PDO;
@ -29,9 +29,9 @@ class UpdateTrackingsCliAction extends CliAction
*/
private readonly MediaWiki $mediawiki;
/**
* @var Mailer the mailer to send emails with
* @var MailManager the mailer to send emails with
*/
private readonly Mailer $mailer;
private readonly MailManager $mailer;
/**
@ -41,10 +41,10 @@ class UpdateTrackingsCliAction extends CliAction
* @param PDO $conn the database connection to interact with
* @param TrackingManager $tracking_manager the manager through which trackings should be updated
* @param MediaWiki $mediawiki the instance to connect to Wikipedia with
* @param Mailer $mailer the mailer to send emails with
* @param MailManager $mailer the mailer to send emails with
*/
public function __construct(mixed $config, PDO $conn, TrackingManager $tracking_manager, MediaWiki $mediawiki,
Mailer $mailer)
public function __construct(mixed $config, PDO $conn, TrackingManager $tracking_manager, MediaWiki $mediawiki,
MailManager $mailer)
{
parent::__construct($config, "update-trackings");

View File

@ -3,7 +3,8 @@
namespace com\fwdekker\deathnotifier\user;
use com\fwdekker\deathnotifier\Database;
use com\fwdekker\deathnotifier\mailer\Mailer;
use com\fwdekker\deathnotifier\LoggerUtil;
use com\fwdekker\deathnotifier\mailer\MailManager;
use com\fwdekker\deathnotifier\Response;
use Monolog\Logger;
use PDO;
@ -49,21 +50,20 @@ class UserManager
*/
private PDO $conn;
/**
* @var Mailer the mailer to send emails with
* @var MailManager the mailer to send emails with
*/
private Mailer $mailer;
private MailManager $mailer;
/**
* Constructs a new user manager.
*
* @param Logger $logger the logger to use for logging
* @param PDO $conn the database connection to interact with
* @param Mailer $mailer the mailer to send emails with
* @param MailManager $mailer the mailer to send emails with
*/
public function __construct(Logger $logger, PDO $conn, Mailer $mailer)
public function __construct(PDO $conn, MailManager $mailer)
{
$this->logger = $logger;
$this->logger = LoggerUtil::with_name("UserManager");
$this->conn = $conn;
$this->mailer = $mailer;
}

View File

@ -2,11 +2,10 @@
namespace com\fwdekker\deathnotifier;
use com\fwdekker\deathnotifier\mailer\Mailer;
use com\fwdekker\deathnotifier\mailer\MailManager;
use com\fwdekker\deathnotifier\tracking\TrackingManager;
use com\fwdekker\deathnotifier\user\UserManager;
use Exception;
use Monolog\Logger;
use Monolog\Test\TestCase;
@ -23,10 +22,6 @@ abstract class DatabaseTestCase extends TestCase
*/
private static string $db_tmp_dir;
/**
* @var Logger the logger
*/
public Logger $logger;
/**
* @var Database the database
*/
@ -34,11 +29,11 @@ abstract class DatabaseTestCase extends TestCase
/**
* @return Mailer the `Mailer` to install the database schema of
* @return MailManager the `Mailer` to install the database schema of
*/
function get_mailer(): Mailer
function get_mailer(): MailManager
{
return $this->createStub(Mailer::class);
return $this->createStub(MailManager::class);
}
/**
@ -91,9 +86,7 @@ abstract class DatabaseTestCase extends TestCase
$db_tmp_file = tempnam(self::$db_tmp_dir, "database-");
if ($db_tmp_file === false) throw new Exception("Failed to create temporary database file.");
$this->logger = new Logger("DatabaseTestCase");
$this->database = new Database($this->logger, $db_tmp_file);
$this->database = new Database($db_tmp_file);
$this->database->auto_install($this->get_mailer(), $this->get_user_manager(), $this->get_tracking_manager());
}
}

View File

@ -2,7 +2,7 @@
namespace com\fwdekker\deathnotifier;
use com\fwdekker\deathnotifier\mailer\Mailer;
use com\fwdekker\deathnotifier\mailer\MailManager;
use com\fwdekker\deathnotifier\user\ChangedEmailEmail;
use com\fwdekker\deathnotifier\user\ChangedPasswordEmail;
use com\fwdekker\deathnotifier\user\RegisterEmail;
@ -19,7 +19,7 @@ use PHPUnit\Framework\MockObject\MockObject;
class UserManagerTest extends DatabaseTestCase
{
private UserManager $user_manager;
private Mailer&MockObject $mailer;
private MailManager&MockObject $mailer;
public function get_user_manager(): UserManager
@ -29,7 +29,7 @@ class UserManagerTest extends DatabaseTestCase
public function setUp(): void
{
$this->mailer = $this->createMock(Mailer::class);
$this->mailer = $this->createMock(MailManager::class);
$this->mailer->method("queue_email")->willReturn(Response::satisfied());
parent::setUp();