Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor more RenderError into RenderErrorReason #581

Merged
merged 5 commits into from
May 18, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
24 changes: 12 additions & 12 deletions examples/decorator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,8 @@ use std::error::Error;
use serde_json::value::{Map, Value as Json};

use handlebars::{
to_json, Context, Decorator, Handlebars, Helper, JsonRender, Output, RenderContext, RenderError,
to_json, Context, Decorator, Handlebars, Helper, JsonRender, Output, RenderContext,
RenderError, RenderErrorReason,
};

// default format helper
Expand All @@ -22,7 +23,7 @@ fn format_helper(
// get parameter from helper or throw an error
let param = h
.param(0)
.ok_or(RenderError::new("Param 0 is required for format helper."))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("format", 0))?;
write!(out, "{} pts", param.value().render())?;
Ok(())
}
Expand All @@ -49,7 +50,7 @@ fn format_decorator(
// get parameter from helper or throw an error
let param = h
.param(0)
.ok_or(RenderError::new("Param 0 is required for format helper."))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("format", 0))?;
write!(out, "{} {}", param.value().render(), suffix)?;
Ok(())
},
Expand Down Expand Up @@ -80,7 +81,7 @@ fn set_decorator(
rc.set_context(Context::wraps(new_ctx_data)?);
Ok(())
} else {
Err(RenderError::new("Cannot extend non-object data"))
Err(RenderErrorReason::Other("Cannot extend non-object data".to_owned()).into())
}
}

Expand All @@ -92,19 +93,18 @@ fn rank_helper(
_: &mut RenderContext,
out: &mut dyn Output,
) -> Result<(), RenderError> {
let rank = h
.param(0)
.and_then(|v| v.value().as_u64())
.ok_or(RenderError::new(
"Param 0 with u64 type is required for rank helper.",
))? as usize;
let rank = h.param(0).and_then(|v| v.value().as_u64()).ok_or(
RenderErrorReason::ParamTypeMismatchForName("rank", "0".to_string(), "u64".to_string()),
)? as usize;
let total = h
.param(1)
.as_ref()
.and_then(|v| v.value().as_array())
.map(|arr| arr.len())
.ok_or(RenderError::new(
"Param 1 with array type is required for rank helper",
.ok_or(RenderErrorReason::ParamTypeMismatchForName(
"rank",
"1".to_string(),
"array".to_string(),
))?;
if rank == 0 {
out.write("champion")?;
Expand Down
6 changes: 4 additions & 2 deletions examples/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@ extern crate serde_json;

use std::error::Error as StdError;

use handlebars::{Context, Handlebars, Helper, Output, RenderContext, RenderError};
use handlebars::{
Context, Handlebars, Helper, Output, RenderContext, RenderError, RenderErrorReason,
};
use thiserror::Error;

#[derive(Debug, Error)]
Expand All @@ -26,7 +28,7 @@ pub fn error_helper(
) -> Result<(), RenderError> {
let param = h
.param(0)
.ok_or(RenderError::new("Param 0 is required for error helper."))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("error", 0))?;
match param.value().as_str() {
Some("db") => Err(RenderError::from_error(
"helper error",
Expand Down
18 changes: 9 additions & 9 deletions examples/render.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use std::error::Error;

use handlebars::{
to_json, Context, Handlebars, Helper, JsonRender, Output, RenderContext, RenderError,
RenderErrorReason,
};

// define a custom helper
Expand All @@ -23,7 +24,7 @@ fn format_helper(
// get parameter from helper or throw an error
let param = h
.param(0)
.ok_or(RenderError::new("Param 0 is required for format helper."))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("format", 0))?;
write!(out, "{} pts", param.value().render())?;
Ok(())
}
Expand All @@ -36,19 +37,18 @@ fn rank_helper(
_: &mut RenderContext,
out: &mut dyn Output,
) -> Result<(), RenderError> {
let rank = h
.param(0)
.and_then(|v| v.value().as_u64())
.ok_or(RenderError::new(
"Param 0 with u64 type is required for rank helper.",
))? as usize;
let rank = h.param(0).and_then(|v| v.value().as_u64()).ok_or(
RenderErrorReason::ParamTypeMismatchForName("rank", "0".to_string(), "u64".to_string()),
)? as usize;
let total = h
.param(1)
.as_ref()
.and_then(|v| v.value().as_array())
.map(|arr| arr.len())
.ok_or(RenderError::new(
"Param 1 with array type is required for rank helper",
.ok_or(RenderErrorReason::ParamTypeMismatchForName(
"rank",
"1".to_string(),
"array".to_string(),
))?;
if rank == 0 {
out.write("champion")?;
Expand Down
19 changes: 10 additions & 9 deletions examples/render_file.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ use std::io::{Read, Write};

use handlebars::{
to_json, Context, Handlebars, Helper, JsonRender, Output, RenderContext, RenderError,
RenderErrorReason,
};

// define a custom helper
Expand All @@ -24,9 +25,10 @@ fn format_helper(
_: &mut RenderContext,
out: &mut dyn Output,
) -> Result<(), RenderError> {
// get parameter from helper or throw an error
let param = h
.param(0)
.ok_or(RenderError::new("Param 0 is required for format helper."))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("format", 0))?;
write!(out, "{} pts", param.value().render())?;
Ok(())
}
Expand All @@ -39,19 +41,18 @@ fn rank_helper(
_: &mut RenderContext,
out: &mut dyn Output,
) -> Result<(), RenderError> {
let rank = h
.param(0)
.and_then(|ref v| v.value().as_u64())
.ok_or(RenderError::new(
"Param 0 with u64 type is required for rank helper.",
))? as usize;
let rank = h.param(0).and_then(|v| v.value().as_u64()).ok_or(
RenderErrorReason::ParamTypeMismatchForName("rank", "0".to_string(), "u64".to_string()),
)? as usize;
let total = h
.param(1)
.as_ref()
.and_then(|v| v.value().as_array())
.map(|arr| arr.len())
.ok_or(RenderError::new(
"Param 1 with array type is required for rank helper",
.ok_or(RenderErrorReason::ParamTypeMismatchForName(
"rank",
"1".to_string(),
"array".to_string(),
))?;
if rank == 0 {
out.write("champion")?;
Expand Down
7 changes: 4 additions & 3 deletions src/decorators/inline.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,19 @@ use crate::decorators::{DecoratorDef, DecoratorResult};
use crate::error::RenderError;
use crate::registry::Registry;
use crate::render::{Decorator, RenderContext};
use crate::RenderErrorReason;

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

fn get_name<'reg: 'rc, 'rc>(d: &Decorator<'rc>) -> Result<String, RenderError> {
d.param(0)
.ok_or_else(|| RenderError::new("Param required for decorator \"inline\""))
.ok_or_else(|| RenderErrorReason::ParamNotFoundForIndex("inline", 0).into())
.and_then(|v| {
v.value()
.as_str()
.map(|v| v.to_owned())
.ok_or_else(|| RenderError::new("inline name must be string"))
.ok_or_else(|| RenderErrorReason::InvalidParamType("String").into())
})
}

Expand All @@ -30,7 +31,7 @@ impl DecoratorDef for InlineDecorator {

let template = d
.template()
.ok_or_else(|| RenderError::new("inline should have a block"))?;
.ok_or(RenderErrorReason::BlockContentRequired)?;

rc.set_partial(name, template);
Ok(())
Expand Down
49 changes: 35 additions & 14 deletions src/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -75,22 +75,41 @@ impl From<TemplateError> for RenderError {
/// Template rendering error
#[derive(Debug, Error)]
pub enum RenderErrorReason {
#[error("missing variable path {0:?}")]
#[error("Template not found {0}")]
TemplateNotFound(String),
#[error("Failed to access variable in strict mode {0:?}")]
MissingVariable(Option<String>),
#[error("partial not found {0}")]
#[error("Partial not found {0}")]
PartialNotFound(String),
#[error("Helper not found {0}")]
HelperNotFound(String),
#[error("Helper/Decorator {0} param at index {1} required but not found")]
ParamNotFoundForIndex(&'static str, usize),
#[error("Helper/Decorator {0} param with name {1} required but not found")]
ParamNotFoundForName(&'static str, String),
#[error("Helper/Decorator {0} param with name {1} type mismatch for {2}")]
ParamTypeMismatchForName(&'static str, String, String),
#[error("Helper/Decorator {0} hash with name {1} type mismatch for {2}")]
HashTypeMismatchForName(&'static str, String, String),
#[error("Decorator not found {0}")]
DecoratorNotFound(String),
#[error("Can not include current template in partial")]
CannotIncludeSelf,
#[error("Invalid logging level: {0}")]
InvalidLoggingLevel(String),
#[error("Invalid param type, {0} expected")]
InvalidParamType(&'static str),
#[error("Block content required")]
BlockContentRequired,
#[error("Invalid json path {0}")]
InvalidJsonPath(String),
#[error("{0}")]
Other(String),
}

impl From<RenderErrorReason> for RenderError {
fn from(e: RenderErrorReason) -> RenderError {
match e {
RenderErrorReason::MissingVariable(_) => {
RenderError::from_error("Failed to access variable in strict mode.", e)
}
RenderErrorReason::PartialNotFound(_) => {
RenderError::from_error("Partial not found.", e)
}
}
RenderError::from_error(&e.to_string(), e)
}
}

Expand All @@ -109,6 +128,7 @@ impl From<ScriptError> for RenderError {
}

impl RenderError {
#[deprecated(since = "5.0.0", note = "Use RenderErrorReason instead")]
pub fn new<T: AsRef<str>>(desc: T) -> RenderError {
RenderError {
desc: desc.as_ref().to_owned(),
Expand All @@ -131,10 +151,11 @@ impl RenderError {
where
E: StdError + Send + Sync + 'static,
{
let mut e = RenderError::new(error_info);
e.cause = Some(Box::new(cause));

e
RenderError {
desc: error_info.to_owned(),
cause: Some(Box::new(cause)),
..Default::default()
}
}

#[inline]
Expand Down
3 changes: 2 additions & 1 deletion src/helpers/helper_each.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use crate::output::Output;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext, Renderable};
use crate::util::copy_on_push_vec;
use crate::RenderErrorReason;

fn update_block_context(
block: &mut BlockContext<'_>,
Expand Down Expand Up @@ -74,7 +75,7 @@ impl HelperDef for EachHelper {
) -> HelperResult {
let value = h
.param(0)
.ok_or_else(|| RenderError::new("Param not found for helper \"each\""))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("each", 0))?;

let template = h.template();

Expand Down
4 changes: 2 additions & 2 deletions src/helpers/helper_if.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
use crate::context::Context;
use crate::error::RenderError;
use crate::helpers::{HelperDef, HelperResult};
use crate::json::value::JsonTruthy;
use crate::output::Output;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext, Renderable};
use crate::RenderErrorReason;

#[derive(Clone, Copy)]
pub struct IfHelper {
Expand All @@ -22,7 +22,7 @@ impl HelperDef for IfHelper {
) -> HelperResult {
let param = h
.param(0)
.ok_or_else(|| RenderError::new("Param not found for helper \"if\""))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("if", 0))?;
let include_zero = h
.hash_get("includeZero")
.and_then(|v| v.value().as_bool())
Expand Down
9 changes: 3 additions & 6 deletions src/helpers/helper_log.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
use crate::context::Context;
#[cfg(not(feature = "no_logging"))]
use crate::error::RenderError;
use crate::helpers::{HelperDef, HelperResult};
#[cfg(not(feature = "no_logging"))]
use crate::json::value::JsonRender;
use crate::output::Output;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext};
#[cfg(not(feature = "no_logging"))]
use crate::RenderErrorReason;
#[cfg(not(feature = "no_logging"))]
use log::Level;
#[cfg(not(feature = "no_logging"))]
use std::str::FromStr;
Expand Down Expand Up @@ -46,10 +46,7 @@ impl HelperDef for LogHelper {
if let Ok(log_level) = Level::from_str(level) {
log!(log_level, "{}", param_to_log)
} else {
return Err(RenderError::new(&format!(
"Unsupported logging level {}",
level
)));
return Err(RenderErrorReason::InvalidLoggingLevel(level.to_string()).into());
}
Ok(())
}
Expand Down
5 changes: 3 additions & 2 deletions src/helpers/helper_lookup.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ use crate::helpers::HelperDef;
use crate::json::value::ScopedJson;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext};
use crate::RenderErrorReason;

#[derive(Clone, Copy)]
pub struct LookupHelper;
Expand All @@ -20,10 +21,10 @@ impl HelperDef for LookupHelper {
) -> Result<ScopedJson<'rc>, RenderError> {
let collection_value = h
.param(0)
.ok_or_else(|| RenderError::new("Param not found for helper \"lookup\""))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("lookup", 0))?;
let index = h
.param(1)
.ok_or_else(|| RenderError::new("Insufficient params for helper \"lookup\""))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("lookup", 1))?;

let value = match *collection_value.value() {
Json::Array(ref v) => index.value().as_u64().and_then(|u| v.get(u as usize)),
Expand Down
3 changes: 2 additions & 1 deletion src/helpers/helper_with.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ use crate::json::value::JsonTruthy;
use crate::output::Output;
use crate::registry::Registry;
use crate::render::{Helper, RenderContext, Renderable};
use crate::RenderErrorReason;

#[derive(Clone, Copy)]
pub struct WithHelper;
Expand All @@ -22,7 +23,7 @@ impl HelperDef for WithHelper {
) -> HelperResult {
let param = h
.param(0)
.ok_or_else(|| RenderError::new("Param not found for helper \"with\""))?;
.ok_or(RenderErrorReason::ParamNotFoundForIndex("with", 0))?;

if param.value().is_truthy(false) {
let mut block = create_block(param);
Expand Down