Dalam paket http Go, bagaimana cara mendapatkan string kueri pada permintaan POST?

114

Saya menggunakan httppaket dari Go untuk menangani permintaan POST. Bagaimana cara mengakses dan mengurai konten string kueri dari Requestobjek? Saya tidak dapat menemukan jawabannya dari dokumentasi resmi.

Fabien
sumber
Satu hal yang perlu diingat, jika Anda menggunakan cURL untuk mengirim permintaan dan Anda menggunakan r.FormValue("id")untuk mengambil parameter kueri, Anda tidak dapat mengirim i melalui data formulir dalam cURL (yaitu, curl 0.0.0.0:8888 -d id=foobartidak akan berfungsi). Anda harus mengirimkannya melalui query params ( curl 0.0.0.0:8888?id=foobar).

Jawaban:

145

QueryString, menurut definisi , ada di URL. Anda dapat mengakses URL permintaan menggunakan req.URL( doc ). Objek URL memiliki Query()metode ( doc ) yang mengembalikan Valuestipe, yang merupakan map[string][]stringparameter QueryString.

Jika yang Anda cari adalah data POST yang dikirimkan oleh formulir HTML , maka ini (biasanya) adalah pasangan nilai kunci di badan permintaan. Anda benar dalam jawaban yang bisa Anda panggil ParseForm()dan kemudian gunakan req.Formbidang untuk mendapatkan peta pasangan nilai kunci, tetapi Anda juga bisa menelepon FormValue(key)untuk mendapatkan nilai kunci tertentu. Panggilan ini ParseForm()jika diperlukan, dan mendapatkan nilai terlepas dari bagaimana mereka dikirim (yaitu dalam string kueri atau dalam isi permintaan).

mna
sumber
2
Terima kasih atas ketelitiannya.
Fabien
2
Saya menemukan metode 'req.FormValue (key)' lebih cepat dan melakukan untuk Anda semua kode yang diperlukan untuk pre-parse url.
OnlyAngel
6
req.URL.RawQuerymengembalikan semuanya setelah ?permintaan GET, jika itu membantu.
kouton
Saya merasa menarik req.Form adalah array kosong kecuali req.formValue ("some_field") dipanggil di sewa sekali.
Qian Chen
Terima kasih banyak! @kouton
Aditya Varma
127

Berikut adalah contoh yang lebih konkret tentang cara mengakses parameter GET. The Requestobjek memiliki metode yang mem-parsing mereka keluar untuk Anda disebut Query :

Dengan asumsi URL permintaan seperti http: // host: port / sesuatu? Param1 = b

func newHandler(w http.ResponseWriter, r *http.Request) {
  fmt.Println("GET params were:", r.URL.Query())

  // if only one expected
  param1 := r.URL.Query().Get("param1")
  if param1 != "" {
    // ... process it, will be the first (only) if multiple were given
    // note: if they pass in like ?param1=&param2= param1 will also be "" :|
  }

  // if multiples possible, or to process empty values like param1 in
  // ?param1=&param2=something
  param1s := r.URL.Query()["param1"]
  if len(param1s) > 0 {
    // ... process them ... or you could just iterate over them without a check
    // this way you can also tell if they passed in the parameter as the empty string
    // it will be an element of the array that is the empty string
  }    
}

Perhatikan juga "kunci dalam peta Nilai [yaitu, Query () nilai kembalian] peka huruf besar / kecil."

rogerdpack
sumber
4
Sebuah jawaban sebelumnya telah disebutkan dan terkait dengan dokumentasi dari melakukan hal itu (dan tidak memiliki contoh yang akan panik dengan luar batas mengiris referensi jika bidang yang diinginkan tidak ada, gunakan r.URL.Query().Get("moviename")untuk menghindari kesalahan fatal ini).
Dave C
1
Terimakasih atas infonya. Ya, dokumennya agak membingungkan bagi saya, jadi saya memposting ini lebih sebagai "contoh langsung" jika berguna. Memperbaiki pemeriksaan nihil. Menggunakan Getmetode ini hanya mengembalikan yang pertama jika ada beberapa, jadi ini adalah contoh lainnya. Info berguna, terima kasih!
rogerdpack
Juga saya rasa Anda tidak dapat membandingkan string dengan nil: devs.cloudimmunity.com/gotchas-and-common-mistakes-in-go-golang yaitu string! = "" Valid
James Milner
Saya tidak berpikir kode itu akan dikompilasi, seandainya contoh selesai. Anda tidak dapat membandingkan string kosong yang Values.Get()kembali dengan nil. golang.org/pkg/net/url/#Values
Daniel Farrell
19

Berikut ini contohnya:

value := r.FormValue("field")

untuk info lebih lanjut. tentang paket http, Anda dapat mengunjungi dokumentasinya di sini . FormValuepada dasarnya mengembalikan nilai POST atau PUT, atau nilai GET, dalam urutan itu, yang pertama ditemukannya.

Muhammad Soliman
sumber
8

Berikut adalah contoh kerja sederhana:

package main

import (
    "io"
    "net/http"
)
func queryParamDisplayHandler(res http.ResponseWriter, req *http.Request) {
    io.WriteString(res, "name: "+req.FormValue("name"))
    io.WriteString(res, "\nphone: "+req.FormValue("phone"))
}

func main() {
    http.HandleFunc("/example", func(res http.ResponseWriter, req *http.Request) {
        queryParamDisplayHandler(res, req)
    })
    println("Enter this in your browser:  http://localhost:8080/example?name=jenny&phone=867-5309")
    http.ListenAndServe(":8080", nil)
}

masukkan deskripsi gambar di sini

l3x
sumber
6

Ada dua cara untuk mendapatkan parameter kueri:

  1. Menggunakan reqeust.URL.Query ()
  2. Menggunakan request.Form

Dalam kasus kedua, seseorang harus berhati-hati karena parameter tubuh akan didahulukan daripada parameter kueri. Penjelasan lengkap tentang mendapatkan parameter kueri dapat ditemukan di sini

https://golangbyexample.com/net-http-package-get-query-params-golang

pengguna27111987
sumber
5

Kata-kata di bawah ini berasal dari dokumen resmi.

Formulir berisi data formulir yang diurai, termasuk parameter kueri bidang URL dan data formulir POST atau PUT . Bidang ini hanya tersedia setelah ParseForm dipanggil.

Jadi, contoh kode seperti di bawah ini akan berfungsi.

func parseRequest(req *http.Request) error {
    var err error

    if err = req.ParseForm(); err != nil {
        log.Error("Error parsing form: %s", err)
        return err
    }

    _ = req.Form.Get("xxx")

    return nil
}
ChrisLee
sumber