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

change failure to thiserror #354

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
116 changes: 51 additions & 65 deletions courses/rust/projects/project-2/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion courses/rust/projects/project-2/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ edition = "2018"

[dependencies]
clap = "2.32.0"
failure = "0.1.5"
thiserror = "1.0"
serde = { version = "1.0.89", features = ["derive"] }
serde_json = "1.0.39"

Expand Down
16 changes: 8 additions & 8 deletions courses/rust/projects/project-2/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ command line_.
- Map in-memory key-indexes to on-disk values
- Periodically compact the log to remove stale data

**Topics**: log-structured file I/O, bitcask, the `failure` crate, `Read` /
**Topics**: log-structured file I/O, bitcask, the `thiserror` crate, `Read` /
`Write` traits, the `serde` crate.

- [Introduction](#user-content-introduction)
Expand Down Expand Up @@ -187,18 +187,18 @@ is crucial to Rust projects: decide on an error handling strategy.
<!-- TODO outline strategies? -->

Rust's error handling is powerful, but involves a lot of boilerplate to use
correctly. For this project the [`failure`] crate will provide the tools to
correctly. For this project the [`thiserror`] crate will provide the tools to
easily handle errors of all kinds.

[`failure`]: https://docs.rs/failure/0.1.5/failure/
[`thiserror`]: https://docs.rs/thiserror/1.0.18/thiserror/

The [failure guide][fg] describes [several] error handling patterns.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This failure guide might be removed or replaced with other materials based on thiserror crate.

Copy link
Author

@mapleFU mapleFU Jun 21, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well, I asked brain anderson about this, but he didn't reply yet. This part shows patterns for using error handling, I think replace it maybe not good.
Would you mind give some suggestion here?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe I can add strikethrough on contents about thiserror @ziyi-yan


[fg]: https://boats.gitlab.io/failure/
[several]: https://boats.gitlab.io/failure/guidance.html

Pick one of those strategies and, in your library, either define your own error
type or import `failure`s `Error`. This is the error type you will use in all of
type or import `thiserror`s `Error`. This is the error type you will use in all of
your `Result`s, converting error types from other crates to your own with the
`?` operator.

Expand Down Expand Up @@ -227,10 +227,10 @@ suite to compile (`cargo test --no-run`).
-->

_Note: Error-handling practices in Rust are still evolving. This course
currently uses the [`failure`] crate to make defining error types easier. While
`failure` has a good design, its use is [arguably not a best practice][nbp]. It
currently uses the [`thiserror`] crate to make defining error types easier. While
`thiserror` has a good design, its use is [arguably not a best practice][nbp]. It
may not continue to be viewed favorably by Rust experts. Future iterations
of the course will likely not use `failure`. In the meantime, it is fine, and
of the course will likely not use `thiserror`. In the meantime, it is fine, and
presents an opportunity to learn more of the history and nuance of Rust error
handling._

Expand Down Expand Up @@ -258,7 +258,7 @@ This is the basic behavior of `kvs` with a log:
- "set"
- The user invokes `kvs set mykey myvalue`
- `kvs` creates a value representing the "set" command, containing its key and
value
value
- It then serializes that command to a `String`
- It then appends the serialized command to a file containing the log
- If that succeeds, it exits silently with error code 0
Expand Down
28 changes: 8 additions & 20 deletions courses/rust/projects/project-2/src/error.rs
Original file line number Diff line number Diff line change
@@ -1,35 +1,23 @@
use failure::Fail;
use std::io;
use thiserror::Error;

/// Error type for kvs.
#[derive(Fail, Debug)]
#[derive(Error, Debug)]
pub enum KvsError {
/// IO error.
#[fail(display = "{}", _0)]
Io(#[cause] io::Error),
#[error("`{0}`")]
Io(#[from] io::Error),
/// Serialization or deserialization error.
#[fail(display = "{}", _0)]
Serde(#[cause] serde_json::Error),
#[error("`{0}`")]
Serde(#[from] serde_json::Error),
/// Removing non-existent key error.
#[fail(display = "Key not found")]
#[error("Key not found")]
KeyNotFound,
/// Unexpected command type error.
/// It indicated a corrupted log or a program bug.
#[fail(display = "Unexpected command type")]
#[error("Unexpected command type")]
UnexpectedCommandType,
}

impl From<io::Error> for KvsError {
fn from(err: io::Error) -> KvsError {
KvsError::Io(err)
}
}

impl From<serde_json::Error> for KvsError {
fn from(err: serde_json::Error) -> KvsError {
KvsError::Serde(err)
}
}

/// Result type for kvs.
pub type Result<T> = std::result::Result<T, KvsError>;
Loading