I did it backwards, I needed to use the explicit context from the block, not the inline partial.

This commit is contained in:
Tom Alexander 2020-05-25 19:22:20 -04:00
parent 6845df7f96
commit 25eb9b10a0
Signed by: talexander
GPG Key ID: D3A179C9A53C0EDE
3 changed files with 20 additions and 56 deletions

View File

@ -31,7 +31,7 @@ Explicitly setting a context on an inline partial does not work, but it does not
Explicitly setting a context on a block does work. Explicitly setting a context on a block does work.
The explicit context for inline partials is evaluated in the context for that template file containing the block, not the inline partial (so, whatever the context is when we invoke the partial containing the block). The explicit context for blocks is evaluated in the context for that template file containing the block, not the inline partial (so, whatever the context is when we invoke the partial containing the block).
References References
---------- ----------

View File

@ -1,23 +1,18 @@
use crate::parser::Body; use crate::parser::Body;
use crate::parser::DustTag; use crate::parser::DustTag;
use crate::parser::Template; use crate::parser::Template;
use crate::parser::{Path, TemplateElement}; use crate::parser::TemplateElement;
use std::collections::HashMap; use std::collections::HashMap;
pub struct InlinePartialTreeValue<'a> {
explicit_context: &'a Option<Path<'a>>,
body: &'a Option<Body<'a>>,
}
pub struct InlinePartialTreeElement<'a> { pub struct InlinePartialTreeElement<'a> {
parent: Option<&'a InlinePartialTreeElement<'a>>, parent: Option<&'a InlinePartialTreeElement<'a>>,
blocks: HashMap<&'a str, InlinePartialTreeValue<'a>>, blocks: HashMap<&'a str, &'a Option<Body<'a>>>,
} }
impl<'a> InlinePartialTreeElement<'a> { impl<'a> InlinePartialTreeElement<'a> {
pub fn new( pub fn new(
parent: Option<&'a InlinePartialTreeElement<'a>>, parent: Option<&'a InlinePartialTreeElement<'a>>,
blocks: HashMap<&'a str, InlinePartialTreeValue<'a>>, blocks: HashMap<&'a str, &'a Option<Body<'a>>>,
) -> InlinePartialTreeElement<'a> { ) -> InlinePartialTreeElement<'a> {
InlinePartialTreeElement { InlinePartialTreeElement {
parent: parent, parent: parent,
@ -25,40 +20,21 @@ impl<'a> InlinePartialTreeElement<'a> {
} }
} }
fn get_value(&self, name: &str) -> Option<&InlinePartialTreeValue<'a>> { pub fn get_block(&self, name: &str) -> Option<&'a Option<Body<'a>>> {
match self.blocks.get(name) { match self.blocks.get(name) {
None => match self.parent { None => match self.parent {
None => None, None => None,
Some(parent_tree_element) => parent_tree_element.get_value(name), Some(parent_tree_element) => parent_tree_element.get_block(name),
}, },
Some(interior) => Some(interior), Some(interior) => Some(interior),
} }
} }
/// Recursively get the body of a block by name
///
/// Returning a double-option because there is a functional
/// difference between not finding the block and not having a
/// body.
pub fn get_block(&self, name: &str) -> Option<&'a Option<Body<'a>>> {
self.get_value(name).map(|interior| interior.body)
}
/// Recursively get the explicit from the inline partial by name
///
/// Returning a double-option because there is a functional
/// difference between not finding the block and not having a
/// body.
pub fn get_explicit_context(&self, name: &str) -> Option<&Option<Path<'a>>> {
self.get_value(name)
.map(|interior| interior.explicit_context)
}
} }
pub fn extract_inline_partials<'a>( pub fn extract_inline_partials<'a>(
template: &'a Template<'a>, template: &'a Template<'a>,
) -> HashMap<&'a str, InlinePartialTreeValue<'a>> { ) -> HashMap<&'a str, &'a Option<Body<'a>>> {
let mut blocks: HashMap<&'a str, InlinePartialTreeValue<'a>> = HashMap::new(); let mut blocks: HashMap<&'a str, &'a Option<Body<'a>>> = HashMap::new();
extract_inline_partials_from_body(&mut blocks, &template.contents); extract_inline_partials_from_body(&mut blocks, &template.contents);
@ -66,7 +42,7 @@ pub fn extract_inline_partials<'a>(
} }
fn extract_inline_partials_from_body<'a, 'b>( fn extract_inline_partials_from_body<'a, 'b>(
blocks: &'b mut HashMap<&'a str, InlinePartialTreeValue<'a>>, blocks: &'b mut HashMap<&'a str, &'a Option<Body<'a>>>,
body: &'a Body<'a>, body: &'a Body<'a>,
) { ) {
for elem in &body.elements { for elem in &body.elements {
@ -81,7 +57,7 @@ fn extract_inline_partials_from_body<'a, 'b>(
} }
fn extract_inline_partials_from_tag<'a, 'b>( fn extract_inline_partials_from_tag<'a, 'b>(
blocks: &'b mut HashMap<&'a str, InlinePartialTreeValue<'a>>, blocks: &'b mut HashMap<&'a str, &'a Option<Body<'a>>>,
tag: &'a DustTag, tag: &'a DustTag,
) { ) {
match tag { match tag {
@ -121,13 +97,7 @@ fn extract_inline_partials_from_tag<'a, 'b>(
} }
DustTag::DTPartial(..) => (), DustTag::DTPartial(..) => (),
DustTag::DTInlinePartial(named_block) => { DustTag::DTInlinePartial(named_block) => {
blocks.insert( blocks.insert(&named_block.name, &named_block.contents);
&named_block.name,
InlinePartialTreeValue {
explicit_context: &named_block.explicit_context,
body: &named_block.contents,
},
);
} }
DustTag::DTBlock(..) => (), DustTag::DTBlock(..) => (),
DustTag::DTHelperEquals(parameterized_block) => { DustTag::DTHelperEquals(parameterized_block) => {

View File

@ -343,27 +343,21 @@ impl<'a> DustRenderer<'a> {
return Ok("".to_owned()); return Ok("".to_owned());
} }
DustTag::DTBlock(named_block) => { DustTag::DTBlock(named_block) => {
let new_breadcrumbs = blocks let new_breadcrumbs = Self::new_breadcrumbs(
.blocks
.get_explicit_context(named_block.name)
.map(|explicit_context| {
Self::new_breadcrumbs(
breadcrumbs, breadcrumbs,
blocks.breadcrumbs, blocks.breadcrumbs,
None, None,
explicit_context, &named_block.explicit_context,
None, None,
) );
})
.flatten();
return match blocks.blocks.get_block(named_block.name) { return match blocks.blocks.get_block(named_block.name) {
None => self.render_maybe_body( None => self.render_maybe_body(
&named_block.contents, &named_block.contents,
new_breadcrumbs.as_ref().unwrap_or(breadcrumbs), new_breadcrumbs.as_ref().unwrap_or(breadcrumbs),
blocks, blocks,
), ),
Some(interior) => self.render_maybe_body( Some(inline_partial) => self.render_maybe_body(
interior, inline_partial,
new_breadcrumbs.as_ref().unwrap_or(breadcrumbs), new_breadcrumbs.as_ref().unwrap_or(breadcrumbs),
blocks, blocks,
), ),