Golang自定义服务器处理程序

huangapple go评论87阅读模式
英文:

Golang custom handler for server

问题

我想在http.ListenAndServe上使用自定义方法。

这是我的代码:

http.ListenAndServe(":8000", ErrorHandler)

func ErrorHandler(h http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        h.ServeHTTP(w, r)
    })
}

错误信息:

无法将ErrorHandler(类型为func(http.Handler)http.Handler)作为http.ListenAndServe的参数类型http.Handler使用:
func(http.Handler)http.Handler未实现http.Handler(缺少ServeHTTP方法)

我该如何向ListenAndServe添加自定义方法?

英文:

I want to use a custom method on http.ListenAndServe

Here is what I have

http.ListenAndServe(":8000", ErrorHandler)

func ErrorHandler(h http.Handler) http.Handler {
	return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
		h.ServeHTTP(w, r)
	})
}

Error

cannot use ErrorHandler (type func(http.Handler) http.Handler) as type http.Handler in argument to http.ListenAndServe:
        func(http.Handler) http.Handler does not implement http.Handler (missing ServeHTTP method)

How can I add a custom method to ListenAndServe?

答案1

得分: 7

你的ErrorHandler(h http.Handler) http.Handler函数实际上只是一个"中间件",而不是一个真正的处理程序。它接受一个处理程序h并返回一个新的处理程序。http.StripPrefix就是这种"中间件"的一个例子。

如果你不想要中间件,而只是一个处理程序,那么你需要稍微改变一下你的函数定义:

func ErrorHandler(w http.ResponseWriter, r *http.Request) {
    // 处理 r 和 w
}

现在你可以将你的ErrorHandler传递给ListenAndServe,尽管你仍然需要将其转换为正确的http.Handler类型,像这样:

http.ListenAndServe(":8000", http.HandlerFunc(ErrorHandler))

http.HandlerFunc是一个适配器,它将一个函数(如果它具有正确的签名)转换为http.Handler

最后,如果你不喜欢类型转换,你需要定义一个类型而不仅仅是一个函数,并且你需要为该类型定义一个方法,以满足http.Handler接口类型的要求。

type ErrorHandler struct{}

func (h *ErrorHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
    // 处理 r 和 w
}

http.ListenAndServe(":8080", &ErrorHandler{})

在这里阅读更多信息:https://golang.org/pkg/net/http/#Handler

英文:

Your ErrorHandler(h http.Handler) http.Handler func is basically just "middleware" and not a real handler. It takes a handler h and returns a new handler. http.StripPrefix is an example of such "middleware".

If you don't want middleware, but just a handler then you need to define your function a little differently:

func ErrorHandler(w http.ResponseWriter, r *http.Request) {
    // do stuff with r and w
}

Now you can pass your ErrorHandler to ListenAndServe although you still need to cast it to the proper http.Handler type like so:

http.ListenAndServe(":8000", http.HandlerFunc(ErrorHandler))

http.HandlerFunc is an adapter that turns a function, if it has the right signature, into an http.Handler.

Finally, if you don't like the casting, you'll need to define a type instead of a just a function and you'll need to define a method on that type that is required for it to satisfy the http.Handler interface type.

type ErrorHandler struct{}

func (h *ErrorHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
	// do stuff with r and w
}

http.ListenAndServe(":8080", &ErrorHandler{})

Read more about it here https://golang.org/pkg/net/http/#Handler

huangapple
  • 本文由 发表于 2017年4月1日 06:54:33
  • 转载请务必保留本文链接:https://go.coder-hub.com/43150775.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定