Skip to content

Commit c0a435e

Browse files
authored
Merge pull request #68 from Setono/readd-push-customer-handler
Readded push customer handler
2 parents cbe7d45 + 05638f4 commit c0a435e

File tree

6 files changed

+171
-13
lines changed

6 files changed

+171
-13
lines changed

composer.json

-1
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@
2020
"fzaninotto/faker": "^1.9",
2121
"knplabs/knp-menu": "^3.1",
2222
"psr/log": "^1.1",
23-
"sarhan/php-flatten": "^3.0",
2423
"setono/doctrine-orm-batcher": "^0.6.2",
2524
"setono/doctrine-orm-batcher-bundle": "^0.3.1",
2625
"sylius/resource-bundle": "^1.6",

src/EventListener/UpdateStoreSubscriber.php

+2-3
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@
66

77
use Psr\Log\LoggerInterface;
88
use function Safe\sprintf;
9-
use Sarhan\Flatten\Flatten;
109
use Setono\SyliusMailchimpPlugin\Client\ClientInterface;
1110
use Setono\SyliusMailchimpPlugin\Exception\ClientException;
1211
use Setono\SyliusMailchimpPlugin\Model\AudienceInterface;
@@ -63,8 +62,8 @@ public function update(ResourceControllerEvent $event): void
6362
$event->stop($this->translator->trans('setono_sylius_mailchimp.ui.channel_association_failed'));
6463

6564
$this->logger->error(sprintf(
66-
"The user tried to update an audience in Sylius, but got this error: %s\n\nErrors array:\n%s",
67-
$e->getMessage(), print_r((new Flatten())->flattenToArray($e->getErrors()), true)
65+
"The user tried to update an audience in Sylius, but got this error: %s\n\nErrors array:\n%s\n\nOptions array:%s",
66+
$e->getMessage(), print_r($e->getErrors(), true), print_r($e->getOptions(), true)
6867
));
6968
}
7069
}

src/Message/Handler/PushCustomerBatchHandler.php

+8-9
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
use Setono\SyliusMailchimpPlugin\Message\Command\PushCustomerBatch;
1414
use Setono\SyliusMailchimpPlugin\Model\CustomerInterface;
1515
use Setono\SyliusMailchimpPlugin\Provider\AudienceProviderInterface;
16+
use Setono\SyliusMailchimpPlugin\Workflow\MailchimpWorkflow;
1617
use Symfony\Component\Messenger\Exception\UnrecoverableMessageHandlingException;
1718
use Symfony\Component\Messenger\Handler\MessageHandlerInterface;
1819
use Symfony\Component\Workflow\Registry;
@@ -74,13 +75,12 @@ public function __invoke(PushCustomerBatch $message): void
7475
foreach ($customers as $customer) {
7576
$workflow = $this->getWorkflow($customer);
7677

77-
// todo use constant
78-
if (!$workflow->can($customer, 'process')) {
78+
if (!$workflow->can($customer, MailchimpWorkflow::TRANSITION_PROCESS)) {
7979
// this means that the state was changed another place
8080
continue;
8181
}
8282

83-
$workflow->apply($customer, 'process'); // todo use constant
83+
$workflow->apply($customer, MailchimpWorkflow::TRANSITION_PROCESS);
8484
$manager->flush();
8585

8686
try {
@@ -95,19 +95,18 @@ public function __invoke(PushCustomerBatch $message): void
9595

9696
$this->client->updateMember($audience, $customer);
9797

98-
// todo use constant
99-
if (!$workflow->can($customer, 'push')) {
98+
if (!$workflow->can($customer, MailchimpWorkflow::TRANSITION_PUSH)) {
10099
throw new UnrecoverableMessageHandlingException(sprintf(
101100
'Could not apply transition "push" on customer with id "%s". Mailchimp state: "%s"',
102101
$customer->getId(), $customer->getMailchimpState()
103102
));
104103
}
105104

106-
$workflow->apply($customer, 'push'); // todo use constant
105+
$workflow->apply($customer, MailchimpWorkflow::TRANSITION_PUSH);
107106
} catch (Throwable $e) {
108-
$this->logger->error($e->getMessage());
107+
$this->logger->error(self::buildErrorMessage($e));
109108
$customer->setMailchimpError(self::buildErrorMessage($e));
110-
$workflow->apply($customer, 'fail'); // todo use constant
109+
$workflow->apply($customer, MailchimpWorkflow::TRANSITION_FAIL);
111110
} finally {
112111
$manager->flush();
113112
}
@@ -117,7 +116,7 @@ public function __invoke(PushCustomerBatch $message): void
117116
private function getWorkflow(object $obj): Workflow
118117
{
119118
if (null === $this->workflow) {
120-
$this->workflow = $this->workflowRegistry->get($obj, 'mailchimp'); // todo use constant here
119+
$this->workflow = $this->workflowRegistry->get($obj, MailchimpWorkflow::NAME); // todo use constant here
121120
}
122121

123122
return $this->workflow;
+120
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace Setono\SyliusMailchimpPlugin\Message\Handler;
6+
7+
use Doctrine\Persistence\ManagerRegistry;
8+
use Psr\Log\LoggerInterface;
9+
use function Safe\sprintf;
10+
use Setono\SyliusMailchimpPlugin\Client\ClientInterface;
11+
use Setono\SyliusMailchimpPlugin\Exception\ClientException;
12+
use Setono\SyliusMailchimpPlugin\Message\Command\PushCustomer;
13+
use Setono\SyliusMailchimpPlugin\Model\CustomerInterface;
14+
use Setono\SyliusMailchimpPlugin\Provider\AudienceProviderInterface;
15+
use Setono\SyliusMailchimpPlugin\Repository\CustomerRepositoryInterface;
16+
use Setono\SyliusMailchimpPlugin\Workflow\MailchimpWorkflow;
17+
use Symfony\Component\Messenger\Exception\UnrecoverableMessageHandlingException;
18+
use Symfony\Component\Messenger\Handler\MessageHandlerInterface;
19+
use Symfony\Component\Workflow\Registry;
20+
use Webmozart\Assert\Assert;
21+
22+
final class PushCustomerHandler implements MessageHandlerInterface
23+
{
24+
/** @var CustomerRepositoryInterface */
25+
private $customerRepository;
26+
27+
/** @var AudienceProviderInterface */
28+
private $audienceProvider;
29+
30+
/** @var ClientInterface */
31+
private $client;
32+
33+
/** @var Registry */
34+
private $workflowRegistry;
35+
36+
/** @var LoggerInterface */
37+
private $logger;
38+
39+
/** @var ManagerRegistry */
40+
private $managerRegistry;
41+
42+
public function __construct(
43+
CustomerRepositoryInterface $customerRepository,
44+
AudienceProviderInterface $audienceProvider,
45+
ClientInterface $client,
46+
Registry $workflowRegistry,
47+
LoggerInterface $logger,
48+
ManagerRegistry $managerRegistry
49+
) {
50+
$this->customerRepository = $customerRepository;
51+
$this->audienceProvider = $audienceProvider;
52+
$this->client = $client;
53+
$this->workflowRegistry = $workflowRegistry;
54+
$this->logger = $logger;
55+
$this->managerRegistry = $managerRegistry;
56+
}
57+
58+
public function __invoke(PushCustomer $message): void
59+
{
60+
/** @var CustomerInterface|null $customer */
61+
$customer = $this->customerRepository->find($message->getCustomerId());
62+
Assert::isInstanceOf($customer, CustomerInterface::class);
63+
64+
$workflow = $this->workflowRegistry->get($customer, MailchimpWorkflow::NAME);
65+
if (!$workflow->can($customer, MailchimpWorkflow::TRANSITION_PROCESS)) {
66+
// this means that the state was changed another place
67+
return;
68+
}
69+
70+
$workflow->apply($customer, MailchimpWorkflow::TRANSITION_PROCESS);
71+
72+
$manager = $this->managerRegistry->getManagerForClass(get_class($customer));
73+
if (null === $manager) {
74+
throw new UnrecoverableMessageHandlingException(sprintf(
75+
'No object manager available for class %s', get_class($customer)
76+
));
77+
}
78+
$manager->flush();
79+
80+
try {
81+
$audience = $this->audienceProvider->getAudienceFromCustomerOrders($customer);
82+
if (null === $audience) {
83+
$audience = $this->audienceProvider->getAudienceFromContext();
84+
}
85+
if (null === $audience) {
86+
// todo maybe this should fire a warning somewhere
87+
return;
88+
}
89+
90+
$this->client->updateMember($audience, $customer);
91+
92+
if (!$workflow->can($customer, MailchimpWorkflow::TRANSITION_PUSH)) {
93+
throw new UnrecoverableMessageHandlingException(sprintf(
94+
'Could not apply transition "push" on customer with id "%s". Mailchimp state: "%s"',
95+
$customer->getId(), $customer->getMailchimpState()
96+
));
97+
}
98+
99+
$workflow->apply($customer, MailchimpWorkflow::TRANSITION_PUSH);
100+
} catch (\Throwable $e) {
101+
$this->logger->error(self::buildErrorMessage($e));
102+
$customer->setMailchimpError(self::buildErrorMessage($e));
103+
$workflow->apply($customer, MailchimpWorkflow::TRANSITION_FAIL);
104+
}
105+
}
106+
107+
private static function buildErrorMessage(\Throwable $e): string
108+
{
109+
$error = $e->getMessage() . "\n\n";
110+
if ($e instanceof ClientException) {
111+
$error .= 'Uri: ' . $e->getUri() . "\n\n";
112+
$error .= 'Status code: ' . $e->getStatusCode() . "\n\n";
113+
$error .= "Options:\n" . print_r($e->getOptions(), true) . "\n\n";
114+
}
115+
116+
$error .= $e->getTraceAsString();
117+
118+
return $error;
119+
}
120+
}

src/Resources/config/services/message.xml

+12
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,18 @@
33
<container xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://symfony.com/schema/dic/services"
44
xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
55
<services>
6+
<service id="setono_sylius_mailchimp.message.handler.push_customer"
7+
class="Setono\SyliusMailchimpPlugin\Message\Handler\PushCustomerHandler">
8+
<argument type="service" id="sylius.repository.customer"/>
9+
<argument type="service" id="setono_sylius_mailchimp.provider.audience"/>
10+
<argument type="service" id="setono_sylius_mailchimp.client"/>
11+
<argument type="service" id="workflow.registry"/>
12+
<argument type="service" id="logger"/>
13+
<argument type="service" id="doctrine"/>
14+
15+
<tag name="messenger.message_handler"/>
16+
</service>
17+
618
<service id="setono_sylius_mailchimp.message.handler.push_customers"
719
class="Setono\SyliusMailchimpPlugin\Message\Handler\PushCustomersHandler">
820
<argument type="service" id="setono_doctrine_orm_batcher.factory.batcher"/>

src/Workflow/MailchimpWorkflow.php

+29
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace Setono\SyliusMailchimpPlugin\Workflow;
6+
7+
/**
8+
* This class has constants for the 'mailchimp' workflow
9+
*/
10+
final class MailchimpWorkflow
11+
{
12+
public const NAME = 'mailchimp';
13+
14+
public const TRANSITION_PROCESS = 'process';
15+
16+
public const TRANSITION_PUSH = 'push';
17+
18+
public const TRANSITION_FAIL = 'fail';
19+
20+
public const TRANSITION_FAIL_TERMINALLY = 'fail_terminally';
21+
22+
public const TRANSITION_RETRY = 'retry';
23+
24+
public const TRANSITION_UPDATE = 'update';
25+
26+
private function __construct()
27+
{
28+
}
29+
}

0 commit comments

Comments
 (0)