aboutsummaryrefslogtreecommitdiffstats
path: root/askama_shared/src
diff options
context:
space:
mode:
authorLibravatar vallentin <mail@vallentin.dev>2020-12-23 15:04:54 +0100
committerLibravatar Dirkjan Ochtman <dirkjan@ochtman.nl>2020-12-25 22:42:44 +0100
commitfd4ece308e851afe0653ab2b2ad2060914de7486 (patch)
tree6891dda6bf8439c679e2433a7c7d60f70ed01f2b /askama_shared/src
parentc7697cbd406dce0962618e99a6b78116b14fdb1c (diff)
downloadaskama-fd4ece308e851afe0653ab2b2ad2060914de7486.tar.gz
askama-fd4ece308e851afe0653ab2b2ad2060914de7486.tar.bz2
askama-fd4ece308e851afe0653ab2b2ad2060914de7486.zip
Added support for redefining variables (fixes #329)
Diffstat (limited to '')
-rw-r--r--askama_shared/src/generator.rs39
1 files changed, 34 insertions, 5 deletions
diff --git a/askama_shared/src/generator.rs b/askama_shared/src/generator.rs
index ab964e9..b5f98ec 100644
--- a/askama_shared/src/generator.rs
+++ b/askama_shared/src/generator.rs
@@ -876,16 +876,34 @@ impl<'a, S: std::hash::BuildHasher> Generator<'a, S> {
match *var {
Target::Name(name) => {
- if !self.locals.contains(&name) {
+ let meta = self.locals.get(&name).cloned();
+
+ let shadowed = matches!(&meta, Some(meta) if meta.initialized);
+ if shadowed {
+ // Need to flush the buffer if the variable is being shadowed,
+ // to ensure the old variable is used.
+ self.write_buf_writable(buf)?;
+ }
+ if shadowed || meta.is_none() {
buf.write("let ");
- self.locals.insert_with_default(name);
}
buf.write(name);
+
+ self.locals.insert(name, LocalMeta::initialized());
}
Target::Tuple(ref targets) => {
+ let shadowed = targets
+ .iter()
+ .any(|name| matches!(self.locals.get(&name), Some(meta) if meta.initialized));
+ if shadowed {
+ // Need to flush the buffer if the variable is being shadowed,
+ // to ensure the old variable is used.
+ self.write_buf_writable(buf)?;
+ }
+
buf.write("let (");
for name in targets {
- self.locals.insert_with_default(name);
+ self.locals.insert(name, LocalMeta::initialized());
buf.write(name);
buf.write(",");
}
@@ -1576,14 +1594,25 @@ impl Buffer {
}
}
-#[derive(Default)]
+#[derive(Clone, Default)]
struct LocalMeta {
refs: Option<String>,
+ initialized: bool,
}
impl LocalMeta {
+ fn initialized() -> Self {
+ Self {
+ refs: None,
+ initialized: true,
+ }
+ }
+
fn with_ref(refs: String) -> Self {
- Self { refs: Some(refs) }
+ Self {
+ refs: Some(refs),
+ initialized: true,
+ }
}
}