Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
100.00% covered (success)
100.00%
10 / 10
100.00% covered (success)
100.00%
2 / 2
CRAP
100.00% covered (success)
100.00%
1 / 1
BulkMailService
100.00% covered (success)
100.00%
10 / 10
100.00% covered (success)
100.00%
2 / 2
6
100.00% covered (success)
100.00%
1 / 1
 __construct
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 sendToFilteredStores
100.00% covered (success)
100.00%
9 / 9
100.00% covered (success)
100.00%
1 / 1
5
1<?php
2
3declare(strict_types=1);
4
5namespace App\Service;
6
7use App\Entity\Store;
8use Symfony\Component\Mailer\Exception\TransportExceptionInterface;
9use Symfony\Component\Mailer\MailerInterface;
10use Symfony\Component\Mime\Email;
11
12class BulkMailService
13{
14    public function __construct(private readonly MailerInterface $mailer) {}
15
16    /**
17     * Send one email per store, filtered to those present in $recipients.
18     *
19     * @param Store[]          $stores
20     * @param array<int, mixed> $recipients  Keys are store IDs
21     * @param callable(Store): Email $emailFactory
22     */
23    public function sendToFilteredStores(array $stores, array $recipients, callable $emailFactory): MailBatchResult
24    {
25        $result = new MailBatchResult();
26
27        foreach ($stores as $store) {
28            if (!array_key_exists((int) $store->getId(), $recipients) || !$store->getUser()) {
29                continue;
30            }
31
32            try {
33                $this->mailer->send($emailFactory($store));
34                $result->addSuccess($store->getId());
35            } catch (TransportExceptionInterface $exception) {
36                $result->addFailure($exception->getMessage());
37            }
38        }
39
40        return $result;
41    }
42}