Count past presentations
This commit is contained in:
parent
820f8d4055
commit
92c413bc80
6 changed files with 143 additions and 6 deletions
|
@ -1,2 +1,3 @@
|
|||
services:
|
||||
Drupal\opd_presentations\PresentationCounter: {}
|
||||
Drupal\opd_presentations\PresentationCounter:
|
||||
autowire: true
|
||||
|
|
|
@ -9,7 +9,11 @@ use Webmozart\Assert\Assert;
|
|||
/**
|
||||
* @implements \IteratorAggregate<Event>
|
||||
*/
|
||||
readonly final class Events implements \IteratorAggregate {
|
||||
readonly final class Events implements \Countable, \IteratorAggregate {
|
||||
|
||||
public function count(): int {
|
||||
return count($this->events);
|
||||
}
|
||||
|
||||
public function filter(\Closure $callback): self {
|
||||
return new self(array_filter(
|
||||
|
|
|
@ -11,9 +11,8 @@ final class Presentation extends Node implements NodeInterface {
|
|||
|
||||
public const NODE_TYPE = 'presentation';
|
||||
|
||||
public function getPastEvents(): Events {
|
||||
return Events::fromEvents($this->get('field_events')->referencedEntities())
|
||||
->getPast();
|
||||
public function getEvents(): Events {
|
||||
return Events::fromEvents($this->get('field_events')->referencedEntities());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
37
modules/opd_presentations/src/PresentationCounter.php
Normal file
37
modules/opd_presentations/src/PresentationCounter.php
Normal file
|
@ -0,0 +1,37 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Drupal\opd_presentations;
|
||||
|
||||
use Drupal\Core\Entity\EntityTypeManagerInterface;
|
||||
use Drupal\node\NodeInterface;
|
||||
|
||||
final class PresentationCounter {
|
||||
|
||||
private array $presentations;
|
||||
|
||||
public function __construct(private EntityTypeManagerInterface $entityTypeManager) {
|
||||
}
|
||||
|
||||
public function getPastCount(): int {
|
||||
$nodeStorage = $this->entityTypeManager->getStorage('node');
|
||||
|
||||
$query = $nodeStorage->getQuery();
|
||||
$query->condition('status', NodeInterface::PUBLISHED);
|
||||
$query->condition('type', Presentation::NODE_TYPE);
|
||||
$query->accessCheck();
|
||||
|
||||
$nodeIds = $query->execute();
|
||||
|
||||
$presentations = $nodeStorage->loadMultiple($nodeIds);
|
||||
|
||||
return array_reduce(
|
||||
array: $presentations,
|
||||
callback: fn (int $count, Presentation $presentation)
|
||||
=> $count + $presentation->getEvents()->getPast()->count(),
|
||||
initial: 0,
|
||||
);
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,95 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Drupal\Tests\opd_presentations;
|
||||
|
||||
use Drupal\Tests\RandomGeneratorTrait;
|
||||
use Drupal\Tests\opd_presentations\Traits\PresentationCreationTrait;
|
||||
use Drupal\node\NodeInterface;
|
||||
use Drupal\opd_presentations\Date;
|
||||
use Drupal\opd_presentations\PresentationCounter;
|
||||
use weitzman\DrupalTestTraits\ExistingSiteBase;
|
||||
|
||||
final class PresentationCounterTest extends ExistingSiteBase {
|
||||
|
||||
use PresentationCreationTrait;
|
||||
use RandomGeneratorTrait;
|
||||
|
||||
public function test_it_counts_events(): void {
|
||||
$counter = $this->container->get(PresentationCounter::class);
|
||||
assert($counter instanceof PresentationCounter);
|
||||
|
||||
$this->createPresentation(
|
||||
events: [
|
||||
$this->createEvent(
|
||||
eventDate: Date::fromString('yesterday'),
|
||||
eventName: $this->randomString(),
|
||||
),
|
||||
],
|
||||
);
|
||||
|
||||
$this->assertGreaterThanOrEqual(
|
||||
actual: $counter->getPastCount(),
|
||||
expected: 1,
|
||||
);
|
||||
}
|
||||
|
||||
public function test_it_only_counts_published_events(): void {
|
||||
$counter = $this->container->get(PresentationCounter::class);
|
||||
assert($counter instanceof PresentationCounter);
|
||||
|
||||
$count = $counter->getPastCount();
|
||||
|
||||
$this->createPresentation(
|
||||
events: [
|
||||
$this->createEvent(
|
||||
eventDate: Date::fromString('yesterday'),
|
||||
eventName: $this->randomString(),
|
||||
),
|
||||
],
|
||||
isPublished: FALSE,
|
||||
);
|
||||
|
||||
$this->assertSame(
|
||||
actual: $counter->getPastCount(),
|
||||
expected: $count,
|
||||
);
|
||||
}
|
||||
|
||||
public function test_it_only_counts_past_events(): void {
|
||||
$counter = $this->container->get(PresentationCounter::class);
|
||||
assert($counter instanceof PresentationCounter);
|
||||
|
||||
// Get the existing presentation count (including existing nodes).
|
||||
$originalCount = $counter->getPastCount();
|
||||
|
||||
$this->assertGreaterThanOrEqual(
|
||||
actual: $originalCount,
|
||||
expected: 0,
|
||||
);
|
||||
|
||||
$this->createPresentation(
|
||||
events: [
|
||||
$this->createEvent(
|
||||
eventDate: Date::fromString('tomorrow'),
|
||||
eventName: $this->randomString(),
|
||||
),
|
||||
|
||||
$this->createEvent(
|
||||
eventDate: Date::fromString('yesterday'),
|
||||
eventName: $this->randomString(),
|
||||
),
|
||||
],
|
||||
);
|
||||
|
||||
$counter = $this->container->get(PresentationCounter::class);
|
||||
|
||||
// Ensure the count has only increased by one, even though a future and past event were created.
|
||||
$this->assertSame(
|
||||
actual: $counter->getPastCount(),
|
||||
expected: $originalCount + 1,
|
||||
);
|
||||
}
|
||||
|
||||
}
|
|
@ -19,9 +19,10 @@ trait PresentationCreationTrait {
|
|||
/**
|
||||
* @param Event[] $events
|
||||
*/
|
||||
private function createPresentation(array $events): Presentation {
|
||||
private function createPresentation(array $events, bool $isPublished = TRUE): Presentation {
|
||||
$presentation = $this->createNode([
|
||||
'field_events' => $events,
|
||||
'status' => $isPublished,
|
||||
'type' => Presentation::NODE_TYPE,
|
||||
]);
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue