Golang Advanced (vi)--restful Development Elegant handling error

Source: Internet
Author: User
This is a creation in Article, where the information may have evolved or changed.

Objective

Golang error processing has been criticized, in fact, through the design pattern can be very good to deal with the error, here is a restful development as an example of error elegant processing

resuful Development, error processing has two purposes, one can return the error message to the user, two to facilitate debugging, in order to achieve elegance and a little, not everywhere is a variety of if language

Of course, as an elegant code, there is a point to ensure that you try not to write duplicate code

Panic processing

Here we take the panic processing, the panic if the judgment is also encapsulated in a method, and the package on the stack information (here to use the github.com/pkg/errors package, the specific use here will not repeat, you can see the documentation on GitHub), convenient debugging:

func ThrowError(err error) {    ifnil {        panic(errors.WithStack(err))    }}

It's pretty simple when we call it.

// MarshalJson 把对象以json格式放到response中funcinterface{}) {    data, err := json.Marshal(v)    ThrowError(err)    w.Write(data)}// UnMarshalJson 从request中取出对象funcinterface{}) {    result, err := ioutil.ReadAll(req.Body)    err = errors.New("TEST")    ThrowError(err)    json.Unmarshal([]byte(bytes.NewBuffer(result).String()), v)}

This throws a mistake down the ladder until it encounters the recover of processing.

Revocer processing

We've encapsulated the corresponding recover.

func CatchError(w http.ResponseWriter, req *http.Request) {    ifrecovernil {        "9001", Msg: r.(error).Error()}        MarshalJson(w, resp)        fmt.Printf("%+v\n", r.(error))    }}

Return the error to the user and print the wrong information, including the stack

Unified Processing

As a RESTful unified processing place, generally is the Servehttp method, but if the use of third-party MUX, forced to change the source code is not too elegant, and the MUX also has an upgrade, you can not upgrade once, then use a packaging method

typestruct {    *mux.Router}func (r *MyRouter) ServeHTTP(w http.ResponseWriter, req *http.Request) {    defer tools.CatchError(w, req)    r.Router.ServeHTTP(w, req)}func NewAPIMux() http.Handler {    r := &MyRouter{mux.NewRouter()}    s := r.PathPrefix("/api").Subrouter()    initUserApi(s)    r.PathPrefix("/").Handler(http.StripPrefix("/", http.FileServer(http.Dir("web/"))))    return r}

In this way, error is handled gracefully, anywhere, just by calling the ThrowError method by business, the client can receive an error message, and the server can print the wrong stack information at the same time.

Sample output


Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.