125 lines
3.9 KiB
Bash
Executable File
125 lines
3.9 KiB
Bash
Executable File
#!/bin/bash
|
|
# mc-log-watcher.sh - Parse les logs MC en temps réel + historique récent
|
|
|
|
OUTPUT="/var/cache/mc-logs.json"
|
|
MAX_EVENTS=200
|
|
LOG_MC1="/srv/Minecraft/logs/latest.log"
|
|
LOG_MC2="/srv/Fabric/logs/latest.log"
|
|
TMP="$OUTPUT.tmp"
|
|
HISTORY_LINES=500 # Lignes historiques à lire au démarrage
|
|
|
|
declare -a EVENTS=()
|
|
|
|
touch "$OUTPUT"
|
|
chmod 644 "$OUTPUT"
|
|
|
|
write_json() {
|
|
local json='{"events":['
|
|
local first=true
|
|
for event in "${EVENTS[@]}"; do
|
|
$first || json+=','
|
|
json+="$event"
|
|
first=false
|
|
done
|
|
json+=']}'
|
|
echo "$json" > "$TMP"
|
|
mv "$TMP" "$OUTPUT"
|
|
}
|
|
|
|
add_event() {
|
|
local server="$1"
|
|
local type="$2"
|
|
local message="$3"
|
|
local ts="$4" # optionnel: timestamp extrait du log
|
|
|
|
# Si pas de timestamp fourni, utiliser l'heure actuelle
|
|
if [ -z "$ts" ]; then
|
|
ts=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
fi
|
|
|
|
message="${message//\\/\\\\}"
|
|
message="${message//\"/\\\"}"
|
|
|
|
local entry="{\"ts\":\"$ts\",\"server\":\"$server\",\"type\":\"$type\",\"msg\":\"$message\"}"
|
|
EVENTS+=("$entry")
|
|
|
|
if [ "${#EVENTS[@]}" -gt "$MAX_EVENTS" ]; then
|
|
EVENTS=("${EVENTS[@]:1}")
|
|
fi
|
|
}
|
|
|
|
# Extraire le timestamp ISO depuis une ligne de log MC
|
|
# Format: [HH:MM:SS] ... → on utilise la date du jour + l'heure du log
|
|
extract_ts() {
|
|
local line="$1"
|
|
local hour
|
|
if [[ "$line" =~ ^\[([0-9]{2}):([0-9]{2}):([0-9]{2})\] ]]; then
|
|
hour="${BASH_REMATCH[1]}:${BASH_REMATCH[2]}:${BASH_REMATCH[3]}"
|
|
echo "$(date -u +%Y-%m-%d)T${hour}Z"
|
|
else
|
|
date -u +"%Y-%m-%dT%H:%M:%SZ"
|
|
fi
|
|
}
|
|
|
|
parse_line() {
|
|
local server="$1"
|
|
local line="$2"
|
|
local write="$3" # "write" pour écrire le JSON après
|
|
|
|
[[ -z "$line" ]] && return
|
|
|
|
local ts
|
|
ts=$(extract_ts "$line")
|
|
|
|
if [[ "$line" =~ ([A-Za-z0-9_]+)\ joined\ the\ game ]]; then
|
|
add_event "$server" "join" "${BASH_REMATCH[1]} a rejoint le serveur" "$ts"
|
|
elif [[ "$line" =~ ([A-Za-z0-9_]+)\ left\ the\ game ]]; then
|
|
add_event "$server" "leave" "${BASH_REMATCH[1]} a quitté le serveur" "$ts"
|
|
elif [[ "$line" =~ ([A-Za-z0-9_]+)\ (was\ slain|was\ shot|drowned|fell|burned|tried\ to\ swim|walked\ into|was\ killed|was\ blown|suffocated|hit\ the\ ground|starved|was\ poked|was\ impaled|was\ fireballed|was\ stung) ]]; then
|
|
local msg="${line#*]: }"
|
|
add_event "$server" "death" "$msg" "$ts"
|
|
elif [[ "$line" =~ ([A-Za-z0-9_]+)\ has\ (made\ the\ advancement|completed\ the\ challenge|reached\ the\ goal)\ \[(.+)\] ]]; then
|
|
add_event "$server" "advancement" "${BASH_REMATCH[1]} : ${BASH_REMATCH[3]}" "$ts"
|
|
elif [[ "$line" =~ \[Server\ thread/INFO\]:\ \<([A-Za-z0-9_]+)\>\ (.+) ]]; then
|
|
add_event "$server" "chat" "<${BASH_REMATCH[1]}> ${BASH_REMATCH[2]}" "$ts"
|
|
elif [[ "$line" =~ Done\ \([0-9.]+s\)\!\ For\ help ]]; then
|
|
add_event "$server" "start" "Serveur démarré" "$ts"
|
|
elif [[ "$line" =~ Stopping\ the\ server ]]; then
|
|
add_event "$server" "stop" "Serveur arrêté" "$ts"
|
|
fi
|
|
|
|
[ "$write" = "write" ] && write_json
|
|
}
|
|
|
|
# ===== Lire l'historique récent des deux logs =====
|
|
echo "[mc-log-watcher] Lecture historique ($HISTORY_LINES lignes)..."
|
|
|
|
if [ -f "$LOG_MC1" ]; then
|
|
while IFS= read -r line; do
|
|
parse_line "MC1" "$line"
|
|
done < <(tail -n "$HISTORY_LINES" "$LOG_MC1")
|
|
fi
|
|
|
|
if [ -f "$LOG_MC2" ]; then
|
|
while IFS= read -r line; do
|
|
parse_line "MC2" "$line"
|
|
done < <(tail -n "$HISTORY_LINES" "$LOG_MC2")
|
|
fi
|
|
|
|
write_json
|
|
echo "[mc-log-watcher] Historique chargé (${#EVENTS[@]} events). Surveillance en cours..."
|
|
|
|
# ===== Surveiller en temps réel =====
|
|
FIFO=$(mktemp -u /tmp/mc-watcher-XXXXXX)
|
|
mkfifo "$FIFO"
|
|
trap "rm -f $FIFO; kill 0" EXIT INT TERM
|
|
|
|
tail -F "$LOG_MC1" 2>/dev/null | sed 's/^/MC1|/' > "$FIFO" &
|
|
tail -F "$LOG_MC2" 2>/dev/null | sed 's/^/MC2|/' > "$FIFO" &
|
|
|
|
while IFS= read -r rawline; do
|
|
server="${rawline%%|*}"
|
|
line="${rawline#*|}"
|
|
parse_line "$server" "$line" "write"
|
|
done < "$FIFO"
|