Move reengagement validations into validator
[MAILPOET-4236]
This commit is contained in:
committed by
Veljko V
parent
27a86d2ca6
commit
a5103f9596
@ -24,7 +24,6 @@ use MailPoet\Newsletter\Scheduler\Scheduler;
|
||||
use MailPoet\Newsletter\Url as NewsletterUrl;
|
||||
use MailPoet\Newsletter\Validator;
|
||||
use MailPoet\Settings\SettingsController;
|
||||
use MailPoet\Settings\TrackingConfig;
|
||||
use MailPoet\UnexpectedValueException;
|
||||
use MailPoet\Util\License\Features\Subscribers as SubscribersFeature;
|
||||
use MailPoet\Util\Security;
|
||||
@ -100,7 +99,6 @@ class Newsletters extends APIEndpoint {
|
||||
SendPreviewController $sendPreviewController,
|
||||
NewsletterSaveController $newsletterSaveController,
|
||||
NewsletterUrl $newsletterUrl,
|
||||
TrackingConfig $trackingConfig,
|
||||
Scheduler $scheduler,
|
||||
Validator $validator
|
||||
) {
|
||||
@ -117,7 +115,6 @@ class Newsletters extends APIEndpoint {
|
||||
$this->sendPreviewController = $sendPreviewController;
|
||||
$this->newsletterSaveController = $newsletterSaveController;
|
||||
$this->newsletterUrl = $newsletterUrl;
|
||||
$this->trackingConfig = $trackingConfig;
|
||||
$this->scheduler = $scheduler;
|
||||
$this->validator = $validator;
|
||||
}
|
||||
@ -197,28 +194,6 @@ class Newsletters extends APIEndpoint {
|
||||
}
|
||||
}
|
||||
|
||||
// if the re-engagement email doesn't contain the re-engage link, it can't be activated
|
||||
if ($newsletter->getType() === NewsletterEntity::TYPE_RE_ENGAGEMENT && $status === NewsletterEntity::STATUS_ACTIVE) {
|
||||
if (strpos($newsletter->getContent(), '[link:subscription_re_engage_url]') === false) {
|
||||
return $this->errorResponse([
|
||||
APIError::FORBIDDEN => __(
|
||||
'A re-engagement email must include a link with [link:subscription_re_engage_url] shortcode.',
|
||||
'mailpoet'
|
||||
),
|
||||
], [], Response::STATUS_FORBIDDEN);
|
||||
}
|
||||
}
|
||||
|
||||
$tracking_enabled = $this->trackingConfig->isEmailTrackingEnabled();
|
||||
if (!$tracking_enabled && $newsletter->getType() === NewsletterEntity::TYPE_RE_ENGAGEMENT && $status === NewsletterEntity::STATUS_ACTIVE) {
|
||||
return $this->errorResponse([
|
||||
APIError::FORBIDDEN => __(
|
||||
'Re-engagement emails are disabled because open and click tracking is disabled in MailPoet → Settings → Advanced.',
|
||||
'mailpoet'
|
||||
),
|
||||
], [], Response::STATUS_FORBIDDEN);
|
||||
}
|
||||
|
||||
$this->newslettersRepository->prefetchOptions([$newsletter]);
|
||||
$newsletter->setStatus($status);
|
||||
|
||||
|
@ -4,49 +4,74 @@ namespace MailPoet\Newsletter;
|
||||
|
||||
use MailPoet\Entities\NewsletterEntity;
|
||||
use MailPoet\Services\Bridge;
|
||||
use MailPoet\Settings\TrackingConfig;
|
||||
use MailPoet\Validator\ValidationException;
|
||||
|
||||
class Validator {
|
||||
|
||||
/** @var Bridge */
|
||||
private $bridge;
|
||||
|
||||
/** @var TrackingConfig */
|
||||
private $trackingConfig;
|
||||
|
||||
public function __construct(
|
||||
Bridge $bridge
|
||||
Bridge $bridge,
|
||||
TrackingConfig $trackingConfig
|
||||
) {
|
||||
$this->bridge = $bridge;
|
||||
$this->trackingConfig = $trackingConfig;
|
||||
}
|
||||
|
||||
public function validate(NewsletterEntity $newsletterEntity): ?string {
|
||||
if (
|
||||
$newsletterEntity->getBody()
|
||||
&& is_array($newsletterEntity->getBody())
|
||||
&& $newsletterEntity->getBody()['content']
|
||||
) {
|
||||
$content = $newsletterEntity->getBody()['content'];
|
||||
$encodedBody = json_encode($content);
|
||||
if ($encodedBody === false) {
|
||||
return $this->emptyContentErrorMessage();
|
||||
} else {
|
||||
$blocks = $content['blocks'] ?? [];
|
||||
if (empty($blocks)) {
|
||||
return $this->emptyContentErrorMessage();
|
||||
}
|
||||
}
|
||||
|
||||
if (
|
||||
$this->bridge->isMailpoetSendingServiceEnabled()
|
||||
&& (strpos($encodedBody, '[link:subscription_unsubscribe_url]') === false)
|
||||
&& (strpos($encodedBody, '[link:subscription_unsubscribe]') === false)
|
||||
) {
|
||||
return __('All emails must include an "Unsubscribe" link. Add a footer widget to your email to continue.');
|
||||
}
|
||||
} else {
|
||||
return $this->emptyContentErrorMessage();
|
||||
try {
|
||||
$this->validateBody($newsletterEntity);
|
||||
$this->validateUnsubscribeRequirements($newsletterEntity);
|
||||
$this->validateReengagementRequirements($newsletterEntity);
|
||||
} catch (ValidationException $exception) {
|
||||
return __($exception->getMessage(), 'mailpoet');
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private function emptyContentErrorMessage(): string {
|
||||
return __('Poet, please add prose to your masterpiece before you send it to your followers.');
|
||||
private function validateUnsubscribeRequirements(NewsletterEntity $newsletterEntity): void {
|
||||
if (!$this->bridge->isMailpoetSendingServiceEnabled()) {
|
||||
return;
|
||||
}
|
||||
$content = $newsletterEntity->getContent();
|
||||
$hasUnsubscribeUrl = strpos($content, '[link:subscription_unsubscribe_url]') !== false;
|
||||
$hasUnsubscribeLink = strpos($content, '[link:subscription_unsubscribe]') !== false;
|
||||
|
||||
if (!$hasUnsubscribeLink && !$hasUnsubscribeUrl) {
|
||||
throw new ValidationException('All emails must include an "Unsubscribe" link. Add a footer widget to your email to continue.');
|
||||
}
|
||||
}
|
||||
|
||||
private function validateBody(NewsletterEntity $newsletterEntity): void {
|
||||
$emptyBodyErrorMessage = 'Poet, please add prose to your masterpiece before you send it to your followers.';
|
||||
$content = $newsletterEntity->getContent();
|
||||
|
||||
if ($content === '') {
|
||||
throw new ValidationException($emptyBodyErrorMessage);
|
||||
}
|
||||
|
||||
$contentBlocks = $newsletterEntity->getBody()['content']['blocks'] ?? [];
|
||||
if (count($contentBlocks) < 1) {
|
||||
throw new ValidationException($emptyBodyErrorMessage);
|
||||
}
|
||||
}
|
||||
|
||||
private function validateReengagementRequirements(NewsletterEntity $newsletterEntity): void {
|
||||
if ($newsletterEntity->getType() !== NewsletterEntity::TYPE_RE_ENGAGEMENT) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (strpos($newsletterEntity->getContent(), '[link:subscription_re_engage_url]') === false) {
|
||||
throw new ValidationException('A re-engagement email must include a link with [link:subscription_re_engage_url] shortcode.');
|
||||
}
|
||||
|
||||
if (!$this->trackingConfig->isEmailTrackingEnabled()) {
|
||||
throw new ValidationException('Re-engagement emails are disabled because open and click tracking is disabled in MailPoet → Settings → Advanced.');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -40,7 +40,6 @@ use MailPoet\Newsletter\Validator;
|
||||
use MailPoet\Router\Router;
|
||||
use MailPoet\Segments\SegmentsRepository;
|
||||
use MailPoet\Settings\SettingsController;
|
||||
use MailPoet\Settings\TrackingConfig;
|
||||
use MailPoet\Tasks\Sending as SendingTask;
|
||||
use MailPoet\Util\License\Features\Subscribers as SubscribersFeature;
|
||||
use MailPoet\Util\Security;
|
||||
@ -695,7 +694,6 @@ class NewslettersTest extends \MailPoetTest {
|
||||
$mocks['sendPreviewController'] ?? $this->diContainer->get(SendPreviewController::class),
|
||||
$this->diContainer->get(NewsletterSaveController::class),
|
||||
$this->diContainer->get(Url::class),
|
||||
$this->diContainer->get(TrackingConfig::class),
|
||||
$this->scheduler,
|
||||
$this->diContainer->get(Validator::class)
|
||||
);
|
||||
|
@ -23,6 +23,7 @@ use MailPoet\Segments\SubscribersFinder;
|
||||
use MailPoet\Services\Bridge;
|
||||
use MailPoet\Settings\SettingsController;
|
||||
use MailPoet\Settings\SettingsRepository;
|
||||
use MailPoet\Settings\TrackingConfig;
|
||||
use MailPoet\Tasks\Sending;
|
||||
use MailPoet\Util\License\Features\Subscribers as SubscribersFeature;
|
||||
|
||||
@ -170,7 +171,7 @@ class SendingQueueTest extends \MailPoetTest {
|
||||
$this->diContainer->get(Scheduler::class),
|
||||
new Validator(Stub::make(Bridge::class, [
|
||||
'isMailpoetSendingServiceEnabled' => true,
|
||||
]))
|
||||
]), $this->diContainer->get(TrackingConfig::class))
|
||||
);
|
||||
$response = $sendingQueue->add(['newsletter_id' => $newsletter->getId()]);
|
||||
$response = $response->getData();
|
||||
|
Reference in New Issue
Block a user