mirror of
https://github.com/askama-rs/askama.git
synced 2025-09-27 13:00:57 +00:00
parser: reject extends
below top-level, too
This commit is contained in:
parent
b744cab2be
commit
52c4dfd8c3
@ -38,8 +38,27 @@ pub enum Node<'a> {
|
||||
|
||||
impl<'a: 'l, 'l> Node<'a> {
|
||||
pub(super) fn parse_template(i: &mut InputStream<'a, 'l>) -> ParseResult<'a, Vec<Box<Self>>> {
|
||||
let mut p = parse_with_unexpected_fallback(Self::many, unexpected_tag);
|
||||
let nodes = p.parse_next(i)?;
|
||||
let mut nodes = vec![];
|
||||
let mut allow_extends = true;
|
||||
while let Some(node) = parse_with_unexpected_fallback(
|
||||
opt(move |i: &mut _| Self::one(i, allow_extends)),
|
||||
unexpected_tag,
|
||||
)
|
||||
.parse_next(i)?
|
||||
{
|
||||
if allow_extends {
|
||||
match &*node {
|
||||
// Since comments don't impact generated code, we allow them before `extends`.
|
||||
Node::Comment(_) => {}
|
||||
// If it only contains whitespace characters, it's fine too.
|
||||
Node::Lit(lit) if lit.val.is_empty() => {}
|
||||
// Everything else must not come before an `extends` block.
|
||||
_ => allow_extends = false,
|
||||
}
|
||||
}
|
||||
nodes.push(node);
|
||||
}
|
||||
|
||||
if !i.is_empty() {
|
||||
opt(unexpected_tag).parse_next(i)?;
|
||||
return cut_error!(
|
||||
@ -53,27 +72,13 @@ impl<'a: 'l, 'l> Node<'a> {
|
||||
}
|
||||
|
||||
fn many(i: &mut InputStream<'a, 'l>) -> ParseResult<'a, Vec<Box<Self>>> {
|
||||
let mut nb_nodes = 0;
|
||||
|
||||
repeat(0.., move |i: &mut _| Self::parse_nodes(i, &mut nb_nodes))
|
||||
.map(|v: Vec<_>| v)
|
||||
.parse_next(i)
|
||||
repeat(0.., |i: &mut _| Self::one(i, false)).parse_next(i)
|
||||
}
|
||||
|
||||
fn parse_nodes(
|
||||
i: &mut InputStream<'a, 'l>,
|
||||
nb_nodes: &mut usize,
|
||||
) -> ParseResult<'a, Box<Self>> {
|
||||
fn one(i: &mut InputStream<'a, 'l>, allow_extends: bool) -> ParseResult<'a, Box<Self>> {
|
||||
let node = alt((Lit::parse, Comment::parse, Self::expr, Self::parse)).parse_next(i)?;
|
||||
match *node {
|
||||
Self::Extends(..) if *nb_nodes > 0 => {
|
||||
return cut_error!("`extends` block must come first in a template", node.span());
|
||||
}
|
||||
// Since comments don't impact generated code, we allow them before `extends`.
|
||||
Self::Comment(..) => {}
|
||||
// If it only contains whitespace characters, it's fine too.
|
||||
Self::Lit(ref lit) if lit.val.trim().is_empty() => {}
|
||||
_ => *nb_nodes += 1,
|
||||
if !allow_extends && let Node::Extends(node) = &*node {
|
||||
return cut_error!("`extends` block must come first in a template", node.span());
|
||||
}
|
||||
Ok(node)
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
error: `extends` blocks are not allowed below top level
|
||||
--> MyTemplate1.txt:3:2
|
||||
error: `extends` block must come first in a template
|
||||
--> <source attribute>:3:2
|
||||
" extends \"bla.txt\" %}\n{% endblock %}\n"
|
||||
--> tests/ui/blocks_below_top_level.rs:4:21
|
||||
|
|
||||
|
Loading…
x
Reference in New Issue
Block a user