/** * Checks whether $routeValues contains elements which correspond to this Dynamic Route Part. * If a corresponding element is found in $routeValues, this element is removed from the array. * * @param array $routeValues An array with key/value pairs to be resolved by Dynamic Route Parts. * @return boolean TRUE if current Route Part could be resolved, otherwise FALSE */ public final function resolve(array &$routeValues) { $this->value = NULL; if ($this->name === NULL || $this->name === '') { return FALSE; } $valueToResolve = $this->findValueToResolve($routeValues); if (!$this->resolveValue($valueToResolve)) { return FALSE; } $routeValues = Arrays::unsetValueByPath($routeValues, $this->name); return TRUE; }
/** * Merges specified arguments with arguments from request. * * If $this->request is no sub request, request arguments will only be merged if $this->addQueryString is set. * Otherwise all request arguments except for the ones prefixed with the current request argument namespace will * be merged. Additionally special arguments (PackageKey, SubpackageKey, ControllerName & Action) are merged. * * The argument provided through the $arguments parameter always overrule the request * arguments. * * The request hierarchy is structured as follows: * root (HTTP) > main (Action) > sub (Action) > sub sub (Action) * * @param array $arguments * @return array */ protected function mergeArgumentsWithRequestArguments(array $arguments) { if ($this->request !== $this->request->getMainRequest()) { $subRequest = $this->request; while ($subRequest instanceof \TYPO3\Flow\Mvc\ActionRequest) { $requestArguments = (array) $subRequest->getArguments(); // Reset arguments for the request that is bound to this UriBuilder instance if ($subRequest === $this->request) { if ($this->addQueryString === false) { $requestArguments = array(); } else { foreach ($this->argumentsToBeExcludedFromQueryString as $argumentToBeExcluded) { unset($requestArguments[$argumentToBeExcluded]); } } } else { // Remove all arguments of the current sub request if it's namespaced if ($this->request->getArgumentNamespace() !== '') { $requestNamespace = $this->getRequestNamespacePath($this->request); if ($this->addQueryString === false) { $requestArguments = Arrays::unsetValueByPath($requestArguments, $requestNamespace); } else { foreach ($this->argumentsToBeExcludedFromQueryString as $argumentToBeExcluded) { $requestArguments = Arrays::unsetValueByPath($requestArguments, $requestNamespace . '.' . $argumentToBeExcluded); } } } } // Merge special arguments (package, subpackage, controller & action) from main request $requestPackageKey = $subRequest->getControllerPackageKey(); if (!empty($requestPackageKey)) { $requestArguments['@package'] = $requestPackageKey; } $requestSubpackageKey = $subRequest->getControllerSubpackageKey(); if (!empty($requestSubpackageKey)) { $requestArguments['@subpackage'] = $requestSubpackageKey; } $requestControllerName = $subRequest->getControllerName(); if (!empty($requestControllerName)) { $requestArguments['@controller'] = $requestControllerName; } $requestActionName = $subRequest->getControllerActionName(); if (!empty($requestActionName)) { $requestArguments['@action'] = $requestActionName; } if (count($requestArguments) > 0) { $requestArguments = $this->addNamespaceToArguments($requestArguments, $subRequest); $arguments = Arrays::arrayMergeRecursiveOverrule($requestArguments, $arguments); } $subRequest = $subRequest->getParentRequest(); } } elseif ($this->addQueryString === true) { $requestArguments = $this->request->getArguments(); foreach ($this->argumentsToBeExcludedFromQueryString as $argumentToBeExcluded) { unset($requestArguments[$argumentToBeExcluded]); } if ($requestArguments !== array()) { $arguments = Arrays::arrayMergeRecursiveOverrule($requestArguments, $arguments); } } return $arguments; }
/** * @test * @expectedException \InvalidArgumentException */ public function unsetValueByPathThrowsExceptionIfPathIsNoArrayOrString() { $array = array('Foo' => array('Bar' => array('Baz' => array(2 => 'the value')))); \TYPO3\Flow\Utility\Arrays::unsetValueByPath($array, NULL); }
/** * @test * @expectedException \InvalidArgumentException */ public function unsetValueByPathThrowsExceptionIfPathIsNoArrayOrString() { $array = array('Foo' => array('Bar' => array('Baz' => array(2 => 'the value')))); Arrays::unsetValueByPath($array, null); }
/** * Checks whether $routeValues can be resolved to a corresponding uri. * If all Route Parts can resolve one or more of the $routeValues, TRUE is * returned and $this->matchingURI contains the generated URI (excluding * protocol and host). * * @param array $routeValues An array containing key/value pairs to be resolved to uri segments * @return boolean TRUE if this Route corresponds to the given $routeValues, otherwise FALSE * @throws InvalidRoutePartValueException * @see getMatchingUri() */ public function resolves(array $routeValues) { $this->resolvedUriPath = null; if ($this->uriPattern === null) { return false; } if (!$this->isParsed) { $this->parse(); } $resolvedUriPath = ''; $remainingDefaults = $this->defaults; $requireOptionalRouteParts = false; $matchingOptionalUriPortion = ''; /** @var $routePart RoutePartInterface */ foreach ($this->routeParts as $routePart) { if (!$routePart->resolve($routeValues)) { if (!$routePart->hasDefaultValue()) { return false; } } if ($routePart->getName() !== null) { $remainingDefaults = Arrays::unsetValueByPath($remainingDefaults, $routePart->getName()); } $routePartValue = null; if ($routePart->hasValue()) { $routePartValue = $routePart->getValue(); if (!is_string($routePartValue)) { throw new InvalidRoutePartValueException('RoutePart::getValue() must return a string after calling RoutePart::resolve(), got ' . (is_object($routePartValue) ? get_class($routePartValue) : gettype($routePartValue)) . ' for RoutePart "' . get_class($routePart) . '" in Route "' . $this->getName() . '".'); } } $routePartDefaultValue = $routePart->getDefaultValue(); if ($routePartDefaultValue !== null && !is_string($routePartDefaultValue)) { throw new InvalidRoutePartValueException('RoutePart::getDefaultValue() must return a string, got ' . (is_object($routePartDefaultValue) ? get_class($routePartDefaultValue) : gettype($routePartDefaultValue)) . ' for RoutePart "' . get_class($routePart) . '" in Route "' . $this->getName() . '".'); } if (!$routePart->isOptional()) { $resolvedUriPath .= $routePart->hasValue() ? $routePartValue : $routePartDefaultValue; $requireOptionalRouteParts = false; continue; } if ($routePart->hasValue() && strtolower($routePartValue) !== strtolower($routePartDefaultValue)) { $matchingOptionalUriPortion .= $routePartValue; $requireOptionalRouteParts = true; } else { $matchingOptionalUriPortion .= $routePartDefaultValue; } if ($requireOptionalRouteParts) { $resolvedUriPath .= $matchingOptionalUriPortion; $matchingOptionalUriPortion = ''; } } if ($this->compareAndRemoveMatchingDefaultValues($remainingDefaults, $routeValues) !== true) { return false; } if (isset($routeValues['@format']) && $routeValues['@format'] === '') { unset($routeValues['@format']); } // add query string if (count($routeValues) > 0) { $routeValues = Arrays::removeEmptyElementsRecursively($routeValues); $routeValues = $this->persistenceManager->convertObjectsToIdentityArrays($routeValues); if (!$this->appendExceedingArguments) { $internalArguments = $this->extractInternalArguments($routeValues); if ($routeValues !== array()) { return false; } $routeValues = $internalArguments; } $queryString = http_build_query($routeValues, null, '&'); if ($queryString !== '') { $resolvedUriPath .= strpos($resolvedUriPath, '?') !== false ? '&' . $queryString : '?' . $queryString; } } $this->resolvedUriPath = $resolvedUriPath; return true; }
/** * Checks whether $routeValues contains elements which correspond to this Dynamic Route Part. * If a corresponding element is found in $routeValues, this element is removed from the array. * * @param array $routeValues An array with key/value pairs to be resolved by Dynamic Route Parts. * @return boolean TRUE if current Route Part could be resolved, otherwise FALSE */ public final function resolve(array &$routeValues) { $this->value = null; if ($this->name === null || $this->name === '') { return false; } $valueToResolve = $this->findValueToResolve($routeValues); if (!$this->resolveValue($valueToResolve)) { return false; } $routeValues = Arrays::unsetValueByPath($routeValues, $this->name); return true; }
/** * @param NodeInterface $node * @return void */ public function refreshCacheIfNecessary(NodeInterface $node) { if ($node->getNodeType()->isOfType('Nezaniel.SystemNodes:SystemNode')) { $currentPath = []; $recursiveIterator = function (array $items) use(&$recursiveIterator, &$currentPath, $node) { foreach ($items as $key => $entry) { $currentPath[] = $key; if (is_array($entry)) { $recursiveIterator($entry); } elseif ($entry === $node->getIdentifier()) { $this->systemNodeIdentifiers = Arrays::unsetValueByPath($this->systemNodeIdentifiers, $currentPath); } array_pop($currentPath); } }; $recursiveIterator($this->systemNodeIdentifiers); $this->initializeSystemNode($node); $this->cache->set('systemNodeIdentifiers', $this->systemNodeIdentifiers); } }