Completed
Push — master ( f30a93...2b3d30 )
by Tim
02:07
created

CalendarController::quarterAction()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 11

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 11
rs 9.9
c 0
b 0
f 0
cc 1
nc 1
nop 2
1
<?php
2
3
/**
4
 * Calendar.
5
 */
6
declare(strict_types=1);
7
8
namespace HDNET\Calendarize\Controller;
9
10
use HDNET\Calendarize\Domain\Model\Index;
11
use HDNET\Calendarize\Register;
12
use HDNET\Calendarize\Utility\DateTimeUtility;
13
use HDNET\Calendarize\Utility\EventUtility;
14
use HDNET\Calendarize\Utility\ExtensionConfigurationUtility;
15
use HDNET\Calendarize\Utility\TranslateUtility;
16
use TYPO3\CMS\Backend\Utility\BackendUtility;
17
use TYPO3\CMS\Core\Utility\ClassNamingUtility;
18
use TYPO3\CMS\Core\Utility\GeneralUtility;
19
use TYPO3\CMS\Core\Utility\MathUtility;
20
use TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface;
21
use TYPO3\CMS\Extbase\DomainObject\DomainObjectInterface;
22
use TYPO3\CMS\Extbase\Object\ObjectManager;
23
use TYPO3\CMS\Extbase\Persistence\QueryInterface;
24
use TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter;
25
use TYPO3\CMS\Extbase\SignalSlot\Dispatcher;
26
27
/**
28
 * Calendar.
29
 */
30
class CalendarController extends AbstractController
31
{
32
    /**
33
     * Init all actions.
34
     */
35
    public function initializeAction()
36
    {
37
        parent::initializeAction();
38
        $this->indexRepository->setIndexTypes(GeneralUtility::trimExplode(',', $this->settings['configuration'], true));
39
        $additionalSlotArguments = [
40
            'contentRecord' => $this->configurationManager->getContentObject()->data,
41
            'settings' => $this->settings,
42
        ];
43
        $this->indexRepository->setAdditionalSlotArguments($additionalSlotArguments);
44
45
        if (isset($this->settings['sorting'])) {
46
            if (isset($this->settings['sortBy'])) {
47
                $this->indexRepository->setDefaultSortingDirection($this->settings['sorting'], $this->settings['sortBy']);
48
            } else {
49
                $this->indexRepository->setDefaultSortingDirection($this->settings['sorting']);
50
            }
51
        }
52
53
        if (isset($this->arguments['startDate'])) {
54
            $this->arguments['startDate']->getPropertyMappingConfiguration()
55
                ->setTypeConverterOption(
56
                    DateTimeConverter::class,
57
                    DateTimeConverter::CONFIGURATION_DATE_FORMAT,
58
                    $this->settings['dateFormat']
59
                );
60
        }
61
        if (isset($this->arguments['endDate'])) {
62
            $this->arguments['endDate']->getPropertyMappingConfiguration()
63
                ->setTypeConverterOption(
64
                    DateTimeConverter::class,
65
                    DateTimeConverter::CONFIGURATION_DATE_FORMAT,
66
                    $this->settings['dateFormat']
67
                );
68
        }
69
        if ($this->request->hasArgument('event') && 'detailAction' === $this->actionMethodName) {
70
            // default configuration
71
            $configurationName = $this->settings['configuration'];
72
            // configuration overwritten by argument?
73
            if ($this->request->hasArgument('extensionConfiguration')) {
74
                $configurationName = $this->request->getArgument('extensionConfiguration');
75
            }
76
            // get the configuration
77
            $configuration = ExtensionConfigurationUtility::get($configurationName);
78
79
            // get Event by Configuration and Uid
80
            $event = EventUtility::getOriginalRecordByConfiguration($configuration, (int) $this->request->getArgument('event'));
81
            $index = $this->indexRepository->findByEventTraversing($event, true, false, 1)->getFirst();
82
83
            // if there is a valid index in the event
84
            if ($index) {
85
                $this->redirect('detail', null, null, ['index' => $index]);
86
            }
87
        }
88
    }
89
90
    /**
91
     * Latest action.
92
     *
93
     * @param \HDNET\Calendarize\Domain\Model\Index $index
94
     * @param \DateTime                             $startDate
95
     * @param \DateTime                             $endDate
96
     * @param array                                 $customSearch *
97
     * @param int                                   $year
98
     * @param int                                   $month
99
     * @param int                                   $week
100
     *
101
     * @ignorevalidation $startDate
102
     * @ignorevalidation $endDate
103
     * @ignorevalidation $customSearch
104
     *
105
     * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
106
     */
107
    public function latestAction(
108
        Index $index = null,
109
        \DateTime $startDate = null,
110
        \DateTime $endDate = null,
111
        array $customSearch = [],
112
        $year = null,
113
        $month = null,
114
        $week = null
115
    ) {
116
        $this->checkStaticTemplateIsIncluded();
117
        if (($index instanceof Index) && \in_array('detail', $this->getAllowedActions(), true)) {
118
            $this->forward('detail');
119
        }
120
121
        $search = $this->determineSearch($startDate, $endDate, $customSearch, $year, $month, null, $week);
122
123
        $this->slotExtendedAssignMultiple([
124
            'indices' => $search['indices'],
125
            'searchMode' => $search['searchMode'],
126
            'searchParameter' => [
127
                'startDate' => $startDate,
128
                'endDate' => $endDate,
129
                'customSearch' => $customSearch,
130
                'year' => $year,
131
                'month' => $month,
132
                'week' => $week,
133
            ],
134
        ], __CLASS__, __FUNCTION__);
135
    }
136
137
    /**
138
     * Result action.
139
     *
140
     * @param \HDNET\Calendarize\Domain\Model\Index $index
141
     * @param \DateTime                             $startDate
142
     * @param \DateTime                             $endDate
143
     * @param array                                 $customSearch
144
     * @param int                                   $year
145
     * @param int                                   $month
146
     * @param int                                   $week
147
     *
148
     * @ignorevalidation $startDate
149
     * @ignorevalidation $endDate
150
     * @ignorevalidation $customSearch
151
     *
152
     * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
153
     */
154
    public function resultAction(
155
        Index $index = null,
156
        \DateTime $startDate = null,
157
        \DateTime $endDate = null,
158
        array $customSearch = [],
159
        $year = null,
160
        $month = null,
161
        $week = null
162
    ) {
163
        $this->checkStaticTemplateIsIncluded();
164
        if (($index instanceof Index) && \in_array('detail', $this->getAllowedActions(), true)) {
165
            $this->forward('detail');
166
        }
167
168
        $search = $this->determineSearch($startDate, $endDate, $customSearch, $year, $month, null, $week);
169
170
        $this->slotExtendedAssignMultiple([
171
            'indices' => $search['indices'],
172
            'searchMode' => $search['searchMode'],
173
            'searchParameter' => [
174
                'startDate' => $startDate,
175
                'endDate' => $endDate,
176
                'customSearch' => $customSearch,
177
                'year' => $year,
178
                'month' => $month,
179
                'week' => $week,
180
            ],
181
        ], __CLASS__, __FUNCTION__);
182
    }
183
184
    /**
185
     * List action.
186
     *
187
     * @param \HDNET\Calendarize\Domain\Model\Index $index
188
     * @param \DateTime                             $startDate
189
     * @param \DateTime                             $endDate
190
     * @param array                                 $customSearch *
191
     * @param int                                   $year
192
     * @param int                                   $month
193
     * @param int                                   $day
194
     * @param int                                   $week
195
     *
196
     * @ignorevalidation $startDate
197
     * @ignorevalidation $endDate
198
     * @ignorevalidation $customSearch
199
     *
200
     * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
201
     */
202
    public function listAction(
203
        Index $index = null,
204
        \DateTime $startDate = null,
205
        \DateTime $endDate = null,
206
        array $customSearch = [],
207
        $year = null,
208
        $month = null,
209
        $day = null,
210
        $week = null
211
    ) {
212
        $this->checkStaticTemplateIsIncluded();
213
        if (($index instanceof Index) && \in_array('detail', $this->getAllowedActions(), true)) {
214
            $this->forward('detail');
215
        }
216
217
        $search = $this->determineSearch($startDate, $endDate, $customSearch, $year, $month, $day, $week);
218
219
        $this->slotExtendedAssignMultiple([
220
            'indices' => $search['indices'],
221
            'searchMode' => $search['searchMode'],
222
            'searchParameter' => [
223
                'startDate' => $startDate,
224
                'endDate' => $endDate,
225
                'customSearch' => $customSearch,
226
                'year' => $year,
227
                'month' => $month,
228
                'day' => $day,
229
                'week' => $week,
230
            ],
231
        ], __CLASS__, __FUNCTION__);
232
    }
233
234
    /**
235
     * Shortcut.
236
     */
237
    public function shortcutAction()
238
    {
239
        list($table, $uid) = \explode(':', $GLOBALS['TSFE']->currentRecord);
240
        $register = Register::getRegister();
241
242
        $event = null;
243
        foreach ($register as $key => $value) {
244
            if ($value['tableName'] === $table) {
245
                $repositoryName = ClassNamingUtility::translateModelNameToRepositoryName($value['modelName']);
246
                if (\class_exists($repositoryName)) {
247
                    $objectManager = new ObjectManager();
248
                    $repository = $objectManager->get($repositoryName);
249
                    $event = $repository->findByUid($uid);
250
                }
251
            }
252
        }
253
254
        if (!($event instanceof DomainObjectInterface)) {
255
            return 'Invalid object';
256
        }
257
258
        $fetchEvent = $this->indexRepository->findByEventTraversing($event, true, false, 1);
259
        if (\count($fetchEvent) <= 0) {
260
            $fetchEvent = $this->indexRepository->findByEventTraversing($event, false, true, 1, QueryInterface::ORDER_DESCENDING);
261
        }
262
263
        $this->view->assignMultiple([
264
            'indices' => $fetchEvent,
265
        ]);
266
    }
267
268
    /**
269
     * Past action.
270
     *
271
     * @param int    $limit
272
     * @param string $sort
273
     *
274
     * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
275
     */
276
    public function pastAction(
277
        $limit = 100,
0 ignored issues
show
Unused Code introduced by
The parameter $limit is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
278
        $sort = 'ASC'
0 ignored issues
show
Unused Code introduced by
The parameter $sort is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
279
    ) {
280
        $limit = (int) ($this->settings['limit']);
281
        $sort = $this->settings['sorting'];
282
        $this->checkStaticTemplateIsIncluded();
283
        $this->slotExtendedAssignMultiple([
284
           'indices' => $this->indexRepository->findByPast($limit, $sort),
285
        ], __CLASS__, __FUNCTION__);
286
    }
287
288
    /**
289
     * Year action.
290
     *
291
     * @param int $year
292
     */
293
    public function yearAction($year = null)
294
    {
295
        $date = DateTimeUtility::normalizeDateTime(1, 1, $year);
296
297
        $this->slotExtendedAssignMultiple([
298
            'indices' => $this->indexRepository->findYear((int) $date->format('Y')),
299
            'date' => $date,
300
        ], __CLASS__, __FUNCTION__);
301
    }
302
303
    /**
304
     * Quarter action.
305
     *
306
     * @param int $year
307
     * @param int $quarter 1-4
308
     */
309
    public function quarterAction(int $year = null, int $quarter = null)
310
    {
311
        $quarter = DateTimeUtility::normalizeQuarter($quarter);
312
        $date = DateTimeUtility::normalizeDateTime(1, 1 + (($quarter - 1) * 3), $year);
313
314
        $this->slotExtendedAssignMultiple([
315
            'indices' => $this->indexRepository->findQuarter((int) $date->format('Y'), $quarter),
316
            'date' => $date,
317
            'quarter' => $quarter,
318
        ], __CLASS__, __FUNCTION__);
319
    }
320
321
    /**
322
     * Month action.
323
     *
324
     * @param int $year
325
     * @param int $month
326
     * @param int $day
327
     */
328
    public function monthAction($year = null, $month = null, $day = null)
329
    {
330
        $date = DateTimeUtility::normalizeDateTime($day, $month, $year);
331
332
        $this->slotExtendedAssignMultiple([
333
            'date' => $date,
334
            'indices' => $this->indexRepository->findMonth((int) $date->format('Y'), (int) $date->format('n')),
335
        ], __CLASS__, __FUNCTION__);
336
    }
337
338
    /**
339
     * Week action.
340
     *
341
     * @param int $year
342
     * @param int $week
343
     */
344
    public function weekAction($year = null, $week = null)
345
    {
346
        $now = DateTimeUtility::getNow();
347
        if (null === $year) {
348
            $year = $now->format('o'); // 'o' instead of 'Y': http://php.net/manual/en/function.date.php#106974
349
        }
350
        if (null === $week) {
351
            $week = $now->format('W');
352
        }
353
        $weekStart = (int) $this->settings['weekStart'];
354
        $firstDay = DateTimeUtility::convertWeekYear2DayMonthYear((int) $week, $year, $weekStart);
355
        $timezone = DateTimeUtility::getTimeZone();
356
        $firstDay->setTimezone($timezone);
357
        $firstDay->setTime(0, 0, 0);
358
359
        $weekConfiguration = [
360
            '+0 day' => 2,
361
            '+1 days' => 2,
362
            '+2 days' => 2,
363
            '+3 days' => 2,
364
            '+4 days' => 2,
365
            '+5 days' => 1,
366
            '+6 days' => 1,
367
        ];
368
369
        $this->slotExtendedAssignMultiple([
370
            'firstDay' => $firstDay,
371
            'indices' => $this->indexRepository->findWeek($year, $week, $this->settings['weekStart']),
372
            'weekConfiguration' => $weekConfiguration,
373
        ], __CLASS__, __FUNCTION__);
374
    }
375
376
    /**
377
     * Day action.
378
     *
379
     * @param int $year
380
     * @param int $month
381
     * @param int $day
382
     */
383
    public function dayAction($year = null, $month = null, $day = null)
384
    {
385
        $date = DateTimeUtility::normalizeDateTime($day, $month, $year);
386
        $date->modify('+12 hours');
387
388
        $previous = clone $date;
389
        $previous->modify('-1 day');
390
391
        $next = clone $date;
392
        $next->modify('+1 day');
393
394
        $this->slotExtendedAssignMultiple([
395
            'indices' => $this->indexRepository->findDay((int) $date->format('Y'), (int) $date->format('n'), (int) $date->format('j')),
396
            'today' => $date,
397
            'previous' => $previous,
398
            'next' => $next,
399
        ], __CLASS__, __FUNCTION__);
400
    }
401
402
    /**
403
     * Detail action.
404
     *
405
     * @param \HDNET\Calendarize\Domain\Model\Index $index
406
     *
407
     * @return string
408
     */
409
    public function detailAction(Index $index = null)
410
    {
411
        if (null === $index) {
412
            // handle fallback for "strange language settings"
413
            if ($this->request->hasArgument('index')) {
414
                $indexId = (int) $this->request->getArgument('index');
415
                if ($indexId > 0) {
416
                    $index = $this->indexRepository->findByUid($indexId);
417
                }
418
            }
419
420
            if (null === $index) {
421
                if (!MathUtility::canBeInterpretedAsInteger($this->settings['listPid'])) {
422
                    return (string) TranslateUtility::get('noEventDetailView');
423
                }
424
                $this->slottedRedirect(__CLASS__, __FUNCTION__ . 'noEvent');
425
            }
426
        }
427
428
        $this->slotExtendedAssignMultiple([
429
            'index' => $index,
430
            'domain' => GeneralUtility::getIndpEnv('TYPO3_HOST_ONLY'),
431
        ], __CLASS__, __FUNCTION__);
432
433
        return $this->view->render();
434
    }
435
436
    /**
437
     * Render the search view.
438
     *
439
     * @param \DateTime $startDate
440
     * @param \DateTime $endDate
441
     * @param array     $customSearch
442
     *
443
     * @ignorevalidation $startDate
444
     * @ignorevalidation $endDate
445
     * @ignorevalidation $customSearch
446
     */
447
    public function searchAction(\DateTime $startDate = null, \DateTime $endDate = null, array $customSearch = [])
448
    {
449
        $baseDate = DateTimeUtility::getNow();
450
        if (!($startDate instanceof \DateTimeInterface)) {
451
            $startDate = clone $baseDate;
452
        }
453
        if (!($endDate instanceof \DateTimeInterface)) {
454
            $endDate = clone $startDate;
455
            $modify = \is_string($this->settings['searchEndModifier']) ? $this->settings['searchEndModifier'] : '+30 days';
456
            $endDate->modify($modify);
457
        }
458
459
        $this->slotExtendedAssignMultiple([
460
            'startDate' => $startDate,
461
            'endDate' => $endDate,
462
            'customSearch' => $customSearch,
463
            'configurations' => $this->getCurrentConfigurations(),
464
        ], __CLASS__, __FUNCTION__);
465
    }
466
467
    /**
468
     * Render single items.
469
     */
470
    public function singleAction()
471
    {
472
        $indicies = [];
473
474
        // prepare selection
475
        $selections = [];
476
        $configurations = $this->getCurrentConfigurations();
477
        foreach (GeneralUtility::trimExplode(',', $this->settings['singleItems']) as $item) {
478
            list($table, $uid) = BackendUtility::splitTable_Uid($item);
479
            foreach ($configurations as $configuration) {
480
                if ($configuration['tableName'] === $table) {
481
                    $selections[] = [
482
                        'configuration' => $configuration,
483
                        'uid' => $uid,
484
                    ];
485
                    break;
486
                }
487
            }
488
        }
489
490
        // fetch index
491
        foreach ($selections as $selection) {
492
            $this->indexRepository->setIndexTypes([$selection['configuration']['uniqueRegisterKey']]);
493
            $dummyIndex = new Index();
494
            $dummyIndex->setForeignTable($selection['configuration']['tableName']);
495
            $dummyIndex->setForeignUid($selection['uid']);
496
497
            $result = $this->indexRepository->findByTraversing($dummyIndex);
498
            $index = $result->getQuery()->setLimit(1)->execute()->getFirst();
499
            if (\is_object($index)) {
500
                $indicies[] = $index;
501
            }
502
        }
503
504
        $this->slotExtendedAssignMultiple([
505
            'indicies' => $indicies,
506
            'configurations' => $configurations,
507
        ], __CLASS__, __FUNCTION__);
508
    }
509
510
    /**
511
     * Build the search structure.
512
     *
513
     * @param \DateTime|null $startDate
514
     * @param \DateTime|null $endDate
515
     * @param array          $customSearch
516
     * @param int            $year
517
     * @param int            $month
518
     * @param int            $day
519
     * @param int            $week
520
     *
521
     * @return array
522
     */
523
    protected function determineSearch(
524
        \DateTime $startDate = null,
525
        \DateTime $endDate = null,
526
        array $customSearch = [],
527
        $year = null,
528
        $month = null,
529
        $day = null,
530
        $week = null
531
    ) {
532
        $searchMode = false;
533
        if ($startDate || $endDate || !empty($customSearch)) {
534
            $searchMode = true;
535
            $limit = isset($this->settings['limit']) ? (int) $this->settings['limit'] : 0;
536
            $indices = $this->indexRepository->findBySearch($startDate, $endDate, $customSearch, $limit);
537
        } elseif (MathUtility::canBeInterpretedAsInteger($year) && MathUtility::canBeInterpretedAsInteger($month) && MathUtility::canBeInterpretedAsInteger($day)) {
538
            $indices = $this->indexRepository->findDay((int) $year, (int) $month, (int) $day);
539
        } elseif (MathUtility::canBeInterpretedAsInteger($year) && MathUtility::canBeInterpretedAsInteger($month)) {
540
            $indices = $this->indexRepository->findMonth((int) $year, (int) $month);
541
        } elseif (MathUtility::canBeInterpretedAsInteger($year) && MathUtility::canBeInterpretedAsInteger($week)) {
542
            $indices = $this->indexRepository->findWeek($year, $week, $this->settings['weekStart']);
543
        } elseif (MathUtility::canBeInterpretedAsInteger($year)) {
544
            $indices = $this->indexRepository->findYear((int) $year);
545
        } else {
546
            $overrideStartDate = (int) $this->settings['overrideStartdate'];
547
            $overrideEndDate = (int) $this->settings['overrideEnddate'];
548
            $indices = $this->indexRepository->findList(
549
                (int) $this->settings['limit'],
550
                $this->settings['listStartTime'],
551
                (int) $this->settings['listStartTimeOffsetHours'],
552
                $overrideStartDate,
553
                $overrideEndDate
554
            );
555
        }
556
557
        // use this variable in your extension to add more custom variables
558
        $variables = [
559
            'extended' => [
560
                'indices' => $indices,
561
                'searchMode' => $searchMode,
562
                'parameters' => [
563
                    'startDate' => $startDate,
564
                    'endDate' => $endDate,
565
                    'customSearch' => $customSearch,
566
                    'year' => $year,
567
                    'month' => $month,
568
                    'day' => $day,
569
                    'week' => $week,
570
                ],
571
            ],
572
        ];
573
        $variables['settings'] = $this->settings;
574
575
        $dispatcher = $this->objectManager->get(Dispatcher::class);
576
        $variables = $dispatcher->dispatch(__CLASS__, __FUNCTION__, $variables);
577
578
        return $variables['extended'];
579
    }
580
581
    /**
582
     * Get the allowed actions.
583
     *
584
     * @return array
585
     */
586
    protected function getAllowedActions(): array
587
    {
588
        $configuration = $this->configurationManager->getConfiguration(ConfigurationManagerInterface::CONFIGURATION_TYPE_FRAMEWORK);
589
        $allowedActions = [];
590
        foreach ($configuration['controllerConfiguration'] as $controllerName => $controllerActions) {
591
            $allowedActions[$controllerName] = $controllerActions['actions'];
592
        }
593
594
        return \is_array($allowedActions['Calendar']) ? $allowedActions['Calendar'] : [];
595
    }
596
597
    /**
598
     * Get the current configurations.
599
     *
600
     * @return array
601
     */
602
    protected function getCurrentConfigurations()
603
    {
604
        $configurations = GeneralUtility::trimExplode(',', $this->settings['configuration'], true);
605
        $return = [];
606
        foreach (Register::getRegister() as $key => $configuration) {
607
            if (\in_array($key, $configurations, true)) {
608
                $return[] = $configuration;
609
            }
610
        }
611
612
        return $return;
613
    }
614
615
    /**
616
     * A redirect that have a slot included.
617
     *
618
     * @param string $signalClassName name of the signal class: __CLASS__
619
     * @param string $signalName      name of the signal: __FUNCTION__
620
     * @param array  $variables       optional: if not set use the defaults
621
     */
622
    protected function slottedRedirect($signalClassName, $signalName, $variables = null)
623
    {
624
        // set default variables for the redirect
625
        if (null === $variables) {
626
            $variables['extended'] = [
627
                'actionName' => 'list',
628
                'controllerName' => null,
629
                'extensionName' => null,
630
                'arguments' => [],
631
                'pageUid' => $this->settings['listPid'],
632
                'delay' => 0,
633
                'statusCode' => 301,
634
            ];
635
            $variables['extended']['pluginHmac'] = $this->calculatePluginHmac();
636
            $variables['settings'] = $this->settings;
637
        }
638
639
        $dispatcher = $this->objectManager->get(Dispatcher::class);
640
        $variables = $dispatcher->dispatch($signalClassName, $signalName, $variables);
641
642
        $this->redirect(
643
            $variables['extended']['actionName'],
644
            $variables['extended']['controllerName'],
645
            $variables['extended']['extensionName'],
646
            $variables['extended']['arguments'],
647
            $variables['extended']['pageUid'],
648
            $variables['extended']['delay'],
649
            $variables['extended']['statusCode']
650
        );
651
    }
652
}
653