Sling Academy
Home/Golang/Logging and Monitoring WebSocket Traffic in Go Applications

Logging and Monitoring WebSocket Traffic in Go Applications

Last updated: November 26, 2024

Introduction

The Go programming language, often referred to as Golang, is popular for building high-performance web servers. One of its powerful features is handling WebSocket connections. WebSockets provide a way to open an interactive communication session between the user's browser and a server. Using WebSockets, you can send messages to a server and receive event-driven responses without having to poll the server for a reply.

In this article, we will explore how to log and monitor WebSocket traffic effectively in Go applications. By implementing comprehensive logging, developers can catch issues early, analyze traffic patterns, and improve application performance.

Setting Up a Basic WebSocket Server in Go

Before delving into logging and monitoring, let's set up a simple WebSocket server. For demonstration purposes, we will use the github.com/gorilla/websocket package, a popular library for WebSocket handling in Go.


package main

import (
	"fmt"
	"net/http"
	"github.com/gorilla/websocket"
)

var upgrader = websocket.Upgrader{
	ReadBufferSize:  1024,
	WriteBufferSize: 1024,
}

func wsHandler(w http.ResponseWriter, r *http.Request) {
	conn, err := upgrader.Upgrade(w, r, nil)
	if err != nil {
		fmt.Println(err)
		return
	}
	for {
		messageType, p, err := conn.ReadMessage()
		if err != nil {
			fmt.Println(err)
			return
		}
		fmt.Printf("Received: %s\n", p)
		if err := conn.WriteMessage(messageType, p); err != nil {
			fmt.Println(err)
			return
		}
	}
}

func main() {
	http.HandleFunc("/ws", wsHandler)
	fmt.Println("Server started on :8080")
	http.ListenAndServe(":8080", nil)
}

This code creates a WebSocket server that listens on port 8080 and echoes back any message it receives.

Adding Logging

Logging WebSocket activity is crucial for maintaining your application. We'll use Go's standard log package to capture server events and errors. Modify the handler function to include logging:


import (
	"log"
	"os"
)

// Initialize a logger
var logger = log.New(os.Stdout, "INFO: ", log.Ldate|log.Ltime|log.Lshortfile)

func init() {
	log.SetOutput(os.Stdout)
}

func wsHandler(w http.ResponseWriter, r *http.Request) {
	conn, err := upgrader.Upgrade(w, r, nil)
	if err != nil {
		logger.Println("Upgrade failed:", err)
		return
	}
	logger.Println("Client connected:", conn.RemoteAddr())
	for {
		messageType, p, err := conn.ReadMessage()
		if err != nil {
			logger.Println("Read error:", err)
			return
		}
		logger.Printf("Received: %s from %s\n", p, conn.RemoteAddr())
		if err := conn.WriteMessage(messageType, p); err != nil {
			logger.Println("Write error:", err)
			return
		}
	}
}

In this enhanced version of the handler, each significant event is logged, including client connections, messages received, and errors encountered.

Monitoring WebSocket Traffic

Monitoring WebSocket traffic requires observing patterns over time. For comprehensive monitoring, you might integrate external services like Prometheus for Go.

The example below shows how to configure a simple counter metric using Prometheus tools:


import (
	"github.com/prometheus/client_golang/prometheus"
	"github.com/prometheus/client_golang/prometheus/promhttp"
)

var totalConnections = prometheus.NewCounter(
	prometheus.CounterOpts{
		Name: "websocket_total_connections",
		Help: "Total number of established WebSocket connections",
	},
)

func init() {
	prometheus.MustRegister(totalConnections)
}

func main() {
	http.HandleFunc("/ws", func(w http.ResponseWriter, r *http.Request) {
		wsHandler(w, r)
		totalConnections.Inc()
	})
	http.Handle("/metrics", promhttp.Handler())
	fmt.Println("Server is running with Prometheus metrics on :8080")
	http.ListenAndServe(":8080", nil)
}

This setup will increment the totalConnections metric every time a new WebSocket connection is made. The metrics endpoint provided by Prometheus (/metrics) allows you to scrape these metrics for monitoring purposes.

Conclusion

Logging and monitoring WebSocket activity in Go applications is an essential practice for scalable and reliable server-side applications. With just a few lines of code, developers can implement efficient WebSocket logging and integrate comprehensive monitoring tools. This observational capacity is invaluable for proactive application maintenance and troubleshooting.

Next Article: Implementing Role-Based Access Control for WebSocket Applications in Go

Previous Article: Working with WebSocket Compression for Efficient Data Transfer in Go

Series: Websocket & Chat Programs in Go

Golang

Related Articles

You May Also Like

  • How to remove HTML tags in a string in Go
  • How to remove special characters in a string in Go
  • How to remove consecutive whitespace in a string in Go
  • How to count words and characters in a string in Go
  • Relative imports in Go: Tutorial & Examples
  • How to run Python code with Go
  • How to generate slug from title in Go
  • How to create an XML sitemap in Go
  • How to redirect in Go (301, 302, etc)
  • Using Go with MongoDB: CRUD example
  • Auto deploy Go apps with CI/ CD and GitHub Actions
  • Fixing Go error: method redeclared with different receiver type
  • Fixing Go error: copy argument must have slice type
  • Fixing Go error: attempted to use nil slice
  • Fixing Go error: assignment to constant variable
  • Fixing Go error: cannot compare X (type Y) with Z (type W)
  • Fixing Go error: method has pointer receiver, not called with pointer
  • Fixing Go error: assignment mismatch: X variables but Y values
  • Fixing Go error: array index must be non-negative integer constant