diff --git a/src/Dto/Search/Query/Filter/RelativeDateRangeFilter.php b/src/Dto/Search/Query/Filter/RelativeDateRangeFilter.php index 7723525..c1ef7d8 100644 --- a/src/Dto/Search/Query/Filter/RelativeDateRangeFilter.php +++ b/src/Dto/Search/Query/Filter/RelativeDateRangeFilter.php @@ -10,6 +10,7 @@ class RelativeDateRangeFilter extends Filter { public function __construct( + private readonly ?\DateTime $base, private readonly ?DateInterval $from, private readonly ?DateInterval $to, ?string $key = null @@ -28,13 +29,13 @@ public function getQuery(): string private function toSolrDateRage(): string { if ($this->from === null) { - $from = "NOW/DAY"; + $from = $this->getBaseInSolrSyntax() . "/DAY"; } else { $from = $this->toSolrIntervalSyntax($this->from); } if ($this->to === null) { - $to = "NOW/DAY+1DAY-1SECOND"; + $to = $this->getBaseInSolrSyntax() . "/DAY+1DAY-1SECOND"; } else { $to = $this->toSolrIntervalSyntax($this->to); } @@ -42,9 +43,20 @@ private function toSolrDateRage(): string return '[' . $from . ' TO ' . $to . ']'; } + private function getBaseInSolrSyntax(): string + { + if ($this->base === null) { + return 'NOW'; + } + + $formatter = clone $this->base; + $formatter->setTimezone(new \DateTimeZone('UTC')); + return $formatter->format('Y-m-d\TH:i:s\Z'); + } + private function toSolrIntervalSyntax(DateInterval $value): string { - $interval = 'NOW'; + $interval = $this->getBaseInSolrSyntax(); if ($value->y > 0) { $interval = $interval . '-' . $value->y . 'YEARS'; } diff --git a/test/Dto/Search/Query/Filter/RelativeDateRangeFilterTest.php b/test/Dto/Search/Query/Filter/RelativeDateRangeFilterTest.php index e857d93..6696212 100644 --- a/test/Dto/Search/Query/Filter/RelativeDateRangeFilterTest.php +++ b/test/Dto/Search/Query/Filter/RelativeDateRangeFilterTest.php @@ -6,6 +6,7 @@ use Atoolo\Search\Dto\Search\Query\Filter\RelativeDateRangeFilter; use DateInterval; +use DateTime; use Exception; use InvalidArgumentException; use PHPUnit\Framework\Attributes\CoversClass; @@ -52,6 +53,36 @@ public static function additionProviderForFromAndToIntervals(): array ]; } + /** + * @return array + */ + public static function additionProviderWithBase(): array + { + return [ + [ + new DateTime('2021-01-01 00:00:00'), + 'P1D', + null, + 'sp_date_list:[2021-01-01T00:00:00Z-1DAYS/DAY' . + ' TO 2021-01-01T00:00:00Z/DAY+1DAY-1SECOND]' + ], + [ + new DateTime('2021-01-01 00:00:00'), + null, + 'P2M', + 'sp_date_list:[2021-01-01T00:00:00Z/DAY' . + ' TO 2021-01-01T00:00:00Z-2MONTHS/DAY]' + ], + [ + new DateTime('2021-01-01 00:00:00'), + 'P1W', + 'P2M', + 'sp_date_list:[2021-01-01T00:00:00Z-7DAYS/DAY' . + ' TO 2021-01-01T00:00:00Z-2MONTHS/DAY]' + ], + ]; + } + /** * @return array */ @@ -73,6 +104,7 @@ public function testGetQueryWithFrom( string $expected ): void { $filter = new RelativeDateRangeFilter( + null, new DateInterval($from), null, ); @@ -93,6 +125,7 @@ public function testGetQueryWithTo( string $expected ): void { $filter = new RelativeDateRangeFilter( + null, null, new DateInterval($to), ); @@ -114,6 +147,7 @@ public function testGetQueryWithFromAndTo( string $expected ): void { $filter = new RelativeDateRangeFilter( + null, new DateInterval($from), new DateInterval($to), ); @@ -125,6 +159,28 @@ public function testGetQueryWithFromAndTo( ); } + /** + * @throws Exception + */ + #[DataProvider('additionProviderWithBase')] + public function testGetQueryWithBase( + DateTime $base, + ?string $from, + ?string $to, + string $expected + ): void { + $filter = new RelativeDateRangeFilter( + $base, + $from === null ? null : new DateInterval($from), + $to === null ? null : new DateInterval($to), + ); + + $this->assertEquals( + $expected, + $filter->getQuery(), + 'unexpected query' + ); + } /** * @throws Exception @@ -134,6 +190,7 @@ public function testGetQueryWithInvalidIntervals( string $interval ): void { $filter = new RelativeDateRangeFilter( + null, null, new DateInterval($interval), );