liveBook · Manning

Backpressure

As explained in Go in Practice, Second Edition

Back pressure is the buildup of pending data when a producer sends faster than a downstream consumer or network can process it.

A network logger can slow an application when log messages arrive faster than the network or remote server can handle them. The pending work builds up; a client sending over TCP may then wait instead of continuing at its usual pace. This is backpressure. section 7.2.2 section 7.3

A busy log server

Imagine a server receiving thousands of messages from many clients. If its throughput falls short, messages accumulate. As acknowledgements are delayed, TCP clients wait to send logs, tying up resources in the applications they serve. section 7.3

Choose a response according to what matters most:

  • Buffer network logs to make the logger more resilient when the connection slows or drops. Buffering is the proposed remedy here, not a complete implementation. section 7.2.2
  • Use UDP when keeping the application moving matters more than receiving every log message. The client need not wait for server acknowledgements, but server hiccups may lose packets. section 7.3
  • Set a dial timeout as a safety net when the network does not behave as expected. In the UDP example, the timeout chiefly covers address resolution and sending. section 7.3
Listing 7.8 UDP-based logging
package main

import (
     "log"
     "net"
     "time"
)

func main() {
     timeout := 30 * time.Second                         #1
     conn, err := net.DialTimeout("udp", 
     "localhost:1902", timeout)                                          #2
     if err != nil {
            panic("Failed to connect to localhost:1902")
     }
     defer     conn.Close()
     f := log.Ldate | log.Lshortfile
     logger := log.New(conn, "example ", f)
     logger.Println("This is a regular message.")
     logger.Panicln("This is a panic.")
}

The Go logging example uses net.DialTimeout with "udp" and passes the resulting connection to log.New. Compare that choice with a TCP network logger when deciding whether the application should wait or risk losing log messages. section 7.3

How Go in Practice, Second Edition covers it

How deep it goes
Explains a busy-server TCP logging scenario and its UDP trade-off; proposes buffering without supplying its implementation here.
Examples
Uses a busy log server and a Go UDP logger built with net.DialTimeout and log.New.
What it assumes
Assumes basic Go network-logging code but explains the slowdown without requiring detailed network mechanics.
What you can do after
Evaluate/understand it by weighing application slowdown against possible log loss when choosing TCP, buffering, or UDP logging.
How it connects
Connects backpressure to network logging, TCP acknowledgements, buffering, UDP, and packet loss.

Also explained in

Compare how 6 books explain backpressure →

Related concepts

This explainer was generated by Manning's knowledge graph from the text of Go in Practice, Second Edition. The section links point to the parts of the book it draws on.