/**
  * Render method
  *
  * @param string $action Target action
  * @param array $arguments Arguments
  * @param string $controller Target controller. If NULL current controllerName is used
  * @param string $extensionName Target Extension Name (without "tx_" prefix and no underscores). If NULL the current
  *     extension name is used
  * @param string $pluginName Target plugin. If empty, the current plugin name is used
  * @param integer $pageUid target page. See TypoLink destination
  * @param integer $pageType type of the target page. See typolink.parameter
  * @param boolean $noCache set this to disable caching for the target page. You should not need this.
  * @param boolean $noCacheHash set this to supress the cHash query parameter created by TypoLink.
  * @param string $section the anchor to be added to the URI
  * @param string $format The requested format, e.g. ".html
  * @param boolean $linkAccessRestrictedPages If set, links pointing to access restricted pages
  *     will still link to the page even though the page cannot be accessed.
  * @param array $additionalParams additional query parameters that won't be prefixed like
  *     $arguments (overrule $arguments)
  * @param boolean $absolute If set, the URI of the rendered link is absolute
  * @param boolean $addQueryString If set, the current query parameters will be kept in the URI
  * @param array $argumentsToBeExcludedFromQueryString arguments to be removed from the URI.
  *     Only active if $addQueryString = TRUE
  * @param string $addQueryStringMethod Set which parameters will be kept. Only active if $addQueryString = TRUE
  *
  * @return string Rendered link
  */
 public function render($action = null, array $arguments = [], $controller = null, $extensionName = null, $pluginName = null, $pageUid = null, $pageType = 0, $noCache = false, $noCacheHash = false, $section = '', $format = '', $linkAccessRestrictedPages = false, array $additionalParams = [], $absolute = false, $addQueryString = false, array $argumentsToBeExcludedFromQueryString = [], $addQueryStringMethod = null)
 {
     if ($action !== null && $arguments !== null && isset($arguments['user'])) {
         $arguments['hash'] = GeneralUtility::hmac($action . '::' . $arguments['user']);
     }
     return parent::render($action, $arguments, $controller, $extensionName, $pluginName, $pageUid, $pageType, $noCache, $noCacheHash, $section, $format, $linkAccessRestrictedPages, $additionalParams, $absolute, $addQueryString, $argumentsToBeExcludedFromQueryString, $addQueryStringMethod);
 }
 /**
  * @param string $listenerId
  * @return object
  */
 public function findById($listenerId)
 {
     if ($listenerId) {
         $object = parent::findById($listenerId);
         if (!$object) {
             list($table, $uid, $rawListenerId) = \TYPO3\CMS\Core\Utility\GeneralUtility::trimExplode('-', $listenerId, false, 3);
             // try to generate the listener cache
             if ($table == 'tt_content' && $uid) {
                 $object = $this->serviceContent->generateListenerCacheForContentElement($table, $uid);
             } elseif ($table == 'h' || $table == 'hInt') {
                 $settingsHash = $uid;
                 $encodedSettings = $rawListenerId;
                 if (\TYPO3\CMS\Core\Utility\GeneralUtility::hmac($encodedSettings) == $settingsHash) {
                     $loadContentFromTypoScript = str_replace('---', '.', $encodedSettings);
                     $eventsToListen = \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('e');
                     $object = $this->serviceContent->generateListenerCacheForHijaxPi1($loadContentFromTypoScript, $eventsToListen[$listenerId], $table == 'h');
                 }
             }
             if ($table == 'f') {
                 $settingsHash = $uid;
                 $encodedSettings = $rawListenerId;
                 if (\TYPO3\CMS\Core\Utility\GeneralUtility::hmac($encodedSettings) == $settingsHash) {
                     $fallbackTypoScriptConfiguration = str_replace('---', '.', $encodedSettings);
                     $object = $this->serviceContent->generateListenerCacheForTypoScriptFallback($fallbackTypoScriptConfiguration);
                 }
             }
         }
         return $object;
     } else {
         return null;
     }
 }
Example #3
0
 /**
  * Renders an ajax-enabled text field. Also adds required JS
  *
  * @param string $fieldName The field name in the form
  * @param string $table The table we render this selector for
  * @param string $field The field we render this selector for
  * @param array $row The row which is currently edited
  * @param array $config The TSconfig of the field
  * @param array $flexFormConfig If field is within flex form, this is the TCA config of the flex field
  * @throws \RuntimeException for incomplete incoming arguments
  * @return string The HTML code for the selector
  */
 public function renderSuggestSelector($fieldName, $table, $field, array $row, array $config, array $flexFormConfig = [])
 {
     $dataStructureIdentifier = '';
     if (!empty($flexFormConfig) && $flexFormConfig['config']['type'] === 'flex') {
         $fieldPattern = 'data[' . $table . '][' . $row['uid'] . '][';
         $flexformField = str_replace($fieldPattern, '', $fieldName);
         $flexformField = substr($flexformField, 0, -1);
         $field = str_replace([']['], '|', $flexformField);
         if (!isset($flexFormConfig['config']['dataStructureIdentifier'])) {
             throw new \RuntimeException('A data structure identifier must be set in [\'config\'] part of a flex form.' . ' This is usually added by TcaFlexPrepare data processor', 1478604742);
         }
         $dataStructureIdentifier = $flexFormConfig['config']['dataStructureIdentifier'];
     }
     // Get minimumCharacters from TCA
     $minChars = 0;
     if (isset($config['fieldConf']['config']['wizards']['suggest']['default']['minimumCharacters'])) {
         $minChars = (int) $config['fieldConf']['config']['wizards']['suggest']['default']['minimumCharacters'];
     }
     // Overwrite it with minimumCharacters from TSConfig if given
     if (isset($config['fieldTSConfig']['suggest.']['default.']['minimumCharacters'])) {
         $minChars = (int) $config['fieldTSConfig']['suggest.']['default.']['minimumCharacters'];
     }
     $minChars = $minChars > 0 ? $minChars : 2;
     // fetch the TCA field type to hand it over to the JS class
     $type = '';
     if (isset($config['fieldConf']['config']['type'])) {
         $type = $config['fieldConf']['config']['type'];
     }
     // Sign those parameters that come back in an ajax request to configure the search in searchAction()
     $hmac = GeneralUtility::hmac((string) $table . (string) $field . (string) $row['uid'] . (string) $row['pid'] . (string) $dataStructureIdentifier, 'formEngineSuggest');
     $this->view->assignMultiple(['placeholder' => 'LLL:EXT:lang/Resources/Private/Language/locallang_core.xlf:labels.findRecord', 'fieldname' => $fieldName, 'table' => $table, 'field' => $field, 'uid' => $row['uid'], 'pid' => (int) $row['pid'], 'dataStructureIdentifier' => $dataStructureIdentifier, 'fieldtype' => $type, 'minchars' => (int) $minChars, 'hmac' => $hmac]);
     return $this->view->render();
 }
 /**
  * Create a link to a file that forces a download
  *
  * @param \TYPO3\CMS\Core\Resource\FileInterface $file
  * @param bool $uriOnly
  * @return string
  */
 public function render(\TYPO3\CMS\Core\Resource\FileInterface $file, $uriOnly = FALSE)
 {
     $queryParameterArray = array('eID' => 'dumpFile', 't' => '');
     if ($file instanceof \TYPO3\CMS\Core\Resource\File) {
         $queryParameterArray['f'] = $file->getUid();
         $queryParameterArray['t'] = 'f';
     } elseif ($file instanceof \TYPO3\CMS\Core\Resource\ProcessedFile) {
         $queryParameterArray['p'] = $file->getUid();
         $queryParameterArray['t'] = 'p';
     }
     $queryParameterArray['token'] = \TYPO3\CMS\Core\Utility\GeneralUtility::hmac(implode('|', $queryParameterArray), 'resourceStorageDumpFile');
     $queryParameterArray['download'] = '';
     $uri = 'index.php?' . str_replace('+', '%20', http_build_query($queryParameterArray));
     // Add absRefPrefix
     if (!empty($GLOBALS['TSFE'])) {
         $uri = $GLOBALS['TSFE']->absRefPrefix . $uri;
     }
     if ($uriOnly) {
         return $uri;
     }
     $this->tag->addAttribute('href', $uri);
     $this->tag->setContent($this->renderChildren());
     $this->tag->forceClosingTag(TRUE);
     return $this->tag->render();
 }
 /**
  * Handler for unknown types.
  *
  * @return array As defined in initializeResultArray() of AbstractNode
  */
 public function render()
 {
     $resultArray = $this->initializeResultArray();
     $languageService = $this->getLanguageService();
     $row = $this->data['databaseRow'];
     $parameterArray = $this->data['parameterArray'];
     // If ratios are set do not add default options
     if (isset($parameterArray['fieldConf']['config']['ratios'])) {
         unset($this->defaultConfig['ratios']);
     }
     $config = ArrayUtility::arrayMergeRecursiveOverrule($this->defaultConfig, $parameterArray['fieldConf']['config']);
     // By default we allow all image extensions that can be handled by the GFX functionality
     if ($config['allowedExtensions'] === null) {
         $config['allowedExtensions'] = $GLOBALS['TYPO3_CONF_VARS']['GFX']['imagefile_ext'];
     }
     if ($config['readOnly']) {
         $options = array();
         $options['parameterArray'] = array('fieldConf' => array('config' => $config), 'itemFormElValue' => $parameterArray['itemFormElValue']);
         $options['renderType'] = 'none';
         return $this->nodeFactory->create($options)->render();
     }
     $file = $this->getFile($row, $config['file_field']);
     if (!$file) {
         return $resultArray;
     }
     $content = '';
     $preview = '';
     if (GeneralUtility::inList(mb_strtolower($config['allowedExtensions']), mb_strtolower($file->getExtension()))) {
         // Get preview
         $preview = $this->getPreview($file, $parameterArray['itemFormElValue']);
         // Check if ratio labels hold translation strings
         foreach ((array) $config['ratios'] as $ratio => $label) {
             $config['ratios'][$ratio] = $languageService->sL($label, true);
         }
         $formFieldId = StringUtility::getUniqueId('formengine-image-manipulation-');
         $wizardData = array('zoom' => $config['enableZoom'] ? '1' : '0', 'ratios' => json_encode($config['ratios']), 'file' => $file->getUid());
         $wizardData['token'] = GeneralUtility::hmac(implode('|', $wizardData), 'ImageManipulationWizard');
         $buttonAttributes = array('data-url' => BackendUtility::getAjaxUrl('wizard_image_manipulation', $wizardData), 'data-severity' => 'notice', 'data-image-name' => $file->getNameWithoutExtension(), 'data-image-uid' => $file->getUid(), 'data-file-field' => $config['file_field'], 'data-field' => $formFieldId);
         $button = '<button class="btn btn-default t3js-image-manipulation-trigger"';
         foreach ($buttonAttributes as $key => $value) {
             $button .= ' ' . $key . '="' . htmlspecialchars($value) . '"';
         }
         $button .= '><span class="t3-icon fa fa-crop"></span>';
         $button .= $languageService->sL('LLL:EXT:lang/locallang_wizards.xlf:imwizard.open-editor', true);
         $button .= '</button>';
         $inputField = '<input type="hidden" ' . 'id="' . $formFieldId . '" ' . 'name="' . $parameterArray['itemFormElName'] . '" ' . 'value="' . htmlspecialchars($parameterArray['itemFormElValue']) . '" />';
         $content .= $inputField . $button;
         $content .= $this->getImageManipulationInfoTable($parameterArray['itemFormElValue']);
         $resultArray['requireJsModules'][] = array('TYPO3/CMS/Backend/ImageManipulation' => 'function(ImageManipulation){ImageManipulation.initializeTrigger()}');
     }
     $content .= '<p class="text-muted"><em>' . $languageService->sL('LLL:EXT:lang/locallang_wizards.xlf:imwizard.supported-types-message', true) . '<br />';
     $content .= mb_strtoupper(implode(', ', GeneralUtility::trimExplode(',', $config['allowedExtensions'])));
     $content .= '</em></p>';
     $item = '<div class="media">';
     $item .= $preview;
     $item .= '<div class="media-body">' . $content . '</div>';
     $item .= '</div>';
     $resultArray['html'] = $item;
     return $resultArray;
 }
 /**
  * Initialiation of the script class
  *
  * @return 	void
  */
 protected function init()
 {
     // Setting backPath
     $this->backPath = $GLOBALS['BACK_PATH'];
     // Setting GPvars:
     $this->currentSubScript = GeneralUtility::_GP('currentSubScript');
     $this->cMR = GeneralUtility::_GP('cMR');
     $scopeData = (string) GeneralUtility::_GP('scopeData');
     $scopeHash = (string) GeneralUtility::_GP('scopeHash');
     if (!empty($scopeData) && GeneralUtility::hmac($scopeData) === $scopeHash) {
         $this->scopeData = unserialize($scopeData);
     }
     // Create folder tree object:
     if (!empty($this->scopeData)) {
         $this->foldertree = GeneralUtility::makeInstance($this->scopeData['class']);
         $this->foldertree->thisScript = $this->scopeData['script'];
         $this->foldertree->ext_noTempRecyclerDirs = $this->scopeData['ext_noTempRecyclerDirs'];
         $GLOBALS['SOBE']->browser = new \stdClass();
         $GLOBALS['SOBE']->browser->mode = $this->scopeData['browser']['mode'];
         $GLOBALS['SOBE']->browser->act = $this->scopeData['browser']['act'];
     } else {
         $this->foldertree = GeneralUtility::makeInstance('TYPO3\\CMS\\Filelist\\FileListFolderTree');
         $this->foldertree->thisScript = 'alt_file_navframe.php';
     }
     $this->foldertree->ext_IconMode = $GLOBALS['BE_USER']->getTSConfigVal('options.folderTree.disableIconLinkToContextmenu');
 }
 /**
  * @test
  */
 public function tokenFromSessionDataIsAvailableForValidateToken()
 {
     $sessionToken = '881ffea2159ac72182557b79dc0c723f5a8d20136f9fab56cdd4f8b3a1dbcfcd';
     $formName = 'foo';
     $action = 'edit';
     $formInstanceName = '42';
     $tokenId = \TYPO3\CMS\Core\Utility\GeneralUtility::hmac($formName . $action . $formInstanceName . $sessionToken);
     $this->backendUserMock->expects($this->atLeastOnce())->method('getSessionData')->with('formProtectionSessionToken')->will($this->returnValue($sessionToken));
     $this->assertTrue($this->subject->validateToken($tokenId, $formName, $action, $formInstanceName));
 }
 /**
  * @test
  */
 public function tokenFromSessionDataIsAvailableForValidateToken()
 {
     $sessionToken = '881ffea2159ac72182557b79dc0c723f5a8d20136f9fab56cdd4f8b3a1dbcfcd';
     $formName = 'foo';
     $action = 'edit';
     $formInstanceName = '42';
     $tokenId = \TYPO3\CMS\Core\Utility\GeneralUtility::hmac($formName . $action . $formInstanceName . $sessionToken);
     $_SESSION['installToolFormToken'] = $sessionToken;
     $this->fixture->_call('retrieveSessionToken');
     $this->assertTrue($this->fixture->validateToken($tokenId, $formName, $action, $formInstanceName));
 }
Example #9
0
	/**
	 * Check if hmac token is correct
	 *
	 * @return bool
	 */
	protected function checkHmacToken() {
		$parameters = array();
		if (GeneralUtility::_GET('file')) {
			$parameters['file'] = GeneralUtility::_GET('file');
		}
		$parameters['zoom'] = GeneralUtility::_GET('zoom') ? '1' : '0';
		$parameters['ratios'] = GeneralUtility::_GET('ratios') ?: '';

		$token = GeneralUtility::hmac(implode('|', $parameters), 'ImageManipulationWizard');
		return $token === GeneralUtility::_GET('token');
	}
Example #10
0
 /**
  * Wrap the plus/minus icon in a link
  *
  * @param string $icon HTML string to wrap, probably an image tag.
  * @param string $cmd Command for 'PM' get var
  * @param boolean $isExpand If expanded
  * @return string Link-wrapped input string
  * @access private
  */
 public function PMiconATagWrap($icon, $cmd, $isExpand = TRUE)
 {
     if (empty($this->scope)) {
         $this->scope = array('class' => get_class($this), 'script' => $this->thisScript, 'ext_noTempRecyclerDirs' => $this->ext_noTempRecyclerDirs, 'browser' => array('mode' => $GLOBALS['SOBE']->browser->mode, 'act' => $GLOBALS['SOBE']->browser->act, 'editorNo' => $GLOBALS['SOBE']->browser->editorNo));
     }
     if ($this->thisScript) {
         // Activates dynamic AJAX based tree
         $scopeData = serialize($this->scope);
         $scopeHash = GeneralUtility::hmac($scopeData);
         $js = htmlspecialchars('Tree.load(' . GeneralUtility::quoteJSvalue($cmd) . ', ' . (int) $isExpand . ', this, ' . GeneralUtility::quoteJSvalue($scopeData) . ', ' . GeneralUtility::quoteJSvalue($scopeHash) . ');');
         return '<a class="pm" onclick="' . $js . '">' . $icon . '</a>';
     } else {
         return $icon;
     }
 }
 /**
  * Main method to dump a file
  *
  * @param ServerRequestInterface $request
  * @param ResponseInterface $response
  * @return NULL|ResponseInterface
  *
  * @throws \InvalidArgumentException
  * @throws \RuntimeException
  * @throws \TYPO3\CMS\Core\Resource\Exception\FileDoesNotExistException
  * @throws \UnexpectedValueException
  */
 public function dumpAction(ServerRequestInterface $request, ResponseInterface $response)
 {
     $parameters = array('eID' => 'dumpFile');
     $t = $this->getGetOrPost($request, 't');
     if ($t) {
         $parameters['t'] = $t;
     }
     $f = $this->getGetOrPost($request, 'f');
     if ($f) {
         $parameters['f'] = $f;
     }
     $p = $this->getGetOrPost($request, 'p');
     if ($p) {
         $parameters['p'] = $p;
     }
     if (GeneralUtility::hmac(implode('|', $parameters), 'resourceStorageDumpFile') === $this->getGetOrPost($request, 'token')) {
         if (isset($parameters['f'])) {
             $file = ResourceFactory::getInstance()->getFileObject($parameters['f']);
             if ($file->isDeleted() || $file->isMissing()) {
                 $file = null;
             }
         } else {
             $file = GeneralUtility::makeInstance(ProcessedFileRepository::class)->findByUid($parameters['p']);
             if ($file->isDeleted()) {
                 $file = null;
             }
         }
         if ($file === null) {
             HttpUtility::setResponseCodeAndExit(HttpUtility::HTTP_STATUS_404);
         }
         // Hook: allow some other process to do some security/access checks. Hook should issue 403 if access is rejected
         if (is_array($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['FileDumpEID.php']['checkFileAccess'])) {
             foreach ($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['FileDumpEID.php']['checkFileAccess'] as $classRef) {
                 $hookObject = GeneralUtility::getUserObj($classRef);
                 if (!$hookObject instanceof FileDumpEIDHookInterface) {
                     throw new \UnexpectedValueException('FileDump hook object must implement interface ' . FileDumpEIDHookInterface::class, 1394442417);
                 }
                 $hookObject->checkFileAccess($file);
             }
         }
         $file->getStorage()->dumpFileContents($file);
         // @todo Refactor FAL to not echo directly, but to implement a stream for output here and use response
         return null;
     } else {
         return $response->withStatus(403);
     }
 }
 /**
  * Generate public url for file
  *
  * @param Resource\ResourceStorage $storage
  * @param Resource\Driver\DriverInterface $driver
  * @param Resource\FileInterface $file
  * @param $relativeToCurrentScript
  * @param array $urlData
  * @return void
  */
 public function generatePublicUrl(Resource\ResourceStorage $storage, Resource\Driver\DriverInterface $driver, Resource\FileInterface $file, $relativeToCurrentScript, array $urlData)
 {
     // We only render special links for non-public files
     if ($this->enabled && !$storage->isPublic()) {
         $queryParameterArray = array('eID' => 'dumpFile', 't' => '');
         if ($file instanceof Resource\File) {
             $queryParameterArray['f'] = $file->getUid();
             $queryParameterArray['t'] = 'f';
         } elseif ($file instanceof Resource\ProcessedFile) {
             $queryParameterArray['p'] = $file->getUid();
             $queryParameterArray['t'] = 'p';
         }
         $queryParameterArray['token'] = GeneralUtility::hmac(implode('|', $queryParameterArray), 'BeResourceStorageDumpFile');
         // $urlData['publicUrl'] is passed by reference, so we can change that here and the value will be taken into account
         $urlData['publicUrl'] = BackendUtility::getAjaxUrl('FalSecuredownload::publicUrl', $queryParameterArray);
     }
 }
 /**
  * Runs a remote function call.
  *
  * @param int $storageUid The UID of the drivers storage.
  * @param string $function The name of the function that should be called.
  * @param array $parameters The parameters passed to the remote function.
  * @return mixed The return value of the remote function.
  */
 public function call($storageUid, $function, $parameters = array())
 {
     $parameters = base64_encode(serialize($parameters));
     $hash = GeneralUtility::hmac($storageUid . $function . $parameters, 'fal_remote');
     $report = array();
     $url = $this->extensionConfiguration->getRemoteTypo3Url() . sprintf('?eID=fal_remote&hash=%s&storageUid=%d&function=%s&parameters=%s', $hash, (int) $storageUid, rawurlencode($function), $parameters);
     $result = GeneralUtility::getUrl($url, 0, FALSE, $report);
     if (!$result) {
         throw new \RuntimeException('Error fetching file information for ' . $function . ': ' . $report['message']);
     }
     $result = json_decode($result, TRUE);
     if (empty($result['success'])) {
         $error = !empty($result['error']) ? ': ' . $result['error'] : '';
         throw new \RuntimeException('Error fetching file information for ' . $function . $error);
     }
     return $result['returnValue'];
 }
Example #14
0
 /**
  * Processes eID request.
  *
  * @return void
  */
 public function main()
 {
     // Due to the nature of OpenID (redrections, etc) we need to force user
     // session fetching if there is no session around. This ensures that
     // our service is called even if there is no login data in the request.
     // Inside the service we will process OpenID response and authenticate
     // the user.
     $GLOBALS['TYPO3_CONF_VARS']['SVCONF']['auth']['FE_fetchUserIfNoSession'] = true;
     // Initialize Frontend user
     EidUtility::initFeUser();
     // Redirect to the original location in any case (authenticated or not)
     @ob_end_clean();
     $location = GeneralUtility::_GP('tx_openid_location');
     $signature = GeneralUtility::hmac($location, 'openid');
     if ($signature === GeneralUtility::_GP('tx_openid_location_signature')) {
         HttpUtility::redirect($location, HttpUtility::HTTP_STATUS_303);
     }
 }
 /**
  * Processed the requested call based on the current GET parameters.
  */
 public function processCall()
 {
     $storageUid = (string) GeneralUtility::_GET('storageUid');
     if ($storageUid === '') {
         $this->result['error'] = 'No storageUid submitted.';
         return;
     }
     $storageUid = (int) $storageUid;
     $function = (string) GeneralUtility::_GET('function');
     if ($function === '') {
         $this->result['error'] = 'No function submitted.';
         return;
     }
     $parameters = (string) GeneralUtility::_GET('parameters');
     if ($parameters === '') {
         $this->result['error'] = 'No parameters submnitted.';
         return;
     }
     $hash = (string) GeneralUtility::_GET('hash');
     if ($hash === '') {
         $this->result['error'] = 'No hash was submitted.';
         return;
     }
     if ($hash !== GeneralUtility::hmac($storageUid . $function . $parameters, 'fal_remote')) {
         $this->result['error'] = 'An invalid hash was submitted.';
         return;
     }
     $parameters = unserialize(base64_decode($parameters));
     if ($parameters === FALSE || !is_array($parameters)) {
         $this->result['error'] = 'The parameters array could not be deserialized.';
         return;
     }
     try {
         $result = call_user_func_array(array($this->getDriver($storageUid), $function), $parameters);
         if ($function === 'getFileContents') {
             $result = base64_encode($result);
         }
         $this->result = array('success' => TRUE, 'returnValue' => $result);
     } catch (\Exception $e) {
         $this->result = array('success' => FALSE, 'error' => $e->getMessage());
     }
 }
 /**
  * Dump file content
  * Copy from /sysext/core/Resources/PHP/FileDumpEID.php
  *
  * @param array $params
  * @param \TYPO3\CMS\Core\Http\AjaxRequestHandler $ajaxObj
  */
 public function dumpFile($params = array(), \TYPO3\CMS\Core\Http\AjaxRequestHandler &$ajaxObj = null)
 {
     $parameters = array('eID' => 'dumpFile');
     if (GeneralUtility::_GP('t')) {
         $parameters['t'] = GeneralUtility::_GP('t');
     }
     if (GeneralUtility::_GP('f')) {
         $parameters['f'] = (int) GeneralUtility::_GP('f');
     }
     if (GeneralUtility::_GP('p')) {
         $parameters['p'] = (int) GeneralUtility::_GP('p');
     }
     if (GeneralUtility::hmac(implode('|', $parameters), 'BeResourceStorageDumpFile') === GeneralUtility::_GP('token')) {
         if (isset($parameters['f'])) {
             $file = \TYPO3\CMS\Core\Resource\ResourceFactory::getInstance()->getFileObject($parameters['f']);
             if ($file->isDeleted() || $file->isMissing()) {
                 $file = null;
             }
             $orgFile = $file;
         } else {
             /** @var \TYPO3\CMS\Core\Resource\ProcessedFile $file */
             $file = GeneralUtility::makeInstance('TYPO3\\CMS\\Core\\Resource\\ProcessedFileRepository')->findByUid($parameters['p']);
             if ($file->isDeleted()) {
                 $file = null;
             }
             $orgFile = $file->getOriginalFile();
         }
         // Check file read permissions
         if (!$orgFile->getStorage()->checkFileActionPermission('read', $orgFile)) {
             HttpUtility::setResponseCodeAndExit(HttpUtility::HTTP_STATUS_403);
         }
         if ($file === null) {
             HttpUtility::setResponseCodeAndExit(HttpUtility::HTTP_STATUS_404);
         }
         ob_start();
         $file->getStorage()->dumpFileContents($file);
         exit;
     } else {
         HttpUtility::setResponseCodeAndExit(HttpUtility::HTTP_STATUS_403);
     }
 }
Example #17
0
 /**
  * Will create and return the HTML code for a browsable tree of folders.
  * Is based on the mounts found in the internal array ->MOUNTS (set in the constructor)
  *
  * @return string HTML code for the browsable tree
  */
 public function getBrowsableTree()
 {
     // TYPO3\CMS\Backend\Controller\FileSystemNavigationFrameController does not set custom parameters on an Ajax expand/collapse request
     if (!$GLOBALS['SOBE']->browser->editorNo) {
         $scopeData = (string) GeneralUtility::_GP('scopeData');
         $scopeHash = (string) GeneralUtility::_GP('scopeHash');
         if (!empty($scopeData) && GeneralUtility::hmac($scopeData) === $scopeHash) {
             $scopeData = unserialize($scopeData);
             if ($scopeData['browser']['editorNo']) {
                 $GLOBALS['SOBE']->browser->editorNo = $scopeData['browser']['editorNo'];
             }
             if ($scopeData['browser']['sys_language_content']) {
                 $GLOBALS['SOBE']->browser->sys_language_content = $scopeData['browser']['sys_language_content'];
             }
             if ($scopeData['browser']['contentTypo3Language']) {
                 $GLOBALS['SOBE']->browser->contentTypo3Language = $scopeData['browser']['contentTypo3Language'];
             }
         }
     }
     return parent::getBrowsableTree();
 }
 /**
  * Start function
  * This class is able to generate a mail in formmail-style from the data in $V
  * Fields:
  *
  * [recipient]:			email-adress of the one to receive the mail. If array, then all values are expected to be recipients
  * [attachment]:		....
  *
  * [subject]:			The subject of the mail
  * [from_email]:		Sender email. If not set, [email] is used
  * [from_name]:			Sender name. If not set, [name] is used
  * [replyto_email]:		Reply-to email. If not set [from_email] is used
  * [replyto_name]:		Reply-to name. If not set [from_name] is used
  * [organisation]:		Organization (header)
  * [priority]:			Priority, 1-5, default 3
  * [html_enabled]:		If mail is sent as html
  * [use_base64]:		If set, base64 encoding will be used instead of quoted-printable
  *
  * @param array $valueList Contains values for the field names listed above (with slashes removed if from POST input)
  * @param boolean $base64 Whether to base64 encode the mail content
  * @return void
  * @todo Define visibility
  */
 public function start($valueList, $base64 = FALSE)
 {
     $this->mailMessage = \TYPO3\CMS\Core\Utility\GeneralUtility::makeInstance('TYPO3\\CMS\\Core\\Mail\\MailMessage');
     if ($GLOBALS['TSFE']->config['config']['formMailCharset']) {
         // Respect formMailCharset if it was set
         $this->characterSet = $GLOBALS['TSFE']->csConvObj->parse_charset($GLOBALS['TSFE']->config['config']['formMailCharset']);
     } elseif ($GLOBALS['TSFE']->metaCharset != $GLOBALS['TSFE']->renderCharset) {
         // Use metaCharset for mail if different from renderCharset
         $this->characterSet = $GLOBALS['TSFE']->metaCharset;
     } else {
         // Otherwise use renderCharset as default
         $this->characterSet = $GLOBALS['TSFE']->renderCharset;
     }
     if ($base64 || $valueList['use_base64']) {
         $this->encoding = 'base64';
     }
     if (isset($valueList['recipient'])) {
         // Convert form data from renderCharset to mail charset
         $this->subject = $valueList['subject'] ? $valueList['subject'] : 'Formmail on ' . \TYPO3\CMS\Core\Utility\GeneralUtility::getIndpEnv('HTTP_HOST');
         $this->subject = $this->sanitizeHeaderString($this->subject);
         $this->fromName = $valueList['from_name'] ? $valueList['from_name'] : ($valueList['name'] ? $valueList['name'] : '');
         $this->fromName = $this->sanitizeHeaderString($this->fromName);
         $this->replyToName = $valueList['replyto_name'] ? $valueList['replyto_name'] : $this->fromName;
         $this->replyToName = $this->sanitizeHeaderString($this->replyToName);
         $this->organisation = $valueList['organisation'] ? $valueList['organisation'] : '';
         $this->organisation = $this->sanitizeHeaderString($this->organisation);
         $this->fromAddress = $valueList['from_email'] ? $valueList['from_email'] : ($valueList['email'] ? $valueList['email'] : '');
         if (!\TYPO3\CMS\Core\Utility\GeneralUtility::validEmail($this->fromAddress)) {
             $this->fromAddress = \TYPO3\CMS\Core\Utility\MailUtility::getSystemFromAddress();
             $this->fromName = \TYPO3\CMS\Core\Utility\MailUtility::getSystemFromName();
         }
         $this->replyToAddress = $valueList['replyto_email'] ? $valueList['replyto_email'] : $this->fromAddress;
         $this->priority = $valueList['priority'] ? \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($valueList['priority'], 1, 5) : 3;
         // Auto responder
         $this->autoRespondMessage = trim($valueList['auto_respond_msg']) && $this->fromAddress ? trim($valueList['auto_respond_msg']) : '';
         if ($this->autoRespondMessage !== '') {
             // Check if the value of the auto responder message has been modified with evil intentions
             $autoRespondChecksum = $valueList['auto_respond_checksum'];
             $correctHmacChecksum = \TYPO3\CMS\Core\Utility\GeneralUtility::hmac($this->autoRespondMessage);
             if ($autoRespondChecksum !== $correctHmacChecksum) {
                 \TYPO3\CMS\Core\Utility\GeneralUtility::sysLog('Possible misuse of t3lib_formmail auto respond method. Subject: ' . $valueList['subject'], 'Core', \TYPO3\CMS\Core\Utility\GeneralUtility::SYSLOG_SEVERITY_ERROR);
                 return;
             } else {
                 $this->autoRespondMessage = $this->sanitizeHeaderString($this->autoRespondMessage);
             }
         }
         $plainTextContent = '';
         $htmlContent = '<table border="0" cellpadding="2" cellspacing="2">';
         // Runs through $V and generates the mail
         if (is_array($valueList)) {
             foreach ($valueList as $key => $val) {
                 if (!\TYPO3\CMS\Core\Utility\GeneralUtility::inList($this->reserved_names, $key)) {
                     $space = strlen($val) > 60 ? LF : '';
                     $val = is_array($val) ? implode($val, LF) : $val;
                     // Convert form data from renderCharset to mail charset (HTML may use entities)
                     $plainTextValue = $val;
                     $HtmlValue = htmlspecialchars($val);
                     $plainTextContent .= strtoupper($key) . ':  ' . $space . $plainTextValue . LF . $space;
                     $htmlContent .= '<tr><td bgcolor="#eeeeee"><font face="Verdana" size="1"><strong>' . strtoupper($key) . '</strong></font></td><td bgcolor="#eeeeee"><font face="Verdana" size="1">' . nl2br($HtmlValue) . '&nbsp;</font></td></tr>';
                 }
             }
         }
         $htmlContent .= '</table>';
         $this->plainContent = $plainTextContent;
         if ($valueList['html_enabled']) {
             $this->mailMessage->setBody($htmlContent, 'text/html', $this->characterSet);
             $this->mailMessage->addPart($plainTextContent, 'text/plain', $this->characterSet);
         } else {
             $this->mailMessage->setBody($plainTextContent, 'text/plain', $this->characterSet);
         }
         for ($a = 0; $a < 10; $a++) {
             $variableName = 'attachment' . ($a ? $a : '');
             if (!isset($_FILES[$variableName])) {
                 continue;
             }
             if (!is_uploaded_file($_FILES[$variableName]['tmp_name'])) {
                 \TYPO3\CMS\Core\Utility\GeneralUtility::sysLog('Possible abuse of t3lib_formmail: temporary file "' . $_FILES[$variableName]['tmp_name'] . '" ("' . $_FILES[$variableName]['name'] . '") was not an uploaded file.', 'Core', \TYPO3\CMS\Core\Utility\GeneralUtility::SYSLOG_SEVERITY_ERROR);
             }
             if ($_FILES[$variableName]['tmp_name']['error'] !== UPLOAD_ERR_OK) {
                 \TYPO3\CMS\Core\Utility\GeneralUtility::sysLog('Error in uploaded file in t3lib_formmail: temporary file "' . $_FILES[$variableName]['tmp_name'] . '" ("' . $_FILES[$variableName]['name'] . '") Error code: ' . $_FILES[$variableName]['tmp_name']['error'], 'Core', \TYPO3\CMS\Core\Utility\GeneralUtility::SYSLOG_SEVERITY_ERROR);
             }
             $theFile = \TYPO3\CMS\Core\Utility\GeneralUtility::upload_to_tempfile($_FILES[$variableName]['tmp_name']);
             $theName = $_FILES[$variableName]['name'];
             if ($theFile && file_exists($theFile)) {
                 if (filesize($theFile) < $GLOBALS['TYPO3_CONF_VARS']['FE']['formmailMaxAttachmentSize']) {
                     $this->mailMessage->attach(Swift_Attachment::fromPath($theFile)->setFilename($theName));
                 }
             }
             $this->temporaryFiles[] = $theFile;
         }
         $from = $this->fromName ? array($this->fromAddress => $this->fromName) : array($this->fromAddress);
         $this->recipient = $this->parseAddresses($valueList['recipient']);
         $this->mailMessage->setSubject($this->subject)->setFrom($from)->setTo($this->recipient)->setPriority($this->priority);
         $replyTo = $this->replyToName ? array($this->replyToAddress => $this->replyToName) : array($this->replyToAddress);
         $this->mailMessage->setReplyTo($replyTo);
         $this->mailMessage->getHeaders()->addTextHeader('Organization', $this->organisation);
         if ($valueList['recipient_copy']) {
             $this->mailMessage->setCc($this->parseAddresses($valueList['recipient_copy']));
         }
         $this->mailMessage->setCharset($this->characterSet);
         // Ignore target encoding. This is handled automatically by Swift Mailer and overriding the defaults
         // is not worth the trouble
         // Log dirty header lines
         if ($this->dirtyHeaders) {
             \TYPO3\CMS\Core\Utility\GeneralUtility::sysLog('Possible misuse of t3lib_formmail: see TYPO3 devLog', 'Core', \TYPO3\CMS\Core\Utility\GeneralUtility::SYSLOG_SEVERITY_ERROR);
             if ($GLOBALS['TYPO3_CONF_VARS']['SYS']['enable_DLOG']) {
                 \TYPO3\CMS\Core\Utility\GeneralUtility::devLog('t3lib_formmail: ' . \TYPO3\CMS\Core\Utility\GeneralUtility::arrayToLogString($this->dirtyHeaders, '', 200), 'Core', 3);
             }
         }
     }
 }
Example #19
0
 /**
  * Returns the path where to store our session files
  *
  * @throws \TYPO3\CMS\Install\Exception
  * @return string Session save path
  */
 private function getSessionSavePath()
 {
     if (empty($GLOBALS['TYPO3_CONF_VARS']['SYS']['encryptionKey'])) {
         throw new \TYPO3\CMS\Install\Exception('No encryption key set to secure session', 1371243449);
     }
     $sessionSavePath = sprintf($this->typo3tempPath . $this->sessionPath, GeneralUtility::hmac('session:' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['encryptionKey']));
     $this->ensureSessionSavePathExists($sessionSavePath);
     return $sessionSavePath;
 }
Example #20
0
 /**
  * Computes the RequireJS configuration, mainly consisting of the paths to the core and all extension JavaScript
  * resource folders plus some additional generic configuration.
  *
  * @param bool $isDevelopment
  * @param array $loadedExtensions
  * @return array The RequireJS configuration
  */
 protected function computeRequireJsConfig($isDevelopment, array $loadedExtensions)
 {
     // load all paths to map to package names / namespaces
     $requireJsConfig = [];
     // In order to avoid browser caching of JS files, adding a GET parameter to the files loaded via requireJS
     if ($isDevelopment) {
         $requireJsConfig['urlArgs'] = 'bust=' . $GLOBALS['EXEC_TIME'];
     } else {
         $requireJsConfig['urlArgs'] = 'bust=' . GeneralUtility::hmac(TYPO3_version . PATH_site);
     }
     $corePath = ExtensionManagementUtility::extPath('core', 'Resources/Public/JavaScript/Contrib/');
     $corePath = PathUtility::getAbsoluteWebPath($corePath);
     // first, load all paths for the namespaces, and configure contrib libs.
     $requireJsConfig['paths'] = ['jquery-ui' => $corePath . 'jquery-ui', 'datatables' => $corePath . 'jquery.dataTables', 'matchheight' => $corePath . 'jquery.matchHeight-min', 'nprogress' => $corePath . 'nprogress', 'moment' => $corePath . 'moment', 'cropper' => $corePath . 'cropper.min', 'imagesloaded' => $corePath . 'imagesloaded.pkgd.min', 'bootstrap' => $corePath . 'bootstrap/bootstrap', 'twbs/bootstrap-datetimepicker' => $corePath . 'bootstrap-datetimepicker', 'autosize' => $corePath . 'autosize', 'taboverride' => $corePath . 'taboverride.min', 'twbs/bootstrap-slider' => $corePath . 'bootstrap-slider.min', 'jquery/autocomplete' => $corePath . 'jquery.autocomplete', 'd3' => $corePath . 'd3/d3'];
     foreach ($loadedExtensions as $packageName) {
         $fullJsPath = 'EXT:' . $packageName . '/Resources/Public/JavaScript/';
         $fullJsPath = GeneralUtility::getFileAbsFileName($fullJsPath);
         $fullJsPath = PathUtility::getAbsoluteWebPath($fullJsPath);
         $fullJsPath = rtrim($fullJsPath, '/');
         if ($fullJsPath) {
             $requireJsConfig['paths']['TYPO3/CMS/' . GeneralUtility::underscoredToUpperCamelCase($packageName)] = $fullJsPath;
         }
     }
     // check if additional AMD modules need to be loaded if a single AMD module is initialized
     if (is_array($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['RequireJS']['postInitializationModules'])) {
         $this->addInlineSettingArray('RequireJS.PostInitializationModules', $GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['RequireJS']['postInitializationModules']);
     }
     return $requireJsConfig;
 }
 /**
  * @test
  */
 public function hmacReturnsNoEqualHashesForNonEqualInput()
 {
     $msg0 = 'message0';
     $msg1 = 'message1';
     $this->assertNotEquals(Utility\GeneralUtility::hmac($msg0), Utility\GeneralUtility::hmac($msg1));
 }
 /**
  * Sends a header "Location" to jumpUrl, if jumpurl is set.
  * Will exit if a location header is sent (for instance if jumpUrl was triggered)
  *
  * "jumpUrl" is a concept where external links are redirected from the index_ts.php script, which first logs the URL.
  *
  * @return void
  * @todo Define visibility
  */
 public function jumpUrl()
 {
     if ($this->jumpurl) {
         if (\TYPO3\CMS\Core\Utility\GeneralUtility::_GP('juSecure')) {
             $locationData = (string) \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('locationData');
             // Need a type cast here because mimeType is optional!
             $mimeType = (string) \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('mimeType');
             $hArr = array($this->jumpurl, $locationData, $mimeType);
             $calcJuHash = \TYPO3\CMS\Core\Utility\GeneralUtility::hmac(serialize($hArr));
             $juHash = (string) \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('juHash');
             if ($juHash === $calcJuHash) {
                 if ($this->locDataCheck($locationData)) {
                     // 211002 - goes with cObj->filelink() rawurlencode() of filenames so spaces can be allowed.
                     $this->jumpurl = rawurldecode($this->jumpurl);
                     // Deny access to files that match TYPO3_CONF_VARS[SYS][fileDenyPattern] and whose parent directory is typo3conf/ (there could be a backup file in typo3conf/ which does not match against the fileDenyPattern)
                     $absoluteFileName = \TYPO3\CMS\Core\Utility\GeneralUtility::getFileAbsFileName(\TYPO3\CMS\Core\Utility\GeneralUtility::resolveBackPath($this->jumpurl), FALSE);
                     if (\TYPO3\CMS\Core\Utility\GeneralUtility::isAllowedAbsPath($absoluteFileName) && \TYPO3\CMS\Core\Utility\GeneralUtility::verifyFilenameAgainstDenyPattern($absoluteFileName) && !\TYPO3\CMS\Core\Utility\GeneralUtility::isFirstPartOfStr($absoluteFileName, PATH_site . 'typo3conf')) {
                         if (@is_file($absoluteFileName)) {
                             $mimeType = $mimeType ? $mimeType : 'application/octet-stream';
                             header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
                             header('Content-Type: ' . $mimeType);
                             header('Content-Disposition: attachment; filename="' . basename($absoluteFileName) . '"');
                             readfile($absoluteFileName);
                             die;
                         } else {
                             throw new \Exception('jumpurl Secure: "' . $this->jumpurl . '" was not a valid file!', 1294585193);
                         }
                     } else {
                         throw new \Exception('jumpurl Secure: The requested file was not allowed to be accessed through jumpUrl (path or file not allowed)!', 1294585194);
                     }
                 } else {
                     throw new \Exception('jumpurl Secure: locationData, ' . $locationData . ', was not accessible.', 1294585195);
                 }
             } else {
                 throw new \Exception('jumpurl Secure: Calculated juHash did not match the submitted juHash.', 1294585196);
             }
         } else {
             $TSConf = $this->getPagesTSconfig();
             if ($TSConf['TSFE.']['jumpUrl_transferSession']) {
                 $uParts = parse_url($this->jumpurl);
                 $params = '&FE_SESSION_KEY=' . rawurlencode($this->fe_user->id . '-' . md5($this->fe_user->id . '/' . $this->TYPO3_CONF_VARS['SYS']['encryptionKey']));
                 // Add the session parameter ...
                 $this->jumpurl .= ($uParts['query'] ? '' : '?') . $params;
             }
             if ($TSConf['TSFE.']['jumpURL_HTTPStatusCode']) {
                 switch (intval($TSConf['TSFE.']['jumpURL_HTTPStatusCode'])) {
                     case 301:
                         $statusCode = \TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_301;
                         break;
                     case 302:
                         $statusCode = \TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_302;
                         break;
                     case 307:
                         $statusCode = \TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_307;
                         break;
                     case 303:
                     default:
                         $statusCode = \TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_303;
                         break;
                 }
             }
             \TYPO3\CMS\Core\Utility\HttpUtility::redirect($this->jumpurl, $statusCode);
         }
     }
 }
 /**
  * Rendering the cObject, FORM
  *
  * Note on $formData:
  * In the optional $formData array each entry represents a line in the ordinary setup.
  * In those entries each entry (0,1,2...) represents a space normally divided by the '|' line.
  *
  * $formData [] = array('Name:', 'name=input, 25 ', 'Default value....');
  * $formData [] = array('Email:', 'email=input, 25 ', 'Default value for email....');
  *
  * - corresponds to the $conf['data'] value being :
  * Name:|name=input, 25 |Default value....||Email:|email=input, 25 |Default value for email....
  *
  * If $formData is an array the value of $conf['data'] is ignored.
  *
  * @param array $conf Array of TypoScript properties
  * @param array $formData Alternative formdata overriding whatever comes from TypoScript
  * @return string Output
  */
 public function render($conf = array(), $formData = '')
 {
     $content = '';
     if (is_array($formData)) {
         $dataArray = $formData;
     } else {
         $data = isset($conf['data.']) ? $this->cObj->stdWrap($conf['data'], $conf['data.']) : $conf['data'];
         // Clearing dataArr
         $dataArray = array();
         // Getting the original config
         if (trim($data)) {
             $data = str_replace(LF, '||', $data);
             $dataArray = explode('||', $data);
         }
         // Adding the new dataArray config form:
         if (is_array($conf['dataArray.'])) {
             // dataArray is supplied
             $sortedKeyArray = \TYPO3\CMS\Core\TypoScript\TemplateService::sortedKeyList($conf['dataArray.'], true);
             foreach ($sortedKeyArray as $theKey) {
                 $singleKeyArray = $conf['dataArray.'][$theKey . '.'];
                 if (is_array($singleKeyArray)) {
                     $temp = array();
                     $label = isset($singleKeyArray['label.']) ? $this->cObj->stdWrap($singleKeyArray['label'], $singleKeyArray['label.']) : $singleKeyArray['label'];
                     list($temp[0]) = explode('|', $label);
                     $type = isset($singleKeyArray['type.']) ? $this->cObj->stdWrap($singleKeyArray['type'], $singleKeyArray['type.']) : $singleKeyArray['type'];
                     list($temp[1]) = explode('|', $type);
                     $required = isset($singleKeyArray['required.']) ? $this->cObj->stdWrap($singleKeyArray['required'], $singleKeyArray['required.']) : $singleKeyArray['required'];
                     if ($required) {
                         $temp[1] = '*' . $temp[1];
                     }
                     $singleValue = isset($singleKeyArray['value.']) ? $this->cObj->stdWrap($singleKeyArray['value'], $singleKeyArray['value.']) : $singleKeyArray['value'];
                     list($temp[2]) = explode('|', $singleValue);
                     // If value array is set, then implode those values.
                     if (is_array($singleKeyArray['valueArray.'])) {
                         $temp_accumulated = array();
                         foreach ($singleKeyArray['valueArray.'] as $singleKey => $singleKey_valueArray) {
                             if (is_array($singleKey_valueArray) && (int) $singleKey . '.' === (string) $singleKey) {
                                 $temp_valueArray = array();
                                 $valueArrayLabel = isset($singleKey_valueArray['label.']) ? $this->cObj->stdWrap($singleKey_valueArray['label'], $singleKey_valueArray['label.']) : $singleKey_valueArray['label'];
                                 list($temp_valueArray[0]) = explode('=', $valueArrayLabel);
                                 $selected = isset($singleKey_valueArray['selected.']) ? $this->cObj->stdWrap($singleKey_valueArray['selected'], $singleKey_valueArray['selected.']) : $singleKey_valueArray['selected'];
                                 if ($selected) {
                                     $temp_valueArray[0] = '*' . $temp_valueArray[0];
                                 }
                                 $singleKeyValue = isset($singleKey_valueArray['value.']) ? $this->cObj->stdWrap($singleKey_valueArray['value'], $singleKey_valueArray['value.']) : $singleKey_valueArray['value'];
                                 list($temp_valueArray[1]) = explode(',', $singleKeyValue);
                             }
                             $temp_accumulated[] = implode('=', $temp_valueArray);
                         }
                         $temp[2] = implode(',', $temp_accumulated);
                     }
                     $specialEval = isset($singleKeyArray['specialEval.']) ? $this->cObj->stdWrap($singleKeyArray['specialEval'], $singleKeyArray['specialEval.']) : $singleKeyArray['specialEval'];
                     list($temp[3]) = explode('|', $specialEval);
                     // Adding the form entry to the dataArray
                     $dataArray[] = implode('|', $temp);
                 }
             }
         }
     }
     $attachmentCounter = '';
     $hiddenfields = '';
     $fieldlist = array();
     $propertyOverride = array();
     $fieldname_hashArray = array();
     $counter = 0;
     $xhtmlStrict = GeneralUtility::inList('xhtml_strict,xhtml_11,xhtml_2', $GLOBALS['TSFE']->xhtmlDoctype);
     // Formname
     $formName = isset($conf['formName.']) ? $this->cObj->stdWrap($conf['formName'], $conf['formName.']) : $conf['formName'];
     $formName = $this->cleanFormName($formName);
     $formName = $GLOBALS['TSFE']->getUniqueId($formName);
     $fieldPrefix = isset($conf['fieldPrefix.']) ? $this->cObj->stdWrap($conf['fieldPrefix'], $conf['fieldPrefix.']) : $conf['fieldPrefix'];
     if (isset($conf['fieldPrefix']) || isset($conf['fieldPrefix.'])) {
         if ($fieldPrefix) {
             $prefix = $this->cleanFormName($fieldPrefix);
         } else {
             $prefix = '';
         }
     } else {
         $prefix = $formName;
     }
     foreach ($dataArray as $dataValue) {
         $counter++;
         $confData = array();
         if (is_array($formData)) {
             $parts = $dataValue;
             // TRUE...
             $dataValue = 1;
         } else {
             $dataValue = trim($dataValue);
             $parts = explode('|', $dataValue);
         }
         if ($dataValue && strcspn($dataValue, '#/')) {
             // label:
             $confData['label'] = GeneralUtility::removeXSS(trim($parts[0]));
             // field:
             $fParts = explode(',', $parts[1]);
             $fParts[0] = trim($fParts[0]);
             if ($fParts[0][0] === '*') {
                 $confData['required'] = 1;
                 $fParts[0] = substr($fParts[0], 1);
             }
             $typeParts = explode('=', $fParts[0]);
             $confData['type'] = trim(strtolower(end($typeParts)));
             if (count($typeParts) === 1) {
                 $confData['fieldname'] = $this->cleanFormName($parts[0]);
                 if (strtolower(preg_replace('/[^[:alnum:]]/', '', $confData['fieldname'])) == 'email') {
                     $confData['fieldname'] = 'email';
                 }
                 // Duplicate fieldnames resolved
                 if (isset($fieldname_hashArray[md5($confData['fieldname'])])) {
                     $confData['fieldname'] .= '_' . $counter;
                 }
                 $fieldname_hashArray[md5($confData['fieldname'])] = $confData['fieldname'];
                 // Attachment names...
                 if ($confData['type'] == 'file') {
                     $confData['fieldname'] = 'attachment' . $attachmentCounter;
                     $attachmentCounter = (int) $attachmentCounter + 1;
                 }
             } else {
                 $confData['fieldname'] = str_replace(' ', '_', trim($typeParts[0]));
             }
             $confData['fieldname'] = htmlspecialchars($confData['fieldname']);
             $fieldCode = '';
             $wrapFieldName = isset($conf['wrapFieldName']) ? $this->cObj->stdWrap($conf['wrapFieldName'], $conf['wrapFieldName.']) : $conf['wrapFieldName'];
             if ($wrapFieldName) {
                 $confData['fieldname'] = $this->cObj->wrap($confData['fieldname'], $wrapFieldName);
             }
             // Set field name as current:
             $this->cObj->setCurrentVal($confData['fieldname']);
             // Additional parameters
             if (trim($confData['type'])) {
                 if (isset($conf['params.'][$confData['type']])) {
                     $addParams = isset($conf['params.'][$confData['type'] . '.']) ? trim($this->cObj->stdWrap($conf['params.'][$confData['type']], $conf['params.'][$confData['type'] . '.'])) : trim($conf['params.'][$confData['type']]);
                 } else {
                     $addParams = isset($conf['params.']) ? trim($this->cObj->stdWrap($conf['params'], $conf['params.'])) : trim($conf['params']);
                 }
                 if ((string) $addParams !== '') {
                     $addParams = ' ' . $addParams;
                 }
             } else {
                 $addParams = '';
             }
             $dontMd5FieldNames = isset($conf['dontMd5FieldNames.']) ? $this->cObj->stdWrap($conf['dontMd5FieldNames'], $conf['dontMd5FieldNames.']) : $conf['dontMd5FieldNames'];
             if ($dontMd5FieldNames) {
                 $fName = $confData['fieldname'];
             } else {
                 $fName = md5($confData['fieldname']);
             }
             // Accessibility: Set id = fieldname attribute:
             $accessibility = isset($conf['accessibility.']) ? $this->cObj->stdWrap($conf['accessibility'], $conf['accessibility.']) : $conf['accessibility'];
             if ($accessibility || $xhtmlStrict) {
                 $elementIdAttribute = ' id="' . $prefix . $fName . '"';
             } else {
                 $elementIdAttribute = '';
             }
             // Create form field based on configuration/type:
             switch ($confData['type']) {
                 case 'textarea':
                     $cols = trim($fParts[1]) ? (int) $fParts[1] : 20;
                     $compensateFieldWidth = isset($conf['compensateFieldWidth.']) ? $this->cObj->stdWrap($conf['compensateFieldWidth'], $conf['compensateFieldWidth.']) : $conf['compensateFieldWidth'];
                     $compWidth = doubleval($compensateFieldWidth ? $compensateFieldWidth : $GLOBALS['TSFE']->compensateFieldWidth);
                     $compWidth = $compWidth ? $compWidth : 1;
                     $cols = \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($cols * $compWidth, 1, 120);
                     $rows = trim($fParts[2]) ? \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($fParts[2], 1, 30) : 5;
                     $wrap = trim($fParts[3]);
                     $noWrapAttr = isset($conf['noWrapAttr.']) ? $this->cObj->stdWrap($conf['noWrapAttr'], $conf['noWrapAttr.']) : $conf['noWrapAttr'];
                     if ($noWrapAttr || $wrap === 'disabled') {
                         $wrap = '';
                     } else {
                         $wrap = $wrap ? ' wrap="' . $wrap . '"' : ' wrap="virtual"';
                     }
                     $noValueInsert = isset($conf['noValueInsert.']) ? $this->cObj->stdWrap($conf['noValueInsert'], $conf['noValueInsert.']) : $conf['noValueInsert'];
                     $default = $this->getFieldDefaultValue($noValueInsert, $confData['fieldname'], str_replace('\\n', LF, trim($parts[2])));
                     $fieldCode = sprintf('<textarea name="%s"%s cols="%s" rows="%s"%s%s>%s</textarea>', $confData['fieldname'], $elementIdAttribute, $cols, $rows, $wrap, $addParams, htmlspecialchars($default));
                     break;
                 case 'input':
                 case 'password':
                     $size = trim($fParts[1]) ? (int) $fParts[1] : 20;
                     $compensateFieldWidth = isset($conf['compensateFieldWidth.']) ? $this->cObj->stdWrap($conf['compensateFieldWidth'], $conf['compensateFieldWidth.']) : $conf['compensateFieldWidth'];
                     $compWidth = doubleval($compensateFieldWidth ? $compensateFieldWidth : $GLOBALS['TSFE']->compensateFieldWidth);
                     $compWidth = $compWidth ? $compWidth : 1;
                     $size = \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($size * $compWidth, 1, 120);
                     $noValueInsert = isset($conf['noValueInsert.']) ? $this->cObj->stdWrap($conf['noValueInsert'], $conf['noValueInsert.']) : $conf['noValueInsert'];
                     $default = $this->getFieldDefaultValue($noValueInsert, $confData['fieldname'], trim($parts[2]));
                     if ($confData['type'] == 'password') {
                         $default = '';
                     }
                     $max = trim($fParts[2]) ? ' maxlength="' . \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($fParts[2], 1, 1000) . '"' : '';
                     $theType = $confData['type'] == 'input' ? 'text' : 'password';
                     $fieldCode = sprintf('<input type="%s" name="%s"%s size="%s"%s value="%s"%s />', $theType, $confData['fieldname'], $elementIdAttribute, $size, $max, htmlspecialchars($default), $addParams);
                     break;
                 case 'file':
                     $size = trim($fParts[1]) ? \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($fParts[1], 1, 60) : 20;
                     $fieldCode = sprintf('<input type="file" name="%s"%s size="%s"%s />', $confData['fieldname'], $elementIdAttribute, $size, $addParams);
                     break;
                 case 'check':
                     // alternative default value:
                     $noValueInsert = isset($conf['noValueInsert.']) ? $this->cObj->stdWrap($conf['noValueInsert'], $conf['noValueInsert.']) : $conf['noValueInsert'];
                     $default = $this->getFieldDefaultValue($noValueInsert, $confData['fieldname'], trim($parts[2]));
                     $checked = $default ? ' checked="checked"' : '';
                     $fieldCode = sprintf('<input type="checkbox" value="%s" name="%s"%s%s%s />', 1, $confData['fieldname'], $elementIdAttribute, $checked, $addParams);
                     break;
                 case 'select':
                     $option = '';
                     $valueParts = explode(',', $parts[2]);
                     // size
                     if (strtolower(trim($fParts[1])) == 'auto') {
                         $fParts[1] = count($valueParts);
                     }
                     // Auto size set here. Max 20
                     $size = trim($fParts[1]) ? \TYPO3\CMS\Core\Utility\MathUtility::forceIntegerInRange($fParts[1], 1, 20) : 1;
                     // multiple
                     $multiple = strtolower(trim($fParts[2])) == 'm' ? ' multiple="multiple"' : '';
                     // Where the items will be
                     $items = array();
                     //RTF
                     $defaults = array();
                     $pCount = count($valueParts);
                     for ($a = 0; $a < $pCount; $a++) {
                         $valueParts[$a] = trim($valueParts[$a]);
                         // Finding default value
                         if ($valueParts[$a][0] === '*') {
                             $sel = 'selected';
                             $valueParts[$a] = substr($valueParts[$a], 1);
                         } else {
                             $sel = '';
                         }
                         // Get value/label
                         $subParts = explode('=', $valueParts[$a]);
                         // Sets the value
                         $subParts[1] = isset($subParts[1]) ? trim($subParts[1]) : trim($subParts[0]);
                         // Adds the value/label pair to the items-array
                         $items[] = $subParts;
                         if ($sel) {
                             $defaults[] = $subParts[1];
                         }
                     }
                     // alternative default value:
                     $noValueInsert = isset($conf['noValueInsert.']) ? $this->cObj->stdWrap($conf['noValueInsert'], $conf['noValueInsert.']) : $conf['noValueInsert'];
                     $default = $this->getFieldDefaultValue($noValueInsert, $confData['fieldname'], $defaults);
                     if (!is_array($default)) {
                         $defaults = array();
                         $defaults[] = $default;
                     } else {
                         $defaults = $default;
                     }
                     // Create the select-box:
                     $iCount = count($items);
                     for ($a = 0; $a < $iCount; $a++) {
                         $option .= '<option value="' . $items[$a][1] . '"' . (in_array($items[$a][1], $defaults) ? ' selected="selected"' : '') . '>' . trim($items[$a][0]) . '</option>';
                     }
                     if ($multiple) {
                         // The fieldname must be prepended '[]' if multiple select. And the reason why it's prepended is, because the required-field list later must also have [] prepended.
                         $confData['fieldname'] .= '[]';
                     }
                     $fieldCode = sprintf('<select name="%s"%s size="%s"%s%s>%s</select>', $confData['fieldname'], $elementIdAttribute, $size, $multiple, $addParams, $option);
                     //RTF
                     break;
                 case 'radio':
                     $option = '';
                     $valueParts = explode(',', $parts[2]);
                     // Where the items will be
                     $items = array();
                     $default = '';
                     $pCount = count($valueParts);
                     for ($a = 0; $a < $pCount; $a++) {
                         $valueParts[$a] = trim($valueParts[$a]);
                         if ($valueParts[$a][0] === '*') {
                             $sel = 'checked';
                             $valueParts[$a] = substr($valueParts[$a], 1);
                         } else {
                             $sel = '';
                         }
                         // Get value/label
                         $subParts = explode('=', $valueParts[$a]);
                         // Sets the value
                         $subParts[1] = isset($subParts[1]) ? trim($subParts[1]) : trim($subParts[0]);
                         // Adds the value/label pair to the items-array
                         $items[] = $subParts;
                         if ($sel) {
                             $default = $subParts[1];
                         }
                     }
                     // alternative default value:
                     $noValueInsert = isset($conf['noValueInsert.']) ? $this->cObj->stdWrap($conf['noValueInsert'], $conf['noValueInsert.']) : $conf['noValueInsert'];
                     $default = $this->getFieldDefaultValue($noValueInsert, $confData['fieldname'], $default);
                     // Create the select-box:
                     $iCount = count($items);
                     for ($a = 0; $a < $iCount; $a++) {
                         $optionParts = '';
                         $radioId = $prefix . $fName . $this->cleanFormName($items[$a][0]);
                         if ($accessibility) {
                             $radioLabelIdAttribute = ' id="' . $radioId . '"';
                         } else {
                             $radioLabelIdAttribute = '';
                         }
                         $optionParts .= '<input type="radio" name="' . $confData['fieldname'] . '"' . $radioLabelIdAttribute . ' value="' . $items[$a][1] . '"' . ((string) $items[$a][1] === (string) $default ? ' checked="checked"' : '') . $addParams . ' />';
                         if ($accessibility) {
                             $label = isset($conf['radioWrap.']) ? $this->cObj->stdWrap(trim($items[$a][0]), $conf['radioWrap.']) : trim($items[$a][0]);
                             $optionParts .= '<label for="' . $radioId . '">' . $label . '</label>';
                         } else {
                             $optionParts .= isset($conf['radioWrap.']) ? $this->cObj->stdWrap(trim($items[$a][0]), $conf['radioWrap.']) : trim($items[$a][0]);
                         }
                         $option .= isset($conf['radioInputWrap.']) ? $this->cObj->stdWrap($optionParts, $conf['radioInputWrap.']) : $optionParts;
                     }
                     if ($accessibility) {
                         $accessibilityWrap = isset($conf['radioWrap.']['accessibilityWrap.']) ? $this->cObj->stdWrap($conf['radioWrap.']['accessibilityWrap'], $conf['radioWrap.']['accessibilityWrap.']) : $conf['radioWrap.']['accessibilityWrap'];
                         if ($accessibilityWrap) {
                             $search = array('###RADIO_FIELD_ID###', '###RADIO_GROUP_LABEL###');
                             $replace = array($elementIdAttribute, $confData['label']);
                             $accessibilityWrap = str_replace($search, $replace, $accessibilityWrap);
                             $option = $this->cObj->wrap($option, $accessibilityWrap);
                         }
                     }
                     $fieldCode = $option;
                     break;
                 case 'hidden':
                     $value = trim($parts[2]);
                     // If this form includes an auto responder message, include a HMAC checksum field
                     // in order to verify potential abuse of this feature.
                     if ($value !== '') {
                         if (GeneralUtility::inList($confData['fieldname'], 'auto_respond_msg')) {
                             $hmacChecksum = GeneralUtility::hmac($value, 'content_form');
                             $hiddenfields .= sprintf('<input type="hidden" name="auto_respond_checksum" id="%sauto_respond_checksum" value="%s" />', $prefix, $hmacChecksum);
                         }
                         if (GeneralUtility::inList('recipient_copy,recipient', $confData['fieldname']) && $GLOBALS['TYPO3_CONF_VARS']['FE']['secureFormmail']) {
                             break;
                         }
                         if (GeneralUtility::inList('recipient_copy,recipient', $confData['fieldname'])) {
                             $value = \TYPO3\CMS\Compatibility6\Utility\FormUtility::codeString($value);
                         }
                     }
                     $hiddenfields .= sprintf('<input type="hidden" name="%s"%s value="%s" />', $confData['fieldname'], $elementIdAttribute, htmlspecialchars($value));
                     break;
                 case 'property':
                     if (GeneralUtility::inList('type,locationData,goodMess,badMess,emailMess', $confData['fieldname'])) {
                         $value = trim($parts[2]);
                         $propertyOverride[$confData['fieldname']] = $value;
                         $conf[$confData['fieldname']] = $value;
                     }
                     break;
                 case 'submit':
                     $value = trim($parts[2]);
                     if ($conf['image.']) {
                         $this->cObj->data[$this->cObj->currentValKey] = $value;
                         $image = $this->cObj->cObjGetSingle('IMG_RESOURCE', $conf['image.']);
                         $params = $conf['image.']['params'] ? ' ' . $conf['image.']['params'] : '';
                         $params .= $this->cObj->getAltParam($conf['image.'], false);
                         $params .= $addParams;
                     } else {
                         $image = '';
                     }
                     if ($image) {
                         $fieldCode = sprintf('<input type="image" name="%s"%s src="%s"%s />', $confData['fieldname'], $elementIdAttribute, $image, $params);
                     } else {
                         $fieldCode = sprintf('<input type="submit" name="%s"%s value="%s"%s />', $confData['fieldname'], $elementIdAttribute, htmlspecialchars($value, ENT_COMPAT, 'UTF-8', false), $addParams);
                     }
                     break;
                 case 'reset':
                     $value = trim($parts[2]);
                     $fieldCode = sprintf('<input type="reset" name="%s"%s value="%s"%s />', $confData['fieldname'], $elementIdAttribute, htmlspecialchars($value, ENT_COMPAT, 'UTF-8', false), $addParams);
                     break;
                 case 'label':
                     $fieldCode = nl2br(htmlspecialchars(trim($parts[2])));
                     break;
                 default:
                     $confData['type'] = 'comment';
                     $fieldCode = trim($parts[2]) . '&nbsp;';
             }
             if ($fieldCode) {
                 // Checking for special evaluation modes:
                 if (trim($parts[3]) !== '' && GeneralUtility::inList('textarea,input,password', $confData['type'])) {
                     $modeParameters = GeneralUtility::trimExplode(':', $parts[3]);
                 } else {
                     $modeParameters = array();
                 }
                 // Adding evaluation based on settings:
                 switch ((string) $modeParameters[0]) {
                     case 'EREG':
                         $fieldlist[] = '_EREG';
                         $fieldlist[] = $modeParameters[1];
                         $fieldlist[] = $modeParameters[2];
                         $fieldlist[] = $confData['fieldname'];
                         $fieldlist[] = $confData['label'];
                         // Setting this so "required" layout is used.
                         $confData['required'] = 1;
                         break;
                     case 'EMAIL':
                         $fieldlist[] = '_EMAIL';
                         $fieldlist[] = $confData['fieldname'];
                         $fieldlist[] = $confData['label'];
                         // Setting this so "required" layout is used.
                         $confData['required'] = 1;
                         break;
                     default:
                         if ($confData['required']) {
                             $fieldlist[] = $confData['fieldname'];
                             $fieldlist[] = $confData['label'];
                         }
                 }
                 // Field:
                 $fieldLabel = $confData['label'];
                 if ($accessibility && trim($fieldLabel) && !preg_match('/^(label|hidden|comment)$/', $confData['type'])) {
                     $fieldLabel = '<label for="' . $prefix . $fName . '">' . $fieldLabel . '</label>';
                 }
                 // Getting template code:
                 if (isset($conf['fieldWrap.'])) {
                     $fieldCode = $this->cObj->stdWrap($fieldCode, $conf['fieldWrap.']);
                 }
                 $labelCode = isset($conf['labelWrap.']) ? $this->cObj->stdWrap($fieldLabel, $conf['labelWrap.']) : $fieldLabel;
                 $commentCode = isset($conf['commentWrap.']) ? $this->cObj->stdWrap($confData['label'], $conf['commentWrap.']) : $confData['label'];
                 $result = $conf['layout'];
                 $req = isset($conf['REQ.']) ? $this->cObj->stdWrap($conf['REQ'], $conf['REQ.']) : $conf['REQ'];
                 if ($req && $confData['required']) {
                     if (isset($conf['REQ.']['fieldWrap.'])) {
                         $fieldCode = $this->cObj->stdWrap($fieldCode, $conf['REQ.']['fieldWrap.']);
                     }
                     if (isset($conf['REQ.']['labelWrap.'])) {
                         $labelCode = $this->cObj->stdWrap($fieldLabel, $conf['REQ.']['labelWrap.']);
                     }
                     $reqLayout = isset($conf['REQ.']['layout.']) ? $this->cObj->stdWrap($conf['REQ.']['layout'], $conf['REQ.']['layout.']) : $conf['REQ.']['layout'];
                     if ($reqLayout) {
                         $result = $reqLayout;
                     }
                 }
                 if ($confData['type'] == 'comment') {
                     $commentLayout = isset($conf['COMMENT.']['layout.']) ? $this->cObj->stdWrap($conf['COMMENT.']['layout'], $conf['COMMENT.']['layout.']) : $conf['COMMENT.']['layout'];
                     if ($commentLayout) {
                         $result = $commentLayout;
                     }
                 }
                 if ($confData['type'] == 'check') {
                     $checkLayout = isset($conf['CHECK.']['layout.']) ? $this->cObj->stdWrap($conf['CHECK.']['layout'], $conf['CHECK.']['layout.']) : $conf['CHECK.']['layout'];
                     if ($checkLayout) {
                         $result = $checkLayout;
                     }
                 }
                 if ($confData['type'] == 'radio') {
                     $radioLayout = isset($conf['RADIO.']['layout.']) ? $this->cObj->stdWrap($conf['RADIO.']['layout'], $conf['RADIO.']['layout.']) : $conf['RADIO.']['layout'];
                     if ($radioLayout) {
                         $result = $radioLayout;
                     }
                 }
                 if ($confData['type'] == 'label') {
                     $labelLayout = isset($conf['LABEL.']['layout.']) ? $this->cObj->stdWrap($conf['LABEL.']['layout'], $conf['LABEL.']['layout.']) : $conf['LABEL.']['layout'];
                     if ($labelLayout) {
                         $result = $labelLayout;
                     }
                 }
                 //RTF
                 $content .= str_replace(array('###FIELD###', '###LABEL###', '###COMMENT###'), array($fieldCode, $labelCode, $commentCode), $result);
             }
         }
     }
     if (isset($conf['stdWrap.'])) {
         $content = $this->cObj->stdWrap($content, $conf['stdWrap.']);
     }
     // Redirect (external: where to go afterwards. internal: where to submit to)
     $theRedirect = isset($conf['redirect.']) ? $this->cObj->stdWrap($conf['redirect'], $conf['redirect.']) : $conf['redirect'];
     // redirect should be set to the page to redirect to after an external script has been used. If internal scripts is used, and if no 'type' is set that dictates otherwise, redirect is used as the url to jump to as long as it's an integer (page)
     $target = isset($conf['target.']) ? $this->cObj->stdWrap($conf['target'], $conf['target.']) : $conf['target'];
     // redirect should be set to the page to redirect to after an external script has been used. If internal scripts is used, and if no 'type' is set that dictates otherwise, redirect is used as the url to jump to as long as it's an integer (page)
     $noCache = isset($conf['no_cache.']) ? $this->cObj->stdWrap($conf['no_cache'], $conf['no_cache.']) : $conf['no_cache'];
     // redirect should be set to the page to redirect to after an external script has been used. If internal scripts is used, and if no 'type' is set that dictates otherwise, redirect is used as the url to jump to as long as it's an integer (page)
     $page = $GLOBALS['TSFE']->page;
     // Internal: Just submit to current page
     if (!$theRedirect) {
         $LD = $GLOBALS['TSFE']->tmpl->linkData($page, $target, $noCache, 'index.php', '', $this->cObj->getClosestMPvalueForPage($page['uid']));
     } elseif (\TYPO3\CMS\Core\Utility\MathUtility::canBeInterpretedAsInteger($theRedirect)) {
         // Internal: Submit to page with ID $theRedirect
         $page = $GLOBALS['TSFE']->sys_page->getPage_noCheck($theRedirect);
         $LD = $GLOBALS['TSFE']->tmpl->linkData($page, $target, $noCache, 'index.php', '', $this->cObj->getClosestMPvalueForPage($page['uid']));
     } else {
         // External URL, redirect-hidden field is rendered!
         $LD = $GLOBALS['TSFE']->tmpl->linkData($page, $target, $noCache, '', '', $this->cObj->getClosestMPvalueForPage($page['uid']));
         $LD['totalURL'] = $theRedirect;
         $hiddenfields .= '<input type="hidden" name="redirect" value="' . htmlspecialchars($LD['totalURL']) . '" />';
     }
     // Formtype (where to submit to!):
     if ($propertyOverride['type']) {
         $formtype = $propertyOverride['type'];
     } else {
         $formtype = isset($conf['type.']) ? $this->cObj->stdWrap($conf['type'], $conf['type.']) : $conf['type'];
     }
     // Submit to a specific page
     if (\TYPO3\CMS\Core\Utility\MathUtility::canBeInterpretedAsInteger($formtype)) {
         $page = $GLOBALS['TSFE']->sys_page->getPage_noCheck($formtype);
         $LD_A = $GLOBALS['TSFE']->tmpl->linkData($page, $target, $noCache, '', '', $this->cObj->getClosestMPvalueForPage($page['uid']));
         $action = $LD_A['totalURL'];
     } elseif ($formtype) {
         // Submit to external script
         $LD_A = $LD;
         $action = $formtype;
     } elseif (\TYPO3\CMS\Core\Utility\MathUtility::canBeInterpretedAsInteger($theRedirect)) {
         $LD_A = $LD;
         $action = $LD_A['totalURL'];
     } else {
         // Submit to "nothing" - which is current page
         $LD_A = $GLOBALS['TSFE']->tmpl->linkData($GLOBALS['TSFE']->page, $target, $noCache, '', '', $this->cObj->getClosestMPvalueForPage($page['uid']));
         $action = $LD_A['totalURL'];
     }
     // Recipient:
     $theEmail = isset($conf['recipient.']) ? $this->cObj->stdWrap($conf['recipient'], $conf['recipient.']) : $conf['recipient'];
     if ($theEmail && !$GLOBALS['TYPO3_CONF_VARS']['FE']['secureFormmail']) {
         $theEmail = \TYPO3\CMS\Compatibility6\Utility\FormUtility::codeString($theEmail);
         $hiddenfields .= '<input type="hidden" name="recipient" value="' . htmlspecialchars($theEmail) . '" />';
     }
     // location data:
     $location = isset($conf['locationData.']) ? $this->cObj->stdWrap($conf['locationData'], $conf['locationData.']) : $conf['locationData'];
     if ($location) {
         if ($location == 'HTTP_POST_VARS' && isset($_POST['locationData'])) {
             $locationData = GeneralUtility::_POST('locationData');
         } else {
             // locationData is [the page id]:[tablename]:[uid of record]. Indicates on which page the record (from tablename with uid) is shown. Used to check access.
             if (isset($this->data['_LOCALIZED_UID'])) {
                 $locationData = $GLOBALS['TSFE']->id . ':' . str_replace($this->data['uid'], $this->data['_LOCALIZED_UID'], $this->cObj->currentRecord);
             } else {
                 $locationData = $GLOBALS['TSFE']->id . ':' . $this->cObj->currentRecord;
             }
         }
         $hiddenfields .= '<input type="hidden" name="locationData" value="' . htmlspecialchars($locationData) . '" />';
     }
     // Hidden fields:
     if (is_array($conf['hiddenFields.'])) {
         foreach ($conf['hiddenFields.'] as $hF_key => $hF_conf) {
             if (substr($hF_key, -1) != '.') {
                 $hF_value = $this->cObj->cObjGetSingle($hF_conf, $conf['hiddenFields.'][$hF_key . '.'], 'hiddenfields');
                 if ((string) $hF_value !== '' && GeneralUtility::inList('recipient_copy,recipient', $hF_key)) {
                     if ($GLOBALS['TYPO3_CONF_VARS']['FE']['secureFormmail']) {
                         continue;
                     }
                     $hF_value = \TYPO3\CMS\Compatibility6\Utility\FormUtility::codeString($hF_value);
                 }
                 $hiddenfields .= '<input type="hidden" name="' . $hF_key . '" value="' . htmlspecialchars($hF_value) . '" />';
             }
         }
     }
     // Wrap all hidden fields in a div tag (see http://forge.typo3.org/issues/14491)
     $hiddenfields = isset($conf['hiddenFields.']['stdWrap.']) ? $this->cObj->stdWrap($hiddenfields, $conf['hiddenFields.']['stdWrap.']) : '<div style="display:none;">' . $hiddenfields . '</div>';
     if ($conf['REQ']) {
         $goodMess = isset($conf['goodMess.']) ? $this->cObj->stdWrap($conf['goodMess'], $conf['goodMess.']) : $conf['goodMess'];
         $badMess = isset($conf['badMess.']) ? $this->cObj->stdWrap($conf['badMess'], $conf['badMess.']) : $conf['badMess'];
         $emailMess = isset($conf['emailMess.']) ? $this->cObj->stdWrap($conf['emailMess'], $conf['emailMess.']) : $conf['emailMess'];
         $validateForm = ' onsubmit="return validateForm(' . GeneralUtility::quoteJSvalue($formName) . ',' . GeneralUtility::quoteJSvalue(implode(',', $fieldlist)) . ',' . GeneralUtility::quoteJSvalue($goodMess) . ',' . GeneralUtility::quoteJSvalue($badMess) . ',' . GeneralUtility::quoteJSvalue($emailMess) . ')"';
         $GLOBALS['TSFE']->additionalHeaderData['JSFormValidate'] = '<script type="text/javascript" src="' . GeneralUtility::createVersionNumberedFilename($GLOBALS['TSFE']->absRefPrefix . 'typo3/sysext/compatibility6/Resources/Public/JavaScript/jsfunc.validateform.js') . '"></script>';
     } else {
         $validateForm = '';
     }
     // Create form tag:
     $theTarget = $theRedirect ? $LD['target'] : $LD_A['target'];
     $method = isset($conf['method.']) ? $this->cObj->stdWrap($conf['method'], $conf['method.']) : $conf['method'];
     $content = array('<form' . ' action="' . htmlspecialchars($action) . '"' . ' id="' . $formName . '"' . ($xhtmlStrict ? '' : ' name="' . $formName . '"') . ' enctype="multipart/form-data"' . ' method="' . ($method ? $method : 'post') . '"' . ($theTarget ? ' target="' . $theTarget . '"' : '') . $validateForm . '>', $hiddenfields . $content, '</form>');
     $arrayReturnMode = isset($conf['arrayReturnMode.']) ? $this->cObj->stdWrap($conf['arrayReturnMode'], $conf['arrayReturnMode.']) : $conf['arrayReturnMode'];
     if ($arrayReturnMode) {
         $content['validateForm'] = $validateForm;
         $content['formname'] = $formName;
         return $content;
     } else {
         return implode('', $content);
     }
 }
 /**
  * Wraps the input string in link-tags that opens the image in a new window.
  *
  * @param string $string String to wrap, probably an <img> tag
  * @param string|File|FileReference $imageFile The original image file
  * @param array $conf TypoScript properties for the "imageLinkWrap" function
  * @return string The input string, $string, wrapped as configured.
  * @see cImage()
  */
 public function imageLinkWrap($string, $imageFile, $conf)
 {
     $string = (string) $string;
     $enable = isset($conf['enable.']) ? $this->stdWrap($conf['enable'], $conf['enable.']) : $conf['enable'];
     if (!$enable) {
         return $string;
     }
     $content = (string) $this->typoLink($string, $conf['typolink.']);
     if (isset($conf['file.'])) {
         $imageFile = $this->stdWrap($imageFile, $conf['file.']);
     }
     if ($imageFile instanceof File) {
         $file = $imageFile;
     } elseif ($imageFile instanceof FileReference) {
         $file = $imageFile->getOriginalFile();
     } else {
         if (MathUtility::canBeInterpretedAsInteger($imageFile)) {
             $file = ResourceFactory::getInstance()->getFileObject((int) $imageFile);
         } else {
             $file = ResourceFactory::getInstance()->getFileObjectFromCombinedIdentifier($imageFile);
         }
     }
     // Create imageFileLink if not created with typolink
     if ($content === $string) {
         $parameterNames = array('width', 'height', 'effects', 'bodyTag', 'title', 'wrap');
         $parameters = array();
         $sample = isset($conf['sample.']) ? $this->stdWrap($conf['sample'], $conf['sample.']) : $conf['sample'];
         if ($sample) {
             $parameters['sample'] = 1;
         }
         foreach ($parameterNames as $parameterName) {
             if (isset($conf[$parameterName . '.'])) {
                 $conf[$parameterName] = $this->stdWrap($conf[$parameterName], $conf[$parameterName . '.']);
             }
             if (isset($conf[$parameterName]) && $conf[$parameterName]) {
                 $parameters[$parameterName] = $conf[$parameterName];
             }
         }
         $parametersEncoded = base64_encode(serialize($parameters));
         $hmac = GeneralUtility::hmac(implode('|', array($file->getUid(), $parametersEncoded)));
         $params = '&md5=' . $hmac;
         foreach (str_split($parametersEncoded, 64) as $index => $chunk) {
             $params .= '&parameters' . rawurlencode('[') . $index . rawurlencode(']') . '=' . rawurlencode($chunk);
         }
         $url = $this->getTypoScriptFrontendController()->absRefPrefix . 'index.php?eID=tx_cms_showpic&file=' . $file->getUid() . $params;
         $directImageLink = isset($conf['directImageLink.']) ? $this->stdWrap($conf['directImageLink'], $conf['directImageLink.']) : $conf['directImageLink'];
         if ($directImageLink) {
             $imgResourceConf = array('file' => $imageFile, 'file.' => $conf);
             $url = $this->cObjGetSingle('IMG_RESOURCE', $imgResourceConf);
             if (!$url) {
                 // If no imagemagick / gm is available
                 $url = $imageFile;
             }
         }
         // Create TARGET-attribute only if the right doctype is used
         $target = '';
         $xhtmlDocType = $this->getTypoScriptFrontendController()->xhtmlDoctype;
         if ($xhtmlDocType !== 'xhtml_strict' && $xhtmlDocType !== 'xhtml_11') {
             $target = isset($conf['target.']) ? (string) $this->stdWrap($conf['target'], $conf['target.']) : (string) $conf['target'];
             if ($target === '') {
                 $target = 'thePicture';
             }
         }
         $a1 = '';
         $a2 = '';
         $conf['JSwindow'] = isset($conf['JSwindow.']) ? $this->stdWrap($conf['JSwindow'], $conf['JSwindow.']) : $conf['JSwindow'];
         if ($conf['JSwindow']) {
             if ($conf['JSwindow.']['altUrl'] || $conf['JSwindow.']['altUrl.']) {
                 $altUrl = isset($conf['JSwindow.']['altUrl.']) ? $this->stdWrap($conf['JSwindow.']['altUrl'], $conf['JSwindow.']['altUrl.']) : $conf['JSwindow.']['altUrl'];
                 if ($altUrl) {
                     $url = $altUrl . ($conf['JSwindow.']['altUrl_noDefaultParams'] ? '' : '?file=' . rawurlencode($imageFile) . $params);
                 }
             }
             $processedFile = $file->process('Image.CropScaleMask', $conf);
             $JSwindowExpand = isset($conf['JSwindow.']['expand.']) ? $this->stdWrap($conf['JSwindow.']['expand'], $conf['JSwindow.']['expand.']) : $conf['JSwindow.']['expand'];
             $offset = GeneralUtility::intExplode(',', $JSwindowExpand . ',');
             $newWindow = isset($conf['JSwindow.']['newWindow.']) ? $this->stdWrap($conf['JSwindow.']['newWindow'], $conf['JSwindow.']['newWindow.']) : $conf['JSwindow.']['newWindow'];
             $onClick = 'openPic(' . GeneralUtility::quoteJSvalue($this->getTypoScriptFrontendController()->baseUrlWrap($url)) . ',' . '\'' . ($newWindow ? md5($url) : 'thePicture') . '\',' . GeneralUtility::quoteJSvalue('width=' . ($processedFile->getProperty('width') + $offset[0]) . ',height=' . ($processedFile->getProperty('height') + $offset[1]) . ',status=0,menubar=0') . '); return false;';
             $a1 = '<a href="' . htmlspecialchars($url) . '"' . ' onclick="' . htmlspecialchars($onClick) . '"' . ($target !== '' ? ' target="' . $target . '"' : '') . $this->getTypoScriptFrontendController()->ATagParams . '>';
             $a2 = '</a>';
             $this->getTypoScriptFrontendController()->setJS('openPic');
         } else {
             $conf['linkParams.']['parameter'] = $url;
             $string = $this->typoLink($string, $conf['linkParams.']);
         }
         if (isset($conf['stdWrap.'])) {
             $string = $this->stdWrap($string, $conf['stdWrap.']);
         }
         $content = $a1 . $string . $a2;
     }
     return $content;
 }
Example #25
0
 /**
  * Injects configuration via AJAX calls.
  * The configuration is validated using HMAC to avoid hijacking.
  *
  * @param array $ajaxArguments
  * @return void
  */
 protected function injectAjaxConfiguration(array $ajaxArguments)
 {
     $level = $this->calculateStructureLevel(-1);
     if (empty($ajaxArguments['context']) || $level === FALSE) {
         return;
     }
     $current =& $this->inlineStructure['stable'][$level];
     $context = json_decode($ajaxArguments['context'], TRUE);
     if (GeneralUtility::hmac(serialize($context['config'])) !== $context['hmac']) {
         return;
     }
     $current['config'] = $context['config'];
     $current['localizationMode'] = BackendUtility::getInlineLocalizationMode($current['table'], $current['config']);
 }
 /**
  * Init function, setting the input vars in the global space.
  *
  * @return void
  * @todo Define visibility
  */
 public function init()
 {
     // Loading internal vars with the GET/POST parameters from outside:
     $this->file = \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('file');
     $parametersArray = \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('parameters');
     $this->frame = \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('frame');
     $this->md5 = \TYPO3\CMS\Core\Utility\GeneralUtility::_GP('md5');
     // Check parameters
     // If no file-param or parameters are given, we must exit
     if (!$this->file || !isset($parametersArray) || !is_array($parametersArray)) {
         \TYPO3\CMS\Core\Utility\HttpUtility::setResponseCodeAndExit(\TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_410);
     }
     $this->parametersEncoded = implode('', $parametersArray);
     // Chech md5-checksum: If this md5-value does not match the one submitted, then we fail... (this is a kind of security that somebody don't just hit the script with a lot of different parameters
     $md5_value = \TYPO3\CMS\Core\Utility\GeneralUtility::hmac(implode('|', array($this->file, $this->parametersEncoded)));
     if ($md5_value !== $this->md5) {
         \TYPO3\CMS\Core\Utility\HttpUtility::setResponseCodeAndExit(\TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_410);
     }
     $parameters = unserialize(base64_decode($this->parametersEncoded));
     foreach ($parameters as $parameterName => $parameterValue) {
         $this->{$parameterName} = $parameterValue;
     }
     // Check the file. If must be in a directory beneath the dir of this script...
     // $this->file remains unchanged, because of the code in stdgraphic, but we do check if the file exists within the current path
     $test_file = PATH_site . $this->file;
     if (!\TYPO3\CMS\Core\Utility\GeneralUtility::validPathStr($test_file)) {
         \TYPO3\CMS\Core\Utility\HttpUtility::setResponseCodeAndExit(\TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_410);
     }
     if (!@is_file($test_file)) {
         \TYPO3\CMS\Core\Utility\HttpUtility::setResponseCodeAndExit(\TYPO3\CMS\Core\Utility\HttpUtility::HTTP_STATUS_404);
     }
 }
Example #27
0
 /**
  * Entry method
  *
  * @return array As defined in initializeResultArray() of AbstractNode
  */
 public function render()
 {
     $languageService = $this->getLanguageService();
     $this->inlineData = $this->data['inlineData'];
     /** @var InlineStackProcessor $inlineStackProcessor */
     $inlineStackProcessor = GeneralUtility::makeInstance(InlineStackProcessor::class);
     $this->inlineStackProcessor = $inlineStackProcessor;
     $inlineStackProcessor->initializeByGivenStructure($this->data['inlineStructure']);
     $table = $this->data['tableName'];
     $row = $this->data['databaseRow'];
     $field = $this->data['fieldName'];
     $parameterArray = $this->data['parameterArray'];
     $resultArray = $this->initializeResultArray();
     $config = $parameterArray['fieldConf']['config'];
     $foreign_table = $config['foreign_table'];
     $language = 0;
     if (BackendUtility::isTableLocalizable($table)) {
         $language = (int) $row[$GLOBALS['TCA'][$table]['ctrl']['languageField']];
     }
     // Add the current inline job to the structure stack
     $newStructureItem = array('table' => $table, 'uid' => $row['uid'], 'field' => $field, 'config' => $config, 'localizationMode' => BackendUtility::getInlineLocalizationMode($table, $config));
     // Extract FlexForm parts (if any) from element name, e.g. array('vDEF', 'lDEF', 'FlexField', 'vDEF')
     if (!empty($parameterArray['itemFormElName'])) {
         $flexFormParts = $this->extractFlexFormParts($parameterArray['itemFormElName']);
         if ($flexFormParts !== null) {
             $newStructureItem['flexform'] = $flexFormParts;
         }
     }
     $inlineStackProcessor->pushStableStructureItem($newStructureItem);
     // e.g. data[<table>][<uid>][<field>]
     $nameForm = $inlineStackProcessor->getCurrentStructureFormPrefix();
     // e.g. data-<pid>-<table1>-<uid1>-<field1>-<table2>-<uid2>-<field2>
     $nameObject = $inlineStackProcessor->getCurrentStructureDomObjectIdPrefix($this->data['inlineFirstPid']);
     $config['inline']['first'] = false;
     // @todo: This initialization shouldn't be required data provider should take care this is set?
     if (!is_array($this->data['parameterArray']['fieldConf']['children'])) {
         $this->data['parameterArray']['fieldConf']['children'] = array();
     }
     $firstChild = reset($this->data['parameterArray']['fieldConf']['children']);
     if (isset($firstChild['databaseRow']['uid'])) {
         $config['inline']['first'] = $firstChild['databaseRow']['uid'];
     }
     $config['inline']['last'] = false;
     $lastChild = end($this->data['parameterArray']['fieldConf']['children']);
     if (isset($lastChild['databaseRow']['uid'])) {
         $config['inline']['last'] = $lastChild['databaseRow']['uid'];
     }
     $top = $inlineStackProcessor->getStructureLevel(0);
     $this->inlineData['config'][$nameObject] = array('table' => $foreign_table, 'md5' => md5($nameObject));
     $this->inlineData['config'][$nameObject . '-' . $foreign_table] = array('min' => $config['minitems'], 'max' => $config['maxitems'], 'sortable' => $config['appearance']['useSortable'], 'top' => array('table' => $top['table'], 'uid' => $top['uid']), 'context' => array('config' => $config, 'hmac' => GeneralUtility::hmac(serialize($config))));
     $this->inlineData['nested'][$nameObject] = $this->data['tabAndInlineStack'];
     // If relations are required to be unique, get the uids that have already been used on the foreign side of the relation
     $uniqueMax = 0;
     $possibleRecords = [];
     $uniqueIds = [];
     if ($config['foreign_unique']) {
         // If uniqueness *and* selector are set, they should point to the same field - so, get the configuration of one:
         $selConfig = FormEngineUtility::getInlinePossibleRecordsSelectorConfig($config, $config['foreign_unique']);
         // Get the used unique ids:
         $uniqueIds = $this->getUniqueIds($this->data['parameterArray']['fieldConf']['children'], $config, $selConfig['type'] == 'groupdb');
         $possibleRecords = $this->getPossibleRecords($table, $field, $row, $config, 'foreign_unique');
         $uniqueMax = $config['appearance']['useCombination'] || $possibleRecords === false ? -1 : count($possibleRecords);
         $this->inlineData['unique'][$nameObject . '-' . $foreign_table] = array('max' => $uniqueMax, 'used' => $uniqueIds, 'type' => $selConfig['type'], 'table' => $config['foreign_table'], 'elTable' => $selConfig['table'], 'field' => $config['foreign_unique'], 'selector' => $selConfig['selector'], 'possible' => $this->getPossibleRecordsFlat($possibleRecords));
     }
     $resultArray['inlineData'] = $this->inlineData;
     // Render the localization links
     $localizationLinks = '';
     if ($language > 0 && $row[$GLOBALS['TCA'][$table]['ctrl']['transOrigPointerField']] > 0 && MathUtility::canBeInterpretedAsInteger($row['uid'])) {
         // Add the "Localize all records" link before all child records:
         if (isset($config['appearance']['showAllLocalizationLink']) && $config['appearance']['showAllLocalizationLink']) {
             $localizationLinks .= ' ' . $this->getLevelInteractionLink('localize', $nameObject . '-' . $foreign_table, $config);
         }
         // Add the "Synchronize with default language" link before all child records:
         if (isset($config['appearance']['showSynchronizationLink']) && $config['appearance']['showSynchronizationLink']) {
             $localizationLinks .= ' ' . $this->getLevelInteractionLink('synchronize', $nameObject . '-' . $foreign_table, $config);
         }
     }
     $numberOfFullChildren = 0;
     foreach ($this->data['parameterArray']['fieldConf']['children'] as $child) {
         if (!$child['inlineIsDefaultLanguage']) {
             $numberOfFullChildren++;
         }
     }
     // Define how to show the "Create new record" link - if there are more than maxitems, hide it
     if ($numberOfFullChildren >= $config['maxitems'] || $uniqueMax > 0 && $numberOfFullChildren >= $uniqueMax) {
         $config['inline']['inlineNewButtonStyle'] = 'display: none;';
         $config['inline']['inlineNewRelationButtonStyle'] = 'display: none;';
     }
     // Render the level links (create new record):
     $levelLinks = $this->getLevelInteractionLink('newRecord', $nameObject . '-' . $foreign_table, $config);
     // Wrap all inline fields of a record with a <div> (like a container)
     $html = '<div class="form-group" id="' . $nameObject . '">';
     // Add the level links before all child records:
     if ($config['appearance']['levelLinksPosition'] === 'both' || $config['appearance']['levelLinksPosition'] === 'top') {
         $html .= '<div class="form-group t3js-formengine-validation-marker">' . $levelLinks . $localizationLinks . '</div>';
     }
     // If it's required to select from possible child records (reusable children), add a selector box
     if ($config['foreign_selector'] && $config['appearance']['showPossibleRecordsSelector'] !== false) {
         // If not already set by the foreign_unique, set the possibleRecords here and the uniqueIds to an empty array
         if (!$config['foreign_unique']) {
             $possibleRecords = $this->getPossibleRecords($table, $field, $row, $config);
             $uniqueIds = array();
         }
         $selectorBox = $this->renderPossibleRecordsSelector($possibleRecords, $config, $uniqueIds);
         $html .= $selectorBox . $localizationLinks;
     }
     $title = $languageService->sL($parameterArray['fieldConf']['label']);
     $html .= '<div class="panel-group panel-hover" data-title="' . htmlspecialchars($title) . '" id="' . $nameObject . '_records">';
     $sortableRecordUids = [];
     foreach ($this->data['parameterArray']['fieldConf']['children'] as $options) {
         $options['inlineParentUid'] = $row['uid'];
         // @todo: this can be removed if this container no longer sets additional info to $config
         $options['inlineParentConfig'] = $config;
         $options['inlineData'] = $this->inlineData;
         $options['inlineStructure'] = $inlineStackProcessor->getStructure();
         $options['inlineExpandCollapseStateArray'] = $this->data['inlineExpandCollapseStateArray'];
         $options['renderType'] = 'inlineRecordContainer';
         $childResult = $this->nodeFactory->create($options)->render();
         $html .= $childResult['html'];
         $childArray['html'] = '';
         $resultArray = $this->mergeChildReturnIntoExistingResult($resultArray, $childResult);
         if (!$options['inlineIsDefaultLanguage']) {
             // Don't add record to list of "valid" uids if it is only the default
             // language record of a not yet localized child
             $sortableRecordUids[] = $options['databaseRow']['uid'];
         }
     }
     $html .= '</div>';
     // Add the level links after all child records:
     if ($config['appearance']['levelLinksPosition'] === 'both' || $config['appearance']['levelLinksPosition'] === 'bottom') {
         $html .= $levelLinks . $localizationLinks;
     }
     if (is_array($config['customControls'])) {
         $html .= '<div id="' . $nameObject . '_customControls">';
         foreach ($config['customControls'] as $customControlConfig) {
             $parameters = array('table' => $table, 'field' => $field, 'row' => $row, 'nameObject' => $nameObject, 'nameForm' => $nameForm, 'config' => $config);
             $html .= GeneralUtility::callUserFunction($customControlConfig, $parameters, $this);
         }
         $html .= '</div>';
     }
     // Add Drag&Drop functions for sorting to FormEngine::$additionalJS_post
     if (count($sortableRecordUids) > 1 && $config['appearance']['useSortable']) {
         $resultArray['additionalJavaScriptPost'][] = 'inline.createDragAndDropSorting("' . $nameObject . '_records' . '");';
     }
     // Publish the uids of the child records in the given order to the browser
     $html .= '<input type="hidden" name="' . $nameForm . '" value="' . implode(',', $sortableRecordUids) . '" ' . $this->getValidationDataAsDataAttribute(array('type' => 'inline', 'minitems' => $config['minitems'], 'maxitems' => $config['maxitems'])) . ' class="inlineRecord" />';
     // Close the wrap for all inline fields (container)
     $html .= '</div>';
     $resultArray['html'] = $html;
     return $resultArray;
 }
Example #28
0
 /**
  * Determines whether submitted field change functions are valid
  * and are coming from the system and not from an external abuse.
  *
  * @param boolean $handleFlexformSections Whether to handle flexform sections differently
  * @return boolean Whether the submitted field change functions are valid
  */
 protected function areFieldChangeFunctionsValid($handleFlexformSections = FALSE)
 {
     $result = FALSE;
     if (isset($this->P['fieldChangeFunc']) && is_array($this->P['fieldChangeFunc']) && isset($this->P['fieldChangeFuncHash'])) {
         $matches = array();
         $pattern = '#\\[el\\]\\[(([^]-]+-[^]-]+-)(idx\\d+-)([^]]+))\\]#i';
         $fieldChangeFunctions = $this->P['fieldChangeFunc'];
         // Special handling of flexform sections:
         // Field change functions are modified in JavaScript, thus the hash is always invalid
         if ($handleFlexformSections && preg_match($pattern, $this->P['itemName'], $matches)) {
             $originalName = $matches[1];
             $cleanedName = $matches[2] . $matches[4];
             foreach ($fieldChangeFunctions as &$value) {
                 $value = str_replace($originalName, $cleanedName, $value);
             }
             unset($value);
         }
         $result = $this->P['fieldChangeFuncHash'] === GeneralUtility::hmac(serialize($fieldChangeFunctions));
     }
     return $result;
 }
 /**
  * Returns a publicly accessible URL for a file.
  *
  * WARNING: Access to the file may be restricted by further means, e.g.
  * some web-based authentication. You have to take care of this yourself.
  *
  * @param ResourceInterface $resourceObject The file or folder object
  * @param bool $relativeToCurrentScript Determines whether the URL returned should be relative to the current script, in case it is relative at all (only for the LocalDriver)
  * @return string
  */
 public function getPublicUrl(ResourceInterface $resourceObject, $relativeToCurrentScript = false)
 {
     $publicUrl = null;
     if ($this->isOnline()) {
         // Pre-process the public URL by an accordant slot
         $this->emitPreGeneratePublicUrlSignal($resourceObject, $relativeToCurrentScript, array('publicUrl' => &$publicUrl));
         if ($publicUrl === null && $resourceObject instanceof File && ($helper = OnlineMediaHelperRegistry::getInstance()->getOnlineMediaHelper($resourceObject)) !== false) {
             $publicUrl = $helper->getPublicUrl($resourceObject, $relativeToCurrentScript);
         }
         // If slot did not handle the signal, use the default way to determine public URL
         if ($publicUrl === null) {
             if ($this->hasCapability(self::CAPABILITY_PUBLIC)) {
                 $publicUrl = $this->driver->getPublicUrl($resourceObject->getIdentifier());
             }
             if ($publicUrl === null && $resourceObject instanceof FileInterface) {
                 $queryParameterArray = array('eID' => 'dumpFile', 't' => '');
                 if ($resourceObject instanceof File) {
                     $queryParameterArray['f'] = $resourceObject->getUid();
                     $queryParameterArray['t'] = 'f';
                 } elseif ($resourceObject instanceof ProcessedFile) {
                     $queryParameterArray['p'] = $resourceObject->getUid();
                     $queryParameterArray['t'] = 'p';
                 }
                 $queryParameterArray['token'] = GeneralUtility::hmac(implode('|', $queryParameterArray), 'resourceStorageDumpFile');
                 $publicUrl = 'index.php?' . str_replace('+', '%20', http_build_query($queryParameterArray));
             }
             // If requested, make the path relative to the current script in order to make it possible
             // to use the relative file
             if ($publicUrl !== null && $relativeToCurrentScript && !GeneralUtility::isValidUrl($publicUrl)) {
                 $absolutePathToContainingFolder = PathUtility::dirname(PATH_site . $publicUrl);
                 $pathPart = PathUtility::getRelativePathTo($absolutePathToContainingFolder);
                 $filePart = substr(PATH_site . $publicUrl, strlen($absolutePathToContainingFolder) + 1);
                 $publicUrl = $pathPart . $filePart;
             }
         }
     }
     return $publicUrl;
 }
 /**
  * Flexforms require additional database columns to be processed to determine the correct
  * data structure to be used from a flexform. The required columns and their values are
  * transmitted in the AJAX context of the request and need to be added to the fake database
  * row for the inline parent.
  *
  * @param array $ajaxArguments The AJAX request arguments
  * @param array $databaseRow The fake database row
  * @return array The database row with the flexform data structure pointer columns added
  */
 protected function addFlexFormDataStructurePointersFromAjaxContext(array $ajaxArguments, array $databaseRow)
 {
     if (!isset($ajaxArguments['context'])) {
         return $databaseRow;
     }
     $context = json_decode($ajaxArguments['context'], true);
     if (GeneralUtility::hmac(serialize($context['config'])) !== $context['hmac']) {
         return $databaseRow;
     }
     if (isset($context['config']['flexDataStructurePointers']) && is_array($context['config']['flexDataStructurePointers'])) {
         $databaseRow = array_merge($context['config']['flexDataStructurePointers'], $databaseRow);
     }
     return $databaseRow;
 }