public static function findTemplateLoader($loader) { if (is_array($loader)) { $loader = $loader[0]; $args = py_slice($loader, 1); } else { $args = array(); } if (is_string($loader)) { $expl_ = explode('.', $loader); $module = join('.', py_slice($expl_, 0, -1)); $attr = $expl_[count($expl_) - 1]; try { $mod = import_module($module); } catch (ImportError $e) { throw new ImproperlyConfigured('Error importing template source loader ' . $loader . ': "' . $e . '"'); } if (!$mod instanceof BaseLoader) { throw new ImproperlyConfigured('Error importing template source loader ' . $loader . ': module doesn\'t return a BaseLoader descendant object.'); } $TemplateLoader = $mod; if (isset($TemplateLoader->load_template_source)) { $func = new $TemplateLoader($args); } else { // Try loading module the old way - string is full path to callable if ($args) { throw new ImproperlyConfigured('Error importing template source loader ' . $loader . ' - can\'t pass arguments to function-based loader.'); } $func = $TemplateLoader; } return $func; } else { throw new ImproperlyConfigured('Loader does not define a "load_template" callable template source loader'); } }
public function testStrSlice() { $this->assertEquals('pyt', py_slice('python_power', null, 3)); $this->assertEquals('power', py_slice('python_power', 7)); $this->assertEquals('power', py_slice('python_power', -5)); $this->assertEquals('pow', py_slice('python_power', -5, -2)); $this->assertEquals('python_', py_slice('python_power', null, -5)); $this->assertEquals(' a ', py_slice('{{ a }}', 2, -2)); }
/** * Registers tag within a library handled * by this naive if template node. * * @static * @param Library $lib * @param string $tag_name * @param Closure $condition */ public static function registerAsTag($lib, $tag_name, $condition) { $class = get_called_class(); $lib->tag($tag_name, function ($parser, $token) use($tag_name, $condition, $class) { /** * @var Parser $parser * @var Token $token */ $bits = py_str_split($token->contents); $nodelist_true = $parser->parse(array('else', 'end' . $tag_name)); $token = $parser->nextToken(); if ($token->contents == 'else') { $nodelist_false = $parser->parse(array('end' . $tag_name)); $parser->deleteFirstToken(); } else { $nodelist_false = new NodeList(); } $values = array(); foreach (py_slice($bits, 1) as $bit) { $values[] = $parser->compileFilter($bit); } return new $class($nodelist_true, $nodelist_false, $values, $condition); }); }
if (count($bits) < 2) { throw new TemplateSyntaxError('\'include\' tag takes at least one argument: the name of the template to be included.'); } $options = array(); $remaining_bits = py_slice($bits, 2); while ($remaining_bits) { $option = py_arr_pop($remaining_bits, 0); if (isset($options[$option])) { throw new TemplateSyntaxError('The ' . $option . ' option was specified more than once.'); } if ($option == 'with') { $value = DjaBase::tokenKwargs($remaining_bits, $parser, False); if (!$value) { throw new TemplateSyntaxError('"with" in \'include\' tag needs at least one keyword argument.'); } } elseif ($option == 'only') { $value = True; } else { throw new TemplateSyntaxError('Unknown argument for \'include\' tag: ' . $option . '.'); } $options[$option] = $value; } $isolated_context = py_arr_get($options, 'only', False); $namemap = py_arr_get($options, 'with', array()); $path = $bits[1]; if (in_array($path[0], array('"', "'")) && py_arr_get($path, -1) == $path[0]) { return new ConstantIncludeNode(py_slice($path, 1, -1), $namemap, $isolated_context); } return new IncludeNode($parser->compileFilter($bits[1]), $namemap, $isolated_context); }); return $lib;
foreach ($this->vary_on as $var) { $v_ = new Variable($var); $vs_[] = urlencode($v_->resolve($context)); } $args = join(':', $vs_); unset($vs_); $cache_key = 'template.cache.' . $this->fragment_name . '.' . md5($args); $manager = Dja::getCacheManager(); $value = $manager->get($cache_key); if ($value === null) { $value = $this->nodelist->render($context); $manager->set($cache_key, $value, $expire_time); } return $value; } } $lib = new Library(); $lib->tag('cache', function ($parser, $token) { /** * @var Parser $parser * @var Token $token */ $nodelist = $parser->parse(array('endcache')); $parser->deleteFirstToken(); $tokens = py_str_split($token->contents); if (count($tokens) < 3) { throw new TemplateSyntaxError('\'cache\' tag requires at least 2 arguments.'); } return new CacheNode($nodelist, $tokens[1], $tokens[2], py_slice($tokens, 3)); }); return $lib;
/** * @static * * @param string $name * @param Closure $func * @param null|array $provided * * @return bool * @throws TemplateSyntaxError */ public static function argsCheck($name, $func, $provided) { if (!is_array($provided)) { $provided = array($provided); } $plen = count($provided); list($args, $varargs, $varkw, $defaults) = py_inspect_getargspec($func); // First argument is filter input. py_arr_pop($args, 0); if ($defaults) { $nondefs = py_slice($args, null, -count($defaults)); } else { $nondefs = $args; } // Args without defaults must be provided. try { foreach ($nondefs as $arg) { py_arr_pop($provided, 0); } } catch (IndexError $e) { // Not enough throw new TemplateSyntaxError($name . ' requires ' . count($nondefs) . ' arguments, ' . $plen . ' provided'); } // Defaults can be overridden. try { foreach ($provided as $parg) { py_arr_pop($defaults, 0); } } catch (IndexError $e) { // Too many. throw new TemplateSyntaxError($name . ' requires ' . count($nondefs) . ' arguments, ' . $plen . ' provided'); } return True; }
/** * Return a list of tokens from a given template_string * * @return array */ public function tokenize() { $result = array(); $upto = 0; $matches = new PyReFinditer(DjaBase::getReTag(), $this->template_string); /** @var $match pyReMatchObject */ foreach ($matches as $match) { list($start, $end) = $match->span(); if ($start > $upto) { $result[] = $this->createToken(py_slice($this->template_string, $upto, $start), False, array($upto, $start)); $upto = $start; } $result[] = $this->createToken(py_slice($this->template_string, $start, $end), True, array($start, $end)); $upto = $end; } $last_bit = py_slice($this->template_string, $upto); if ($last_bit) { $result[] = $this->createToken($last_bit, False, array($upto, $upto + strlen($last_bit))); } return $result; }
/** * Truncates a string after a certain number of words. * * Newlines in the string will be stripped. * * @param $length * @param $truncate * * @return string */ private function _text_words($length, $truncate) { $words = py_str_split($this->_wrapped); if (count($words) > $length) { $words = py_slice($words, null, $length); return self::add_truncation_text(join(' ', $words), $truncate); } return join(' ', $words); }
function py_zip($a1, $a2) { if (!is_array($a1) || !is_array($a2)) { throw new TypeError(); } $a1c = count($a1); $a2c = count($a2); if ($a1c < $a2c) { $a2 = py_slice($a2, null, $a1c); } else { $a1 = py_slice($a1, null, $a2c); } return array_combine($a1, $a2); }
/** * @var Parser $parser * @var Token $token */ $bits = $token->splitContents(); if (count($bits) < 2) { throw new TemplateSyntaxError('\'url\' takes at least one argument (path to a view)'); } $viewname = $parser->compileFilter($bits[1]); $args = array(); $kwargs = array(); $asvar = null; $bits = py_slice($bits, 2); if (count($bits) >= 2 && py_arr_get($bits, -2) == 'as') { $asvar = py_arr_get($bits, -1); $bits = py_slice($bits, null, -2); } if (count($bits)) { foreach ($bits as $bit) { $match = py_re_match(DjaBase::$re_kwarg, $bit); if (!$match) { throw new TemplateSyntaxError('Malformed arguments to url tag'); } list($name, $value) = $match->groups(); if ($name) { $kwargs[$name] = $parser->compileFilter($value); } else { $args[] = $parser->compileFilter($value); } } }
$lib->tag('widthratio', function ($parser, $token) { /** * @var Parser $parser * @var Token $token */ $bits = py_str_split($token->contents); if (count($bits) != 4) { throw new TemplateSyntaxError('widthratio takes three arguments'); } list($tag, $this_value_expr, $max_value_expr, $max_width) = $bits; return new WidthRatioNode($parser->compileFilter($this_value_expr), $parser->compileFilter($max_value_expr), $parser->compileFilter($max_width)); }); $lib->tag('with', function ($parser, $token) { /** * @var Parser $parser * @var Token $token */ $bits = py_str_split($token->contents); $remaining_bits = py_slice($bits, 1); $extra_context = DjaBase::tokenKwargs($remaining_bits, $parser, True); if (!$extra_context) { throw new TemplateSyntaxError('\'with\' expected at least one variable assignment'); } if ($remaining_bits) { throw new TemplateSyntaxError('\'with\' received an invalid token: ' . $remaining_bits[0]); } $nodelist = $parser->parse(array('endwith')); $parser->deleteFirstToken(); return new WithNode(null, null, $nodelist, $extra_context); }); return $lib;
function do_echo($token) { return new EchoNode(py_slice(explode(' ', $token->contents), 1)); }
} return $no; }, array('is_safe' => False)); /* * MISC */ // TODO filesizeformat $lib->filter('pluralize', function ($value, $arg = 's') { if (strpos($arg, ',') == false) { $arg = ',' . $arg; } $bits = explode(',', $arg); if (count($bits) > 2) { return ''; } list($singular_suffix, $plural_suffix) = py_slice($bits, null, 2); if (is_numeric($value)) { if ($value != 1) { return $plural_suffix; } } elseif (is_array($value)) { if (count($value) != 1) { return $plural_suffix; } } return $singular_suffix; }, array('is_safe' => False)); $lib->filter('phone2numeric', function ($value) { $char2number = array('a' => '2', 'b' => '2', 'c' => '2', 'd' => '3', 'e' => '3', 'f' => '3', 'g' => '4', 'h' => '4', 'i' => '4', 'j' => '5', 'k' => '5', 'l' => '5', 'm' => '6', 'n' => '6', 'o' => '6', 'p' => '7', 'q' => '7', 'r' => '7', 's' => '7', 't' => '8', 'u' => '8', 'v' => '8', 'w' => '9', 'x' => '9', 'y' => '9', 'z' => '9'); foreach ($char2number as $k => $v) { $value = str_ireplace($k, $v, $value);