<commit_before>use crate::context::{BlockParams, Context};
use crate::error::RenderError;
use crate::helpers::{HelperDef, HelperResult};
use crate::output::Output;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext, Renderable};
use crate::value::JsonTruthy;

#[derive(Clone, Copy)]
pub struct WithHelper;

impl HelperDef for WithHelper {
    fn call<'reg: 'rc, 'rc>(
        &self,
        h: &Helper<'reg, 'rc>,
        r: &'reg Registry,
        ctx: &'rc Context,
        rc: &mut RenderContext<'reg>,
        out: &mut dyn Output,
    ) -> HelperResult {
        let param = h
            .param(0)
            .ok_or_else(|| RenderError::new("Param not found for helper \"with\""))?;

        rc.promote_local_vars();
        let local_path_root = param.path_root();

        let result = {
            let mut local_rc = rc.derive();

            let not_empty = param.value().is_truthy(false);
            let template = if not_empty { h.template() } else { h.inverse() };

            if let Some(path_root) = local_path_root {
                local_rc.push_local_path_root(path_root.to_vec());
            }

            if not_empty {
                let new_path = param.context_path();
                if let Some(new_path) = new_path {
                    local_rc.set_path(new_path.clone());
                }

                if let Some(block_param) = h.block_param() {
                    let mut params = BlockParams::new();
                    if new_path.is_some() {
                        params.add_path(block_param, local_rc.get_path().clone())?;
                    } else {
                        params.add_value(block_param, param.value().clone())?;
                    }

                    local_rc.push_block_context(params)?;
                }
            }

            match template {
                Some(t) => t.render(r, ctx, &mut local_rc, out),
                None => Ok(()),
            }<commit_msg>(refactor) avoid render_context clone in with helper<commit_after>use crate::context::{BlockParams, Context};
use crate::error::RenderError;
use crate::helpers::{HelperDef, HelperResult};
use crate::output::Output;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext, Renderable};
use crate::value::JsonTruthy;

#[derive(Clone, Copy)]
pub struct WithHelper;

impl HelperDef for WithHelper {
    fn call<'reg: 'rc, 'rc>(
        &self,
        h: &Helper<'reg, 'rc>,
        r: &'reg Registry,
        ctx: &'rc Context,
        rc: &mut RenderContext<'reg>,
        out: &mut dyn Output,
    ) -> HelperResult {
        let param = h
            .param(0)
            .ok_or_else(|| RenderError::new("Param not found for helper \"with\""))?;

        rc.promote_local_vars();
        let local_path_root = param.path_root();

        let result = {
            let not_empty = param.value().is_truthy(false);
            let template = if not_empty { h.template() } else { h.inverse() };

            if let Some(path_root) = local_path_root {
                rc.push_local_path_root(path_root.to_vec());
            }

            if not_empty {
                let new_path = param.context_path();
                if let Some(new_path) = new_path {
                    rc.set_path(new_path.clone());
                }

                if let Some(block_param) = h.block_param() {
                    let mut params = BlockParams::new();
                    if new_path.is_some() {
                        params.add_path(block_param, rc.get_path().clone())?;
                    } else {
                        params.add_value(block_param, param.value().clone())?;
                    }

                    rc.push_block_context(params)?;
                }
            }

            let result = match template {
                Some(t) => t.render(r, ctx, rc, out),
                None => Ok(()),
            };

            if h.has_block_param() {
                rc.pop_block_context();
            }

            if local_path_root.is_some() {
                rc.pop_local_path_root();
            }

            result
{'fraction_non_alphanumeric': 0.127215343529983, 'fraction_numerical': 0.00048555474629764507, 'mean_word_length': 1.7140974967061924, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 15, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '211241', 'n_tokens_mistral': 1205, 'n_tokens_neox': 1182, 'n_words': 252}