handler接口

实现handler接口,用来处理请求。

type Handler interface {
    ServerHTTP(w ResponseWriter, r *Request)
}

例如,显示一个电子商务网站的库存:

type dollars float32

func (d dollars) String() string {
    return fmt.Sprintf("$%.2f", d)
}

type database map[string]dollars  //这里用map来表示库存

func (db database) ServeHTTP(w http.ResponseWriter, r *http.Request) {
    for item, price := range db {
        fmt.Fprintf(w, "%s: %s\n", item, price)
    }
    fmt.Println(w)
}

主函数,ListenAndServe函数需要一个服务器地址,以及一个Handler接口的实例:

db := database{"shoes": 50, "socks": 5.5}
log.Fatal(http.ListenAndServe("localhost:8000", db))

处理不同的路径时:

func (db database) ServeHTTP(w http.ResponseWriter, r *http.Request) {
    switch r.URL.Path {
    case "/price":
        item := r.URL.Query().Get("item")
        price, ok := db[item]
        if !ok {
            w.WriteHeader(http.StatusNotFound)
            fmt.Fprintf(w, "no such item: %q\n", item)
            return
        }
        fmt.Fprintf(w, "price:%s\n", price)
    case "/list":
        fmt.Fprintf(w, "物品如下:\n")
        for item, _ := range db {
            fmt.Fprintf(w, "%s\n", item)
        }
    }
}

go语言net/http包提供了一个全局的ServerMux实例DefaultServeMux,以及包级别的注册程序http.Handle和http.Handlefunc。要让DefaultServeMux作为服务器的主处理程序,无须把它传给ListenAndServe,直接传nil即可。
对于部分程序来说,一个Web服务器足够用,所以用包默认提供的DefaultServeMux。

注册处理程序:

//list必须要和接口的ServerHTTP()方法有一样的签名
func (db database) list(w http.ResponseWriter, r *http.Request) {
    fmt.Fprintf(w, "物品如下:\n")
    for item, _ := range db {
        fmt.Fprintf(w, "%s\n", item)
    }
}

主函数:

db := database{"shoes": 50, "socks": 5.5}
http.HandleFunc("/list", db.list)  //db.list必须要和接口的ServerHTTP()方法有一样的签名
log.Fatal(http.ListenAndServe("localhost:8000", nil))

http.HandleFunc函数实质上是把db.list方法进行了类型转换,利用HandlerFunc类型(名字不一样噢)

type HandlerFunc func(ResponseWriter, *Request)

func (f HandlerFunc) ServeHTTP(w ResponseWriter, r *Request) {
    f(w, r)
}

当然也可以自己创建一个ServerMux:

mux := http.NewServeMux()

猜你喜欢

转载自blog.csdn.net/weixin_42506905/article/details/81392847
今日推荐