Wie kann ich mit http-Anfragen verschiedener Methoden an / in Go umgehen?


77

Ich versuche herauszufinden, wie Anfragen an /und nur /in Go am besten verarbeitet werden können, und verschiedene Methoden auf unterschiedliche Weise zu behandeln. Hier ist das Beste, was ich mir ausgedacht habe:

package main

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

func main() {
    http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
        if r.URL.Path != "/" {
            http.NotFound(w, r)
            return
        }

        if r.Method == "GET" {
            fmt.Fprintf(w, "GET, %q", html.EscapeString(r.URL.Path))
        } else if r.Method == "POST" {
            fmt.Fprintf(w, "POST, %q", html.EscapeString(r.URL.Path))
        } else {
            http.Error(w, "Invalid request method.", 405)
        }
    })

    log.Fatal(http.ListenAndServe(":8080", nil))
}

Ist das idiomatisch Go? Ist dies das Beste, was ich mit der Standard-http-Bibliothek machen kann? Ich würde viel lieber so etwas wie http.HandleGet("/", handler)Express oder Sinatra machen. Gibt es einen guten Rahmen für das Schreiben einfacher REST-Services? web.go sieht attraktiv aus, stagniert aber.

Danke für deinen Rat.


2
Sie könnten an gorillatoolkit.org/pkg/mux interessiert sein, wenn Sie nur nach einer Routing-Abstraktion suchen.
Dskinner

1
+1. mux oder gorillatoolkit.org/pkg/pat eignen sich hervorragend, um dies zu abstrahieren.
Minikomi

Antworten:


96

Um sicherzustellen, dass Sie nur der Wurzel dienen: Sie tun das Richtige. In einigen Fällen möchten Sie die ServeHttp-Methode eines http.FileServer-Objekts aufrufen, anstatt NotFound aufzurufen. Es hängt davon ab, ob Sie verschiedene Dateien haben, die Sie ebenfalls bereitstellen möchten.

So gehen Sie mit verschiedenen Methoden unterschiedlich um: Viele meiner HTTP-Handler enthalten nur eine switch-Anweisung wie die folgende:

switch r.Method {
case http.MethodGet:
    // Serve the resource.
case http.MethodPost:
    // Create a new record.
case http.MethodPut:
    // Update an existing record.
case http.MethodDelete:
    // Remove the record.
default:
    // Give an error message.
}

Natürlich können Sie feststellen, dass ein Drittanbieterpaket wie Gorilla für Sie besser funktioniert.


32

eh, ich war tatsächlich auf dem Weg ins Bett und daher der kurze Kommentar zum Betrachten von http://www.gorillatoolkit.org/pkg/mux, der wirklich nett ist und macht, was Sie wollen, geben Sie einfach einen Blick auf die Dokumente. Zum Beispiel

func main() {
    r := mux.NewRouter()
    r.HandleFunc("/", HomeHandler)
    r.HandleFunc("/products", ProductsHandler)
    r.HandleFunc("/articles", ArticlesHandler)
    http.Handle("/", r)
}

und

r.HandleFunc("/products", ProductsHandler).
    Host("www.domain.com").
    Methods("GET").
    Schemes("http")

und viele andere Möglichkeiten und Wege, um die obigen Operationen durchzuführen.

Aber ich hatte das Bedürfnis, den anderen Teil der Frage anzusprechen: "Ist das das Beste, was ich tun kann?". Wenn die Standardbibliothek etwas zu leer ist, finden Sie hier eine großartige Ressource zum Auschecken: https://github.com/golang/go/wiki/Projects#web-libraries (speziell mit Webbibliotheken verknüpft).


Und vergessen Sie nicht, Ihren neuen Router rin Ihrer ServerInstanz als Handler zu registrieren
MAZux
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.