OpenXE/classes/Modules/SystemMailer/Service/MailerTransportFactory.php
2021-05-21 08:49:41 +02:00

188 lines
6.4 KiB
PHP

<?php
declare(strict_types=1);
namespace Xentral\Modules\SystemMailer\Service;
use PHPMailer\PHPMailer\PHPMailer;
use Xentral\Components\Logger\LoggerAwareTrait;
use Xentral\Components\Mailer\Config\OAuthMailerConfig;
use Xentral\Components\Mailer\Config\SmtpMailerConfig;
use Xentral\Components\Mailer\Transport\MailerTransportInterface;
use Xentral\Components\Mailer\Transport\PhpMailerOAuth;
use Xentral\Components\Mailer\Transport\PhpMailerTransport;
use Xentral\Core\DependencyInjection\ContainerInterface;
use Xentral\Modules\GoogleApi\Exception\GoogleAccountNotFoundException;
use Xentral\Modules\GoogleApi\Exception\GoogleCredentialsException;
use Xentral\Modules\GoogleApi\Service\GoogleAccountGateway;
use Xentral\Modules\GoogleApi\Service\GoogleAuthorizationService;
use Xentral\Modules\GoogleApi\Service\GoogleCredentialsService;
use Xentral\Modules\SystemMailer\Data\EmailBackupAccount;
use Xentral\Modules\SystemMailer\Exception\GmailOAuthException;
use Xentral\Modules\SystemMailer\Exception\InvalidArgumentException;
use Xentral\Modules\SystemMailer\Transport\PhpMailerGoogleAuthentification;
class MailerTransportFactory
{
use LoggerAwareTrait;
/** @var ContainerInterface $container */
private $container;
/**
* @param ContainerInterface $container
*/
public function __construct(ContainerInterface $container) {
$this->container = $container;
}
/**
* @param EmailBackupAccount $account
*
* @throws InvalidArgumentException
*
* @return MailerTransportInterface
*/
public function createMailerTransport(EmailBackupAccount $account):MailerTransportInterface
{
switch ($account->getSmtpAuthType()) {
case EmailBackupAccount::AUTH_SMTP:
return $this->createSmtpTransport($account);
break;
case EmailBackupAccount::AUTH_GMAIL:
return $this->createGoogleOAuthTransport($account);
default:
throw new InvalidArgumentException('Only SMTP accounts are supported.');
}
}
/**
* @param EmailBackupAccount $account
*
* @return SmtpMailerConfig
*/
public function createSmtpMailerConfig(EmailBackupAccount $account):SmtpMailerConfig
{
if ($account->isSmtpEnabled() === false || $account->getSmtpAuthType() !== EmailBackupAccount::AUTH_SMTP) {
throw new InvalidArgumentException('Only SMTP accounts are supported.');
}
$email = $account->getSmtpSenderEmail();
if ($email === '') {
$email = $account->getEmailAddress();
}
$sender = $account->getSmtpSenderName();
if ($sender === '') {
$sender = $account->getDisplayName();
}
$debug = 0;
if ($account->isSmtpDebugEnabled()) {
$debug = 4;
}
return new SmtpMailerConfig([
'sender_email' => $email,
'sender_name' => $sender,
'host' => $account->getSmtpServer(),
'hostname' => $account->getClientAlias(),
'username' => $account->getUserName(),
'password' => $account->getPassword(),
'port' => $account->getSmtpPort(),
'smtp_security' => $account->getSmtpSecurity(),
'mailer' => 'smtp',
'smtp_debug' => $debug
]);
}
/**
* @param EmailBackupAccount $account
*
* @throws InvalidArgumentException
*
* @return OAuthMailerConfig
*/
public function createGmailMailerConfig(EmailBackupAccount $account):OAuthMailerConfig
{
if (
$account->isSmtpEnabled() === false
|| $account->getSmtpAuthType() !== EmailBackupAccount::AUTH_GMAIL
) {
throw new InvalidArgumentException('Only SMTP OAUTH accounts are supported.');
}
$email = $account->getSmtpSenderEmail();
if ($email === '') {
$email = $account->getEmailAddress();
}
$sender = $account->getSmtpSenderName();
if ($sender === '') {
$sender = $account->getDisplayName();
}
$debug = 0;
if ($account->isSmtpDebugEnabled()) {
$debug = 4;
}
$cfgValues = [
'sender_email' => $email,
'sender_name' => $sender,
'host' => $account->getSmtpServer(),
'hostname' => $account->getClientAlias(),
'port' => $account->getSmtpPort(),
'smtp_security' => $account->getSmtpSecurity(),
'mailer' => 'smtp',
'smtp_debug' => $debug
];
if ($cfgValues['host'] === '') {
$cfgValues['host'] = 'smtp.gmail.com';
}
return new OAuthMailerConfig($cfgValues);
}
/**
* @param EmailBackupAccount $account
*
* @return PhpMailerTransport
*/
public function createSmtpTransport(EmailBackupAccount $account):PhpMailerTransport
{
$config = $this->createSmtpMailerConfig($account);
$mailer = new PHPMailer(true);
return new PhpMailerTransport($mailer, $config, $this->logger);
}
/**
* @param EmailBackupAccount $account
*
* @throws GoogleCredentialsException
* @throws GmailOAuthException
* @throws GoogleAccountNotFoundException
*
* @return PhpMailerTransport
*/
public function createGoogleOAuthTransport(EmailBackupAccount $account):PhpMailerTransport
{
$config = $this->createGmailMailerConfig($account);
/** @var GoogleCredentialsService $credentialsService */
$credentialsService = $this->container->get('GoogleCredentialsService');
$credentialsService->getCredentials()->validate();
/** @var GoogleAccountGateway $googleApiGateway */
$googleApiGateway = $this->container->get('GoogleAccountGateway');
$googleAccount = $googleApiGateway->getAccountByGmailAddress($account->getSenderEmailAddress());
/** @var GoogleAuthorizationService $googleAuth */
$googleAuth = $this->container->get('GoogleAuthorizationService');
$oauth = new PhpMailerGoogleAuthentification(
$googleApiGateway,
$googleAuth,
$googleAccount
);
$mailer = new PhpMailerOAuth(true, $oauth);
return new PhpMailerTransport($mailer, $config, $this->logger);
}
}