This tutorial covers a golang udp server and golang udp client with the standard net package: ListenPacket for a udp server golang style listener, ReadFrom and WriteTo on the server, and ResolveUDPAddr with DialUDP plus Write for golang send udp packet flows. Together they form a minimal go udp server and client pair you can extend. If you also want a reliable stream, compare with Golang TCP server and client.
Examples assume a recent Go toolchain on Linux. Run the server and client in two terminals on the same machine; both programs bind or dial a local UDP port (1053 in the samples).
UDP, TCP, and the Go net package
UDP is connectionless: each datagram is independent, there is no built-in retry, and ordering is not guaranteed. That suits latency-sensitive workloads where applications tolerate loss. TCP is connection-oriented and reliable—better when you need an ordered byte stream.
The net package documents Dial, Listen, ListenPacket, and types such as PacketConn and UDPConn. For UDP, ListenPacket("udp", address) returns a PacketConn suitable for ReadFrom and WriteTo. A UDPConn from DialUDP supports Read and Write to one peer.
Golang udp server example: ListenPacket, ReadFrom, WriteTo
ListenPacket announces on a local UDP address. Use udp, udp4, or udp6 as needed. The server loop allocates a buffer, calls ReadFrom, and must use only the n bytes returned (buf[:n]) when building a reply so you do not echo uninitialized buffer tail (a common bug in udp server example code).
Avoid shadowing the time package with a local variable named time; use something like ts for the formatted timestamp.
package main
import (
"fmt"
"log"
"net"
"time"
)
func main() {
pc, err := net.ListenPacket("udp", ":1053")
if err != nil {
log.Fatal(err)
}
defer pc.Close()
for {
buf := make([]byte, 1024)
n, addr, err := pc.ReadFrom(buf)
if err != nil {
log.Println("read:", err)
continue
}
go respond(pc, addr, buf[:n])
}
}
func respond(pc net.PacketConn, addr net.Addr, payload []byte) {
ts := time.Now().Format(time.ANSIC)
msg := fmt.Sprintf("time received: %s. Your message: %s!", ts, string(payload))
if _, err := pc.WriteTo([]byte(msg), addr); err != nil {
log.Println("write:", err)
}
}Start this program in one terminal; it listens on UDP port 1053 on all interfaces.
Golang udp client, go udp, and golang send udp packet
The client resolves 127.0.0.1:1053 (adjust if your server binds elsewhere), opens a UDPConn with DialUDP, then Write sends the datagram—this is the usual golang send udp packet path from a client. Read waits for one reply (set deadlines in real services so Read cannot hang forever).
package main
import (
"fmt"
"log"
"net"
)
func main() {
raddr, err := net.ResolveUDPAddr("udp", "127.0.0.1:1053")
if err != nil {
log.Fatal(err)
}
c, err := net.DialUDP("udp", nil, raddr)
if err != nil {
log.Fatal(err)
}
defer c.Close()
if _, err := c.Write([]byte("This is a UDP message")); err != nil {
log.Fatal(err)
}
buf := make([]byte, 2048)
n, err := c.Read(buf)
if err != nil {
log.Fatal(err)
}
fmt.Println(string(buf[:n]))
}With the server running, this client prints one line containing your payload and a timestamp—similar to the historical sample output for this go udp walkthrough.
Run this udp example locally
- Save the server as
server.go, the client asclient.go(or use one module with twomainpackages in subfolders). - Run
go run server.gofirst. - In another shell, run
go run client.go.
If bind: address already in use appears, pick another free port in both programs. For production code, add SetReadDeadline and SetWriteDeadline, structured logging, and consider message size limits (very large UDP payloads may fragment).
Summary
Golang udp networking centers on net.ListenPacket for a golang udp server example that reads datagrams with ReadFrom and replies with WriteTo per net.Addr, and on ResolveUDPAddr plus DialUDP for a golang udp client where golang send udp packet work uses Write. Go udp server and udp server golang searches map to the same pattern: bound PacketConn, correct buf[:n] slicing, and goroutines only if you accept concurrent handlers—see goroutines in Go for background on the go statement here. Udp example readers should treat UDP as datagram-based, unlike TCP sessions in the TCP article, and validate buffer sizes and timeouts for their workload.
References
- User Datagram Protocol (Wikipedia)
- Package net
- net.ListenPacket
- net.PacketConn
- net.DialUDP
- net.ResolveUDPAddr

