Comments (6)
The only difference is in the behavior of CodeOf function?
Yes, for now, it just makes a difference in CodeOf
function.
MessageOf
does not check "unexpected" wrapper because even if the error is unexpected, I want to provide a hint to fix the error to the developers.
But in the future, I may change MessageOf
to respect "unexpected" errors. I'm still considering which behavior is more appropriate.
How to define unexpected?
With failure
, an unexpected or unknown error is one that doesn't have error code.
So your code
code := failure.StringCode("unknown state")
return 0, failure.New(code)
is a part of expected errors.
Reduce declare Sentinel errors.
const (
NotFound failure.StringCode = "NotFound"
)
I guess you want to reduce this kind of declaration regarding the article, right?
The Sentinel error that is described in the article is one that is completely static.
But failure
allows you to add more information into errors even if you definefailure.Code
as public const variables.
So it is different from the Sentinel error.
I recommend defining all error codes public and use it as a part of your function's/method's interface.
This article may be helpful for you: https://middlemost.com/failure-is-your-domain/
from failure.
@Min-Feng Hello! Let me explain the idea of "unexpected" functions.
To put it simply, if you have already gotten an error from some function call, and that error should not happen, then you can use MarkUnexpected
. If you haven't gotten any errors yet, you can use Unexpected
.
BUT basically, you shouldn't use both two functions unless you want to stop error code propagation. The errors that happen in your application should have some error code as much as possible.
For Unexpected
example,
type State int
const (
A State = iota + 1
B
)
func (s State) Value() (int, error) {
switch s {
case A:
return 10, nil
case B:
return 20, nil
default:
return 0, failure.Unexpected("unexpected state")
}
For here, you don't have an error in default
block, therefore you can use Unexpected
. But if the situation can be expected to happen, you should use New
with some error code instead of Unexpected
.
For MarkUnexpected
example,
const (
NotFound failure.StringCode = "NotFound"
InvalidArgument failure.StringCode = "InvalidArgument"
AlreadyExists failure.StringCode = "AlreadyExists"
)
// CallAPI may return NotFound or InvalidArgument error.
func CallAPI() error {
// do something
}
// Do may return InvalidArgument (doesn't return NotFound or other codes).
func Do() (int, error) {
err := CallAPI()
if err != nil {
switch { // you can also switch with failure.CodeOf, but to be simple here.
case failure.Is(err, NotFound):
return 1, nil
case failure.Is(err, InvalidArgument):
// just return InvalidArgument, but wrap it to add function name Do into err.Error().
return 0, failure.Wrap(err)
default: // I don't expect Do returns other errors.
// since I don't want to propagate other errors like AlreadyExists, wrap the error with MarkUnexpected
return 0, failure.MarkUnexpected(err)
}
}
}
For here, the CallAPI
function may return some error code but I don't want to propagate it transparently. Therefore, I used MarkUnexpected
to prevent returning unexpected error code from the Do
function. If you use Unexpected
here, the original error from CallAPI
is discarded, therefore MarkUnexpected
is more appropriate.
Note: if you wrap an error by MarkUexpected
, the underlying error code is not returned from CodeOf
function.
from failure.
I don't know that stop error code propagation what you mean.
what is the error you're talking about error by std lib or error by StringCode?
failure.Wrap(err) vs failure.MarkUnexpected(err)
What's the difference between them?
They're both error type.
return 0, failure.MarkUnexpected(err)
, the statement does stop error propagation?
But I see the statement still returning error.
return error != propagation ?
My English is poor.
Can you understand my description?
Thank you very much for your detailed reply.
from failure.
I don't know that stop error code propagation what you mean.
what is the error you're talking about error by std lib or error by StringCode?
"Stop error code propagation" means that it performs like it hides error code made by StringCode
.
failure.Wrap(err) vs failure.MarkUnexpected(err)
The difference is here.
https://play.golang.org/p/LV1pWrKi5Dl
If you use Wrap
function, CodeOf
function will return an error code in the error with true
.
If you use MarkUnexpected
function, CodeOf
function will not return an error code in the error, and it will return false
.
I recommend following way, if you don't understand when you should use it.
- Do not use
failure.Unexpected
andfailure.MarkUnexpected
- These two functions should not be used so often. So you don't have to use it until you will want those functions
- Use
failure.New
,failure.Tarnslate
when you want to add an error code into the error- These three functions are fundamental functions in
failure
to handle errors by error code
- These three functions are fundamental functions in
- Use
failure.Wrap
when you want to add stack trace into the error- If you want to write code with the normal (no-
failure
) Go way but just want stack trace,failure.Wrap
can perform like an alternative topkg/errors.Wrap
.
- If you want to write code with the normal (no-
from failure.
problem 1
If you use Wrap function, CodeOf function will return an error code in the error with true.
If you use MarkUnexpected function, CodeOf function will not return an error code in the error, and it will return false.
The only difference is in the behavior of CodeOf function?
I try to use two functions, MessageOf and CauseOf.
The results are identical.
https://play.golang.org/p/BnsgLgm519s
This question is just to reconfirm.
problem 2
// your code
switch s {
case A:
return 10, nil
case B:
return 20, nil
default:
return 0, failure.Unexpected("unexpected state")
// my code
switch s {
case A:
return 10, nil
case B:
return 20, nil
default:
code := failure.StringCode("unknown state")
return 0, failure.New(code)
}
I try to follow suggestions from the article: Donβt just check errors, handle them gracefully
Reduce declare Sentinel errors.
Do you have any suggestions for my code?
How to define unexpected?
I knew for a fact that something would go wrong.
But defining unexpected error?
end
Once pkg/errors.Wrap is executed multiple times, it print call stack is Redundant
I like format of your stack trace.
beautiful and clear!!
from failure.
I guess you want to reduce this kind of declaration regarding the article, right?
Yes
Thank you for your reply.
I'll read the articles you recommend.
from failure.
Related Issues (3)
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
π Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. πππ
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google β€οΈ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from failure.