public static function findPathForSetting(&$settings, $settingPath, $basicScope = false) { $searchResults = ArrayTools::TraverseTreeWithPath($settings, $settingPath); if (empty($searchResults)) { LogCLI::MessageResult(LogCLI::YELLOW . 'Sorry, no settings found for: ' . LogCLI::BLUE . $settingPath . LogCLI::RESET, 0, LogCLI::INFO); return false; } else { if (count($searchResults['all']) > 1) { LogCLI::MessageResult(LogCLI::YELLOW . 'Multiple settings found for: ' . LogCLI::BLUE . $settingPath . LogCLI::RESET, 4, LogCLI::INFO); } LogCLI::MessageResult(LogCLI::GREEN . 'Best match: ' . LogCLI::BLUE . $searchResults['best'] . LogCLI::RESET, 0, LogCLI::INFO); $path = $searchResults['best']; if ($basicScope !== false) { if (($pos = strpos($path, $basicScope)) !== false && $pos === 0) { $path = StringTools::DropLastBit($path, -1); } } $parent = ArrayTools::accessArrayElementByPath($settings, StringTools::DropLastBit($searchResults['best'])); if (isset($parent['iterative'])) { $path = StringTools::DropLastBit($path, -1); } LogCLI::MessageResult('Fixed path: ' . LogCLI::YELLOW . $searchResults['best'] . ' => ' . LogCLI::BLUE . $path . LogCLI::RESET, 6, LogCLI::INFO); return $path; } }
private function parseWithConfig($configuration, $result) { $output = null; foreach ($this->options as $option) { /* * if there are multiple paths for one setting */ if (is_array($option->path)) { foreach ($option->path as $config => $path) { //($setting = ArrayTools::accessArrayElementByPath($configuration, $path)) !== null ?: $setting = $option->default[$config]; $setting = ArrayTools::accessArrayElementByPath($configuration, $path); if ($setting === null) { if ($option->default[$config] !== null) { LogCLI::MessageResult('Setting ' . $config . ' not set, defaulting to: ' . $option->default[$config], 7, LogCLI::OK); } $setting = $option->default[$config]; } $values[$config] = $setting; } $this->_dispatchAction($option, $values, $result); } else { //($setting = ArrayTools::accessArrayElementByPath($configuration, $option->path)) !== null ?: $setting = $option->default; $setting = ArrayTools::accessArrayElementByPath($configuration, $option->path); if ($setting === null) { $option->setDefaults(); if ($option->default !== null) { LogCLI::MessageResult('Setting ' . $option->name . ' not set, defaulting to: ' . $option->default, 7, LogCLI::OK); } $setting = $option->default; } //var_dump($setting); /* * If we got an array, how do we divide it? * By default by ' ' (space), but sometimes we want eg. PHP_EOL, or comma. */ $value = StringTools::makeList($setting, $option->divideBy); $this->_dispatchAction($option, $value, $result); } } //foreach(preg_split("/(\r?\n)/", $this->template) as $line) foreach (explode(PHP_EOL, $this->template) as $line) { //$parsedline = ParseTools::sprintfn($line, $result->options); $parsedline = ParseTools::parseStringWithReplacementList($line, $result->options); // if all we got is whitespace, don't add it if (strlen(rtrim($parsedline)) < 1) { continue; } // if we got a multiline responds we have to indent it // TODO: maybe explode "\n" or PHP_EOL would be better? // if(count($lines = preg_split("/(\r?\n)/", $parsedline)) > 1) if (count($lines = explode(PHP_EOL, $parsedline)) > 1) { $indentedlines = array_shift($lines) . PHP_EOL; foreach ($lines as &$multiline) { $indentedlines .= StringTools::indentLinesToMatchOther(trim($line), $line, $multiline) . PHP_EOL; } $parsedline = rtrim($indentedlines); } $output .= $parsedline . PHP_EOL; } return $output; }
/** * similar to makeTree, but also parses the tree and puts the actual elements in place * * @param string $scope * @param bool $parseResult * @param int $depth * @param bool $parentIterative * @param string $parent * @return array */ public function parseTree($scope, $parseResult = false, $depth = 0, $parentIterative = false, $parent = '') { $parentDisplay = null; ++$depth; $return = array(); if (!empty($parent)) { $fullScopePath = $parent . '/' . $scope; $parentDisplay = LogCLI::GREEN . $parent . LogCLI::RESET . ' => '; } else { $fullScopePath = $scope; } if ($parseResult === false) { $pregSubject =& $this->templates[$scope]; } elseif (isset($this->results[$scope])) { $pregSubject =& $this->results[$scope]; } else { return $return; } preg_match_all('/<<(?<name>\\w+)>>/', $pregSubject, $matches); preg_match_all('/<!<(?<name>\\w+)>!>/', $pregSubject, $matchesIterative); if (!empty($matches['name'])) { foreach ($matches['name'] as $match) { if (!$this->patterns[$match]) { $this->patterns[$match] = '<<' . $match . '>>'; } LogCLI::Message('(' . $depth . ') Non-iterative match: ' . $parentDisplay . LogCLI::BLUE . $scope . LogCLI::RESET . " => " . LogCLI::YELLOW . $match . LogCLI::RESET, 2); $children = $this->parseTree($match, false, $depth, $parentIterative, $scope); LogCLI::Result(LogCLI::INFO); if ($parentIterative === true) { $path = $scope . '/' . $match; if (!$this->parsers[$match]->loadConfiguration($this->config, $path)) { LogCLI::MessageResult('No configuration data for: ' . LogCLI::BLUE . $scope . LogCLI::RESET, LogCLI::INFO); } LogCLI::Message("Ordering parsing of: " . LogCLI::BLUE . $path . LogCLI::RESET . " at depth = {$depth}", 3); LogCLI::MessageResult('Parent scope is iterative: ' . LogCLI::BLUE . $scope . LogCLI::RESET, LogCLI::INFO); $this->results[$path] = $this->parsers[$match]->getParsed(); LogCLI::Result(LogCLI::INFO); } elseif (!isset($this->results[$match])) { $this->parsers[$match]->loadConfiguration($this->config, $match); LogCLI::Message("Ordering parsing of: " . LogCLI::BLUE . $match . LogCLI::RESET . " at depth = {$depth}", 3); LogCLI::MessageResult('Parent scope is not iterative: ' . LogCLI::BLUE . $scope . LogCLI::RESET, LogCLI::INFO); $this->results[$match] = $this->parsers[$match]->getParsed(); foreach ($children as $child) { //LogCLI::MessageResult("Inserting: $child to ".LogCLI::BLUE.$match.LogCLI::RESET." at depth = $depth", 5); $this->results[$match] = $this->insertScope($child, $match, $this->patterns[$child]); } LogCLI::Result(LogCLI::INFO); } } $return = $matches['name']; } if (!empty($matchesIterative['name'])) { foreach ($matchesIterative['name'] as $match) { $path = $fullScopePath . '/' . $match; $this->patterns[$match] = '<!<' . $match . '>!>'; $this->results[$match] = null; $this->results[$path] = null; /* * recursive iterative matching */ //$currentConfig = $this->parsers[$match]->loadConfiguration(&$this->config, $path, $match); $currentConfig =& ArrayTools::accessArrayElementByPath($this->config, $path); //$parentConfig = ArrayTools::accessArrayElementByPath(&$this->config, $fullScopePath); // translation: if (!ArrayTools::isIterativeScope($currentConfig)) { LogCLI::MessageResult('Non-iterative format, translating path: ' . LogCLI::BLUE . $path . LogCLI::RESET, LogCLI::INFO); //ArrayTools::replaceArrayElementByPath(&$this->config, $path, ArrayTools::translateToIterativeScope($match, $currentConfig)); $currentConfig = ArrayTools::translateToIterativeScope($match, $currentConfig); } foreach (array_keys($currentConfig) as $id) { LogCLI::Message('(' . $depth . ') ' . $parentDisplay . LogCLI::BLUE . $scope . LogCLI::RESET . " => " . LogCLI::YELLOW . $match . LogCLI::RESET . " => [" . LogCLI::GREEN_LIGHT . $id . LogCLI::RESET . "]", 2); LogCLI::MessageResult("Ordering parsing of: " . LogCLI::BLUE . "{$match}" . LogCLI::RESET . " at depth = {$depth}", 3); $iterativePath = "{$fullScopePath}/{$match}/{$id}"; $this->parsers[$match]->loadConfiguration($this->config, $iterativePath); // at this moment it's still the same configuration, just cut out $this->results[$iterativePath] = $this->parsers[$match]->getParsed(); /** * let's parse all the children */ LogCLI::Message('(' . $depth . ') ' . $parentDisplay . LogCLI::BLUE . $scope . LogCLI::RESET . " => " . LogCLI::YELLOW . $match . LogCLI::RESET . " => " . LogCLI::RED . '[iterative]' . LogCLI::RESET, 2); $children = $this->parseTree($iterativePath, true, $depth, true, ''); //LogCLI::MessageResult("Child's path: ".LogCLI::YELLOW.$iterativePath.LogCLI::RESET, 7); foreach ($children as $child) { $this->results[$iterativePath] = $this->insertScope("{$iterativePath}/{$child}", $iterativePath, $this->patterns[$child], $this->results[$iterativePath]); } LogCLI::MessageResult("Adding up the iterative scope values: " . LogCLI::YELLOW . $iterativePath . LogCLI::RESET, 5); $this->results[$path] .= trim($this->results[$iterativePath]) . PHP_EOL; LogCLI::Result(LogCLI::INFO); // end children parse LogCLI::Result(LogCLI::INFO); // end iteration } $this->results[$match] = rtrim($this->results[$path]); } $return = array_merge($return, $matchesIterative['name']); } if ($depth == 1) { $this->parsers[$scope]->loadConfiguration($this->config, $scope); $this->results[$scope] = $this->parsers[$scope]->getParsed(); $all_matches = array_merge_recursive($matches, $matchesIterative); if (!empty($all_matches['name'])) { foreach ($all_matches['name'] as $match) { //LogCLI::MessageResult("Inserting: $match to ".LogCLI::BLUE.$scope.LogCLI::RESET, 5); $this->results[$scope] = $this->insertScope($match, $scope); } } } return $return; }