feat: Add OpenVPN monitoring for pfSense via Zabbix UserParameters, a discovery script, and an installation guide.
This commit is contained in:
parent
fb54294e00
commit
bc4d64f1eb
|
|
@ -0,0 +1,106 @@
|
||||||
|
# Instalação do Monitoramento OpenVPN no pfSense
|
||||||
|
## Padrão IT Guys Gold (v2 - Management Interface)
|
||||||
|
|
||||||
|
Este guia descreve como instalar os scripts de monitoramento OpenVPN no pfSense usando a Management Interface via sockets Unix.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Pré-requisitos
|
||||||
|
|
||||||
|
- pfSense 2.x ou superior
|
||||||
|
- Zabbix Agent 2 instalado (pacote `zabbix-agent72`)
|
||||||
|
- Pelo menos um servidor OpenVPN configurado
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Passo 1: Copiar o Script de Discovery
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Via SSH no pfSense:
|
||||||
|
mkdir -p /opt/zabbix
|
||||||
|
|
||||||
|
# Copie o conteúdo do arquivo openvpn-discovery.sh para:
|
||||||
|
vi /opt/zabbix/openvpn-discovery.sh
|
||||||
|
|
||||||
|
# Torne executável
|
||||||
|
chmod +x /opt/zabbix/openvpn-discovery.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Passo 2: Instalar os UserParameters
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Copie o conteúdo do arquivo userparameter_openvpn.conf para:
|
||||||
|
vi /usr/local/etc/zabbix72/zabbix_agentd.conf.d/userparameter_openvpn.conf
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Passo 3: Reiniciar o Zabbix Agent
|
||||||
|
|
||||||
|
```bash
|
||||||
|
service zabbix_agentd restart
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Passo 4: Testar a Instalação
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Testar discovery de usuários
|
||||||
|
zabbix_agentd -t openvpn.discovery
|
||||||
|
|
||||||
|
# Saída esperada (JSON com usuários conectados):
|
||||||
|
# {"data":[{"{#VPN.USER}":"joao.silva","{#VPN.SERVER}":"server14",...}]}
|
||||||
|
|
||||||
|
# Testar contagem total de usuários
|
||||||
|
zabbix_agentd -t openvpn.user.count.total
|
||||||
|
|
||||||
|
# Testar status de servidor específico
|
||||||
|
zabbix_agentd -t openvpn.server.status[server14]
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Passo 5: Importar Template no Zabbix
|
||||||
|
|
||||||
|
1. Acesse **Configuração → Templates → Importar**
|
||||||
|
2. Selecione o arquivo `template_pfsense_hybrid_gold.yaml`
|
||||||
|
3. Clique em **Importar**
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Troubleshooting
|
||||||
|
|
||||||
|
### Script retorna `{"data":[]}`
|
||||||
|
- Verifique se os sockets existem: `ls -la /var/etc/openvpn/server*/sock`
|
||||||
|
- Verifique permissões: o usuário `zabbix` precisa ler os sockets
|
||||||
|
|
||||||
|
### Erro de permissão nos sockets
|
||||||
|
```bash
|
||||||
|
# Adicione o usuário zabbix ao grupo wheel (temporário)
|
||||||
|
pw groupmod wheel -m zabbix
|
||||||
|
service zabbix_agentd restart
|
||||||
|
```
|
||||||
|
|
||||||
|
### Testar manualmente um socket
|
||||||
|
```bash
|
||||||
|
echo "status 2" | nc -U /var/etc/openvpn/server14/sock
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Métricas Disponíveis
|
||||||
|
|
||||||
|
| UserParameter | Descrição |
|
||||||
|
|---------------|-----------|
|
||||||
|
| `openvpn.discovery` | Discovery LLD de usuários conectados |
|
||||||
|
| `openvpn.server.discovery` | Discovery LLD de servidores OpenVPN |
|
||||||
|
| `openvpn.user.count.total` | Total de usuários conectados |
|
||||||
|
| `openvpn.user.count[serverX]` | Usuários por servidor |
|
||||||
|
| `openvpn.server.status[serverX]` | Status do servidor (1/0) |
|
||||||
|
| `openvpn.user.bytes_received[user]` | Bytes recebidos pelo usuário |
|
||||||
|
| `openvpn.user.bytes_sent[user]` | Bytes enviados pelo usuário |
|
||||||
|
| `openvpn.user.connected_since[user]` | Timestamp de conexão |
|
||||||
|
| `openvpn.user.status[user]` | Status do usuário (1/0) |
|
||||||
|
|
@ -1,34 +1,47 @@
|
||||||
#!/bin/sh
|
#!/bin/sh
|
||||||
# OpenVPN Discovery Script (Arthur's Gold Standard)
|
# OpenVPN Discovery Script via Management Interface (Arthur's Gold Standard v5-FINAL)
|
||||||
# Outputs: {#VPN.USER}, {#VPN.SERVER}, {#VPN.REAL_IP}
|
# Compatível com: pfSense 2.x / FreeBSD
|
||||||
|
#
|
||||||
|
# Outputs: {#VPN.USER}, {#VPN.SERVER}, {#VPN.REAL_IP}, {#VPN.VIRTUAL_IP}
|
||||||
|
|
||||||
JSON_OUTPUT="{\"data\":["
|
SOCKET_DIR="/var/etc/openvpn"
|
||||||
FIRST_ITEM=1
|
|
||||||
|
|
||||||
# Loop through all status logs
|
# Inicia JSON
|
||||||
for logfile in /var/log/openvpn/status*.log; do
|
printf '{"data":['
|
||||||
[ -e "$logfile" ] || continue
|
|
||||||
|
|
||||||
# Extract Server Name from Filename "status_SERVERNAME.log"
|
first=1
|
||||||
# Note: Busybox filename parsing
|
|
||||||
filename=$(basename "$logfile")
|
|
||||||
# Remove prefix "status_" and suffix ".log"
|
|
||||||
server_name=$(echo "$filename" | sed -e 's/^status_//' -e 's/\.log$//')
|
|
||||||
|
|
||||||
# Read the file and parse "CLIENT_LIST" lines
|
# Loop através de cada socket
|
||||||
# Format: CLIENT_LIST,CommonName,RealAddress,VirtualAddress,BytesReceived,BytesSent,Since,Since(time_t),Username,ClientID,PeerID
|
for sockdir in "$SOCKET_DIR"/server*/; do
|
||||||
while IFS=, read -r type common_name real_address virtual_address bytes_rx bytes_tx since since_unix username client_id peer_id; do
|
[ -d "$sockdir" ] || continue
|
||||||
if [ "$type" = "CLIENT_LIST" ] && [ "$common_name" != "Common Name" ]; then
|
|
||||||
# Extract IP only from RealAddress (IP:PORT)
|
|
||||||
real_ip=$(echo "$real_address" | cut -d: -f1)
|
|
||||||
|
|
||||||
# Append to JSON
|
sockfile="${sockdir}sock"
|
||||||
if [ $FIRST_ITEM -eq 0 ]; then JSON_OUTPUT="$JSON_OUTPUT,"; fi
|
[ -S "$sockfile" ] || continue
|
||||||
JSON_OUTPUT="$JSON_OUTPUT{\"{#VPN.USER}\":\"$common_name\",\"{#VPN.SERVER}\":\"$server_name\",\"{#VPN.REAL_IP}\":\"$real_ip\"}"
|
|
||||||
FIRST_ITEM=0
|
server_name=$(basename "$sockdir")
|
||||||
|
|
||||||
|
# Consulta o socket e processa linha por linha
|
||||||
|
(echo "status 2"; sleep 0.3; echo "quit") | /usr/bin/nc -U "$sockfile" 2>/dev/null | \
|
||||||
|
grep "^CLIENT_LIST," | grep -v "Common Name" | \
|
||||||
|
while IFS=',' read -r type cn realaddr virtaddr rest; do
|
||||||
|
# Ignora se CN está vazio ou é o header
|
||||||
|
[ -z "$cn" ] && continue
|
||||||
|
|
||||||
|
# Extrai apenas IP (remove porta)
|
||||||
|
real_ip=$(echo "$realaddr" | cut -d: -f1)
|
||||||
|
virt_ip=$(echo "$virtaddr" | cut -d: -f1)
|
||||||
|
|
||||||
|
# Imprime separador se não for primeiro
|
||||||
|
if [ $first -eq 0 ]; then
|
||||||
|
printf ','
|
||||||
fi
|
fi
|
||||||
done < "$logfile"
|
|
||||||
|
printf '{"{#VPN.USER}":"%s","{#VPN.SERVER}":"%s","{#VPN.REAL_IP}":"%s","{#VPN.VIRTUAL_IP}":"%s"}' "$cn" "$server_name" "$real_ip" "$virt_ip"
|
||||||
|
first=0
|
||||||
done
|
done
|
||||||
|
|
||||||
JSON_OUTPUT="$JSON_OUTPUT]}"
|
# Atualiza flag first se houve saída
|
||||||
echo "$JSON_OUTPUT"
|
first=0
|
||||||
|
done
|
||||||
|
|
||||||
|
printf ']}\n'
|
||||||
|
|
@ -1,16 +1,43 @@
|
||||||
# OpenVPN UserParameters for Zabbix Agent (Arthur's Gold Standard)
|
# OpenVPN UserParameters for Zabbix Agent (Arthur's Gold Standard v5-FINAL)
|
||||||
# Compatible with: Zabbix 7.0+
|
# Compatível com: Zabbix 7.0+ / pfSense 2.x / FreeBSD
|
||||||
# Installation: Copy to /usr/local/etc/zabbix72/zabbix_agentd.conf.d/
|
# Instalação: Copiar para /usr/local/etc/zabbix7/zabbix_agentd.conf.d/
|
||||||
|
#
|
||||||
|
# IMPORTANTE: Usa Management Interface via sockets Unix
|
||||||
|
# Testado em pfSense 2.8.0-RELEASE
|
||||||
|
|
||||||
|
# Discovery de usuários conectados (via sockets)
|
||||||
UserParameter=openvpn.discovery,/opt/zabbix/openvpn-discovery.sh
|
UserParameter=openvpn.discovery,/opt/zabbix/openvpn-discovery.sh
|
||||||
|
|
||||||
# Fetch raw metrics for a specific user (Usernames must be unique across servers or we grab the first match)
|
# Versão do OpenVPN
|
||||||
UserParameter=openvpn.user.bytes_received.total[*],grep -h "^CLIENT_LIST,$1," /var/log/openvpn/status*.log 2>/dev/null | head -1 | cut -d, -f5
|
|
||||||
UserParameter=openvpn.user.bytes_sent.total[*],grep -h "^CLIENT_LIST,$1," /var/log/openvpn/status*.log 2>/dev/null | head -1 | cut -d, -f6
|
|
||||||
UserParameter=openvpn.user.connected_since[*],grep -h "^CLIENT_LIST,$1," /var/log/openvpn/status*.log 2>/dev/null | head -1 | cut -d, -f8
|
|
||||||
UserParameter=openvpn.user.real_address.new[*],grep -h "^CLIENT_LIST,$1," /var/log/openvpn/status*.log 2>/dev/null | head -1 | cut -d, -f3 | cut -d: -f1
|
|
||||||
UserParameter=openvpn.user.status[*],if grep -q "^CLIENT_LIST,$1," /var/log/openvpn/status*.log 2>/dev/null; then echo 1; else echo 0; fi
|
|
||||||
|
|
||||||
# General OpenVPN Instance Metrics
|
|
||||||
UserParameter=openvpn.version,openvpn --version 2>&1 | head -1 | awk '{print $2}'
|
UserParameter=openvpn.version,openvpn --version 2>&1 | head -1 | awk '{print $2}'
|
||||||
UserParameter=openvpn.user.count,grep -h "^CLIENT_LIST" /var/log/openvpn/status*.log 2>/dev/null | grep -v "Common Name" | wc -l
|
|
||||||
|
# Contagem total de usuários conectados (todos os servidores)
|
||||||
|
UserParameter=openvpn.user.count.total,for sock in /var/etc/openvpn/server*/sock; do [ -S "$sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "$sock" 2>/dev/null; done | grep -c "^CLIENT_LIST," 2>/dev/null || echo 0
|
||||||
|
|
||||||
|
# Contagem de usuários por servidor
|
||||||
|
# Uso: openvpn.user.count[server14]
|
||||||
|
UserParameter=openvpn.user.count[*],[ -S "/var/etc/openvpn/$1/sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "/var/etc/openvpn/$1/sock" 2>/dev/null | grep -c "^CLIENT_LIST," || echo 0
|
||||||
|
|
||||||
|
# Status do servidor OpenVPN (1=online, 0=offline)
|
||||||
|
# Uso: openvpn.server.status[server14]
|
||||||
|
UserParameter=openvpn.server.status[*],[ -S "/var/etc/openvpn/$1/sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "/var/etc/openvpn/$1/sock" 2>/dev/null | grep -q "^TITLE" && echo 1 || echo 0
|
||||||
|
|
||||||
|
# Bytes recebidos pelo usuário (busca em todos os servidores)
|
||||||
|
# Uso: openvpn.user.bytes_received[joao.silva]
|
||||||
|
UserParameter=openvpn.user.bytes_received.total[*],for sock in /var/etc/openvpn/server*/sock; do [ -S "$sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "$sock" 2>/dev/null | grep "^CLIENT_LIST,$1,"; done | head -1 | cut -d, -f6
|
||||||
|
|
||||||
|
# Bytes enviados pelo usuário
|
||||||
|
# Uso: openvpn.user.bytes_sent[joao.silva]
|
||||||
|
UserParameter=openvpn.user.bytes_sent.total[*],for sock in /var/etc/openvpn/server*/sock; do [ -S "$sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "$sock" 2>/dev/null | grep "^CLIENT_LIST,$1,"; done | head -1 | cut -d, -f7
|
||||||
|
|
||||||
|
# Timestamp de conexão do usuário (epoch)
|
||||||
|
# Uso: openvpn.user.connected_since[joao.silva]
|
||||||
|
UserParameter=openvpn.user.connected_since[*],for sock in /var/etc/openvpn/server*/sock; do [ -S "$sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "$sock" 2>/dev/null | grep "^CLIENT_LIST,$1,"; done | head -1 | cut -d, -f9
|
||||||
|
|
||||||
|
# IP real do usuário
|
||||||
|
# Uso: openvpn.user.real_address.new[joao.silva]
|
||||||
|
UserParameter=openvpn.user.real_address.new[*],for sock in /var/etc/openvpn/server*/sock; do [ -S "$sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "$sock" 2>/dev/null | grep "^CLIENT_LIST,$1,"; done | head -1 | cut -d, -f3 | cut -d: -f1
|
||||||
|
|
||||||
|
# Status do usuário (1=conectado, 0=desconectado)
|
||||||
|
# Uso: openvpn.user.status[joao.silva]
|
||||||
|
UserParameter=openvpn.user.status[*],for sock in /var/etc/openvpn/server*/sock; do [ -S "$sock" ] && (echo "status 2"; sleep 0.2; echo "quit") | /usr/bin/nc -U "$sock" 2>/dev/null | grep -q "^CLIENT_LIST,$1," && echo 1 && exit; done; echo 0
|
||||||
Loading…
Reference in New Issue