‪TYPO3CMS  10.4
DateTimeConverter.php
Go to the documentation of this file.
1 <?php
2 
3 declare(strict_types=1);
4 
5 /*
6  * This file is part of the TYPO3 CMS project.
7  *
8  * It is free software; you can redistribute it and/or modify it under
9  * the terms of the GNU General Public License, either version 2
10  * of the License, or any later version.
11  *
12  * For the full copyright and license information, please read the
13  * LICENSE.txt file that was distributed with this source code.
14  *
15  * The TYPO3 project - inspiring people to share!
16  */
17 
19 
24 
64 {
68  const ‪CONFIGURATION_DATE_FORMAT = 'dateFormat';
69 
76  const ‪DEFAULT_DATE_FORMAT = \DateTime::W3C;
77 
81  protected ‪$sourceTypes = ['string', 'integer', 'array'];
82 
86  protected ‪$targetType = \DateTime::class;
87 
91  protected ‪$priority = 10;
92 
101  public function ‪canConvertFrom($source, string ‪$targetType): bool
102  {
103  if (!is_callable([‪$targetType, 'createFromFormat'])) {
104  // todo: this check does not make sense as this converter is only called on \DateTime targets
105  return false;
106  }
107  if (is_array($source)) {
108  return true;
109  }
110  if (is_int($source)) {
111  return true;
112  }
113  return is_string($source);
114  }
115 
127  public function ‪convertFrom($source, string ‪$targetType, array $convertedChildProperties = [], ‪PropertyMappingConfigurationInterface $configuration = null): ?object
128  {
129  $dateFormat = $this->‪getDefaultDateFormat($configuration);
130  if (is_string($source)) {
131  $dateAsString = $source;
132  } elseif (is_int($source)) {
133  $dateAsString = (string)$source;
134  } else {
135  if (isset($source['date']) && is_string($source['date'])) {
136  $dateAsString = $source['date'];
137  } elseif (isset($source['date']) && is_int($source['date'])) {
138  $dateAsString = (string)$source['date'];
139  } elseif ($this->‪isDatePartKeysProvided($source)) {
140  if ($source['day'] < 1 || $source['month'] < 1 || $source['year'] < 1) {
141  return new Error('Could not convert the given date parts into a DateTime object because one or more parts were 0.', 1333032779);
142  }
143  $dateAsString = sprintf('%d-%d-%d', $source['year'], $source['month'], $source['day']);
144  } else {
145  throw new TypeConverterException('Could not convert the given source into a DateTime object because it was not an array with a valid date as a string', 1308003914);
146  }
147  if (isset($source['dateFormat']) && $source['dateFormat'] !== '') {
148  $dateFormat = $source['dateFormat'];
149  }
150  }
151  if ($dateAsString === '') {
152  return null;
153  }
154  if (ctype_digit($dateAsString) && $configuration === null && (!is_array($source) || !isset($source['dateFormat']))) {
155  // todo: type converters are never called without a property mapping configuration
156  $dateFormat = 'U';
157  }
158  if (is_array($source) && isset($source['timezone']) && (string)$source['timezone'] !== '') {
159  try {
160  $timezone = new \DateTimeZone($source['timezone']);
161  } catch (\Exception $e) {
162  throw new TypeConverterException('The specified timezone "' . $source['timezone'] . '" is invalid.', 1308240974);
163  }
164  $date = $targetType::createFromFormat($dateFormat, $dateAsString, $timezone);
165  } else {
166  $date = $targetType::createFromFormat($dateFormat, $dateAsString);
167  }
168  if ($date === false) {
169  return new \TYPO3\CMS\Extbase\Validation\Error('The date "%s" was not recognized (for format "%s").', 1307719788, [$dateAsString, $dateFormat]);
170  }
171  if (is_array($source)) {
172  $date = $this->‪overrideTimeIfSpecified($date, $source);
173  }
174  return $date;
175  }
176 
183  protected function ‪isDatePartKeysProvided(array $source): bool
184  {
185  return isset($source['day']) && ctype_digit($source['day'])
186  && isset($source['month']) && ctype_digit($source['month'])
187  && isset($source['year']) && ctype_digit($source['year']);
188  }
189 
198  protected function ‪getDefaultDateFormat(PropertyMappingConfigurationInterface $configuration = null): string
199  {
200  if ($configuration === null) {
201  // todo: type converters are never called without a property mapping configuration
203  }
204  $dateFormat = $configuration->getConfigurationValue(DateTimeConverter::class, self::CONFIGURATION_DATE_FORMAT);
205  if ($dateFormat === null) {
207  }
208  if ($dateFormat !== null && !is_string($dateFormat)) {
209  throw new InvalidPropertyMappingConfigurationException('CONFIGURATION_DATE_FORMAT must be of type string, "' . (is_object($dateFormat) ? get_class($dateFormat) : gettype($dateFormat)) . '" given', 1307719569);
210  }
211  return $dateFormat;
212  }
213 
221  protected function ‪overrideTimeIfSpecified(\DateTime $date, array $source): \DateTime
222  {
223  if (!isset($source['hour']) && !isset($source['minute']) && !isset($source['second'])) {
224  return $date;
225  }
226  $hour = isset($source['hour']) ? (int)$source['hour'] : 0;
227  $minute = isset($source['minute']) ? (int)$source['minute'] : 0;
228  $second = isset($source['second']) ? (int)$source['second'] : 0;
229  return $date->setTime($hour, $minute, $second);
230  }
231 }
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\DEFAULT_DATE_FORMAT
‪const DEFAULT_DATE_FORMAT
Definition: DateTimeConverter.php:76
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\getDefaultDateFormat
‪string getDefaultDateFormat(PropertyMappingConfigurationInterface $configuration=null)
Definition: DateTimeConverter.php:195
‪TYPO3\CMS\Extbase\Property\Exception\TypeConverterException
Definition: TypeConverterException.php:26
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\overrideTimeIfSpecified
‪DateTime overrideTimeIfSpecified(\DateTime $date, array $source)
Definition: DateTimeConverter.php:218
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\canConvertFrom
‪bool canConvertFrom($source, string $targetType)
Definition: DateTimeConverter.php:98
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter
Definition: DateTimeConverter.php:64
‪TYPO3\CMS\Extbase\Property\PropertyMappingConfigurationInterface
Definition: PropertyMappingConfigurationInterface.php:22
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\CONFIGURATION_DATE_FORMAT
‪const CONFIGURATION_DATE_FORMAT
Definition: DateTimeConverter.php:68
‪TYPO3\CMS\Extbase\Error\Error
Definition: Error.php:25
‪TYPO3\CMS\Extbase\Property\TypeConverter
Definition: AbstractFileCollectionConverter.php:18
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\convertFrom
‪DateTime TYPO3 CMS Extbase Error Error null convertFrom($source, string $targetType, array $convertedChildProperties=[], PropertyMappingConfigurationInterface $configuration=null)
Definition: DateTimeConverter.php:124
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\$priority
‪int $priority
Definition: DateTimeConverter.php:88
‪TYPO3\CMS\Extbase\Property\Exception
Definition: Exception.php:26
‪TYPO3\CMS\Extbase\Property\TypeConverter\AbstractTypeConverter
Definition: AbstractTypeConverter.php:34
‪TYPO3\CMS\Extbase\Property\Exception\InvalidPropertyMappingConfigurationException
Definition: InvalidPropertyMappingConfigurationException.php:26
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\$sourceTypes
‪string[] $sourceTypes
Definition: DateTimeConverter.php:80
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\isDatePartKeysProvided
‪bool isDatePartKeysProvided(array $source)
Definition: DateTimeConverter.php:180
‪TYPO3\CMS\Extbase\Property\TypeConverter\DateTimeConverter\$targetType
‪string $targetType
Definition: DateTimeConverter.php:84