diff --git a/composer.json b/composer.json
index 9f12640..2f42660 100644
--- a/composer.json
+++ b/composer.json
@@ -25,19 +25,23 @@
},
"autoload-dev": {
"psr-4": {
- "Tests\\": "tests/"
+ "Welp\\MailchimpBundle\\Tests\\": "tests/"
}
},
"require": {
- "php": ">=5.6",
- "drewm/mailchimp-api": "2.5.*"
+ "php": ">=8.1",
+ "drewm/mailchimp-api": "^2.5",
+ "symfony/event-dispatcher": "^6.3||^7.0",
+ "symfony/framework-bundle": "^6.3||^7.0"
},
"require-dev": {
- "phpspec/phpspec": "~2@dev",
- "phpunit/phpunit": "~5",
- "symfony/symfony": ">=2.7"
+ "phpspec/phpspec": "^7.5",
+ "phpunit/phpunit": "^9.6",
+ "symfony/symfony": "^6.3||^7.0"
},
"config": {
- "bin-dir": "bin"
+ "bin-dir": "bin",
+ "preferred-install": "dist",
+ "sort-packages": true
}
}
diff --git a/config/routes.yaml b/config/routes.yaml
new file mode 100644
index 0000000..514d848
--- /dev/null
+++ b/config/routes.yaml
@@ -0,0 +1,3 @@
+welp_mailchimp_webhook:
+ resource: '../src/Controller'
+ type: attribute
\ No newline at end of file
diff --git a/src/Resources/config/services.yml b/config/services.yaml
similarity index 95%
rename from src/Resources/config/services.yml
rename to config/services.yaml
index 7aac2bc..d9c9959 100644
--- a/src/Resources/config/services.yml
+++ b/config/services.yaml
@@ -6,6 +6,13 @@ parameters:
welp_mailchimp.config_list_provider_class: Welp\MailchimpBundle\Provider\ConfigListProvider
services:
+ _defaults:
+ autowire: true
+ autoconfigure: true
+
+ Welp\MailchimpBundle\Controller\:
+ resource: '../src/Controller/*'
+
# MailChimp
welp_mailchimp.mailchimp_master:
class: DrewM\MailChimp\MailChimp
diff --git a/src/Command/SynchronizeMergeFieldsCommand.php b/src/Command/SynchronizeMergeFieldsCommand.php
index 4c80468..fe79ca5 100644
--- a/src/Command/SynchronizeMergeFieldsCommand.php
+++ b/src/Command/SynchronizeMergeFieldsCommand.php
@@ -15,14 +15,14 @@ class SynchronizeMergeFieldsCommand extends Command
*
* @var ListSynchronizer
*/
- private $listSynchronizer;
+ private ListSynchronizer $listSynchronizer;
/**
* The configured list provider.
*
* @var ListProviderInterface
*/
- private $listProvider;
+ private ListProviderInterface $listProvider;
public function __construct(ListSynchronizer $listSynchronizer, ListProviderInterface $listProvider)
{
@@ -32,7 +32,7 @@ public function __construct(ListSynchronizer $listSynchronizer, ListProviderInte
parent::__construct();
}
- protected function configure()
+ protected function configure(): void
{
$this
->setDescription('Synchronizing merge fields in MailChimp')
@@ -41,7 +41,7 @@ protected function configure()
;
}
- protected function execute(InputInterface $input, OutputInterface $output)
+ protected function execute(InputInterface $input, OutputInterface $output): int
{
$output->writeln(sprintf('%s', $this->getDescription()));
@@ -50,5 +50,7 @@ protected function execute(InputInterface $input, OutputInterface $output)
foreach ($lists as $list) {
$this->listSynchronizer->synchronizeMergeFields($list->getListId(), $list->getMergeFields());
}
+
+ return Command::SUCCESS;
}
}
diff --git a/src/Command/SynchronizeSubscribersCommand.php b/src/Command/SynchronizeSubscribersCommand.php
index a71c88b..822c931 100644
--- a/src/Command/SynchronizeSubscribersCommand.php
+++ b/src/Command/SynchronizeSubscribersCommand.php
@@ -17,21 +17,21 @@ class SynchronizeSubscribersCommand extends Command
*
* @var ListSynchronizer
*/
- private $listSynchronizer;
+ private ListSynchronizer $listSynchronizer;
/**
* The configured list provider.
*
* @var ListProviderInterface
*/
- private $listProvider;
+ private ListProviderInterface $listProvider;
/**
* Mailchimp API class.
*
* @var MailChimp
*/
- private $mailchimp;
+ private MailChimp $mailchimp;
public function __construct(ListSynchronizer $listSynchronizer, ListProviderInterface $listProvider, MailChimp $mailchimp)
{
@@ -45,7 +45,7 @@ public function __construct(ListSynchronizer $listSynchronizer, ListProviderInte
/**
* {@inheritdoc}
*/
- protected function configure()
+ protected function configure(): void
{
$this
->setDescription('Synchronizing subscribers in MailChimp')
@@ -63,7 +63,7 @@ protected function configure()
/**
* {@inheritdoc}
*/
- protected function execute(InputInterface $input, OutputInterface $output)
+ protected function execute(InputInterface $input, OutputInterface $output): int
{
$output->writeln(sprintf('%s', $this->getDescription()));
@@ -72,16 +72,21 @@ protected function execute(InputInterface $input, OutputInterface $output)
foreach ($lists as $list) {
$output->writeln(sprintf('Synchronize list %s', $list->getListId()));
$batchesResult = $this->listSynchronizer->synchronize($list);
+
if ($input->getOption('follow-sync')) {
while (!$this->batchesFinished($batchesResult)) {
$batchesResult = $this->refreshBatchesResult($batchesResult);
+
foreach ($batchesResult as $key => $batch) {
$output->writeln($this->displayBatchInfo($batch));
}
+
sleep(2);
}
}
}
+
+ return Command::SUCCESS;
}
/**
@@ -91,13 +96,13 @@ protected function execute(InputInterface $input, OutputInterface $output)
*
* @return array
*/
- private function refreshBatchesResult($batchesResult)
+ private function refreshBatchesResult(array $batchesResult): array
{
$refreshedBatchsResults = [];
foreach ($batchesResult as $key => $batch) {
$batch = $this->mailchimp->get('batches/'.$batch['id']);
- array_push($refreshedBatchsResults, $batch);
+ $refreshedBatchsResults[] = $batch;
}
return $refreshedBatchsResults;
@@ -110,11 +115,11 @@ private function refreshBatchesResult($batchesResult)
*
* @return bool
*/
- private function batchesFinished($batchesResult)
+ private function batchesFinished(array $batchesResult): bool
{
$allfinished = true;
foreach ($batchesResult as $key => $batch) {
- if ('finished' != $batch['status']) {
+ if ('finished' !== $batch['status']) {
$allfinished = false;
}
}
@@ -129,9 +134,9 @@ private function batchesFinished($batchesResult)
*
* @return string
*/
- private function displayBatchInfo($batch)
+ private function displayBatchInfo(array $batch): string
{
- if ('finished' == $batch['status']) {
+ if ('finished' === $batch['status']) {
return sprintf('batch %s is finished, operations %d/%d with %d errors. http responses: %s', $batch['id'], $batch['finished_operations'], $batch['total_operations'], $batch['errored_operations'], $batch['response_body_url']);
}
diff --git a/src/Command/WebhookCommand.php b/src/Command/WebhookCommand.php
index 7b42e16..59a677a 100644
--- a/src/Command/WebhookCommand.php
+++ b/src/Command/WebhookCommand.php
@@ -15,14 +15,14 @@ class WebhookCommand extends Command
*
* @var ListProviderInterface
*/
- private $listProvider;
+ private ListProviderInterface $listProvider;
/**
* The configured list repository.
*
* @var ListRepository
*/
- private $listRepository;
+ private ListRepository $listRepository;
public function __construct(ListProviderInterface $listProvider, ListRepository $listRepository)
{
@@ -32,7 +32,7 @@ public function __construct(ListProviderInterface $listProvider, ListRepository
parent::__construct();
}
- protected function configure()
+ protected function configure(): void
{
$this
->setDescription('Add main webhook to a MailChimp List')
@@ -41,7 +41,7 @@ protected function configure()
// @TODO add params : listId, webhookurl
}
- protected function execute(InputInterface $input, OutputInterface $output)
+ protected function execute(InputInterface $input, OutputInterface $output): int
{
$output->writeln(sprintf('%s', $this->getDescription()));
@@ -56,5 +56,7 @@ protected function execute(InputInterface $input, OutputInterface $output)
}
$output->writeln('✔ done');
+
+ return Command::SUCCESS;
}
}
diff --git a/src/Controller/WebhookController.php b/src/Controller/WebhookController.php
index a0e2809..b859ad1 100644
--- a/src/Controller/WebhookController.php
+++ b/src/Controller/WebhookController.php
@@ -2,34 +2,33 @@
namespace Welp\MailchimpBundle\Controller;
-use Sensio\Bundle\FrameworkExtraBundle\Configuration\Route;
-use Sensio\Bundle\FrameworkExtraBundle\Configuration\Method;
-use Symfony\Bundle\FrameworkBundle\Controller\Controller;
+use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
+use Symfony\Component\DependencyInjection\Attribute\Autowire;
+use Symfony\Component\EventDispatcher\EventDispatcherInterface;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
-use Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException;
-
+use Symfony\Component\Routing\Annotation\Route; // @TODO: deprecated since Symfony 6.4/7.0
use Welp\MailchimpBundle\Provider\ListProviderInterface;
use Welp\MailchimpBundle\Event\WebhookEvent;
-/**
- * @Route("/webhook")
- */
-class WebhookController extends Controller
+#[Route('/webhook')]
+class WebhookController extends AbstractController
{
/**
* Endpoint for the mailchimp list Webhook
* https://apidocs.mailchimp.com/webhooks/
- * @Route("/endpoint", name="webhook_index")
- * @Method({"POST", "GET"})
* @param Request $request
- * @throws AccessDeniedHttpException
+ * @param EventDispatcherInterface $eventDispatcher
* @return JsonResponse
*/
- public function indexAction(Request $request)
+ #[Route('/endpoint', name: 'webhook_index')]
+ public function indexAction(
+ Request $request,
+ EventDispatcherInterface $eventDispatcher,
+ #[Autowire('@welp_mailchimp.list_provider')] $listProvider,
+ ): JsonResponse
{
-
// For Mailchimp ping GET
if ($request->isMethod('GET')) {
return new JsonResponse([
@@ -37,10 +36,9 @@ public function indexAction(Request $request)
'ping' => 'pong',
]);
}
-
// Handle POST request of Mailchimp
$type = $request->request->get('type');
- $data = $request->request->get('data');
+ $data = $request->request->all('data'); // all() returns an array
/* Response example:
data[merges][FNAME]: Tztz
data[merges][EMAIL]: tztz@gmail.com
@@ -55,64 +53,39 @@ public function indexAction(Request $request)
$hooksecret = $request->query->get('hooksecret');
if (empty($type) || empty($data) || empty($hooksecret) || !array_key_exists('list_id', $data)) {
- throw new AccessDeniedHttpException('incorrect data format!');
+ throw $this->createAccessDeniedException('Incorrect data format!');
}
$listId = $data['list_id'];
- $listProviderKey = $this->getParameter('welp_mailchimp.list_provider');
- try {
- $listProvider = $this->get($listProviderKey);
- } catch (ServiceNotFoundException $e) {
- throw new \InvalidArgumentException(sprintf('List Provider "%s" should be defined as a service.', $listProviderKey), $e->getCode(), $e);
- }
-
if (!$listProvider instanceof ListProviderInterface) {
- throw new \InvalidArgumentException(sprintf('List Provider "%s" should implement Welp\MailchimpBundle\Provider\ListProviderInterface.', $listProviderKey));
+ throw new \InvalidArgumentException(sprintf('List Provider "%s" should implement Welp\MailchimpBundle\Provider\ListProviderInterface.', $listProvider::class));
}
$list = $listProvider->getList($listId);
// Check the webhook_secret
$authorized = false;
- if($list != null && $list->getWebhookSecret() == $hooksecret) {
+
+ if ($list !== null && $list->getWebhookSecret() === $hooksecret) {
$authorized = true;
}
if (!$authorized) {
- throw new AccessDeniedHttpException('Webhook secret mismatch!');
+ throw $this->createAccessDeniedException('Webhook secret mismatch!');
}
- // Trigger the right event
- switch ($type) {
- case 'subscribe':
- $dispatcher = $this->get('event_dispatcher');
- $dispatcher->dispatch(WebhookEvent::EVENT_SUBSCRIBE, new WebhookEvent($data));
- break;
- case 'unsubscribe':
- $dispatcher = $this->get('event_dispatcher');
- $dispatcher->dispatch(WebhookEvent::EVENT_UNSUBSCRIBE, new WebhookEvent($data));
- break;
- case 'profile':
- $dispatcher = $this->get('event_dispatcher');
- $dispatcher->dispatch(WebhookEvent::EVENT_PROFILE, new WebhookEvent($data));
- break;
- case 'cleaned':
- $dispatcher = $this->get('event_dispatcher');
- $dispatcher->dispatch(WebhookEvent::EVENT_CLEANED, new WebhookEvent($data));
- break;
- case 'upemail':
- $dispatcher = $this->get('event_dispatcher');
- $dispatcher->dispatch(WebhookEvent::EVENT_UPEMAIL, new WebhookEvent($data));
- break;
- case 'campaign':
- $dispatcher = $this->get('event_dispatcher');
- $dispatcher->dispatch(WebhookEvent::EVENT_CAMPAIGN, new WebhookEvent($data));
- break;
- default:
- throw new AccessDeniedHttpException('type mismatch!');
- break;
- }
+ $eventName = match ($type) {
+ 'subscribe' => WebhookEvent::EVENT_SUBSCRIBE,
+ 'unsubscribe' => WebhookEvent::EVENT_UNSUBSCRIBE,
+ 'profile' => WebhookEvent::EVENT_PROFILE,
+ 'cleaned' => WebhookEvent::EVENT_CLEANED,
+ 'upemail' => WebhookEvent::EVENT_UPEMAIL,
+ 'campaign' => WebhookEvent::EVENT_CAMPAIGN,
+ default => throw $this->createAccessDeniedException('Type mismatch!'),
+ };
+
+ $eventDispatcher->dispatch(new WebhookEvent($data), $eventName);
return new JsonResponse([
'type' => $type,
diff --git a/src/DependencyInjection/Configuration.php b/src/DependencyInjection/Configuration.php
index 0cc8a99..3e9bc4e 100644
--- a/src/DependencyInjection/Configuration.php
+++ b/src/DependencyInjection/Configuration.php
@@ -15,17 +15,12 @@ class Configuration implements ConfigurationInterface
/**
* {@inheritDoc}
*/
- public function getConfigTreeBuilder()
+ public function getConfigTreeBuilder(): TreeBuilder
{
$treeBuilder = new TreeBuilder('welp_mailchimp');
- if (method_exists($treeBuilder, 'getRootNode')) {
- $rootNode = $treeBuilder->getRootNode();
- } else {
- $rootNode = $treeBuilder->root('welp_mailchimp');
- }
-
- $rootNode
+ $treeBuilder
+ ->getRootNode()
->children()
->scalarNode('api_key')
->isRequired()
diff --git a/src/DependencyInjection/WelpMailchimpExtension.php b/src/DependencyInjection/WelpMailchimpExtension.php
index 72c3a2e..69081ff 100644
--- a/src/DependencyInjection/WelpMailchimpExtension.php
+++ b/src/DependencyInjection/WelpMailchimpExtension.php
@@ -4,13 +4,13 @@
use Symfony\Component\Config\FileLocator;
use Symfony\Component\DependencyInjection\ContainerBuilder;
-use Symfony\Component\DependencyInjection\Loader;
+use Symfony\Component\DependencyInjection\Loader\YamlFileLoader;
use Symfony\Component\DependencyInjection\Reference;
use Symfony\Component\HttpKernel\DependencyInjection\Extension;
class WelpMailchimpExtension extends Extension
{
- public function load(array $configs, ContainerBuilder $container)
+ public function load(array $configs, ContainerBuilder $container): void
{
$configuration = new Configuration();
$config = $this->processConfiguration($configuration, $configs);
@@ -19,8 +19,8 @@ public function load(array $configs, ContainerBuilder $container)
$container->setParameter('welp_mailchimp.list_provider', $config['list_provider']);
$container->setParameter('welp_mailchimp.api_key', isset($config['api_key']) ? $config['api_key'] : null);
- $loader = new Loader\YamlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
- $loader->load('services.yml');
+ $loader = new YamlFileLoader($container, new FileLocator(__DIR__ . '/../../config'));
+ $loader->load('services.yaml');
// create an alias for the chosen list provider service
$alias = $config['list_provider'];
@@ -35,9 +35,10 @@ public function getAlias(): string
return 'welp_mailchimp';
}
- public function loadSubscriberProviders(ContainerBuilder $container, $lists)
+ public function loadSubscriberProviders(ContainerBuilder $container, $lists): void
{
$providerFactory = $container->getDefinition('welp_mailchimp.provider.factory');
+
foreach ($lists as $list) {
$providerKey = $list['subscriber_provider'];
$providerFactory->addMethodCall('addProvider', [$providerKey, new Reference($providerKey)]);
diff --git a/src/Event/SubscriberEvent.php b/src/Event/SubscriberEvent.php
index 68934f4..5587347 100644
--- a/src/Event/SubscriberEvent.php
+++ b/src/Event/SubscriberEvent.php
@@ -2,7 +2,7 @@
namespace Welp\MailchimpBundle\Event;
-use Symfony\Component\EventDispatcher\Event;
+use Symfony\Contracts\EventDispatcher\Event;
use Welp\MailchimpBundle\Subscriber\Subscriber;
/**
@@ -14,69 +14,69 @@ class SubscriberEvent extends Event
* Event to subscribe a User
* @var string
*/
- const EVENT_SUBSCRIBE = 'welp.mailchimp.subscribe';
+ public const EVENT_SUBSCRIBE = 'welp.mailchimp.subscribe';
/**
* Event to unsubscribe a User
* @var string
*/
- const EVENT_UNSUBSCRIBE = 'welp.mailchimp.unsubscribe';
+ public const EVENT_UNSUBSCRIBE = 'welp.mailchimp.unsubscribe';
/**
* Event to pending a User
* @var string
*/
- const EVENT_PENDING = 'welp.mailchimp.pending';
+ public const EVENT_PENDING = 'welp.mailchimp.pending';
/**
* Event to clean a User
* @var string
*/
- const EVENT_CLEAN = 'welp.mailchimp.clean';
+ public const EVENT_CLEAN = 'welp.mailchimp.clean';
/**
* Event to update a User
* @var string
*/
- const EVENT_UPDATE = 'welp.mailchimp.update';
+ public const EVENT_UPDATE = 'welp.mailchimp.update';
/**
* Event to change email of a User
* @var string
*/
- const EVENT_CHANGE_EMAIL = 'welp.mailchimp.change_email';
+ public const EVENT_CHANGE_EMAIL = 'welp.mailchimp.change_email';
/**
* Event to delete a User
* @var string
*/
- const EVENT_DELETE = 'welp.mailchimp.delete';
+ public const EVENT_DELETE = 'welp.mailchimp.delete';
/**
* MailChimp ListId
* @var string
*/
- protected $listId;
+ protected string $listId;
/**
* User as Subscriber
* @var Subscriber
*/
- protected $subscriber;
+ protected Subscriber $subscriber;
/**
* Subscriber's oldEmail (used for EVENT_CHANGE_EMAIL)
* @var string
*/
- protected $oldEmail;
+ protected ?string $oldEmail;
/**
*
- * @param string $listId
+ * @param string $listId
* @param Subscriber $subscriber
- * @param string $oldEmail
+ * @param string|null $oldEmail
*/
- public function __construct($listId, Subscriber $subscriber, $oldEmail = null)
+ public function __construct(string $listId, Subscriber $subscriber, ?string $oldEmail = null)
{
$this->listId = $listId;
$this->subscriber = $subscriber;
@@ -87,7 +87,7 @@ public function __construct($listId, Subscriber $subscriber, $oldEmail = null)
* Get MailChimp listId
* @return string
*/
- public function getListId()
+ public function getListId(): string
{
return $this->listId;
}
@@ -96,16 +96,16 @@ public function getListId()
* Get the User as Subscriber
* @return Subscriber
*/
- public function getSubscriber()
+ public function getSubscriber(): Subscriber
{
return $this->subscriber;
}
/**
* Get Subscriber's oldEmail (used for EVENT_CHANGE_EMAIL)
- * @return string
+ * @return string|null
*/
- public function getOldEmail()
+ public function getOldEmail(): ?string
{
return $this->oldEmail;
}
diff --git a/src/Event/SubscriberListener.php b/src/Event/SubscriberListener.php
index c6c8663..bb5a380 100644
--- a/src/Event/SubscriberListener.php
+++ b/src/Event/SubscriberListener.php
@@ -2,18 +2,18 @@
namespace Welp\MailchimpBundle\Event;
+use Symfony\Contracts\EventDispatcher\Event;
use Welp\MailchimpBundle\Subscriber\ListRepository;
-use Welp\MailchimpBundle\Event\SubscriberEvent;
/**
* Listener for subscriber unit synchronization
*/
-class SubscriberListener
+class SubscriberListener extends Event
{
/**
* @var ListRepository
*/
- protected $listRepository;
+ protected ListRepository $listRepository;
/**
* @param ListRepository $listRepository
@@ -28,7 +28,7 @@ public function __construct(ListRepository $listRepository)
* @param SubscriberEvent $event
* @return void
*/
- public function onSubscribe(SubscriberEvent $event)
+ public function onSubscribe(SubscriberEvent $event): void
{
$this->listRepository->subscribe(
$event->getListId(),
@@ -41,7 +41,7 @@ public function onSubscribe(SubscriberEvent $event)
* @param SubscriberEvent $event
* @return void
*/
- public function onUnsubscribe(SubscriberEvent $event)
+ public function onUnsubscribe(SubscriberEvent $event): void
{
$this->listRepository->unsubscribe(
$event->getListId(),
@@ -54,7 +54,7 @@ public function onUnsubscribe(SubscriberEvent $event)
* @param SubscriberEvent $event
* @return void
*/
- public function onPending(SubscriberEvent $event)
+ public function onPending(SubscriberEvent $event): void
{
$this->listRepository->pending(
$event->getListId(),
@@ -67,7 +67,7 @@ public function onPending(SubscriberEvent $event)
* @param SubscriberEvent $event
* @return void
*/
- public function onClean(SubscriberEvent $event)
+ public function onClean(SubscriberEvent $event): void
{
$this->listRepository->clean(
$event->getListId(),
@@ -80,7 +80,7 @@ public function onClean(SubscriberEvent $event)
* @param SubscriberEvent $event
* @return void
*/
- public function onUpdate(SubscriberEvent $event)
+ public function onUpdate(SubscriberEvent $event): void
{
$this->listRepository->update(
$event->getListId(),
@@ -93,7 +93,7 @@ public function onUpdate(SubscriberEvent $event)
* @param SubscriberEvent $event
* @return void
*/
- public function onChangeEmail(SubscriberEvent $event)
+ public function onChangeEmail(SubscriberEvent $event): void
{
$this->listRepository->changeEmailAddress(
$event->getListId(),
@@ -107,7 +107,7 @@ public function onChangeEmail(SubscriberEvent $event)
* @param SubscriberEvent $event
* @return void
*/
- public function onDelete(SubscriberEvent $event)
+ public function onDelete(SubscriberEvent $event): void
{
$this->listRepository->delete(
$event->getListId(),
diff --git a/src/Event/WebhookEvent.php b/src/Event/WebhookEvent.php
index 8f808d5..a75cca2 100644
--- a/src/Event/WebhookEvent.php
+++ b/src/Event/WebhookEvent.php
@@ -2,7 +2,7 @@
namespace Welp\MailchimpBundle\Event;
-use Symfony\Component\EventDispatcher\Event;
+use Symfony\Contracts\EventDispatcher\Event;
/**
* Event for MailChimp webhook
@@ -13,44 +13,44 @@ class WebhookEvent extends Event
* Event triggered when received webhook for user subscribe
* @var string
*/
- const EVENT_SUBSCRIBE = 'welp.mailchimp.webhook.subscribe';
+ public const EVENT_SUBSCRIBE = 'welp.mailchimp.webhook.subscribe';
/**
* Event triggered when received webhook for user unsubscribe
* @var string
*/
- const EVENT_UNSUBSCRIBE = 'welp.mailchimp.webhook.unsubscribe';
+ public const EVENT_UNSUBSCRIBE = 'welp.mailchimp.webhook.unsubscribe';
/**
* Event triggered when received webhook for user update profile
* @var string
*/
- const EVENT_PROFILE = 'welp.mailchimp.webhook.profile';
+ public const EVENT_PROFILE = 'welp.mailchimp.webhook.profile';
/**
* Event triggered when received webhook for user cleaned
* @var string
*/
- const EVENT_CLEANED = 'welp.mailchimp.webhook.cleaned';
+ public const EVENT_CLEANED = 'welp.mailchimp.webhook.cleaned';
/**
* Event triggered when received webhook for user update email [legacy?]
* @var string
*/
- const EVENT_UPEMAIL = 'welp.mailchimp.webhook.upemail';
+ public const EVENT_UPEMAIL = 'welp.mailchimp.webhook.upemail';
/**
* Event triggered when received webhook for new campaign send
* @var string
*/
- const EVENT_CAMPAIGN = 'welp.mailchimp.webhook.campaign';
+ public const EVENT_CAMPAIGN = 'welp.mailchimp.webhook.campaign';
/**
* Data form webhook request
* @var array
*/
- protected $data;
+ protected array $data;
/**
*
* @param array $data
*/
- public function __construct($data)
+ public function __construct(array $data)
{
$this->data = $data;
}
@@ -59,7 +59,7 @@ public function __construct($data)
* Get data form webhook request
* @return array
*/
- public function getData()
+ public function getData(): array
{
return $this->data;
}
diff --git a/src/Exception/MailchimpException.php b/src/Exception/MailchimpException.php
index c4a9416..b007310 100644
--- a/src/Exception/MailchimpException.php
+++ b/src/Exception/MailchimpException.php
@@ -12,20 +12,20 @@ class MailchimpException extends \Exception
* for this occurrence of the problem.
* @var int
*/
- private $status;
+ private int $status;
/**
* A human-readable explanation specific to this occurrence of the problem.
* @var string
*/
- private $detail;
+ private string $detail;
/**
* An absolute URI that identifies the problem type. When dereferenced,
* it should provide human-readable documentation for the problem type.
* @var string
*/
- private $type;
+ private string $type;
/**
* A short, human-readable summary of the problem type.
@@ -33,20 +33,20 @@ class MailchimpException extends \Exception
* except for purposes of localization.
* @var string
*/
- private $title;
+ private string $title;
/**
* For field-specific details, see the 'errors' array.
- * @var array
+ * @var array|null
*/
- private $errors;
+ private ?array $errors;
/**
* A string that identifies this specific occurrence of the problem.
* Please provide this ID when contacting support.
* @var string
*/
- private $instance;
+ private ?string $instance;
/**
* http://developer.mailchimp.com/documentation/mailchimp/guides/get-started-with-mailchimp-api-3/#errors
@@ -57,8 +57,9 @@ class MailchimpException extends \Exception
* @param array $errors
* @param string $instance
* @param \Throwable $previous
+ * @todo Fix $status: Optional parameter is provided before required.
*/
- public function __construct($status=0, $detail, $type, $title, $errors=null, $instance=null, \Throwable $previous=null)
+ public function __construct($status = 0, $detail, $type, $title, $errors = null, $instance = null, \Throwable $previous=null)
{
parent::__construct($detail, $status, $previous);
@@ -75,7 +76,7 @@ public function __construct($status=0, $detail, $type, $title, $errors=null, $in
*
* @return static
*/
- public function setType($type)
+ public function setType(string $type): static
{
$this->type = $type;
return $this;
@@ -86,7 +87,7 @@ public function setType($type)
*
* @return static
*/
- public function setTitle($title)
+ public function setTitle(string $title): static
{
$this->title = $title;
return $this;
@@ -97,7 +98,7 @@ public function setTitle($title)
*
* @return static
*/
- public function setErrors(array $errors)
+ public function setErrors(array $errors): static
{
$this->errors = $errors;
return $this;
@@ -108,7 +109,7 @@ public function setErrors(array $errors)
*
* @return static
*/
- public function setInstance($instance)
+ public function setInstance(string $instance): static
{
$this->instance = $instance;
return $this;
@@ -117,7 +118,7 @@ public function setInstance($instance)
/**
* @return int
*/
- public function getStatus()
+ public function getStatus(): int
{
return $this->status;
}
@@ -125,7 +126,7 @@ public function getStatus()
/**
* @return string
*/
- public function getDetail()
+ public function getDetail(): string
{
return $this->detail;
}
@@ -133,7 +134,7 @@ public function getDetail()
/**
* @return string
*/
- public function getType()
+ public function getType(): string
{
return $this->type;
}
@@ -141,7 +142,7 @@ public function getType()
/**
* @return string
*/
- public function getTitle()
+ public function getTitle(): string
{
return $this->title;
}
@@ -149,13 +150,14 @@ public function getTitle()
/**
* @return string
*/
- public function getInstance()
+ public function getInstance(): ?string
{
return $this->instance;
}
/**
* @return
+ * @todo: Artifact?
*/
public function getString()
{
@@ -163,9 +165,9 @@ public function getString()
}
/**
- * @return array
+ * @return array|null
*/
- public function getErrors()
+ public function getErrors(): ?array
{
return $this->errors;
}
diff --git a/src/Provider/ConfigListProvider.php b/src/Provider/ConfigListProvider.php
index bc39e41..9642259 100644
--- a/src/Provider/ConfigListProvider.php
+++ b/src/Provider/ConfigListProvider.php
@@ -2,13 +2,13 @@
namespace Welp\MailchimpBundle\Provider;
-use Welp\MailchimpBundle\Provider\ListProviderInterface;
use Welp\MailchimpBundle\Subscriber\SubscriberList;
+use Welp\MailchimpBundle\Subscriber\SubscriberListInterface;
class ConfigListProvider implements ListProviderInterface
{
- private $providerFactory;
- private $lists;
+ private ProviderFactory $providerFactory;
+ private array $lists;
public function __construct(ProviderFactory $providerFactory, $lists)
{
@@ -20,16 +20,18 @@ public function __construct(ProviderFactory $providerFactory, $lists)
* Default list provider, retrieve the lists from the config file.
* {@inheritdoc}
*/
- public function getLists()
+ public function getLists(): array
{
- if (sizeof($this->lists) == 0) {
- throw new \RuntimeException("No Mailchimp list has been defined. Check the your config.yml file based on MailchimpBundle's README.md");
+ if (count($this->lists) === 0) {
+ throw new \RuntimeException('No Mailchimp list has been defined. Check the your config.yml file based on MailchimpBundle\'s README.md');
}
- $lists = array();
- foreach ($this->lists as $listId => $listParameters)
- {
+
+ $lists = [];
+
+ foreach ($this->lists as $listId => $listParameters) {
$lists[] = $this->createList($listId, $listParameters);
}
+
return $lists;
}
@@ -37,24 +39,24 @@ public function getLists()
* Default list provider, retrieve one list from the config file.
* {@inheritdoc}
*/
- public function getList($listId)
+ public function getList($listId): SubscriberListInterface
{
- foreach ($this->lists as $id => $listParameters)
- {
- if($id == $listId)
- {
+ foreach ($this->lists as $id => $listParameters) {
+ if ($id === $listId) {
return $this->createList($id, $listParameters);
}
}
+
+ throw new \RuntimeException('Selected Mailchimp list has not been found. Check the your config.yml file based on MailchimpBundle\'s README.md');
}
/**
* create one SubscriberList
* @param string $listId
- * @param string $listParameters
+ * @param array $listParameters
* @return SubscriberList
*/
- private function createList($listId, $listParameters)
+ private function createList(string $listId, array $listParameters): SubscriberList
{
$providerServiceKey = $listParameters['subscriber_provider'];
$provider = $this->providerFactory->create($providerServiceKey);
diff --git a/src/Provider/DynamicProviderInterface.php b/src/Provider/DynamicProviderInterface.php
index 17d92a8..c5541ea 100644
--- a/src/Provider/DynamicProviderInterface.php
+++ b/src/Provider/DynamicProviderInterface.php
@@ -14,5 +14,5 @@ interface DynamicProviderInterface extends ProviderInterface
* @param string $listId
* @return void
*/
- public function setListId(string $listId);
+ public function setListId(string $listId): void;
}
diff --git a/src/Provider/ExampleSubscriberProvider.php b/src/Provider/ExampleSubscriberProvider.php
index 1536b50..f49da3c 100644
--- a/src/Provider/ExampleSubscriberProvider.php
+++ b/src/Provider/ExampleSubscriberProvider.php
@@ -27,11 +27,11 @@ public function __construct(UserRepository $userRepository)
/**
* {@inheritdoc}
*/
- public function getSubscribers()
+ public function getSubscribers(): array
{
$users = $this->userRepository->findSubscribers();
- $subscribers = array_map(function (User $user) {
+ $subscribers = array_map(static function (User $user) {
$subscriber = new Subscriber($user->getEmail(), [
self::TAG_NICKNAME => $user->getNickname(),
self::TAG_GENDER => $user->getGender(),
diff --git a/src/Provider/FosSubscriberProvider.php b/src/Provider/FosSubscriberProvider.php
index f041656..0a34387 100644
--- a/src/Provider/FosSubscriberProvider.php
+++ b/src/Provider/FosSubscriberProvider.php
@@ -25,13 +25,13 @@ public function __construct(UserManagerInterface $userManager)
/**
* {@inheritdoc}
*/
- public function getSubscribers()
+ public function getSubscribers(): array
{
$users = $this->userManager->findUsers();
// or find only enabled users :
// $users = $this->userManager->findUserBy(array('enabled' => true));
- $subscribers = array_map(function (User $user) {
+ $subscribers = array_map(static function (User $user) {
$subscriber = new Subscriber($user->getEmail(), [
self::TAG_USERNAME => $user->getUsername(),
self::TAG_ENABLED => $user->isEnabled(),
diff --git a/src/Provider/ListProviderInterface.php b/src/Provider/ListProviderInterface.php
index c80825d..98f8192 100644
--- a/src/Provider/ListProviderInterface.php
+++ b/src/Provider/ListProviderInterface.php
@@ -2,6 +2,8 @@
namespace Welp\MailchimpBundle\Provider;
+use Welp\MailchimpBundle\Subscriber\SubscriberListInterface;
+
/**
* List provider interface
*/
@@ -11,11 +13,12 @@ interface ListProviderInterface
* Get all the available Mailchimp lists
* @return array of SubscriberListInterface
*/
- public function getLists();
+ public function getLists(): array;
/**
* Get one Mailchimp list by id
+ * @param $listId
* @return SubscriberListInterface
*/
- public function getList($listId);
+ public function getList($listId): SubscriberListInterface;
}
diff --git a/src/Provider/ProviderFactory.php b/src/Provider/ProviderFactory.php
index 65ace96..ccc730d 100644
--- a/src/Provider/ProviderFactory.php
+++ b/src/Provider/ProviderFactory.php
@@ -9,7 +9,7 @@ class ProviderFactory
*
* @var array
*/
- private $providers;
+ private array $providers;
/**
* Add a provider to the provider array.
@@ -28,7 +28,7 @@ public function addProvider(string $providerKey, ProviderInterface $provider): v
*
* @return ProviderInterface $provider
*/
- public function create($providerKey)
+ public function create(string $providerKey): ProviderInterface
{
if (!isset($this->providers[$providerKey])) {
throw new \InvalidArgumentException(sprintf('Provider "%s" should be defined as a service.', $providerKey));
diff --git a/src/Provider/ProviderInterface.php b/src/Provider/ProviderInterface.php
index 1aee611..92a4a62 100644
--- a/src/Provider/ProviderInterface.php
+++ b/src/Provider/ProviderInterface.php
@@ -12,5 +12,5 @@ interface ProviderInterface
* in order to sync with MailChimp List
* @return array of Subscriber
*/
- public function getSubscribers();
+ public function getSubscribers(): array;
}
diff --git a/src/Resources/config/routing.yml b/src/Resources/config/routing.yml
deleted file mode 100644
index c4033b7..0000000
--- a/src/Resources/config/routing.yml
+++ /dev/null
@@ -1,3 +0,0 @@
-welp_mailchimp_webhook:
- resource: Welp\MailchimpBundle\Controller\WebhookController
- type: annotation
diff --git a/src/Subscriber/ListRepository.php b/src/Subscriber/ListRepository.php
index b43666d..6a03859 100644
--- a/src/Subscriber/ListRepository.php
+++ b/src/Subscriber/ListRepository.php
@@ -3,7 +3,6 @@
namespace Welp\MailchimpBundle\Subscriber;
use DrewM\MailChimp\MailChimp;
-use phpDocumentor\Reflection\Types\Void_;
use Welp\MailchimpBundle\Exception\MailchimpException;
/**
@@ -15,19 +14,19 @@ class ListRepository
* Numbers of subscribers per batch
* @var int
*/
- const SUBSCRIBER_BATCH_SIZE = 300;
+ public const SUBSCRIBER_BATCH_SIZE = 300;
/**
* MailChimp count limit for result set
* @var int
*/
- const MAILCHIMP_DEFAULT_COUNT_LIMIT = 10;
+ public const MAILCHIMP_DEFAULT_COUNT_LIMIT = 10;
/**
* MailChimp Object
* @var MailChimp
*/
- protected $mailchimp;
+ protected MailChimp $mailchimp;
/**
* @param MailChimp $mailchimp
@@ -41,23 +40,25 @@ public function __construct(MailChimp $mailchimp)
* Get MailChimp Object to do custom actions
* @return MailChimp https://github.com/drewm/mailchimp-api
*/
- public function getMailChimp()
+ public function getMailChimp(): MailChimp
{
return $this->mailchimp;
}
/**
- * Find MailChimp List by list Id
+ * Find MailChimp List by list ID
* @param string $listId
- * @return array list http://developer.mailchimp.com/documentation/mailchimp/reference/lists/#read-get_lists_list_id
+ * @return array list https://mailchimp.com/developer/marketing/api/lists/get-list-info/
+ * @throws MailchimpException
*/
- public function findById($listId)
+ public function findById(string $listId): array
{
- $listData = $this->mailchimp->get("lists/$listId");
+ $listData = $this->mailchimp->get('lists/' . $listId);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
}
+
return $listData;
}
@@ -67,14 +68,17 @@ public function findById($listId)
* @param Subscriber $subscriber
* @param string $status
* @return array
+ * @throws MailchimpException
*/
- protected function putSubscriberInList($listId, Subscriber $subscriber, $status)
+ protected function putSubscriberInList(string $listId, Subscriber $subscriber, string $status): array
{
if (!in_array($status, ['subscribed', 'unsubscribed', 'cleaned', 'pending', 'transactional'])) {
throw new \RuntimeException('$status must be one of these values: subscribed, unsubscribed, cleaned, pending, transactional');
}
+
$subscriberHash = MailChimp::subscriberHash($subscriber->getEmail());
- $result = $this->mailchimp->put("lists/$listId/members/$subscriberHash",
+
+ $result = $this->mailchimp->put('lists/' . $listId . '/members/' . $subscriberHash,
array_merge(
$subscriber->formatMailChimp(),
['status' => $status]
@@ -93,8 +97,9 @@ protected function putSubscriberInList($listId, Subscriber $subscriber, $status)
* @param string $listId
* @param Subscriber $subscriber
* @return array
+ * @throws MailchimpException
*/
- public function subscribe($listId, Subscriber $subscriber)
+ public function subscribe(string $listId, Subscriber $subscriber): array
{
return $this->putSubscriberInList($listId, $subscriber, 'subscribed');
}
@@ -103,8 +108,9 @@ public function subscribe($listId, Subscriber $subscriber)
* Subscribe a Subscriber to a list
* @param string $listId
* @param Subscriber $subscriber
+ * @throws MailchimpException
*/
- public function unsubscribe($listId, Subscriber $subscriber)
+ public function unsubscribe(string $listId, Subscriber $subscriber): array
{
return $this->putSubscriberInList($listId, $subscriber, 'unsubscribed');
}
@@ -113,8 +119,10 @@ public function unsubscribe($listId, Subscriber $subscriber)
* Clean a Subscriber to a list
* @param string $listId
* @param Subscriber $subscriber
+ * @return array
+ * @throws MailchimpException
*/
- public function clean($listId, Subscriber $subscriber)
+ public function clean(string $listId, Subscriber $subscriber): array
{
return $this->putSubscriberInList($listId, $subscriber, 'cleaned');
}
@@ -123,8 +131,10 @@ public function clean($listId, Subscriber $subscriber)
* Add/set pending a Subscriber to a list
* @param string $listId
* @param Subscriber $subscriber
+ * @return array
+ * @throws MailchimpException
*/
- public function pending($listId, Subscriber $subscriber)
+ public function pending(string $listId, Subscriber $subscriber): array
{
return $this->putSubscriberInList($listId, $subscriber, 'pending');
}
@@ -133,22 +143,26 @@ public function pending($listId, Subscriber $subscriber)
* set transactional a Subscriber to a list
* @param string $listId
* @param Subscriber $subscriber
+ * @return array
+ * @throws MailchimpException
*/
- public function transactional($listId, Subscriber $subscriber)
+ public function transactional(string $listId, Subscriber $subscriber): array
{
return $this->putSubscriberInList($listId, $subscriber, 'transactional');
}
/**
* Update a Subscriber to a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/members/#edit-patch_lists_list_id_members_subscriber_hash
+ * https://mailchimp.com/developer/marketing/api/list-members/update-list-member/
* @param string $listId
* @param Subscriber $subscriber
+ * @return array|bool
+ * @throws MailchimpException
*/
- public function update($listId, Subscriber $subscriber)
+ public function update(string $listId, Subscriber $subscriber): bool|array
{
$subscriberHash = MailChimp::subscriberHash($subscriber->getEmail());
- $result = $this->mailchimp->patch("lists/$listId/members/$subscriberHash", $subscriber->formatMailChimp());
+ $result = $this->mailchimp->patch('lists/' . $listId . '/members/' . $subscriberHash, $subscriber->formatMailChimp());
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -162,20 +176,23 @@ public function update($listId, Subscriber $subscriber)
* one possible solution is to delete old subscriber and add a new one
* with the same mergeFieds and Options...
* Change email address
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/members/#edit-put_lists_list_id_members_subscriber_hash
+ * https://mailchimp.com/developer/marketing/api/list-members/update-list-member/
* @param string $listId
* @param Subscriber $newSubscriber
* @param string $oldEmailAddress
+ * @return array|bool
+ * @throws MailchimpException
*/
- public function changeEmailAddress($listId, Subscriber $newSubscriber, $oldEmailAddress)
+ public function changeEmailAddress(string $listId, Subscriber $newSubscriber, string $oldEmailAddress): bool|array
{
# @NOTE handle special cases:
# 1. new email address already exists in List
# 2. old email address not exists in list
- # 3. old or new email address doesn't exists in list
+ # 3. old or new email address doesn't exist in list
$subscriberHash = MailChimp::subscriberHash($oldEmailAddress);
- $oldMember = $this->mailchimp->get("lists/$listId/members/$subscriberHash");
+ $oldMember = $this->mailchimp->get('lists/' . $listId . '/members/' . $subscriberHash);
+
if (!$this->mailchimp->success()) {
// problem with the oldSubcriber (doest not exist, ...)
// np we will take the new Subscriber
@@ -183,21 +200,15 @@ public function changeEmailAddress($listId, Subscriber $newSubscriber, $oldEmail
$newMember['status_if_new'] = 'subscribed';
} else {
// clean member
- unset($oldMember['_links']);
- unset($oldMember['id']);
- unset($oldMember['stats']);
- unset($oldMember['unique_email_id']);
- unset($oldMember['member_rating']);
- unset($oldMember['last_changed']);
- unset($oldMember['email_client']);
- unset($oldMember['list_id']);
+ unset($oldMember['_links'], $oldMember['id'], $oldMember['stats'], $oldMember['unique_email_id'], $oldMember['member_rating'], $oldMember['last_changed'], $oldMember['email_client'], $oldMember['list_id']);
$newMember = $oldMember;
$newMember['email_address'] = $newSubscriber->getEmail();
$newMember['status_if_new'] = 'subscribed';
// delete the old Member
- $deleteOld = $this->mailchimp->delete("lists/$listId/members/$subscriberHash");
+ $deleteOld = $this->mailchimp->delete('lists/' . $listId . '/members/' . $subscriberHash);
+
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
}
@@ -205,7 +216,8 @@ public function changeEmailAddress($listId, Subscriber $newSubscriber, $oldEmail
// add/update the new member
$subscriberHash = MailChimp::subscriberHash($newSubscriber->getEmail());
- $result = $this->mailchimp->put("lists/$listId/members/$subscriberHash", $newMember);
+ $result = $this->mailchimp->put('lists/' . $listId . '/members/' . $subscriberHash, $newMember);
+
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
}
@@ -217,11 +229,13 @@ public function changeEmailAddress($listId, Subscriber $newSubscriber, $oldEmail
* Delete a Subscriber to a list
* @param string $listId
* @param Subscriber $subscriber
+ * @return array|bool
+ * @throws MailchimpException
*/
- public function delete($listId, Subscriber $subscriber)
+ public function delete(string $listId, Subscriber $subscriber): bool|array
{
$subscriberHash = MailChimp::subscriberHash($subscriber->getEmail());
- $result = $this->mailchimp->delete("lists/$listId/members/$subscriberHash");
+ $result = $this->mailchimp->delete('lists/' . $listId . '/members/' . $subscriberHash);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -236,24 +250,32 @@ public function delete($listId, Subscriber $subscriber)
* @param array $subscribers
* @return array $batchIds
*/
- public function batchSubscribe($listId, array $subscribers)
+ public function batchSubscribe(string $listId, array $subscribers): array
{
$batchResults = [];
// as suggested in MailChimp API docs, we send multiple smaller requests instead of a bigger one
$subscriberChunks = array_chunk($subscribers, self::SUBSCRIBER_BATCH_SIZE);
+
foreach ($subscriberChunks as $subscriberChunk) {
- $Batch = $this->mailchimp->new_batch();
+ $batch = $this->mailchimp->new_batch();
+
foreach ($subscriberChunk as $index => $newsubscribers) {
$subscriberHash = MailChimp::subscriberHash($newsubscribers->getEmail());
- $Batch->put("op$index", "lists/$listId/members/$subscriberHash", array_merge(
- $newsubscribers->formatMailChimp(),
- ['status' => 'subscribed']
- ));
+
+ $batch->put(
+ 'op' . $index,
+ 'lists/' . $listId . '/members/' . $subscriberHash,
+ array_merge(
+ $newsubscribers->formatMailChimp(),
+ ['status' => 'subscribed']
+ )
+ );
}
- $Batch->execute();
- $currentBatch = $Batch->check_status();
- array_push($batchResults, $currentBatch);
+ $batch->execute();
+ $currentBatch = $batch->check_status();
+ $batchResults[] = $currentBatch; // faster than array_push() here
}
+
return $batchResults;
}
@@ -263,23 +285,28 @@ public function batchSubscribe($listId, array $subscribers)
* @param array $emails
* @return array $batchIds
*/
- public function batchUnsubscribe($listId, array $emails)
+ public function batchUnsubscribe(string $listId, array $emails): array
{
$batchIds = [];
// as suggested in MailChimp API docs, we send multiple smaller requests instead of a bigger one
$emailsChunks = array_chunk($emails, self::SUBSCRIBER_BATCH_SIZE);
+
foreach ($emailsChunks as $emailsChunk) {
- $Batch = $this->mailchimp->new_batch();
+ $batch = $this->mailchimp->new_batch();
+
foreach ($emailsChunk as $index => $email) {
$emailHash = MailChimp::subscriberHash($email);
- $Batch->patch("op$index", "lists/$listId/members/$emailHash", [
+ $batch->patch('op' . $index, 'lists/' . $listId . '/members/' . $emailHash, [
'status' => 'unsubscribed'
]);
}
- $result = $Batch->execute();
- $currentBatch = $Batch->check_status();
- array_push($batchIds, $currentBatch['id']);
+
+ $batch->execute();
+ $currentBatch = $batch->check_status();
+
+ $batchIds[] = $currentBatch['id']; // faster than array_push() here
}
+
return $batchIds;
}
@@ -289,20 +316,23 @@ public function batchUnsubscribe($listId, array $emails)
* @param array $emails
* @return array $batchIds
*/
- public function batchDelete($listId, array $emails)
+ public function batchDelete(string $listId, array $emails): array
{
$batchIds = [];
// as suggested in MailChimp API docs, we send multiple smaller requests instead of a bigger one
$emailsChunks = array_chunk($emails, self::SUBSCRIBER_BATCH_SIZE);
+
foreach ($emailsChunks as $emailsChunk) {
- $Batch = $this->mailchimp->new_batch();
+ $batch = $this->mailchimp->new_batch();
+
foreach ($emailsChunk as $index => $email) {
$emailHash = MailChimp::subscriberHash($email);
- $Batch->delete("op$index", "lists/$listId/members/$emailHash");
+ $batch->delete('op' . $index, 'lists/' . $listId . '/members/' . $emailHash);
}
- $result = $Batch->execute();
- $currentBatch = $Batch->check_status();
- array_push($batchIds, $currentBatch['id']);
+
+ $batch->execute();
+ $currentBatch = $batch->check_status();
+ $batchIds[] = $currentBatch['id'];
}
return $batchIds;
}
@@ -311,11 +341,11 @@ public function batchDelete($listId, array $emails)
* Get Members of a list
* @param string $listId
* @return array
+ * @throws MailchimpException
*/
- public function getMembers($listId)
+ public function getMembers(string $listId): array
{
- $emails = [];
- $result = $this->mailchimp->get("lists/$listId/members");
+ $result = $this->mailchimp->get('lists/' . $listId . '/members');
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -328,14 +358,15 @@ public function getMembers($listId)
* Get an array of subscribers emails from a list
* @param string $listId
* @return array
+ * @throws MailchimpException
*/
- public function getSubscriberEmails($listId)
+ public function getSubscriberEmails(string $listId): array
{
$emails = [];
$members = [];
- $offset=0;
+ $offset = 0;
$maxresult = 200;
- $result = $this->mailchimp->get("lists/$listId/members", ['count'=> $maxresult]);
+ $result = $this->mailchimp->get('lists/' . $listId . '/members', ['count' => $maxresult]);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -345,20 +376,21 @@ public function getSubscriberEmails($listId)
$members = array_merge($members, $result['members']);
while ($offset < $totalItems) {
- $offset+=$maxresult;
- $result = $this->mailchimp->get("lists/$listId/members", [
- 'count' => $maxresult,
- 'offset' => $offset
- ]);
+ $offset += $maxresult;
+ $result = $this->mailchimp->get('lists/' . $listId . '/members', [
+ 'count' => $maxresult,
+ 'offset' => $offset
+ ]);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
}
+
$members = array_merge($members, $result['members']);
- };
+ }
foreach ($members as $key => $member) {
- array_push($emails, $member['email_address']);
+ $emails[] = $member['email_address'];
}
return $emails;
@@ -366,17 +398,18 @@ public function getSubscriberEmails($listId)
/**
* find all merge fields for a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/merge-fields/#
+ * https://mailchimp.com/developer/marketing/api/list-merges/
* @param string $listId
* @return array
+ * @throws MailchimpException
*/
- public function getMergeFields($listId)
+ public function getMergeFields(string $listId): array
{
- $result = $this->mailchimp->get("lists/$listId/merge-fields");
+ $result = $this->mailchimp->get('lists/' . $listId . '/merge-fields');
# Handle mailchimp default count limit
if ($result['total_items'] > self::MAILCHIMP_DEFAULT_COUNT_LIMIT) {
- $result = $this->mailchimp->get("lists/$listId/merge-fields", array("count" => $result['total_items']));
+ $result = $this->mailchimp->get('lists/' . $listId . '/merge-fields', ['count' => $result['total_items']]);
}
if (!$this->mailchimp->success()) {
@@ -388,14 +421,15 @@ public function getMergeFields($listId)
/**
* add merge field for a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/merge-fields/#
+ * https://mailchimp.com/developer/marketing/api/list-merges/
* @param string $listId
* @param array $mergeData ["name" => '', "type" => '']
* @return array
+ * @throws MailchimpException
*/
- public function addMergeField($listId, array $mergeData)
+ public function addMergeField(string $listId, array $mergeData): array
{
- $result = $this->mailchimp->post("lists/$listId/merge-fields", $mergeData);
+ $result = $this->mailchimp->post('lists/' . $listId . '/merge-fields', $mergeData);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -406,15 +440,16 @@ public function addMergeField($listId, array $mergeData)
/**
* add merge field for a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/merge-fields/#edit-patch_lists_list_id_merge_fields_merge_id
+ * https://mailchimp.com/developer/marketing/api/list-merges/
* @param string $listId
* @param string $mergeId
* @param array $mergeData ["name" => '', "type" => '', ...]
* @return array
+ * @throws MailchimpException
*/
- public function updateMergeField($listId, $mergeId, $mergeData)
+ public function updateMergeField(string $listId, string $mergeId, array $mergeData): array
{
- $result = $this->mailchimp->patch("lists/$listId/merge-fields/$mergeId", $mergeData);
+ $result = $this->mailchimp->patch('lists/' . $listId . '/merge-fields/' . $mergeId, $mergeData);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -424,15 +459,16 @@ public function updateMergeField($listId, $mergeId, $mergeData)
}
/**
- * delete merge field for a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/merge-fields/#
- * @param string $listId
- * @param string $mergeId
- * @return array
- */
- public function deleteMergeField($listId, $mergeId)
+ * delete merge field for a list
+ * https://mailchimp.com/developer/marketing/api/list-merges/
+ * @param string $listId
+ * @param string $mergeId
+ * @return array
+ * @throws MailchimpException
+ */
+ public function deleteMergeField(string $listId, string $mergeId): array
{
- $result = $this->mailchimp->delete("lists/$listId/merge-fields/$mergeId");
+ $result = $this->mailchimp->delete('lists/' . $listId . '/merge-fields/' . $mergeId);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -442,12 +478,13 @@ public function deleteMergeField($listId, $mergeId)
}
/**
- * Automatically configure Webhook for a list
- * @param string $listId
- * @param string $webhookurl
- * @return array
- */
- public function registerMainWebhook($listId, $webhookurl)
+ * Automatically configure Webhook for a list
+ * @param string $listId
+ * @param string $webhookurl
+ * @return array
+ * @throws MailchimpException
+ */
+ public function registerMainWebhook(string $listId, string $webhookurl): array
{
// Configure webhook
$subscribeWebhook = [
@@ -463,7 +500,7 @@ public function registerMainWebhook($listId, $webhookurl)
'sources' => [
'user' => true,
'admin' => true,
- 'api' => false // to avoid double (infinite loop) update (update an subscriber with the API and the webhook reupdate the user, ...)
+ 'api' => false // to avoid double (infinite loop) update (update a subscriber with the API and the webhook reupdate the user, ...)
]
];
@@ -471,15 +508,16 @@ public function registerMainWebhook($listId, $webhookurl)
}
/**
- * Add a new webhook to a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/webhooks/#
- * @param string $listId
- * @param array $webhookData
- * @return array
- */
- public function addWebhook($listId, array $webhookData)
+ * Add a new webhook to a list
+ * https://mailchimp.com/developer/marketing/api/list-webhooks/
+ * @param string $listId
+ * @param array $webhookData
+ * @return array
+ * @throws MailchimpException
+ */
+ public function addWebhook(string $listId, array $webhookData): array
{
- $result = $this->mailchimp->post("lists/$listId/webhooks", $webhookData);
+ $result = $this->mailchimp->post('lists/' . $listId . '/webhooks', $webhookData);
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -489,14 +527,15 @@ public function addWebhook($listId, array $webhookData)
}
/**
- * Get webhooks of a list
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/webhooks/#
- * @param string $listId
- * @return array
- */
- public function getWebhooks($listId)
+ * Get webhooks of a list
+ * https://mailchimp.com/developer/marketing/api/list-webhooks/
+ * @param string $listId
+ * @return array
+ * @throws MailchimpException
+ */
+ public function getWebhooks(string $listId): array
{
- $result = $this->mailchimp->get("lists/$listId/webhooks");
+ $result = $this->mailchimp->get('lists/' . $listId . '/webhooks');
if (!$this->mailchimp->success()) {
$this->throwMailchimpError($this->mailchimp->getLastResponse());
@@ -507,31 +546,41 @@ public function getWebhooks($listId)
/**
* [throwMailchimpError description]
- * @param array $errorResponse [description]
+ * @param array $errorResponse [description]
* @return void
* @throws MailchimpException [description]
*/
- private function throwMailchimpError(array $errorResponse)
+ private function throwMailchimpError(array $errorResponse): void
{
- $errorArray = json_decode($errorResponse['body'], true);
- if (is_array($errorArray) && array_key_exists('errors', $errorArray)) {
+ try {
+ $errorArray = json_decode($errorResponse['body'], true, 512, JSON_THROW_ON_ERROR);
+ } catch (\JsonException $e) {
throw new MailchimpException(
- $errorArray['status'],
- $errorArray['detail'],
- $errorArray['type'],
- $errorArray['title'],
- $errorArray['errors'],
- $errorArray['instance']
+ 400,
+ $e->getMessage(),
+ 'JSON',
+ 'Invalid JSON response.',
);
- } else {
+ }
+
+ if (is_array($errorArray) && array_key_exists('errors', $errorArray)) {
throw new MailchimpException(
$errorArray['status'],
$errorArray['detail'],
$errorArray['type'],
$errorArray['title'],
- null,
+ $errorArray['errors'],
$errorArray['instance']
);
}
+
+ throw new MailchimpException(
+ $errorArray['status'],
+ $errorArray['detail'],
+ $errorArray['type'],
+ $errorArray['title'],
+ null,
+ $errorArray['instance']
+ );
}
}
diff --git a/src/Subscriber/ListSynchronizer.php b/src/Subscriber/ListSynchronizer.php
index 55c6a23..e21cf65 100644
--- a/src/Subscriber/ListSynchronizer.php
+++ b/src/Subscriber/ListSynchronizer.php
@@ -2,6 +2,8 @@
namespace Welp\MailchimpBundle\Subscriber;
+use Welp\MailchimpBundle\Exception\MailchimpException;
+
/**
* Handle Synchronization between SubscriberList and specific MailChimp List
*/
@@ -10,7 +12,7 @@ class ListSynchronizer
/**
* @var ListRepository
*/
- protected $listRepository;
+ protected ListRepository $listRepository;
/**
* @param ListRepository $listRepository
@@ -23,9 +25,10 @@ public function __construct(ListRepository $listRepository)
/**
* Synchronise user from provider with MailChimp List
* @param SubscriberListInterface $list
- * @return void
+ * @return array
+ * @throws MailchimpException
*/
- public function synchronize(SubscriberListInterface $list)
+ public function synchronize(SubscriberListInterface $list): array
{
$listData = $this->listRepository->findById($list->getListId());
@@ -34,6 +37,7 @@ public function synchronize(SubscriberListInterface $list)
// unsubscribe difference
$this->unsubscribeDifference($list->getListId(), $subscribers);
+
// subscribe the rest
return $this->batchSubscribe($list->getListId(), $subscribers);
}
@@ -42,29 +46,31 @@ public function synchronize(SubscriberListInterface $list)
* Subscribe a batch of user
* @param string $listId
* @param array $subscribers
- * @return void
+ * @return array
*/
- protected function batchSubscribe($listId, array $subscribers = [])
+ protected function batchSubscribe(string $listId, array $subscribers = []): array
{
return $this->listRepository->batchSubscribe($listId, $subscribers);
}
/**
- * Unsubscribe the difference between the array subscriber an user
+ * Unsubscribe the difference between the array subscriber a user
* @param string $listId
* @param array $subscribers
* @return void
+ * @throws MailchimpException
*/
- protected function unsubscribeDifference($listId, array $subscribers)
+ protected function unsubscribeDifference(string $listId, array $subscribers): void
{
$mailchimpEmails = $this->listRepository->getSubscriberEmails($listId);
- $internalEmails = array_map(function (Subscriber $subscriber) {
+ $internalEmails = array_map(static function (Subscriber $subscriber) {
return $subscriber->getEmail();
}, $subscribers);
// emails that are present in mailchimp but not internally should be unsubscribed
$diffenceEmails = array_diff($mailchimpEmails, $internalEmails);
- if (sizeof($diffenceEmails) == 0) {
+
+ if (count($diffenceEmails) === 0) {
return;
}
@@ -76,8 +82,9 @@ protected function unsubscribeDifference($listId, array $subscribers)
* @param string $listId
* @param array $mergeFields
* @return void
+ * @throws MailchimpException
*/
- public function synchronizeMergeFields($listId, array $mergeFields = [])
+ public function synchronizeMergeFields(string $listId, array $mergeFields = []): void
{
$mailChimpMergeFields = $this->listRepository->getMergeFields($listId);
@@ -99,21 +106,23 @@ public function synchronizeMergeFields($listId, array $mergeFields = [])
}
/**
- * Test if the merge field Tag exists in an array
- * @param string $tagName
- * @param array $tags
- * @return mixed (Boolean true|false) or $tag['merge_id']
- */
- protected function tagExists($tagName, array $tags)
+ * Test if the merge field Tag exists in an array
+ * @param string $tagName
+ * @param array $tags
+ * @return bool|string (Boolean true|false) or $tag['merge_id']
+ */
+ protected function tagExists(string $tagName, array $tags): bool|string
{
foreach ($tags as $tag) {
- if ($tag['tag'] == $tagName) {
+ if ($tag['tag'] === $tagName) {
if (array_key_exists('merge_id', $tag)) {
return $tag['merge_id'];
}
+
return true;
}
}
+
return false;
}
}
diff --git a/src/Subscriber/Subscriber.php b/src/Subscriber/Subscriber.php
index 93a96bc..a4d7fc2 100644
--- a/src/Subscriber/Subscriber.php
+++ b/src/Subscriber/Subscriber.php
@@ -4,7 +4,7 @@
/**
* Class to represent a subscriber
- * http://developer.mailchimp.com/documentation/mailchimp/reference/lists/members/
+ * https://mailchimp.com/developer/marketing/api/list-members/
*/
class Subscriber
{
@@ -12,19 +12,19 @@ class Subscriber
* Subscriber's email
* @var string
*/
- protected $email;
+ protected string $email;
/**
* Subscriber's merge fields
* @var array
*/
- protected $mergeFields;
+ protected array $mergeFields;
/**
* Subscriber's options
* @var array
*/
- protected $options;
+ protected array $options;
/**
*
@@ -32,7 +32,7 @@ class Subscriber
* @param array $mergeFields
* @param array $options
*/
- public function __construct($email, array $mergeFields = [], array $options = [])
+ public function __construct(string $email, array $mergeFields = [], array $options = [])
{
$this->email = $email;
$this->mergeFields = $mergeFields;
@@ -40,10 +40,10 @@ public function __construct($email, array $mergeFields = [], array $options = []
}
/**
- * Formate Subscriber for MailChimp API request
+ * Format Subscriber for MailChimp API request
* @return array
*/
- public function formatMailChimp()
+ public function formatMailChimp(): array
{
$options = $this->options;
if (!empty($this->getMergeFields())) {
@@ -61,7 +61,7 @@ public function formatMailChimp()
* Correspond to email_address in MailChimp request
* @return string
*/
- public function getEmail()
+ public function getEmail(): string
{
return $this->email;
}
@@ -71,9 +71,9 @@ public function getEmail()
* @param array $mergeFields
* @return array ['TAGKEY' => value, ...]
*/
- public function setMergeFields(array $mergeFields)
+ public function setMergeFields(array $mergeFields): array
{
- // since fev2017, MailChimp API doesn't handle null value en throw 400
+ // since feb2017, MailChimp API doesn't handle null value en throw 400
// errors when you try to add subscriber with a mergefields value to null
foreach ($mergeFields as $key => $value) {
if ($value === null) {
@@ -89,7 +89,7 @@ public function setMergeFields(array $mergeFields)
* Correspond to merge_fields in MailChimp request
* @return array ['TAGKEY' => value, ...]
*/
- public function getMergeFields()
+ public function getMergeFields(): array
{
// since fev2017, MailChimp API doesn't handle null value en throw 400
// errors when you try to add subscriber with a mergefields value to null
@@ -98,6 +98,7 @@ public function getMergeFields()
unset($this->mergeFields[$key]);
}
}
+
return $this->mergeFields;
}
@@ -106,7 +107,7 @@ public function getMergeFields()
* email_type, interests, language, vip, location, ip_signup, timestamp_signup, ip_opt, timestamp_opt
* @return array
*/
- public function getOptions()
+ public function getOptions(): array
{
return $this->options;
}
diff --git a/src/Subscriber/SubscriberList.php b/src/Subscriber/SubscriberList.php
index 8aca8b5..9376478 100644
--- a/src/Subscriber/SubscriberList.php
+++ b/src/Subscriber/SubscriberList.php
@@ -14,39 +14,39 @@ class SubscriberList implements SubscriberListInterface
* MailChimp ListId
* @var string
*/
- protected $listId;
+ protected string $listId;
/**
* Subscriber provider
* @var ProviderInterface
*/
- protected $provider;
+ protected ProviderInterface $provider;
/**
* Merge fields
* @var array
*/
- protected $mergeFields;
+ protected array $mergeFields;
/**
* MailChimp webhook URL
* @var string
*/
- protected $webhookUrl;
-
+ protected string $webhookUrl = '';
+
/**
* MailChimp webhook secret
* @var string
*/
- protected $webhookSecret;
+ protected string $webhookSecret = '';
/**
*
- * @param string $listId
+ * @param string $listId
* @param ProviderInterface $provider
* @param array $mergeFields
*/
- public function __construct($listId, ProviderInterface $provider, array $mergeFields = array())
+ public function __construct(string $listId, ProviderInterface $provider, array $mergeFields = [])
{
$this->listId = $listId;
$this->provider = $provider;
@@ -55,14 +55,14 @@ public function __construct($listId, ProviderInterface $provider, array $mergeFi
//If the provider implements DynamicProviderInterface, set the list id in the provider
if ($this->provider instanceof DynamicProviderInterface) {
$this->provider->setListId($this->listId);
- }
+ }
}
/**
* get the MailChimp ListId
* @return string
*/
- public function getListId()
+ public function getListId(): string
{
return $this->listId;
}
@@ -71,7 +71,7 @@ public function getListId()
* Get the subscriber provider
* @return ProviderInterface
*/
- public function getProvider()
+ public function getProvider(): ProviderInterface
{
return $this->provider;
}
@@ -80,7 +80,7 @@ public function getProvider()
* Get the list merge fields
* @return array
*/
- public function getMergeFields()
+ public function getMergeFields(): array
{
return $this->mergeFields;
}
@@ -89,16 +89,16 @@ public function getMergeFields()
* Get the list webhook URL
* @return string
*/
- public function getWebhookUrl()
+ public function getWebhookUrl(): string
{
return $this->webhookUrl;
}
/**
* Set the list webhook URL
- * @param string
+ * @param string $webhookUrl
*/
- public function setWebhookUrl($webhookUrl)
+ public function setWebhookUrl(string $webhookUrl): void
{
$this->webhookUrl = $webhookUrl;
}
@@ -107,16 +107,16 @@ public function setWebhookUrl($webhookUrl)
* Get the list webhook secret
* @return string
*/
- public function getWebhookSecret()
+ public function getWebhookSecret(): string
{
return $this->webhookSecret;
}
/**
* Set the list webhook secret
- * @param string
+ * @param string $webhookSecret
*/
- public function setWebhookSecret($webhookSecret)
+ public function setWebhookSecret(string $webhookSecret): void
{
$this->webhookSecret = $webhookSecret;
}
diff --git a/src/Subscriber/SubscriberListInterface.php b/src/Subscriber/SubscriberListInterface.php
index 001a60b..a6683f3 100644
--- a/src/Subscriber/SubscriberListInterface.php
+++ b/src/Subscriber/SubscriberListInterface.php
@@ -2,6 +2,8 @@
namespace Welp\MailchimpBundle\Subscriber;
+use Welp\MailchimpBundle\Provider\ProviderInterface;
+
/**
* SubscriberList interface linked a MailChimpList with a SubscriberProvider
*/
@@ -11,41 +13,41 @@ interface SubscriberListInterface
* get the MailChimp ListId
* @return string
*/
- public function getListId();
+ public function getListId(): string;
/**
* Get the subscriber provider
* @return ProviderInterface
*/
- public function getProvider();
+ public function getProvider(): ProviderInterface;
/**
* Get the list merge fields
* @return array
*/
- public function getMergeFields();
+ public function getMergeFields(): array;
/**
* Get the list webhook URL
* @return string
*/
- public function getWebhookUrl();
+ public function getWebhookUrl(): string;
/**
* Set the list webhook URL
- * @param string
+ * @param string $webhookUrl
*/
- public function setWebhookUrl($webhookUrl);
+ public function setWebhookUrl(string $webhookUrl);
/**
* Get the list webhook secret
* @return string
*/
- public function getWebhookSecret();
+ public function getWebhookSecret(): string;
/**
* Set the list webhook secret
- * @param string
+ * @param string $webhookSecret
*/
- public function setWebhookSecret($webhookSecret);
+ public function setWebhookSecret(string $webhookSecret);
}
diff --git a/src/WelpMailchimpBundle.php b/src/WelpMailchimpBundle.php
index a1136e1..bd0a1f3 100644
--- a/src/WelpMailchimpBundle.php
+++ b/src/WelpMailchimpBundle.php
@@ -1,13 +1,21 @@