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

Combine error types #104

Merged
merged 7 commits into from Feb 10, 2017
Merged

Combine error types #104

merged 7 commits into from Feb 10, 2017

Conversation

@ZoeyR
Copy link
Collaborator

ZoeyR commented Feb 1, 2017

Closes #100

@dtolnay
Copy link
Collaborator

dtolnay commented Feb 1, 2017

I can recommend what I have done for serde::de::value::Error, serde_json::Error and serde_yaml::Error which is hide them behind an opaque newtype wrapper.

pub struct Error(Box<ErrorImpl>);

enum ErrorImpl {
    /* variants */
}

The Box is to drop the size of Error from 48 bytes down to 8 bytes which sped up performance of all of serde_json by 5%, and the newtype wrapper is to let us add or change error variants without a breaking change. Nobody actually pattern-matches on these errors - they just print the message and fail.

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 1, 2017

Sounds like a good idea. @TyOverby what do you think?

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 1, 2017

@dtolnay @dgriffen: I'm all for sticking it inside of a Box, but my use-cases for bincode require pattern matching on the error: I really care if the deserialization failed because of a dropped network connection (IoError) or because they sent bad bytes over the wire (programmer error).

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 1, 2017

I am surprised that allocating is cheaper than moving an extra 40 bytes though.

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 1, 2017

Oh, I guess if you rarely hit error cases, then it's a pretty good speedup in the happy-path.

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 1, 2017

Oops, looks like I made a mistake when fixing conflicts. That's the last time I use the Github's conflict resolver.

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 1, 2017

So how should I move forward with any changes to Error? It sounds like we either change the Result type to carry a Box<Error> or do what @dtolnay said, but make ErrorImpl public and give it a better name if we want pattern matching.

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 3, 2017

@dgriffen: yeah, that sounds like a good move forward! Off the top of my head I can't think of a good enum name though. ErrorKind maybe?

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 3, 2017

ErrorKind sounds good to me.

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 3, 2017

I tried to resolve the merge conflicts with githubs online tool. Let's see if it actually worked!

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 3, 2017

Looks like you kept the old error types

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 3, 2017

Well, that's the last time I use that tool.

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 3, 2017

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 3, 2017

And here I thought I was helping :|

@ZoeyR
Copy link
Collaborator Author

ZoeyR commented Feb 3, 2017

Looks like a few more merge errors that didnt get caught, I'll clean those up

@TyOverby
Copy link
Collaborator

TyOverby commented Feb 3, 2017

@dtolnay Want to do another pass?

match *self {
ErrorKind::IoError(ref err) => error::Error::description(err),
ErrorKind::InvalidEncoding(ref ib) => ib.desc,
ErrorKind::SequenceMustHaveLength => "bincode can't encode infinite sequences",

This comment has been minimized.

@dtolnay

dtolnay Feb 3, 2017

Collaborator

I don't think this error is accurate - the one you have in Display is a better characterization of SequenceMustHaveLength.

ErrorKind::SequenceMustHaveLength =>
write!(fmt, "Bincode can only encode sequences and maps that have a knowable size ahead of time."),
ErrorKind::SizeLimit =>
write!(fmt, "SizeLimit"),

This comment has been minimized.

@dtolnay

dtolnay Feb 3, 2017

Collaborator

This is the Display representation not the Debug representation, so please make this message self-explanatory.

fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
match *self {
ErrorKind::IoError(ref ioerr) =>
write!(fmt, "IoError: {}", ioerr),

This comment has been minimized.

@dtolnay

dtolnay Feb 3, 2017

Collaborator

Rust identifiers like IoError belong in the Debug representation. For the Display representation I would prefer "IO error: {}".

ErrorKind::IoError(ref ioerr) =>
write!(fmt, "IoError: {}", ioerr),
ErrorKind::InvalidEncoding(ref ib) =>
write!(fmt, "InvalidEncoding: {}", ib),

This comment has been minimized.

@dtolnay

dtolnay Feb 3, 2017

Collaborator

Ditto here - "invalid encoding: {}".

@dtolnay
Copy link
Collaborator

dtolnay commented Feb 3, 2017

The code looks good but the error messages are not as helpful as they could be. Ok to merge and follow up under #98 in another PR.

@ZoeyR ZoeyR mentioned this pull request Feb 9, 2017
@TyOverby
Copy link
Collaborator

TyOverby commented Feb 10, 2017

Looks good! We'll take care of error messages as a part of #98

@TyOverby TyOverby merged commit 9cfa2e0 into servo:master Feb 10, 2017
1 check passed
1 check passed
continuous-integration/travis-ci/pr The Travis CI build passed
Details
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked issues

Successfully merging this pull request may close these issues.

None yet

3 participants
You can’t perform that action at this time.