Rumah > Artikel > pembangunan bahagian belakang > Bagaimanakah Saya Boleh Mengakses Soket Dasar Respons HTTP dalam Go?
Mengakses Soket Dasar Respons HTTP
Dalam Go, anda mungkin menghadapi situasi di mana anda perlu mengakses soket asas HTTP tindak balas. Biasanya, mengakses soket diperlukan apabila anda ingin melakukan operasi khusus platform padanya, seperti TCP_INFO. Walaupun tiada cara mudah untuk mendapatkan soket terus daripada respons HTTP, terdapat beberapa pendekatan yang boleh anda terokai:
1. Menggunakan Kunci Konteks (Go 1.13 ):
Setelah Go 1.13 dikeluarkan, ia dijangka menyokong penyimpanan net.Conn dalam Konteks Permintaan. Ini menyediakan kaedah yang bersih dan mudah:
<code class="go">package main import ( "net/http" "context" "net" "log" ) type contextKey struct { key string } var ConnContextKey = &contextKey{"http-conn"} func SaveConnInContext(ctx context.Context, c net.Conn) (context.Context) { return context.WithValue(ctx, ConnContextKey, c) } func GetConn(r *http.Request) (net.Conn) { return r.Context().Value(ConnContextKey).(net.Conn) } func main() { http.HandleFunc("/", myHandler) server := http.Server{ Addr: ":8080", ConnContext: SaveConnInContext, } server.ListenAndServe() } func myHandler(w http.ResponseWriter, r *http.Request) { conn := GetConn(r) ... }</code>
2. Pemetaan Sambungan melalui Alamat Jauh (TCP):
Untuk pelayan mendengar pada TCP, setiap sambungan mempunyai nilai net.Conn.RemoteAddr().String() yang unik. Nilai ini boleh digunakan sebagai kunci kepada peta global sambungan:
<code class="go">package main import ( "net/http" "net" "fmt" "log" ) var conns = make(map[string]net.Conn) func ConnStateEvent(conn net.Conn, event http.ConnState) { if event == http.StateActive { conns[conn.RemoteAddr().String()] = conn } else if event == http.StateHijacked || event == http.StateClosed { delete(conns, conn.RemoteAddr().String()) } } func GetConn(r *http.Request) (net.Conn) { return conns[r.RemoteAddr] } func main() { http.HandleFunc("/", myHandler) server := http.Server{ Addr: ":8080", ConnState: ConnStateEvent, } server.ListenAndServe() } func myHandler(w http.ResponseWriter, r *http.Request) { conn := GetConn(r) ... }</code>
3. Mengatasi Alamat Jauh untuk Soket UNIX:
Untuk soket UNIX, net.Conn.RemoteAddr().String() sentiasa mengembalikan "@", menjadikannya tidak sesuai untuk pemetaan. Untuk mengatasinya:
<code class="go">package main import ( "net/http" "net" "os" "golang.org/x/sys/unix" "fmt" "log" ) // ... (code omitted for brevity) func main() { http.HandleFunc("/", myHandler) listenPath := "/var/run/go_server.sock" l, err := NewUnixListener(listenPath) if err != nil { log.Fatal(err) } defer os.Remove(listenPath) server := http.Server{ ConnState: ConnStateEvent, } server.Serve(NewConnSaveListener(l)) } // ... (code omitted for brevity)</code>
Atas ialah kandungan terperinci Bagaimanakah Saya Boleh Mengakses Soket Dasar Respons HTTP dalam Go?. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!