| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136 |
- <?php
- declare(strict_types = 1);
- namespace Avolver\CompanyEventsKitchen\Command;
- use Avolver\CompanyEventsKitchen\Application;
- use Avolver\CompanyEventsKitchen\Event\CompanyEvent;
- use Avolver\CompanyEventsKitchen\Repository\EventsRepository;
- use Avolver\CompanyEventsKitchen\Transformer\MonthEventsReportTransformer;
- use MongoDB\BSON\ObjectId;
- use Gregwar\GnuPlot\GnuPlot;
- use Symfony\Component\Console\Command\Command;
- use Symfony\Component\Console\Helper\Table;
- use Symfony\Component\Console\Input\InputInterface;
- use Symfony\Component\Console\Input\InputOption;
- use Symfony\Component\Console\Output\OutputInterface;
- /**
- * Команда для получения отчёта по событиям для конкретной компании
- *
- * @method Application getApplication
- *
- * @package Avolver\CompanyEventsKitchen\Command
- */
- class EventsReportCommand extends Command
- {
- private const FORMAT_TABLE = 'table';
- private const FORMAT_GRAPH = 'graph';
- /**
- * {@inheritdoc}
- */
- protected function configure(): void
- {
- $formats = implode(', ', [self::FORMAT_TABLE, self::FORMAT_GRAPH]);
- $this
- ->setName('events-report')
- ->setDescription('Создание случайных событий для каждой компании')
- ->addOption('company-id', null, InputOption::VALUE_REQUIRED, 'ID компании')
- ->addOption('month', null, InputOption::VALUE_OPTIONAL, 'Месяц')
- ->addOption('year', null, InputOption::VALUE_REQUIRED, 'Год')
- ->addOption('format', null, InputOption::VALUE_OPTIONAL, 'Тип вывода: ' . $formats, self::FORMAT_TABLE);
- }
- /**
- * {@inheritdoc}
- */
- protected function execute(InputInterface $input, OutputInterface $output)
- {
- $eventsRepo = new EventsRepository(
- $this->getApplication()->getClickhouseClient()
- );
- if (!$input->getOption('company-id')) {
- throw new \InvalidArgumentException('Не указан идентификатор компании');
- }
- $today = new \DateTime();
- $month = $input->getOption('month') ?: (int) $today->format('m');
- $year = $input->getOption('year') ?: (int) $today->format('Y');
- $result = $eventsRepo->findEventsByCompanyId(
- new ObjectId($input->getOption('company-id')),
- $month,
- $year
- );
- $result = MonthEventsReportTransformer::transform($result);
- switch ($input->getOption('format')) {
- case self::FORMAT_TABLE:
- $this->renderTable($output, $result);
- break;
- case self::FORMAT_GRAPH:
- $this->renderGraph($result);
- break;
- default:
- throw new \InvalidArgumentException('Некорректный формат вывода');
- }
- }
- /**
- * Вывод таблицы с событиями
- *
- * @param OutputInterface $output
- * @param array $result
- */
- private function renderTable(OutputInterface $output, array $result): void
- {
- $eventTypes = CompanyEvent::keys();
- $rows = [];
- foreach ($result as $date => $counts) {
- $row = [$date];
- foreach ($eventTypes as $eventType) {
- $row[] = $counts[$eventType] ?? '0';
- }
- $rows[] = $row;
- }
- $table = new Table($output);
- $table
- ->setHeaders(array_merge(['Дата'], $eventTypes))
- ->setRows($rows);
- $table->render();
- }
- /**
- * Сохранение графика
- *
- * @param array $result
- */
- public function renderGraph(array $result)
- {
- $eventTypes = CompanyEvent::keys();
- $plot = (new GnuPlot())
- ->setXTimeFormat('%Y-%m-%d')
- ->setXLabel('Дата')
- ->setYLabel('Количество')
- ->setWidth(640);
- foreach ($eventTypes as $eventIndex => $eventType) {
- $plot->setTitle($eventIndex, $eventType);
- }
- foreach ($result as $date => $counts) {
- foreach ($eventTypes as $eventIndex => $eventType) {
- $plot->push($date, $counts[$eventType] ?? '0', $eventIndex);
- }
- }
- echo $plot->get();
- }
- }
|