TYPO3CMS  8
 All Classes Namespaces Files Functions Variables Pages
DataStructureIdentifierHook.php
Go to the documentation of this file.
1 <?php
2 declare(strict_types=1);
3 namespace TYPO3\CMS\Form\Hooks;
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 
24 
35 {
36 
50  array $fieldTca,
51  string $tableName,
52  string $fieldName,
53  array $row,
54  array $identifier
55  ): array {
56  if ($tableName === 'tt_content' && $fieldName === 'pi_flexform' && $row['CType'] === 'form_formframework') {
57  $currentFlexData = [];
58  if (!is_array($row['pi_flexform']) && !empty($row['pi_flexform'])) {
59  $currentFlexData = GeneralUtility::xml2array($row['pi_flexform']);
60  }
61 
62  // Add selected form value
63  $identifier['ext-form-persistenceIdentifier'] = '';
64  if (!empty($currentFlexData['data']['sDEF']['lDEF']['settings.persistenceIdentifier']['vDEF'])) {
65  $identifier['ext-form-persistenceIdentifier'] = $currentFlexData['data']['sDEF']['lDEF']['settings.persistenceIdentifier']['vDEF'];
66  }
67 
68  // Add bool - finisher override active or not
69  $identifier['ext-form-overrideFinishers'] = false;
70  if (
71  isset($currentFlexData['data']['sDEF']['lDEF']['settings.overrideFinishers']['vDEF'])
72  && (int)$currentFlexData['data']['sDEF']['lDEF']['settings.overrideFinishers']['vDEF'] === 1
73  ) {
74  $identifier['ext-form-overrideFinishers'] = true;
75  }
76  }
77  return $identifier;
78  }
79 
90  public function parseDataStructureByIdentifierPostProcess(array $dataStructure, array $identifier): array
91  {
92  if (isset($identifier['ext-form-persistenceIdentifier'])) {
93  // Add list of existing forms to drop down if we find our key in the identifier
94  $formPersistenceManager = GeneralUtility::makeInstance(ObjectManager::class)->get(FormPersistenceManagerInterface::class);
95  foreach ($formPersistenceManager->listForms() as $form) {
96  $dataStructure['sheets']['sDEF']['ROOT']['el']['settings.persistenceIdentifier']['TCEforms']['config']['items'][] = [
97  $form['name'] . ' (' . $form['persistenceIdentifier'] . ')',
98  $form['persistenceIdentifier'],
99  ];
100  }
101 
102  // If a specific form is selected and if finisher override is active, add finisher sheets
103  if (!empty($identifier['ext-form-persistenceIdentifier'])
104  && isset($identifier['ext-form-overrideFinishers'])
105  && $identifier['ext-form-overrideFinishers'] === true
106  ) {
107  $persistenceIdentifier = $identifier['ext-form-persistenceIdentifier'];
108  $formDefinition = $formPersistenceManager->load($persistenceIdentifier);
109  $newSheets = $this->getAdditionalFinisherSheets($persistenceIdentifier, $formDefinition);
111  $dataStructure,
112  $newSheets
113  );
114  }
115  }
116  return $dataStructure;
117  }
118 
126  protected function getAdditionalFinisherSheets(string $persistenceIdentifier, array $formDefinition): array
127  {
128  if (!isset($formDefinition['finishers']) || empty($formDefinition['finishers'])) {
129  return [];
130  }
131 
132  $prototypeName = isset($formDefinition['prototypeName']) ? $formDefinition['prototypeName'] : 'standard';
133  $prototypeConfiguration = GeneralUtility::makeInstance(ObjectManager::class)
134  ->get(ConfigurationService::class)
135  ->getPrototypeConfiguration($prototypeName);
136 
137  if (!isset($prototypeConfiguration['finishersDefinition']) || empty($prototypeConfiguration['finishersDefinition'])) {
138  return [];
139  }
140 
141  $formIdentifier = $formDefinition['identifier'];
142  $finishersDefinition = $prototypeConfiguration['finishersDefinition'];
143 
144  $sheets = ['sheets' => []];
145  foreach ($formDefinition['finishers'] as $finisherValue) {
146  $finisherIdentifier = $finisherValue['identifier'];
147  if (!isset($finishersDefinition[$finisherIdentifier]['FormEngine']['elements'])) {
148  continue;
149  }
150  $sheetIdentifier = md5(
151  implode('', [
152  $persistenceIdentifier,
153  $prototypeName,
154  $formIdentifier,
155  $finisherIdentifier
156  ])
157  );
158 
159  $translationFile = $finishersDefinition[$finisherIdentifier]['FormEngine']['translationFile'];
160  $finishersDefinition[$finisherIdentifier]['FormEngine'] = TranslationService::getInstance()->translateValuesRecursive(
161  $finishersDefinition[$finisherIdentifier]['FormEngine'],
162  $translationFile
163  );
164  $finisherLabel = $finishersDefinition[$finisherIdentifier]['FormEngine']['label'];
165  $sheet = $this->initializeNewSheetArray($sheetIdentifier, $finisherLabel);
166 
167  $sheetElements = [];
168  foreach ($finisherValue['options'] as $optionKey => $optionValue) {
169  if (is_array($optionValue)) {
170  $optionKey = $optionKey . '.' . $this->extractDottedPathToLastElement($finisherValue['options'][$optionKey]);
171  try {
172  $elementConfiguration = ArrayUtility::getValueByPath(
173  $finishersDefinition[$finisherIdentifier]['FormEngine']['elements'],
174  $optionKey,
175  '.'
176  );
177  } catch (\RuntimeException $exception) {
178  $elementConfiguration = null;
179  }
180  try {
181  $optionValue = ArrayUtility::getValueByPath($finisherValue['options'], $optionKey, '.');
182  } catch (\RuntimeException $exception) {
183  $optionValue = null;
184  }
185  } else {
186  $elementConfiguration = $finishersDefinition[$finisherIdentifier]['FormEngine']['elements'][$optionKey];
187  }
188 
189  if (empty($elementConfiguration)) {
190  continue;
191  }
192 
193  if (empty($optionValue)) {
194  $elementConfiguration['label'] .= ' (default: "[Empty]")';
195  } else {
196  $elementConfiguration['label'] .= ' (default: "' . $optionValue . '")';
197  }
198  $elementConfiguration['config']['default'] = $optionValue;
199  $sheetElements['settings.finishers.' . $finisherIdentifier . '.' . $optionKey] = $elementConfiguration;
200  }
201 
202  ksort($sheetElements);
203 
204  $sheet[$sheetIdentifier]['ROOT']['el'] = $sheetElements;
205  ArrayUtility::mergeRecursiveWithOverrule($sheets['sheets'], $sheet);
206  }
207  if (empty($sheets['sheets'])) {
208  return [];
209  }
210 
211  return $sheets;
212  }
213 
222  protected function initializeNewSheetArray(string $sheetIdentifier, string $finisherName): array
223  {
224  if (empty($sheetIdentifier)) {
225  throw new \InvalidArgumentException('$sheetIdentifier must not be empty.', 1472060918);
226  }
227  if (empty($finisherName)) {
228  throw new \InvalidArgumentException('$finisherName must not be empty.', 1472060919);
229  }
230 
231  return [
232  $sheetIdentifier => [
233  'ROOT' => [
234  'TCEforms' => [
235  'sheetTitle' => $finisherName,
236  ],
237  'type' => 'array',
238  'el' => [],
239  ],
240  ],
241  ];
242  }
243 
250  protected function extractDottedPathToLastElement(array $array): string
251  {
252  $dottedPath = key($array);
253  foreach ($array as $key => $value) {
254  if (is_array($value)) {
255  $dottedPath = $dottedPath . '.' . $this->extractDottedPathToLastElement($value);
256  }
257  }
258  return $dottedPath;
259  }
260 }
getAdditionalFinisherSheets(string $persistenceIdentifier, array $formDefinition)
static xml2array($string, $NSprefix= '', $reportDocTag=false)
static getValueByPath(array $array, $path, $delimiter= '/')
initializeNewSheetArray(string $sheetIdentifier, string $finisherName)
static mergeRecursiveWithOverrule(array &$original, array $overrule, $addKeys=true, $includeEmptyValues=true, $enableUnsetFeature=true)
static makeInstance($className,...$constructorArguments)
parseDataStructureByIdentifierPostProcess(array $dataStructure, array $identifier)
getDataStructureIdentifierPostProcess(array $fieldTca, string $tableName, string $fieldName, array $row, array $identifier)