I have the function split_parse that splits and parses a given string by a given separator using FromStr.
Also, I've implemented FromStr for my own type and it has Err = anyhow::Error
And I can't use this type with split_parse because
trait std::error::Error is not implemented for anyhow::Error
What can I do with this?
I've tried changing Err constraint from std::error::Error to Into<anyhow::Error>, but that did not work.
Also, I can create its own ErrorType for my FromStr, but I don't want to do this.
use anyhow::{Context, Result};
use std::{str::FromStr};
pub fn split_parse<T: FromStr>(data: &str, sep: &str) -> Result<Vec<T>>
where
<T as FromStr>::Err: Send,
<T as FromStr>::Err: Sync,
<T as FromStr>::Err: std::error::Error,
<T as FromStr>::Err: 'static,
{
data.split(sep)
.map(|it| it.parse::<T>().context(format!("can't parse '{}'", it)))
.collect()
}
#[derive(Debug)]
pub struct Foo(i32);
impl FromStr for Foo {
type Err = anyhow::Error;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let i: i32 = s.parse()?;//.with_context(|| format!("parsing {:?}", s))?;
Ok(Foo(i))
}
}
fn main() -> Result<()> {
// works for standart types
println!("{:?}", split_parse::<i32>("100,200,300", ",")?);
// FromStr for Foo also works
println!("{:?}", "100".parse::<Foo>()?);
// std::error::Error` is not implemented for `anyhow::Error`
println!("{:?}", split_parse::<Foo>("100,200,300", ",")?);
Ok(())
}
There are some non-public traits involved in Context conformances so I think the simplest solution is just to explicitly ask for the Context bound on Result
pub fn split_parse<T: FromStr>(data: &str, sep: &str) -> Result<Vec<T>>
where
<T as FromStr>::Err: Send,
<T as FromStr>::Err: Sync,
Result<T, <T as FromStr>::Err>: Context<T, <T as FromStr>::Err>,
<T as FromStr>::Err: 'static,