net/http.Request.PathValue în Go

Returnează valoarea unui parametru din calea rutei, de exemplu id din modelul "/produse/{id}".

Sintaxă
func (r *Request) PathValue(name string) string

Ce face net/http.Request.PathValue

Când o rută are parametri în acolade ("/utilizatori/{nume}/comenzi/{id}"), r.PathValue("id") returnează partea din cale care s-a potrivit cu {id}. Valoarea este decodată: %20 devine spațiu, %2F devine /.

Dacă parametrul nu există în model sau cererea nu a trecut printr-un ServeMux, rezultatul este textul gol. Valoarea este mereu string; pentru numere o convertești cu strconv.Atoi și tratezi eroarea (cererea vine de la utilizator).

r.SetPathValue(nume, valoare) setează manual o valoare, util în teste fără router.

Parametri

Parametru Descriere
name Numele parametrului, fără acolade.

Ce returnează

Valoarea parametrului (string) sau "".

Exemple

Exemplul 1: Parametri numerici validați

package main

import (
	"fmt"
	"net/http"
	"net/http/httptest"
	"strconv"
)

func main() {
	mux := http.NewServeMux()
	mux.HandleFunc("GET /clienti/{client}/comenzi/{id}", func(w http.ResponseWriter, r *http.Request) {
		id, err := strconv.Atoi(r.PathValue("id"))
		if err != nil {
			http.Error(w, "id invalid", http.StatusBadRequest)
			return
		}
		fmt.Fprintf(w, "comanda %d a clientului %q", id, r.PathValue("client"))
	})

	for _, cale := range []string{"/clienti/ana/comenzi/42", "/clienti/Ion%20Pop/comenzi/7", "/clienti/ana/comenzi/abc"} {
		rec := httptest.NewRecorder()
		mux.ServeHTTP(rec, httptest.NewRequest("GET", cale, nil))
		fmt.Printf("%d %s\n", rec.Code, rec.Body.String())
	}
}

Rezultat

200 comanda 42 a clientului "ana"
200 comanda 7 a clientului "Ion Pop"
400 id invalid

Exemplul 2: Restul căii cu {nume…}

package main

import (
	"fmt"
	"net/http"
	"net/http/httptest"
)

func main() {
	mux := http.NewServeMux()
	mux.HandleFunc("/docs/{sectiune}/{pagina...}", func(w http.ResponseWriter, r *http.Request) {
		fmt.Fprintf(w, "secțiune=%q pagină=%q inexistent=%q",
			r.PathValue("sectiune"), r.PathValue("pagina"), r.PathValue("altceva"))
	})
	rec := httptest.NewRecorder()
	mux.ServeHTTP(rec, httptest.NewRequest("GET", "/docs/go/net/http/server", nil))
	fmt.Println(rec.Body.String())
}

Rezultat

secțiune="go" pagină="net/http/server" inexistent=""

Greșeli frecvente

  • Scrii numele cu acolade: r.PathValue("{id}") returnează mereu textul gol. Numele este doar "id".
  • Folosești PathValue pentru parametrii din query string (?pagina=2). Aceia se citesc cu r.URL.Query().Get sau r.FormValue.

Comenzi înrudite

  • net/http.NewServeMux: Creează un router (ServeMux) propriu care alege handler-ul după metoda și calea cererii; HandleFunc și Handle adaugă rute.
  • net/http.Request.FormValue: FormValue citește un câmp dintr-un formular sau din query string; ParseForm le citește pe toate în r.Form și r.PostForm.
  • net/http.Request: Structura unei cereri HTTP: metoda, URL-ul, antetele, corpul și contextul (Context()) care se anulează când clientul pleacă.