How To Do Graceful Shutdown for Go HTTP Server

Hi, I am a cat lover and software engineer from Malang, mostly doing PHP and stuff. Software Engineer Live in Malang, Indonesia Visit my resume and portfolios at didiktrisusanto.dev See you, folks!
Search for a command to run...

Hi, I am a cat lover and software engineer from Malang, mostly doing PHP and stuff. Software Engineer Live in Malang, Indonesia Visit my resume and portfolios at didiktrisusanto.dev See you, folks!
No comments yet. Be the first to comment.
I believed this topic is a lot in the internet but I want to write it anyway, because documenting your own learning journey and share it to the world is good right? Request middleware performs some specific function on the HTTP request or response a...

So my unemployed journey was stopped at #10 because many things happened and today at #37 or 57 days since my last day at work, I finally secured some job offers and agreed to join at a Singapore based company in 2nd January 2025 which I become first...

I was finding a fun project to work with Go, HTMX, and Tailwwindcss and ended up built a simple real-time web based system monitor with the power of web socket. Here’s the result. It shows system information, memories, disk, CPU, and running process...

No update on the job hunting today. An ex coworker gave me a job vacancy from Switzerland and didn’t took any action yet. Decided to continue on my playground building a short url service using Go. The first one was how to implement templ in go as vi...

Long time no see. After took a long break, I finally started to writing again. I missed code with Go so I decided to share about Graceful shutdown in this post.
Graceful shutdown is safer and proper way to shutdown your HTTP server especially in Go where we usually managed the server script by ourself.
The “Graceful shutdown function” facilitates this process, allowing the server to transition smoothly without abruptly terminating active connections.
The most basic and simple way to run the HTTP server in Go is like this
s := &http.Server{
Addr: ":8080",
Handler: mux,
ReadTimeout: 10 * time.Second,
WriteTimeout: 10 * time.Second,
}
log.Fatal(s.ListenAndServe())
s.ListenAndServe() is called to run the server and listen incoming http requests. Yes this works, but when we’re talking about production system, we need more proper way using graceful shutdown to prevent unexpected behavior when the server needs to be stopped.
Here’s how graceful shutdown would be
s := &http.Server{
Addr: ":8080",
Handler: mux,
}
stop := make(chan os.Signal, 1)
signal.Notify(stop, os.Interrupt, syscall.SIGTERM)
go func() {
if err := s.ListenAndServe(); !errors.Is(err, http.ErrServerClosed) {
log.Fatal(err)
}
log.Println("Stopped serving new connections")
}()
<-stop
log.Println("Shutting down gracefully...")
shutdownCtx, shutdownRelease := context.WithTimeout(context.Background(), 10*time.Second)
defer shutdownRelease()
if err := s.Shutdown(shutdownCtx); err != nil {
log.Printf("server shutdown error: %v\n", err)
}
log.Println("Server stoppped")
It’s using goroutine and channel to notify server if there is termination signal. More example of this implementation at my fun project simple real-time system monitoring using Go & HTMX.
Happy coding!