Go Begins Work on HTTP/3: Is Go’s Performance Set to Soar?

Life is ultimately about experiences, especially those that are unresolved. “Dream of the Red Chamber” unexpectedly tells us that the specific ending is not that important; what you unfold in each word and sentence is already interesting enough.

Introduction

With the continuous evolution of internet technology, the HTTP protocol is also undergoing constant upgrades. From HTTP/1.1 to HTTP/2, and now to the latest HTTP/3, each upgrade has brought significant improvements in performance and efficiency. HTTP/3 is based on the QUIC protocol, aiming to address the performance bottlenecks of HTTP/2 in mobile networks and high-latency environments.

History of HTTP/3

The history of HTTP/3 is essentially a history of “solving TCP’s shortcomings” and “the rise of the QUIC protocol”.

Root of the History: TCP’s “Head-of-Line Blocking” Issue

To understand why HTTP/3 emerged, one must first grasp the core flaws of its predecessor protocols.

HTTP/1.1 (1997): Based on TCP. The classic problem is the unordered request/response queue, leading to “Head-of-Line Blocking (HOLB)”—if the first request in the queue is delayed, all subsequent requests are blocked. The solution was to use multiple TCP connections, but this is inefficient.

HTTP/2 (2015): A significant advancement. It introduced “Multiplexing”—allowing multiple request/response streams to be sent in parallel over a single TCP connection, solving the application layer’s head-of-line blocking.

However, there is a fatal flaw: HTTP/2 streams run over the same TCP connection. The TCP protocol itself transmits packets in order. If any TCP packet is lost, the entire connection must stop and wait for that lost packet to be retransmitted and acknowledged. Even if packets from other streams have arrived, they will be blocked by the lost packet. This is known as head-of-line blocking at the TCP layer.

A simple analogy is:

HTTP/1.1: Multiple single-lane roads (multiple TCP connections), with a train of cars (request queue) on each road; if the lead car breaks down, the entire road is paralyzed.

HTTP/2: A wide highway (one TCP connection) with multiple lanes (multiple streams). But the highway has only one exit; if any car (TCP packet) has an accident, all lanes must stop and wait, causing the entire traffic to come to a halt.

HTTP/2 also aligns better with current road rules.

Key Innovation: The Birth of the QUIC Protocol

Google engineers realized that to completely solve this problem, a revolution at the transport layer was necessary. In 2012, Google publicly launched an experimental project: QUIC (Quick UDP Internet Connections).

The core idea of QUIC is to reimplement a reliable, secure, multiplexed transport protocol similar to TCP+TLS+HTTP/2 on top of user-space UDP. In May 2021, the IETF released the final standards for QUIC and HTTP/3. Over the next five years, as major browsers like Chrome and Firefox, along with infrastructure providers like Cloudflare, embraced HTTP/3, community expectations grew.

In Go, the net/http package has always been a proud HTTP library. However, with HTTP/3 maturing, the Go team decided to enter the HTTP/3 arena.

Yet, the Go team approaches every major decision with caution, considering not only the stability of the protocol but also the complexity of implementation.

Go Begins Work on HTTP/3: Is Go's Performance Set to Soar?

Considering that the protocol is now stable, the Go team, facing significant implementation challenges, decided to proceed in two steps: first QUIC, then HTTP/3.

Step One: Building the QUIC Foundation (x/net/quic)

Core member of the Go team, neild, recently announced that the QUIC implementation has moved from the internal package (internal/quic) to the public x/net/quic. Although it is still in the experimental stage and the API may change, this marks that it is mature enough for the community to “taste” and provide feedback.

Step Two: Implementing HTTP/3 (x/net/http3)

Like QUIC, it will first be developed in the internal package (x/net/internal/http3), and once the API stabilizes, it will be moved to the public package and submitted for final API review proposals.

The Next Evolution of Go Network Programming

Go’s support for HTTP/3 further enriches the net/http library, enhancing Go’s performance in network programming and providing all Go developers with a faster, more reliable network experience.

From another perspective, while one of Go’s core advantages is its “out-of-the-box” high performance, Go is also not a young programming language anymore. Compared to newer languages like Zig and Moonbit, Go must continue to strive to maintain its high-performance edge.

Imagine: A Code Example for Go HTTP/3

package main

import(
"net/http"
"x/net/http3"
)

func main() {
    mux := http.NewServeMux()
    mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
        w.Write([]byte("Hello HTTP/3!"))
    })

// Expected to integrate well with the existing http package
    server :=&http3.Server{
        Addr:    ":8080",
        Handler: mux,
    }

    server.ListenAndServe()
}

Conclusion

With Go starting to work on HTTP/3, it is evident that the Go team is committed to pursuing performance in network programming. This will also break the awkward situation where HTTP/3 could only be introduced through third-party libraries. However, it must be noted that even the Go team acknowledges the complexity of this implementation, and achieving stability and usability will require considerable time and effort.

Leave a Comment