使用bunrouter在Golang中创建HTTP路由

Gobunrouter教程展示了如何使用bunrouter在Golang中创建HTTP路由。

路由将一个HTTP动词(例如GET、POST、PUT、DELETE)和一个URL路径关联到一个处理函数。路由器是创建路由的对象;即它将HTTP请求映射到处理程序。

bunrouter是一个快速灵活的GoHTTP路由器。它支持中间件、分组路由和灵活的错误处理。它与内置的net/httpAPI兼容。

$ go version
go version go1.18.1 linux/amd64

我们使用Go版本1.18。

Gobunrouter简单例子

在第一个示例中,我们使用bunrouter设置了一个简单的服务器。

package main

import (
    "log"
    "net/http"

    "github.com/uptrace/bunrouter"
)

func main() {

    router := bunrouter.New()

    router.GET("/", func(w http.ResponseWriter, req bunrouter.Request) error {

        w.Write([]byte("index"))
        return nil
    })

    log.Println("listening on http://localhost:8080")
    log.Println(http.ListenAndServe(":8080", router))
}

服务器用一条短消息响应GET请求。

import (
    "log"
    "net/http"

    "github.com/uptrace/bunrouter"
)

我们导入github.com/uptrace/bunrouter包。

router := bunrouter.New()

创建了一个新的bunrouter。

router.GET("/", func(w http.ResponseWriter, req bunrouter.Request) error {

    w.Write([]byte("index"))
    return nil
})

我们创建一个GET路由。匿名处理函数以“索引”消息响应。

Gobunrouternotfound处理程序

在下一个示例中,我们设置了notfound处理程序。它用于处理没有路由的请求。

package main

import (
    "fmt"
    "log"
    "net/http"

    "github.com/uptrace/bunrouter"
)

func main() {

    router := bunrouter.New(
        bunrouter.WithNotFoundHandler(notFoundHandler),
    )

    router.GET("/hello", func(w http.ResponseWriter, req bunrouter.Request) error {

        fmt.Fprintf(w, "hello")
        return nil
    })

    log.Println("listening on http://localhost:8080")
    log.Println(http.ListenAndServe(":8080", router))
}

func notFoundHandler(w http.ResponseWriter, req bunrouter.Request) error {

    w.WriteHeader(http.StatusNotFound)

    fmt.Fprintf(w, "404 - failed to find %s", req.URL.Path)
    return nil
}

代码委托给notFoundHandler函数。

router := bunrouter.New(
    bunrouter.WithNotFoundHandler(notFoundHandler),
)

未找到的处理程序使用WithNotFoundHandler注册。

func notFoundHandler(w http.ResponseWriter, req bunrouter.Request) error {

    w.WriteHeader(http.StatusNotFound)

    fmt.Fprintf(w, "404 - failed to find %s", req.URL.Path)
    return nil
}

notFoundHandler中,我们设置了状态码和错误消息。

$ curl localhost:8080/about
404 - failed to find /about

不允许的方法

HTTP405MethodNotAllowed响应状态代码表示服务器知道请求方法,但目标资源不支持此方法。

例如,我们有一个只响应GET请求的路由。如果我们发送一个POST请求,服务器可以响应405MethodNotAllowed消息。默认情况下,bunrouter在这种情况下什么都不做。

package main

import (
    "fmt"
    "log"
    "net/http"

    "github.com/uptrace/bunrouter"
)

func main() {

    router := bunrouter.New(bunrouter.WithMethodNotAllowedHandler(methodNotAllowedHandler))

    router.GET("/", func(w http.ResponseWriter, req bunrouter.Request) error {

        fmt.Fprintln(w, "index")

        return nil
    })

    log.Println("listening on http://localhost:8080")
    log.Println(http.ListenAndServe(":8080", router))
}

func methodNotAllowedHandler(w http.ResponseWriter, req bunrouter.Request) error {

    w.WriteHeader(http.StatusMethodNotAllowed)

    fmt.Fprintln(w, "405 - method not allowed")
    return nil
}

在示例中,我们使用bunrouter.WithMethodNotAllowedHandler函数设置方法不允许处理程序。

$  curl localhost:8080/
index
$ curl localhost:8080/ -d "name=Peter"
405 - method not allowed

去bunrouterPOST请求

HTTPPOST方法向服务器发送数据。它通常在上传文件或提交完整的Web表单时使用。

package main

import (
    "fmt"
    "log"
    "net/http"

    "github.com/uptrace/bunrouter"
)

func main() {

    router := bunrouter.New()

    router.GET("/", func(w http.ResponseWriter, req bunrouter.Request) error {

        fmt.Fprintln(w, "index")

        return nil
    })

    router.POST("/", func(w http.ResponseWriter, req bunrouter.Request) error {

        err := req.ParseForm()

        if err != nil {
            http.Error(w, fmt.Sprint(err), http.StatusUnprocessableEntity)
        }

        fmt.Fprintln(w, req.Form)

        return nil
    })

    log.Println("listening on http://localhost:8080")
    log.Println(http.ListenAndServe(":8080", router))
}

该示例处理POST请求。

err := req.ParseForm()

ParseForm函数解析请求的主体并使用任何数据填充Req.Form

if err != nil {
    http.Error(w, fmt.Sprint(err), http.StatusUnprocessableEntity)
}

如果出现错误,我们会使用http.Error函数发送错误消息。

路由器组

路由功能可以组织成组。

package main

import (
    "fmt"
    "log"
    "net/http"

    "github.com/uptrace/bunrouter"
)

func main() {

    router := bunrouter.New()

    router.WithGroup("/api/", func(group *bunrouter.Group) {

        group.GET("/index", index)
        group.GET("/hello", hello)

    })

    router.WithGroup("/api2/", func(group *bunrouter.Group) {

        group.GET("/index", index2)
        group.GET("/hello", hello2)

    })

    log.Println("listening on http://localhost:8080")
    log.Println(http.ListenAndServe(":8080", router))
}

func index(w http.ResponseWriter, req bunrouter.Request) error {

    fmt.Fprintln(w, "index")
    return nil
}

func hello(w http.ResponseWriter, req bunrouter.Request) error {

    fmt.Fprintln(w, "hello")
    return nil
}

func index2(w http.ResponseWriter, req bunrouter.Request) error {

    fmt.Fprintln(w, "index2")
    return nil
}

func hello2(w http.ResponseWriter, req bunrouter.Request) error {

    fmt.Fprintln(w, "hello2")
    return nil
}

在示例中,我们有两个组:/api//api2/

router.WithGroup("/api/", func(group *bunrouter.Group) {

    group.GET("/index", index)
    group.GET("/hello", hello)

})

使用WithGroup创建了一个新组。

$ curl localhost:8080/api/index
index
$ curl localhost:8080/api/hello
hello
$ curl localhost:8080/api2/hello
hello2
$ curl localhost:8080/api2/index
index2

在本教程中,我们使用了bunrouter。

列出所有Go教程。

赞(0) 打赏

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏