/** * Execute the block and replace the results * * @return \SalesforceEng\Breakout\Document instance */ public function execute() { $tokens = $this->getTokens(); $data = $this->getData(); $document = $this->getDocument(); $forBlock = array_shift($tokens); $last = array_pop($tokens); preg_match_all('/{% for (.+?) in (.+?) %}/', $forBlock->getFull(), $matches); $varname = $matches[2][0]; $itemName = $matches[1][0]; $loopData = Parser::resolveValue($data, $varname); if ($loopData == null) { throw new \Exception('Variable "' . $varname . '" not found for use in for loop!'); } $between = $document->between($forBlock, $last); $token = new Tokenizer(); $container = $token->execute($between); $content = ''; foreach ($loopData as $var) { $parser = new Parser($container, $between); $content .= $parser->execute([$itemName => $var]); } $contentToken = new Token(['content' => $content, 'start' => $forBlock->getStart(), 'end' => $last->getEnd()]); $document->replace($contentToken, $content); return $document; }
/** * Execute the "if" block handling * * @return \SalesforceEng\Breakout\Document instance */ public function execute() { $tokens = $this->getTokens(); $data = $this->getData(); $document = $this->getDocument(); // get the details for the "if" $ifBlock = array_shift($tokens); $last = array_pop($tokens); // Parse out the block contents preg_match('/{% if (.+?) ([=!]*)(.*?)%}/', $ifBlock->getFull(), $matches); $varname = $matches[1]; $operator = isset($matches[2]) && !empty($matches[2]) ? $matches[2] : 'isset'; $elseBetween = null; $matchValue = null; // If we have a value to match against, normalize it a bit if (isset($matches[3])) { $matchValue = $this->normalizeValue($matches[3]); } // See if we have an "else" we need to get it out and update our current tokens if (!empty($tokens) && count($tokens) == 1 && !is_array($tokens[0]) && $tokens[0]->getToken() == 'else') { $else = array_pop($tokens); $elseBetween = $document->between($else, $last); $between = $document->between($ifBlock, $else); } else { $between = $document->between($ifBlock, $last); } $resolved = Parser::resolveValue($data, $varname); // Match the replacement template depending on evaluation result $template = $this->evaluate($operator, $resolved, $matchValue) === true ? $between : $elseBetween; // Now perform the replacement $token = new Tokenizer(); $parser = new Parser($token->execute($template), $template); $content = $parser->execute($data); $contentToken = new Token(['content' => $content, 'start' => $ifBlock->getStart(), 'end' => $last->getEnd()]); $document->replace($contentToken, $content); return $document; }
/** * Render the document, replacing data with provided escaping * * @param string $document Document to replace content inside of * @param array $data Data to replace * @return string Document with content replaced and escaped */ public static function render($document, array $data, $delimiters = null) { if ($delimiters === null) { $delimiters = self::getDelimiters(); } $token = new Tokenizer($delimiters); $result = $token->execute($document); $parser = new Parser($result, $document); return $parser->execute($data); }