Generalize VisitsDateRangeInput to VisitsListInput to add more common params

This commit is contained in:
Alejandro Celaya
2025-12-28 11:59:37 +01:00
parent a65c5c3b56
commit faed7ae60b
7 changed files with 22 additions and 20 deletions

View File

@@ -5,7 +5,7 @@ declare(strict_types=1);
namespace Shlinkio\Shlink\CLI\Command\Domain;
use Shlinkio\Shlink\CLI\Command\Visit\VisitsCommandUtils;
use Shlinkio\Shlink\CLI\Input\VisitsDateRangeInput;
use Shlinkio\Shlink\CLI\Input\VisitsListInput;
use Shlinkio\Shlink\CLI\Util\ShlinkTable;
use Shlinkio\Shlink\Core\ShortUrl\Helper\ShortUrlStringifierInterface;
use Shlinkio\Shlink\Core\Visit\Entity\Visit;
@@ -34,9 +34,9 @@ class GetDomainVisitsCommand extends Command
SymfonyStyle $io,
#[Argument('The domain which visits we want to get'), Ask('For what domain do you want to get visits?')]
string $domain,
#[MapInput] VisitsDateRangeInput $dateRangeInput,
#[MapInput] VisitsListInput $input,
): int {
$paginator = $this->visitsHelper->visitsForDomain($domain, new VisitsParams($dateRangeInput->toDateRange()));
$paginator = $this->visitsHelper->visitsForDomain($domain, new VisitsParams($input->dateRange()));
[$rows, $headers] = VisitsCommandUtils::resolveRowsAndHeaders($paginator, $this->mapExtraFields(...));
ShlinkTable::default($io)->render($headers, $rows);

View File

@@ -5,7 +5,7 @@ declare(strict_types=1);
namespace Shlinkio\Shlink\CLI\Command\ShortUrl;
use Shlinkio\Shlink\CLI\Command\Visit\VisitsCommandUtils;
use Shlinkio\Shlink\CLI\Input\VisitsDateRangeInput;
use Shlinkio\Shlink\CLI\Input\VisitsListInput;
use Shlinkio\Shlink\CLI\Util\ShlinkTable;
use Shlinkio\Shlink\Core\ShortUrl\Model\ShortUrlIdentifier;
use Shlinkio\Shlink\Core\Visit\Model\VisitsParams;
@@ -32,14 +32,14 @@ class GetShortUrlVisitsCommand extends Command
SymfonyStyle $io,
#[Argument('The short code which visits we want to get'), Ask('Which short code do you want to use?')]
string $shortCode,
#[MapInput] VisitsDateRangeInput $dateRangeInput,
#[MapInput] VisitsListInput $input,
#[Option('The domain for the short code', shortcut: 'd')]
string|null $domain = null,
): int {
$identifier = ShortUrlIdentifier::fromShortCodeAndDomain($shortCode, $domain);
$dateRange = $dateRangeInput->toDateRange();
$dateRange = $input->dateRange();
$paginator = $this->visitsHelper->visitsForShortUrl($identifier, new VisitsParams($dateRange));
[$rows, $headers] = VisitsCommandUtils::resolveRowsAndHeaders($paginator, static fn () => []);
[$rows, $headers] = VisitsCommandUtils::resolveRowsAndHeaders($paginator);
ShlinkTable::default($io)->render($headers, $rows);

View File

@@ -5,7 +5,7 @@ declare(strict_types=1);
namespace Shlinkio\Shlink\CLI\Command\Tag;
use Shlinkio\Shlink\CLI\Command\Visit\VisitsCommandUtils;
use Shlinkio\Shlink\CLI\Input\VisitsDateRangeInput;
use Shlinkio\Shlink\CLI\Input\VisitsListInput;
use Shlinkio\Shlink\CLI\Util\ShlinkTable;
use Shlinkio\Shlink\Core\Domain\Entity\Domain;
use Shlinkio\Shlink\Core\ShortUrl\Helper\ShortUrlStringifierInterface;
@@ -35,7 +35,7 @@ class GetTagVisitsCommand extends Command
public function __invoke(
SymfonyStyle $io,
#[Argument('The tag which visits we want to get'), Ask('For what tag do you want to get visits')] string $tag,
#[MapInput] VisitsDateRangeInput $dateRangeInput,
#[MapInput] VisitsListInput $input,
#[Option(
'Return visits that belong to this domain only. Use ' . Domain::DEFAULT_AUTHORITY . ' keyword for visits '
. 'in default domain',
@@ -44,7 +44,7 @@ class GetTagVisitsCommand extends Command
string|null $domain = null,
): int {
$paginator = $this->visitsHelper->visitsForTag($tag, new WithDomainVisitsParams(
dateRange: $dateRangeInput->toDateRange(),
dateRange: $input->dateRange(),
domain: $domain,
));
[$rows, $headers] = VisitsCommandUtils::resolveRowsAndHeaders($paginator, $this->mapExtraFields(...));

View File

@@ -4,7 +4,7 @@ declare(strict_types=1);
namespace Shlinkio\Shlink\CLI\Command\Visit;
use Shlinkio\Shlink\CLI\Input\VisitsDateRangeInput;
use Shlinkio\Shlink\CLI\Input\VisitsListInput;
use Shlinkio\Shlink\CLI\Util\ShlinkTable;
use Shlinkio\Shlink\Core\Domain\Entity\Domain;
use Shlinkio\Shlink\Core\ShortUrl\Helper\ShortUrlStringifierInterface;
@@ -31,7 +31,7 @@ class GetNonOrphanVisitsCommand extends Command
public function __invoke(
SymfonyStyle $io,
#[MapInput] VisitsDateRangeInput $dateRangeInput,
#[MapInput] VisitsListInput $input,
#[Option(
'Return visits that belong to this domain only. Use ' . Domain::DEFAULT_AUTHORITY . ' keyword for visits '
. 'in default domain',
@@ -40,7 +40,7 @@ class GetNonOrphanVisitsCommand extends Command
string|null $domain = null,
): int {
$paginator = $this->visitsHelper->nonOrphanVisits(new WithDomainVisitsParams(
dateRange: $dateRangeInput->toDateRange(),
dateRange: $input->dateRange(),
domain: $domain,
));
[$rows, $headers] = VisitsCommandUtils::resolveRowsAndHeaders($paginator, $this->mapExtraFields(...));

View File

@@ -4,7 +4,7 @@ declare(strict_types=1);
namespace Shlinkio\Shlink\CLI\Command\Visit;
use Shlinkio\Shlink\CLI\Input\VisitsDateRangeInput;
use Shlinkio\Shlink\CLI\Input\VisitsListInput;
use Shlinkio\Shlink\CLI\Util\ShlinkTable;
use Shlinkio\Shlink\Core\Domain\Entity\Domain;
use Shlinkio\Shlink\Core\Visit\Entity\Visit;
@@ -29,7 +29,7 @@ class GetOrphanVisitsCommand extends Command
public function __invoke(
SymfonyStyle $io,
#[MapInput] VisitsDateRangeInput $dateRangeInput,
#[MapInput] VisitsListInput $input,
#[Option(
'Return visits that belong to this domain only. Use ' . Domain::DEFAULT_AUTHORITY . ' keyword for visits '
. 'in default domain',
@@ -39,7 +39,7 @@ class GetOrphanVisitsCommand extends Command
#[Option('Return visits only with this type', shortcut: 't')] OrphanVisitType|null $type = null,
): int {
$paginator = $this->visitsHelper->orphanVisits(new OrphanVisitsParams(
dateRange: $dateRangeInput->toDateRange(),
dateRange: $input->dateRange(),
domain: $domain,
type: $type,
));

View File

@@ -16,11 +16,13 @@ class VisitsCommandUtils
{
/**
* @param Paginator<Visit> $paginator
* @param callable(Visit $visits): array<string, string> $mapExtraFields
* @param null|callable(Visit $visits): array<string, string> $mapExtraFields
*/
public static function resolveRowsAndHeaders(Paginator $paginator, callable $mapExtraFields): array
public static function resolveRowsAndHeaders(Paginator $paginator, callable|null $mapExtraFields = null): array
{
$extraKeys = [];
$mapExtraFields ??= static fn (Visit $_) => [];
$rows = array_map(function (Visit $visit) use (&$extraKeys, $mapExtraFields) {
$extraFields = $mapExtraFields($visit);
$extraKeys = array_keys($extraFields);

View File

@@ -10,7 +10,7 @@ use Symfony\Component\Console\Attribute\Option;
use function Shlinkio\Shlink\Common\buildDateRange;
use function Shlinkio\Shlink\Core\normalizeOptionalDate;
class VisitsDateRangeInput
class VisitsListInput
{
#[Option('Only return visits older than this date', shortcut: 's')]
public string|null $startDate = null;
@@ -18,7 +18,7 @@ class VisitsDateRangeInput
#[Option('Only return visits newer than this date', shortcut: 'e')]
public string|null $endDate = null;
public function toDateRange(): DateRange
public function dateRange(): DateRange
{
return buildDateRange(
startDate: normalizeOptionalDate($this->startDate),