nosurf
adalah paket HTTP untuk Go yang membantu Anda mencegah serangan Pemalsuan Permintaan Lintas Situs. Ia bertindak seperti middleware dan oleh karena itu pada dasarnya kompatibel dengan semua aplikasi Go HTTP.
Meskipun CSRF merupakan kerentanan yang menonjol, infrastruktur paket terkait web Go sebagian besar terdiri dari kerangka mikro yang tidak menerapkan pemeriksaan CSRF, dan juga tidak seharusnya menerapkannya.
nosurf
memecahkan masalah ini dengan menyediakan CSRFHandler
yang membungkus http.Handler
Anda dan memeriksa serangan CSRF pada setiap metode yang tidak aman (non-GET/HEAD/OPTIONS/TRACE).
nosurf
membutuhkan Go 1.1 atau lebih baru.
Mendukung http.Handler
apa pun (kerangka kerja, penangan Anda sendiri, dll.) dan bertindak seperti itu sendiri.
Memungkinkan pengecualian titik akhir tertentu dari pemeriksaan CSRF dengan URL yang tepat, glob, atau ekspresi reguler.
Memungkinkan menentukan penangan kegagalan Anda sendiri. Ingin memberi peretas jari tengah ASCII dan bukan HTTP 400
biasa? Tidak masalah.
Menggunakan token bertopeng untuk mengurangi serangan BREACH.
Tidak memiliki ketergantungan di luar perpustakaan standar Go.
paket mainimport ("fmt""github.com/justinas/nosurf""html/template""net/http")var templateString string = `<!doctype html><html><body>{{ if .name }}< p>Nama Anda: {{ .name }}</p>{{ end }}<form action="/" method="POST"><input type="text" name="name"><!-- Coba hapus ini atau ubah nilainya dan lihat apa yang terjadi --><input type="hidden" name="csrf_token" value="{{ .token }}"><input type="submit" value="Send"></form></body>< /html>`var templ = template.Must(template.New("t1").Parse(templateString))func myFunc(w http.ResponseWriter, r *http.Request) {konteks := make(map[string]string)context["token"] = nosurf.Token(r)if r.Method == "POST" {context["name"] = r.FormValue("name") }templ.Execute(w, konteks) }func main() {myHandler := http.HandlerFunc(myFunc)fmt.Println("Mendengarkan di http://127.0.0.1:8000/")http.ListenAndServe(":8000", nosurf.New(myHandler)) }
Dalam beberapa kasus, token CSRF dapat dikirim melalui cara yang tidak standar, misalnya badan atau permintaan adalah pesan berkode JSON dengan salah satu bidangnya menjadi token.
Dalam kasus seperti ini, pengendali (jalur) harus dikecualikan dari verifikasi otomatis dengan menggunakan salah satu metode pengecualian:
func (h *CSRFHandler) ExemptFunc(fn func(r *http.Request) bool)func (h *CSRFHandler) ExemptGlob(pola string)func (h *CSRFHandler) ExemptGlobs(patterns ...string)func (h *CSRFHandler) ExemptPath(string jalur)fungsi (h *CSRFHandler) ExemptPaths(jalur ...string)func (h *CSRFHandler) ExemptRegexp(re interface{})func (h *CSRFHandler) ExemptRegexps(res ...interface{})
Nantinya, token tersebut harus diverifikasi dengan cara mengambil token dari cookie secara manual dan memberikan token yang dikirim dalam isi melalui: VerifyToken(tkn, tkn2 string) bool
.
Contoh:
func HandleJson(w http.ResponseWriter, r *http.Request) {d := struct{X,Y intTkn string {}json.Unmarshal(ioutil.ReadAll(r.Body), &d)if !nosurf.VerifyToken(nosurf.Token(r), d.Tkn) {http.Errorf(w, "Token CSRF salah", http. StatusBadRequest) kembali }// lakukan sesuatu yang keren}
Temukan masalah yang mengganggu Anda / buka masalah baru.
Membahas.
Cabang, komit, uji.
Buat permintaan tarik/lampirkan komit ke masalah tersebut.