Spaces:
No application file
No application file
declare(strict_types=1); | |
namespace Mautic\CampaignBundle\Tests\Controller; | |
use Mautic\CampaignBundle\Command\SummarizeCommand; | |
use Mautic\CampaignBundle\Entity\Campaign; | |
use Mautic\CampaignBundle\Entity\Event; | |
use Mautic\CampaignBundle\Entity\LeadEventLog; | |
use Mautic\CampaignBundle\Model\CampaignModel; | |
use Mautic\CampaignBundle\Tests\Campaign\AbstractCampaignTest; | |
use Mautic\LeadBundle\Entity\Lead; | |
use PHPUnit\Framework\Assert; | |
use Symfony\Component\DomCrawler\Crawler; | |
use Symfony\Component\HttpFoundation\Request; | |
use Symfony\Component\HttpFoundation\Response; | |
class CampaignControllerFunctionalTest extends AbstractCampaignTest | |
{ | |
private const CAMPAIGN_SUMMARY_PARAM = 'campaign_use_summary'; | |
private const CAMPAIGN_RANGE_PARAM = 'campaign_by_range'; | |
/** | |
* @var CampaignModel | |
*/ | |
private $campaignModel; | |
/** | |
* @var string | |
*/ | |
private $campaignLeadsLabel; | |
protected function setUp(): void | |
{ | |
$functionForUseSummary = ['testCampaignContactCountThroughStatsWithSummary', | |
'testCampaignContactCountOnCanvasWithSummaryWithoutRange', 'testCampaignContactCountOnCanvasWithSummaryAndRange', | |
'testCampaignCountsBeforeSummarizeCommandWithSummaryWithoutRange', 'testCampaignCountsBeforeSummarizeCommandWithSummaryAndRange', | |
'testCampaignCountsAfterSummarizeCommandWithSummaryWithoutRange', 'testCampaignCountsAfterSummarizeCommandWithSummaryAndRange', | |
'testCampaignPendingCountsWithSummaryWithoutRange', 'testCampaignPendingCountsWithSummaryAndRange', ]; | |
$functionForUseRange = ['testCampaignContactCountOnCanvasWithoutSummaryWithRange', 'testCampaignContactCountOnCanvasWithSummaryAndRange', | |
'testCampaignCountsBeforeSummarizeCommandWithoutSummaryWithRange', 'testCampaignCountsBeforeSummarizeCommandWithSummaryAndRange', | |
'testCampaignCountsAfterSummarizeCommandWithoutSummaryWithRange', 'testCampaignCountsAfterSummarizeCommandWithSummaryAndRange', | |
'testCampaignPendingCountsWithoutSummaryAndRange', 'testCampaignPendingCountsWithoutSummaryWithRange', ]; | |
$this->configParams[self::CAMPAIGN_SUMMARY_PARAM] = in_array($this->getName(), $functionForUseSummary); | |
$this->configParams[self::CAMPAIGN_RANGE_PARAM] = in_array($this->getName(), $functionForUseRange); | |
parent::setUp(); | |
$this->campaignModel = static::getContainer()->get('mautic.model.factory')->getModel('campaign'); | |
$this->campaignLeadsLabel = static::getContainer()->get('translator')->trans('mautic.campaign.campaign.leads'); | |
$this->configParams['delete_campaign_event_log_in_background'] = false; | |
} | |
public function testCampaignContactCountThroughStatsWithSummary(): void | |
{ | |
$this->campaignContactCountThroughStats(); | |
} | |
public function testCampaignContactCountThroughStatsWithoutSummary(): void | |
{ | |
$this->campaignContactCountThroughStats(); | |
} | |
public function testCampaignContactCountOnCanvasWithoutSummaryAndRange(): void | |
{ | |
$this->campaignContactCountOnCanvas(); | |
} | |
public function testCampaignContactCountOnCanvasWithSummaryWithoutRange(): void | |
{ | |
$this->campaignContactCountOnCanvas(); | |
} | |
public function testCampaignContactCountOnCanvasWithoutSummaryWithRange(): void | |
{ | |
$this->campaignContactCountOnCanvas(); | |
} | |
public function testCampaignContactCountOnCanvasWithSummaryAndRange(): void | |
{ | |
$this->campaignContactCountOnCanvas(); | |
} | |
public function testCampaignCountsBeforeSummarizeCommandWithoutSummaryAndRange(): void | |
{ | |
$this->getCountAndDetails(false, false, 100, 2, 0); | |
} | |
public function testCampaignCountsBeforeSummarizeCommandWithSummaryWithoutRange(): void | |
{ | |
$this->getCountAndDetails(false, false, 0, 0, 0); | |
} | |
public function testCampaignCountsBeforeSummarizeCommandWithoutSummaryWithRange(): void | |
{ | |
$this->getCountAndDetails(false, false, 100, 2, 0); | |
} | |
public function testCampaignCountsBeforeSummarizeCommandWithSummaryAndRange(): void | |
{ | |
$this->getCountAndDetails(false, false, 0, 0, 0); | |
} | |
public function testCampaignCountsAfterSummarizeCommandWithoutSummaryAndRange(): void | |
{ | |
$this->getCountAndDetails(false, true, 100, 2, 0); | |
} | |
public function testCampaignCountsAfterSummarizeCommandWithSummaryWithoutRange(): void | |
{ | |
$this->getCountAndDetails(false, true, 100, 2, 0); | |
} | |
public function testCampaignCountsAfterSummarizeCommandWithoutSummaryWithRange(): void | |
{ | |
$this->getCountAndDetails(false, true, 100, 2, 0); | |
} | |
public function testCampaignCountsAfterSummarizeCommandWithSummaryAndRange(): void | |
{ | |
$this->getCountAndDetails(false, true, 100, 2, 0); | |
} | |
public function testCampaignPendingCountsWithoutSummaryAndRange(): void | |
{ | |
$this->getCountAndDetails(true, true, 100, 2, 1); | |
} | |
public function testCampaignPendingCountsWithSummaryWithoutRange(): void | |
{ | |
$this->getCountAndDetails(true, true, 100, 2, 1); | |
} | |
public function testCampaignPendingCountsWithoutSummaryWithRange(): void | |
{ | |
$this->getCountAndDetails(true, true, 100, 2, 1); | |
} | |
public function testCampaignPendingCountsWithSummaryAndRange(): void | |
{ | |
$this->getCountAndDetails(true, true, 100, 2, 1); | |
} | |
private function getStatTotalContacts(int $campaignId): int | |
{ | |
$from = date('Y-m-d', strtotime('-2 months')); | |
$to = date('Y-m-d', strtotime('-1 month')); | |
$stats = $this->campaignModel->getCampaignMetricsLineChartData( | |
null, | |
new \DateTime($from), | |
new \DateTime($to), | |
null, | |
['campaign_id' => $campaignId] | |
); | |
$datasets = $stats['datasets'] ?? []; | |
return $this->processTotalContactStats($datasets); | |
} | |
private function getCanvasTotalContacts(int $campaignId): int | |
{ | |
$crawler = $this->getCrawlers($campaignId); | |
$canvasJson = trim($crawler->filter('canvas')->html()); | |
$canvasData = json_decode($canvasJson, true); | |
$datasets = $canvasData['datasets'] ?? []; | |
return $this->processTotalContactStats($datasets); | |
} | |
/** | |
* @param array<string, array<int|string>> $datasets | |
*/ | |
private function processTotalContactStats(array $datasets): int | |
{ | |
$totalContacts = 0; | |
foreach ($datasets as $dataset) { | |
if ($dataset['label'] === $this->campaignLeadsLabel) { | |
$data = $dataset['data'] ?? []; | |
$totalContacts = array_sum($data); | |
break; | |
} | |
} | |
return $totalContacts; | |
} | |
private function getCrawlers(int $campaignId): Crawler | |
{ | |
$from = date('F d, Y', strtotime('-2 months')); | |
$to = date('F d, Y', strtotime('-1 month')); | |
$parameters = [ | |
'daterange' => [ | |
'date_from' => $from, | |
'date_to' => $to, | |
], | |
]; | |
return $this->client->request(Request::METHOD_POST, '/s/campaigns/view/'.$campaignId, $parameters); | |
} | |
/** | |
* @return array<string, string> | |
*/ | |
private function getActionCounts(int $campaignId): array | |
{ | |
$crawler = $this->getCrawlers($campaignId); | |
$successPercent = trim($crawler->filter('#actions-container')->filter('span')->eq(0)->html()); | |
$completed = trim($crawler->filter('#actions-container')->filter('span')->eq(1)->html()); | |
$pending = trim($crawler->filter('#actions-container')->filter('span')->eq(2)->html()); | |
return [ | |
'successPercent' => $successPercent, | |
'completed' => $completed, | |
'pending' => $pending, | |
]; | |
} | |
private function campaignContactCountThroughStats(): void | |
{ | |
$campaign = $this->saveSomeCampaignLeadEventLogs(); | |
$campaignId = $campaign->getId(); | |
$totalContacts = $this->getStatTotalContacts($campaignId); | |
Assert::assertSame(2, $totalContacts); | |
} | |
private function campaignContactCountOnCanvas(): void | |
{ | |
$campaign = $this->saveSomeCampaignLeadEventLogs(); | |
$campaignId = $campaign->getId(); | |
$totalContacts = $this->getCanvasTotalContacts($campaignId); | |
Assert::assertSame(2, $totalContacts); | |
} | |
private function getCountAndDetails(bool $emulatePendingCount, bool $runCommand, int $expectedSuccessPercent, int $expectedCompleted, int $expectedPending): void | |
{ | |
$campaign = $this->saveSomeCampaignLeadEventLogs($emulatePendingCount); | |
$campaignId = $campaign->getId(); | |
if ($runCommand) { | |
$this->testSymfonyCommand( | |
SummarizeCommand::NAME, | |
[ | |
'--env' => 'test', | |
'--max-hours' => 768, | |
] | |
); | |
} | |
$actionCounts = $this->getActionCounts($campaignId); | |
Assert::assertSame($expectedSuccessPercent.'%', $actionCounts['successPercent']); | |
Assert::assertSame($expectedCompleted, (int) $actionCounts['completed']); | |
Assert::assertSame($expectedPending, (int) $actionCounts['pending']); | |
} | |
public function testDeleteCampaign(): void | |
{ | |
$lead = $this->createLead(); | |
$campaign = $this->createCampaign(); | |
$event = $this->createEvent('Event 1', $campaign); | |
$this->createEventLog($lead, $event, $campaign); | |
$this->client->request(Request::METHOD_POST, '/s/campaigns/delete/'.$campaign->getId()); | |
$response = $this->client->getResponse(); | |
Assert::assertSame(Response::HTTP_OK, $response->getStatusCode(), $response->getContent()); | |
$eventLogs = $this->em->getRepository(LeadEventLog::class)->findAll(); | |
Assert::assertCount(0, $eventLogs); | |
} | |
private function createLead(): Lead | |
{ | |
$lead = new Lead(); | |
$lead->setFirstname('Test'); | |
$this->em->persist($lead); | |
$this->em->flush(); | |
return $lead; | |
} | |
private function createCampaign(): Campaign | |
{ | |
$campaign = new Campaign(); | |
$campaign->setName('My campaign'); | |
$this->em->persist($campaign); | |
$this->em->flush(); | |
return $campaign; | |
} | |
private function createEvent(string $name, Campaign $campaign): Event | |
{ | |
$event = new Event(); | |
$event->setName($name); | |
$event->setCampaign($campaign); | |
$event->setType('email.send'); | |
$event->setEventType('action'); | |
$this->em->persist($event); | |
$this->em->flush(); | |
return $event; | |
} | |
private function createEventLog(Lead $lead, Event $event, Campaign $campaign): LeadEventLog | |
{ | |
$leadEventLog = new LeadEventLog(); | |
$leadEventLog->setLead($lead); | |
$leadEventLog->setEvent($event); | |
$leadEventLog->setCampaign($campaign); | |
$this->em->persist($leadEventLog); | |
$this->em->flush(); | |
return $leadEventLog; | |
} | |
} | |