Skip to content

Baseline Memory (ML Tab) ​

Since v2.4.0, OpenShield doesn't just learn your traffic — it remembers it. The dynamic baseline (the "what does normal look like" reference every detection is measured against) now has a 30-day memory with operator controls, visible in the TUI's ML tab (press m).

How it works ​

  • The live baseline is a fast-adapting EMA of your inbound traffic (PPS, BPS, TCP, UDP, ICMP, SYN) — updated every few seconds, frozen during attacks.
  • Every day at local midnight, the learned baseline is snapshotted to disk. Up to 30 daily snapshots are kept; the oldest rolls off.
  • The baseline the detector actually uses is a recency-weighted merge: the live EMA gets ~15% of the vote, the 30 days of history ~85% (recent days weigh more — 0.85 decay per day of age).

The practical effect: one weird day — an attack that slipped under detection, a one-off event, a migration — can only drag your detection so far. The other 29 days outvote it.

When an attack bypasses detection ​

If an attack was slow enough to stay under the trigger, the ceiling guard stops it from fully poisoning the baseline — but it can still tilt that day's learning. Fix it in two keystrokes:

  1. Open the TUI → m (ML tab).
  2. Find the poisoned day in the 30-day history, press d (confirm) — the snapshot is deleted and the merged baseline reconfigures immediately.

If the bypass happened today (not yet snapshotted), press D — this resets the live baseline from the remaining history. Same effect, same immediacy.

CLI equivalent:

bash
openshield baseline                    # live + merged values, thresholds, history
openshield baseline delete 2026-08-04  # remove a day, recompute
openshield baseline delete $(date +%F) # reset today's live baseline

Import / export ​

Move a trained baseline between servers (e.g. a replacement node, or after reinstall):

bash
openshield baseline export backup.json   # live baseline + all 30 days
openshield baseline import backup.json   # replace + reconfigure instantly

In the TUI: e exports to /var/lib/openshield/state/baseline-export-<timestamp>.json; i prompts for a path and imports.

Importing also seeds cold starts: a fresh install with imported (or retained) history converges to sane detection in seconds instead of learning for hours.

What the ML tab shows ​

PanelContents
Learningactive / frozen (attack active) / suppressed (schedule), merge weights, spike thresholds and the configured floors
Baselinelive vs merged side by side — PPS, BPS, TCP, UDP, ICMP, SYN
30-Day Historyevery snapshot with date + rates; cursor selects a day for deletion

The tab auto-refreshes every 5 seconds. Keys: j/k scroll, PgUp/PgDn page, d delete day, D reset today, e export, i import, r refresh.

  • dynamic.spike_percentage — how far above the merged baseline = attack (default 200 → 3×).
  • dynamic.attack_min_pps / attack_min_bps — absolute floors; detection never goes blind on quiet servers.
  • openshield schedule suppress baseline <duration> — pause learning ahead of a known traffic spike (maintenance, launches).