feat(ingestion): implement log monitoring script with webhook integration

- Add logwhisperer.sh script for tailing and monitoring system logs
- Implement pattern matching for critical errors (FATAL, ERROR, OOM, segfault)
- Add JSON payload generation with severity levels
- Implement rate limiting and offset tracking per log source
- Add install.sh with interactive configuration and systemd support
- Create comprehensive test suite with pytest
- Add technical specification documentation
- Update CHANGELOG.md following Common Changelog standard

All 12 tests passing. Follows Metodo Sacchi (Safety first, little often, double check).
This commit is contained in:
Luca Sacchi Ricciardi
2026-04-02 16:09:00 +02:00
parent 34dbba1201
commit 69f475ec78
6 changed files with 1148 additions and 0 deletions

View File

@@ -0,0 +1,126 @@
# Technical Specification - Log Ingestion Script (Feature 1)
**Status:** Draft
**Sprint:** 1
**Author:** Tech Lead
**Date:** 2026-04-02
---
## 1. Overview
Uno script Bash leggero da installare sui server dei clienti che monitora i log di sistema, rileva pattern di errore critici e invia i payload via HTTP POST a un webhook n8n configurabile.
## 2. Requisiti Funzionali
### 2.1 Log Sources Monitorati
- `/var/log/syslog` (o `/var/log/messages` su RHEL-based)
- `/var/log/nginx/error.log`
- `/var/log/postgresql/*.log`
### 2.2 Pattern di Errore Rilevati
- `FATAL`
- `ERROR`
- `OOM` / `Out of memory`
- `segfault`
- `disk full` / `No space left on device`
- `Connection refused`
- `Permission denied` (in contesti critici)
### 2.3 Payload JSON (POST al Webhook)
```json
{
"client_id": "<CLIENT_ID>",
"hostname": "<HOSTNAME>",
"source": "/var/log/syslog",
"severity": "critical",
"timestamp": "2026-04-02T10:30:00Z",
"raw_log": "Apr 2 10:30:00 server kernel: Out of memory: Kill process 1234",
"matched_pattern": "OOM"
}
```
### 2.4 Configurazione
File di configurazione: `/etc/logwhisperer/config.env`
```bash
WEBHOOK_URL="https://your-n8n-instance.com/webhook/logwhisperer"
CLIENT_ID="unique-client-uuid"
LOG_SOURCES="/var/log/syslog,/var/log/nginx/error.log"
POLL_INTERVAL=5
MAX_LINE_LENGTH=2000
```
## 3. Requisiti Non Funzionali
### 3.1 Safety First (Metodo Sacchi)
- **Read-only**: Lo script NON scrive mai sui log monitorati
- **Graceful degradation**: Se un file di log non esiste, lo salta silenziosamente
- **Rate limiting**: Max 1 alert/30s per source per evitare flood
- **No root escalation**: Funziona con permessi di lettura sui log (gruppo `adm`)
### 3.2 Little Often
- Polling interval configurabile (default: 5s)
- Tiene traccia dell'ultima posizione letta (offset) per ogni file
- Non ricarica mai righe già processate
### 3.3 Double Check
- Verifica connettività al webhook prima di inviare
- Retry con backoff esponenziale (max 3 tentativi)
- Log locale di debug in `/var/log/logwhisperer/debug.log`
## 4. Architettura
```
┌─────────────────────────────────────────────┐
│ LogWhisperer Agent │
│ │
│ ┌─────────┐ ┌──────────┐ ┌────────────┐ │
│ │ File │ │ Pattern │ │ HTTP │ │
│ │ Tailing │─>│ Matcher │─>│ Dispatcher │ │
│ └─────────┘ └──────────┘ └────────────┘ │
│ ^ | │
│ │ ┌──────────┐ | │
│ └─────│ Offset │<─────────┘ │
│ │ Tracker │ (on success) │
│ └──────────┘ │
└─────────────────────────────────────────────┘
```
## 5. Struttura File
```
scripts/
logwhisperer.sh # Script principale
install.sh # Script di installazione (setup config, systemd)
tests/
conftest.py
test_logwhisperer.py # Test Python con subprocess
docs/
specs/
ingestion_script.md # Questo file
```
## 6. Criteri di Accettazione
- [ ] Lo script legge da almeno 2 source di log configurabili
- [ ] Rileva pattern di errore (case-insensitive)
- [ ] Invia POST JSON al webhook con payload corretto
- [ ] Gestisce retry su fallimento HTTP
- [ ] Non blocca il sistema se il webhook è down
- [ ] Test Python passano con pytest
- [ ] Script installabile con un solo comando
## 7. Note di Sicurezza
- Il `CLIENT_ID` è un UUID v4 generato in fase di installazione
- Il webhook URL deve essere HTTPS
- Nessuna credenziale hardcoded nello script
- I log di debug non contengono dati sensibili
## 8. Dipendenze
- Bash 4.0+
- `curl` (già presente su qualsiasi server Linux)
- `date` (GNU coreutils)
- `sha256sum` o `md5sum` (per deduplicazione opzionale)
- Nessuna dipendenza Python lato server (solo lato test)