I will show you how to deploy HermitMQ and integrate clients. The broker comes as a ready package for Debian and Ubuntu systems. Download the latest release and install it using the package manager. The service will start automatically.
cd /tmp/
wget https://github.com/ekhidirov/hermitmq/releases/latest/download/hermitmq_amd64.deb
sudo apt install -y ./hermitmq_amd64.deb
sudo systemctl status hermitmq
Client installation
To work with the broker download the SDK into your project. The import paths are now configured correctly for public access.
go get github.com/ekhidirov/hermitmq/pkg/client
Project structure
The Go compiler forbids keeping two entry points in one folder. I placed the files in different directories inside the cmd folder. This solves all compilation problems. Prepare the following file structure before writing code.
my_project/
├── cmd/
│ ├── consumer/
│ │ └── main.go
│ └── producer/
│ └── main.go
├── go.mod
└── go.sum
Interactive sender
First we initialize the producer. When connecting we specify the server address topic and partition number. Instead of a placeholder be sure to specify the real IP address where your broker is deployed. I added a loop to read keyboard input. The program will wait for your text and send it to the broker.
package main
import (
"bufio"
"fmt"
"log"
"os"
"github.com/ekhidirov/hermitmq/pkg/client"
)
func main() {
// Connect to the broker replacing YOUR_SERVER_IP with actual IP
producer, err := client.NewProducer("YOUR_SERVER_IP:9092", "test_topic", 0)
if err != nil {
log.Fatalf("Connection error: %v", err)
}
defer producer.Close()
fmt.Println("Connected to the cloud! Type your messages and press Enter:")
// Start the command line scanner
scanner := bufio.NewScanner(os.Stdin)
for scanner.Scan() {
text := scanner.Text()
if text == "" {
continue // Ignore empty Enter key presses
}
offset, err := producer.Send([]byte(text))
if err != nil {
log.Printf("Send error: %v\n", err)
continue
}
fmt.Printf("✔ Delivered (Offset: %d)\n", offset)
}
if err := scanner.Err(); err != nil {
log.Printf("Console read error: %v", err)
}
}
Reading and committing
Listener configuration is done similarly. I create a consumer and pass the group name. The broker itself will remember the reading position. The receive method works by blocking the goroutine. I trigger a manual commit only after the text is successfully printed to the screen to guarantee delivery.
package main
import (
"fmt"
"log"
"github.com/ekhidirov/hermitmq/pkg/client"
)
func main() {
// Connect to the broker replacing YOUR_SERVER_IP with actual IP
consumer, err := client.NewConsumer("YOUR_SERVER_IP:9092", "test_group", "test_topic", 0)
if err != nil {
log.Fatalf("Connection error: %v", err)
}
defer consumer.Close()
fmt.Println("Listening to the network. Waiting for new messages...")
for {
msg, err := consumer.Receive()
if err != nil {
log.Fatalf("Network error or disconnection: %v", err)
}
// Print the received payload
fmt.Printf("[Incoming | Offset: %d] %s\n", msg.Offset, string(msg.Payload))
// Commit the read offset
consumer.Commit(msg.Offset)
}
}
Launching the integration
Open two terminal windows. In the first one start the listener. In the second one start the sender and write messages.
go run cmd/consumer/main.go
go run cmd/producer/main.go


