- net/http
- gin-gonic/gin
- go-chi/chi
- gorilla/mux
其中gin 我是用的最多,但是在最近的使用中我有一些特殊需求,比如 /gitlab/{uuid}/notify,我只获取{uuid}的值才能满足,gin 不能更好的满足我的需求
这时候 gorilla/mux 就能满足我的需求
package main import ( "context" "errors" "fmt" "github.com/go-playground/webhooks/v6/gitlab" "github.com/gorilla/handlers" "github.com/gorilla/mux" "io" "log" "net/http" "os" "os/signal" "time" ) func gitlabWebhook(w http.ResponseWriter, r *http.Request) { ctx := r.Context() fmt.Println("ctx:", ctx) XGitlabToken, ok := ctx.Value("X-Gitlab-Token").(string) if !ok { http.Error(w, http.StatusText(422), 422) return } fmt.Println("X-Gitlab-Token", XGitlabToken) fmt.Println("r.Header.Get(\"X-Gitlab-Token\")", r.Header.Get("X-Gitlab-Token")) vars := mux.Vars(r) name := vars["uuid"] w.Write([]byte("Hello, " + name + "!")) //hook, err := gitlab.New(gitlab.Options.Secret("122333")) hook, err := gitlab.New() if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return } payload, err := hook.Parse(r, gitlab.PushEvents, gitlab.TagEvents, gitlab.MergeRequestEvents, gitlab.BuildEvents, gitlab.JobEvents, gitlab.PipelineEvents) if err != nil { if errors.Is(err, gitlab.ErrEventNotFound) { // ok event wasn't one of the ones asked to be parsed http.Error(w, err.Error(), http.StatusInternalServerError) return } if errors.Is(err, gitlab.ErrGitLabTokenVerificationFailed) { // ok event wasn't one of the ones asked to be parsed http.Error(w, err.Error(), http.StatusInternalServerError) return } fmt.Println("err", err.Error()) http.Error(w, err.Error(), http.StatusInternalServerError) return } if payload == nil { fmt.Println(payload) } switch payload.(type) { case gitlab.MergeRequestEventPayload: release := payload.(gitlab.MergeRequestEventPayload) // Do whatever you want from here... fmt.Printf("%+v", release) case gitlab.PushEventPayload: pushRequest := payload.(gitlab.PushEventPayload) // Do whatever you want from here... fmt.Printf("%+v", pushRequest) case gitlab.TagEventPayload: TagRequest := payload.(gitlab.TagEventPayload) // Do whatever you want from here... fmt.Printf("%+v", TagRequest) } _, err = io.WriteString(w, r.URL.Path) if err != nil { return } } type Handler func(w http.ResponseWriter, r *http.Request) error func (h Handler) ServeHTTP(w http.ResponseWriter, r *http.Request) { if err := h(w, r); err != nil { // handle returned error here. w.WriteHeader(503) w.Write([]byte("bad")) } } // MyMiddleware HTTP middleware setting a value on the request context func MyMiddleware(next http.Handler) http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { // create new context from `r` request context, and assign key `"user"` // to value of `"123"` ctx := context.WithValue(r.Context(), "X-Gitlab-Token", r.Header.Get("X-Gitlab-Token")) // call the next handler in the chain, passing the response writer and // the updated request object with the new context value. // // note: context.Context values are nested, so any previously set // values will be accessible as well, and the new `"user"` key // will be accessible from this point forward. next.ServeHTTP(w, r.WithContext(ctx)) }) } func main() { // 创建一个新的路由器 r := mux.NewRouter() //// 定义一个路由 //r.HandleFunc("/gitlab/{uuid}/notify", func(w http.ResponseWriter, r *http.Request) { // vars := mux.Vars(r) // name := vars["uuid"] // w.Write([]byte("Hello, " + name + "!")) //}).Methods("POST") r.Use(MyMiddleware) r.HandleFunc("/gitlab/{uuid}/notify", gitlabWebhook).Methods("POST") loggedRouter := handlers.LoggingHandler(os.Stdout, r) srv := &http.Server{ Addr: ":8080", // Good practice to set timeouts to avoid Slowloris attacks. WriteTimeout: time.Second * 15, ReadTimeout: time.Second * 15, IdleTimeout: time.Second * 60, Handler: loggedRouter, // Pass our instance of gorilla/mux in. } go func() { // 服务连接 if err := srv.ListenAndServe(); err != nil && !errors.Is(err, http.ErrServerClosed) { //errChan <- err log.Fatalf("listen: %s\n", err) } }() c := make(chan os.Signal, 1) // We'll accept graceful shutdowns when quit via SIGINT (Ctrl+C) // SIGKILL, SIGQUIT or SIGTERM (Ctrl+/) will not be caught. signal.Notify(c, os.Interrupt) // Block until we receive our signal. <-c wait := time.Second * 60 // Create a deadline to wait for. ctx, cancel := context.WithTimeout(context.Background(), wait) defer cancel() // Doesn't block if no connections, but will otherwise wait // until the timeout deadline. srv.Shutdown(ctx) // Optionally, you could run srv.Shutdown in a goroutine and block on // <-ctx.Done() if your application should wait for other services // to finalize based on context cancellation. log.Println("shutting down") os.Exit(0) }
标签:web,http,框架,err,fmt,gitlab,func,Error,go From: https://www.cnblogs.com/leon-coder/p/18211481