Announcing error-chain, a library for consistent and reliable Rust error handling

I've just discovered that error-chain seems to not work on 1.10 stable: error-chain doesn't work on stable 1.10! · Issue #12 · rust-lang-deprecated/error-chain · GitHub

This is surprising to me since at one point rustup did build on stable.

error-chain 0.3.0 is out. In this revision, foreign errors are stored in the ErrorKind variant instead of boxed into Error's 'cause' field, and the Display impl shows output of the foreign error's Display impl instead of the simple description.

0.3.0

Contributors: Brian Anderson, Taylor Cramer

There's a PR open against error-chain that introduces a major breaking change, and I'm curious what people think.

So after the last release that changes how foreign links are represented, their 'description' is basically useless. As a reminder the description is the string here:

error_chain! {
    ...

    foreign_links {
        ForeignError, ForeignErrorKind, "description"
    }
}

So this PR removes it completely, with no backwards-compatibility considerations. My inclination is to just do it, along with a major version bump (0.3 -> 0.4 - cargo considers minor bumps less than 1.0 to be incompatible). ISTM that this library is immature enough, and has few enough users that when they do decide to upgrade it's not such a big deal to make the changes. But it may be possible to have the macro continue parsing the description and throw it away. Any opinions?

I think this breaking change is a good idea: I've personally never been 100% sure as to the purpose of the description. It somehow always seemed "extra" to me in the foreign_links section. And as the PR author mentions, fixing the code that'll break because of this change isn't too difficult.

I'm entirely in favor of this change. Please document it in the README as a release note for people upgrading from previous versions, but otherwise, this seems like a great refinement of the library.

error-chain 0.4.2 is out. In this release the foreign_links no longer take a description, and all sections are optional.

Note though the implementation of optional sections is lacking. It allows you to duplicate the section, and if you do then things will go bad. If anybody has an easy fix for this please help me!

You'll also see below that I failed to release this twice... Long day.

0.4.2

Contributors: Brian Anderson

0.4.1 (yanked)

Contributors: Brian Anderson

0.4.0 (yanked)

Contributors: Brian Anderson, Taylor Cramer

2 Likes

I made a pull request.

2 Likes

Thanks @birkenfeld!

error-chain 0.5.0 is out. In this revision backtraces are only collected when RUST_BACKTRACE is on, which brings behavior inline with the upstream panic backtraces and works around performance problems present in Windows backtrace generation. This means that the backtrace is stored in an Option now, making this a breaking change. It may be worth thinking about additional programmatic ways to turn on backtraces. This also improves handling of repeated 'sections', and the 'types' section now must not repeat.

0.5.0

Contributors: benaryorg, Brian Anderson, Georg Brandl

1 Like

error-chain 0.7.1 is out. This release reverts some changes from the 0.6 series that caused regressions in inference and usability. It also comes with a new bail! macro, syntax sugar for early return with type conversions.

The main things to be aware of compared to 0.6:

Declaring links { } again requires the ErrorKind name:

links {
    Utils(::utils::Error, ::utils::ErrorKind);
}

The ResultExt trait is once again defined by the error_chain! macro, not in the error_chain crate, and so must be mentioned in the types { } block:

types {
    Error, ErrorKind, ResultExt, Result;
}

The Error kind is again a tuple, not a struct, and is matched like a tuple:

match Error::from("error!") {
    Error(ErrorKind::InvalidToolchainName(_), _) => { }
    Error(ErrorKind::Msg(_), _) => { }
}

And the bail! macro:

fn foo() -> Result<()> {
    if bad_condition() {
        bail!(ErrorKind::FooError);
    }

    Ok(())
}

Which also works with fmt specifiers:

fn foo() -> Result<()> {
    if bad_condition() {
        bail!("bad stuff happened: {}", bad_stuff);
    }

    Ok(())
}

The bail! macro is inspired by a similar macro in Cargo and a similar throw construct in the exception handling RFC.

Finally, thanks to @Yamakaky for taking on some of the error-chain maintenance responsibilities in the last few weeks.

Contributors: Brian Anderson, Yamakaky

0.7.1

0.7.0

4 Likes