How do you handle HTTP timeouts with an HTTP client in Go?
Example
import (
"net/http"
"time"
)
func main() {
// Create an http client with a timeout of 5 seconds
client := &http.Client{
Timeout: time.Second * 5,
}
// Send an HTTP request
resp, err := client.Get("http://example.com")
if err != nil {
// Handle the error
}
// Handle the response
defer resp.Body.Close()
// ...
}
In this example, we create an http.Client instance and set its Timeout field to time.Second * 5, which is a duration of 5 seconds. This means that if the request takes longer than 5 seconds to complete, the client will cancel the request and return an error.
Note that you can set a timeout for different types of HTTP requests, such as GET, POST, PUT, and DELETE, by using the appropriate method on the http.Client instance. For example, you can use client.Post() to set a timeout for an HTTP POST request.
Example
package main
import (
"fmt"
"log"
"net/http"
"time"
)
func main() {
// Create a new HTTP client with a timeout of 10 seconds
client := &http.Client{
Timeout: 10 * time.Second,
}
// Define the endpoints for the CRUD operations
http.HandleFunc("/create", createHandler(client))
http.HandleFunc("/read", readHandler(client))
http.HandleFunc("/update", updateHandler(client))
http.HandleFunc("/delete", deleteHandler(client))
// Start the server and log any errors
log.Fatal(http.ListenAndServe(":8080", nil))
}
func createHandler(client *http.Client) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
// Set the request timeout to 5 seconds
ctx, cancel := context.WithTimeout(r.Context(), 5*time.Second)
defer cancel()
// Make the request with the client
_, err := client.PostContext(ctx, "http://localhost:8080/create", nil)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
// Write the success message to the response
fmt.Fprint(w, "Create successful")
}
}
func readHandler(client *http.Client) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
// Set the request timeout to 5 seconds
ctx, cancel := context.WithTimeout(r.Context(), 5*time.Second)
defer cancel()
// Make the request with the client
_, err := client.GetContext(ctx, "http://localhost:8080/read")
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
// Write the success message to the response
fmt.Fprint(w, "Read successful")
}
}
func updateHandler(client *http.Client) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
// Set the request timeout to 5 seconds
ctx, cancel := context.WithTimeout(r.Context(), 5*time.Second)
defer cancel()
// Make the request with the client
_, err := client.PutContext(ctx, "http://localhost:8080/update", nil)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
// Write the success message to the response
fmt.Fprint(w, "Update successful")
}
}
func deleteHandler(client *http.Client) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
// Set the request timeout to 5 seconds
ctx, cancel := context.WithTimeout(r.Context(), 5*time.Second)
defer cancel()
// Make the request with the client
_, err := client.DeleteContext(ctx, "http://localhost:8080/delete")
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
// Write the success message to the response
fmt.Fprint(w, "Delete successful")
}
}
This code creates an HTTP client with a timeout of 10 seconds, and then defines four endpoint handlers for the CRUD operations. Each handler sets a request timeout of 5 seconds using the request's context, and then makes a request to the corresponding endpoint using the HTTP client. If the request fails, an error response is written to the HTTP response. If the request succeeds, a success message is written to the HTTP response.