Skip to content

Commit

Permalink
Merge branch 'wip' into feat/1419-user-notifier
Browse files Browse the repository at this point in the history
  • Loading branch information
Fan2Shrek committed Mar 7, 2024
2 parents 7eb8319 + 50c1656 commit 5ca58b3
Show file tree
Hide file tree
Showing 5 changed files with 47 additions and 58 deletions.
2 changes: 0 additions & 2 deletions config/services.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -109,8 +109,6 @@ services:
App\Security\TwoFactorAuthManager:
public: true
class: App\Security\TwoFactorAuthManager
arguments:
$options: { from: '%env(APP_MAILER_FROM_EMAIL)%', fromName: '%env(APP_MAILER_FROM_NAME)%' }

App\Service\SecurityAdvisoryWorker:
$sources:
Expand Down
11 changes: 8 additions & 3 deletions src/Controller/ProfileController.php
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ public function packagesAction(Request $req, #[VarName('name')] User $user, Favo
public function editAction(Request $request, UserNotifier $userNotifier): Response
{
$user = $this->getUser();
if (!is_object($user)) {
if (!$user instanceof User) {
throw $this->createAccessDeniedException('This user does not have access to this section.');
}

Expand All @@ -131,9 +131,14 @@ public function editAction(Request $request, UserNotifier $userNotifier): Respon

$diffs = array_intersect(array_keys($changeSet), ['email', 'username']);

if (!empty($diffs) && $user instanceof User) {
if (!empty($diffs)) {
$reason = sprintf('Your %s has been changed', implode(' and ', $diffs));
$userNotifier->notifyChange($changeSet['email'][0] ?? $user->getEmail(), $reason);

if (isset($changeSet['email'][0])) {
$userNotifier->notifyChange($changeSet['email'][0], $reason);
}

$userNotifier->notifyChange($user->getEmail(), $reason);
}

$this->getEM()->persist($user);
Expand Down
47 changes: 3 additions & 44 deletions src/Security/TwoFactorAuthManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,17 +13,11 @@
namespace App\Security;

use App\Entity\User;
use Psr\Log\LoggerInterface;
use Scheb\TwoFactorBundle\Model\BackupCodeInterface;
use Scheb\TwoFactorBundle\Security\TwoFactor\Backup\BackupCodeManagerInterface;
use Doctrine\Persistence\ManagerRegistry;
use Symfony\Component\HttpFoundation\RequestStack;
use Symfony\Component\HttpFoundation\Session\FlashBagAwareSessionInterface;
use Symfony\Component\Mailer\Exception\TransportExceptionInterface;
use Twig\Environment;
use Symfony\Component\Mailer\MailerInterface;
use Symfony\Component\Mime\Address;
use Symfony\Component\Mime\Email;

/**
* @author Colin O'Dell <[email protected]>
Expand All @@ -32,12 +26,8 @@ class TwoFactorAuthManager implements BackupCodeManagerInterface
{
public function __construct(
private ManagerRegistry $doctrine,
private MailerInterface $mailer,
private Environment $twig,
private LoggerInterface $logger,
private RequestStack $requestStack,
/** @var array{from: string, fromName: string} */
private array $options
private UserNotifier $userNotifier,
) {
}

Expand All @@ -49,22 +39,7 @@ public function enableTwoFactorAuth(User $user, string $secret): void
$user->setTotpSecret($secret);
$this->doctrine->getManager()->flush();

$body = $this->twig->render('email/two_factor_enabled.txt.twig', [
'username' => $user->getUsername(),
]);

$message = (new Email())
->subject('[Packagist] Two-factor authentication enabled')
->from(new Address($this->options['from'], $this->options['fromName']))
->to($user->getEmail())
->text($body)
;

try {
$this->mailer->send($message);
} catch (TransportExceptionInterface $e) {
$this->logger->error('['.get_class($e).'] '.$e->getMessage());
}
$this->userNotifier->notifyTwoFactorAuth($user->getEmail(), ['username' => $user->getUsername()], true);
}

/**
Expand All @@ -76,23 +51,7 @@ public function disableTwoFactorAuth(User $user, string $reason): void
$user->invalidateAllBackupCodes();
$this->doctrine->getManager()->flush();

$body = $this->twig->render('email/two_factor_disabled.txt.twig', [
'username' => $user->getUsername(),
'reason' => $reason,
]);

$message = (new Email())
->subject('[Packagist] Two-factor authentication disabled')
->from(new Address($this->options['from'], $this->options['fromName']))
->to($user->getEmail())
->text($body)
;

try {
$this->mailer->send($message);
} catch (TransportExceptionInterface $e) {
$this->logger->error('['.get_class($e).'] '.$e->getMessage());
}
$this->userNotifier->notifyTwoFactorAuth($user->getEmail(), ['username' => $user->getUsername(), 'reason' => $reason,], false);
}

/**
Expand Down
43 changes: 35 additions & 8 deletions src/Security/UserNotifier.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@
use Symfony\Bridge\Twig\Mime\TemplatedEmail;
use Symfony\Component\Mailer\MailerInterface;
use Symfony\Component\Mime\Address;
use Symfony\Component\Mailer\Exception\TransportExceptionInterface;
use Psr\Log\LoggerInterface;

/**
* @author Pierre Ambroise <[email protected]>
Expand All @@ -14,25 +16,50 @@ class UserNotifier
private MailerInterface $mailer;
private string $mailFromEmail;
private string $mailFromName;
private LoggerInterface $logger;

public function __construct(string $mailFromEmail, string $mailFromName, MailerInterface $mailer)
public function __construct(string $mailFromEmail, string $mailFromName, MailerInterface $mailer, LoggerInterface $logger)
{
$this->mailer = $mailer;
$this->mailFromEmail = $mailFromEmail;
$this->mailFromName = $mailFromName;
$this->logger = $logger;
}

public function notifyChange(string $email, string $reason): void
{
$email = (new TemplatedEmail())
$this->notify($email, 'A change has been made to your account', 'email/alert_change.txt.twig', ['change' => $reason]);
}

/**
* @param string[] $context
*/
public function notifyTwoFactorAuth(string $email, array $context, bool $enabled): void
{
$this->notify(
$email,
$enabled ? '[Packagist] Two-factor authentication enabled' : '[Packagist] Two-factor authentication disabled',
$enabled ? 'email/two_factor_enabled.txt.twig' : 'email/two_factor_disabled.txt.twig',
$context
);
}

/**
* @param string[] $context
*/
public function notify(string $email, string $subject, string $template, array $context = []): void
{
$mail = (new TemplatedEmail())
->from(new Address($this->mailFromEmail, $this->mailFromName))
->to($email)
->subject('A change has been made to your account')
->textTemplate('email/alert_change.txt.twig')
->context([
'reason' => $reason,
]);
->subject($subject)
->textTemplate($template)
->context($context);

$this->mailer->send($email);
try {
$this->mailer->send($mail);
} catch (TransportExceptionInterface $e) {
$this->logger->error('[' . get_class($e) . '] ' . $e->getMessage());
}
}
}
2 changes: 1 addition & 1 deletion templates/email/alert_change.txt.twig
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
A critical account security change has been made to your account:

-------------------------------
Reason: {{ reason }}
Change: {{ change }}
Time: {{ 'now'|date('c') }}
-------------------------------

Expand Down

0 comments on commit 5ca58b3

Please sign in to comment.