Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/proteo5/waf-autoblock/llms.txt

Use this file to discover all available pages before exploring further.

WAF Auto-Block uses standard .NET structured logging. Log entries cover the full polling and blocking lifecycle — startup, every poll cycle, each block and unblock decision, cleanup passes, and API failures — and are designed to let you operate the service safely without reading source code. Every significant state transition emits a log entry that includes enough context to understand what happened and why.

Log Levels

The default configuration emits Information-level logs for most components. This includes cycle start and end summaries, block and unblock events, cleanup summaries, and any error conditions. Changing the log level Set the WafAutoblock-scoped log level to Debug to see fine-grained matching decisions: per-candidate evaluation, threshold comparisons, and skip reasons for IPs that were considered but not blocked. Override via environment variable (recommended for Docker deployments):
Logging__LogLevel__WafAutoblock=Debug
Override at the command line when running locally:
dotnet run -- --Logging:LogLevel:Default=Debug --Logging:LogLevel:WafAutoblock=Debug
Block and unblock events are logged at Warning level so they are easy to filter and alert on in log aggregation systems. Query for level >= Warning in your log pipeline to build a dedicated block-event feed without the noise of routine cycle summaries.

Key Log Messages

The entries below reflect the actual log calls in Worker.cs. Template placeholders like {Ip} and {RuleId} are replaced with real values at runtime.
Level: InformationEmitted once at startup before the first poll cycle begins. Confirms that the background service has been scheduled by the host and the SQLite store initialization is about to run.
Level: WarningEmitted at the start of every poll cycle when the service is not yet fully configured. This happens when any required Cloudflare credential is missing (ApiToken, ZoneTag, AccountId, or BlocklistId), or when no detector (WAF rule or HTTP status code rule) is enabled. The service continues running and will retry on the next cycle — no restart is needed after completing configuration.
Level: InformationEmitted at the beginning of each active poll cycle. {WindowSeconds} reflects the configured Polling.WindowSeconds value (minimum 1). Seeing this message confirms credentials are present and at least one detector is enabled.
Level: WarningEmitted when a WAF rule triggers a block. Fields:
  • {Ip} — the offending IP address
  • {RuleName} / {RuleId} — the matched rule’s display name and Cloudflare rule ID
  • {Count} — number of WAF events observed within the polling window
  • {Threshold} — the configured minimum count required to block
  • {TtlMinutes} — how long (in minutes) this block will be maintained
  • {ItemId} — the Cloudflare account-level IP list item ID, used for TTL-based removal
Level: WarningEmitted when an HTTP status code detector triggers a block. Fields:
  • {Ip} — the offending IP address
  • {DetectorName} — the configured detector name, defaulting to http_status_{StatusCode}
  • {StatusCode} — the HTTP status code that triggered the rule
  • totalErrors {TotalErrors} — total error requests from this IP across all monitored codes
  • distinctPaths {DistinctPaths} — number of distinct request paths hit
  • codeCount {CodeCount} — requests matching this specific status code
  • ratio {CodeRatio} — fraction of total errors attributable to this status code
  • ttl {TtlMinutes}m — block duration in minutes
  • item {ItemId} — Cloudflare IP list item ID
Level: InformationEmitted when a previously blocked IP has its TTL expire and is successfully removed from both the Cloudflare account-level IP list and the local SQLite store. {RuleId} identifies the original rule that triggered the block.
Level: InformationEnd-of-cycle summary emitted after both WAF rule evaluation and HTTP status detection complete. Key fields:
  • {EventCount} — total WAF event records returned by Cloudflare analytics for the window
  • {HttpStatusSignalCount} — total HTTP status signal records evaluated
  • {BlockedCount} — net new IPs added to the blocklist in this cycle (0 is normal when no new offenders appear)
Level: InformationEnd-of-cleanup summary. {RemovedCount} is the number of IPs successfully removed from both Cloudflare and SQLite. {DeferredCount} is the number of entries whose Cloudflare item ID could not be resolved and will be retried on the next cycle.
Level: InformationEmitted when an IP that meets blocking thresholds is excluded because it resolves to a loopback address (127.0.0.1, ::1, localhost, or IPv4-mapped IPv6 loopback). Loopback addresses are monitored but never auto-blocked by design.
Level: WarningEmitted when the Cloudflare API returns HTTP 429 during an IP add operation. The service logs the warning and continues processing remaining candidates in the current cycle. The affected IP will be reconsidered on the next poll cycle.
Level: ErrorEmitted when a non-rate-limit error occurs during an IP add operation. The exception is included in the log entry. The service continues with remaining candidates rather than aborting the cycle.

HTTP Status Detection Logs

When HttpStatusDetection.Enabled = true, additional log entries appear at Debug level during per-IP threshold evaluation.
MessageLevelMeaning
Evaluating HTTP status detector for codes {Codes} over {WindowSeconds} secondsDebugStatus detection sub-cycle is starting; lists all active status codes
HTTP status signal {Ip} status {StatusCode} path {Path} count {Count}DebugRaw signal from Cloudflare analytics before aggregation
Skipping {Ip} for HTTP {StatusCode} because thresholds were not met (total …, paths …, ratio …)DebugIP evaluated but did not meet MinTotalErrors, MinDistinctPaths, or MinCodeRatio
Skipping {Ip} for HTTP {StatusCode} because it is already in the local block storeDebugIP already blocked; evaluation short-circuits
BLOCKED {Ip} via {DetectorName} (HTTP {StatusCode}) …WarningBlock decision — see full field list in Key Log Messages above
Skipping {Ip} in HTTP status detector because it is a loopback addressInformationLoopback exclusion
HTTP status detector excluded {Count} loopback IP aggregate(s) in this cycleInformationCycle-level summary of loopback exclusions

Distributed Path Detector Logs

When HttpStatusDetection.DistributedPathDetection.Enabled = true, additional entries appear for the path-level analysis layer.
MessageLevelMeaning
Distributed HTTP path detector found no suspicious paths for HTTP {StatusCode}DebugNo paths met MinPathTotalErrors and MinDistinctIpsPerPath thresholds
Skipping {Ip} in distributed HTTP path detector because thresholds were not metDebugIP hit suspicious paths but below MinIpHitsOnSuspiciousPaths or MinDistinctSuspiciousPathsPerIp
BLOCKED {Ip} via {DetectorName} (HTTP {StatusCode}) suspiciousPathHits … suspiciousPathCount …WarningDistributed path detector triggered a block
Skipping {Ip} in distributed HTTP path detector because it is a loopback addressInformationLoopback exclusion in the path detector
Distributed HTTP path detector evaluated codes {StatusCodes} and blocked {BlockedCount}InformationEnd-of-detector summary

Log Level Recommendations

ScenarioRecommended LevelReason
Production steady-stateInformationCycle summaries and block/unblock events without per-candidate noise
Troubleshooting missing blocksDebug for WafAutoblockExposes skip reasons, rule ID mismatches, and threshold comparisons
Alerting integrationsWarning or aboveBlock events, rate-limit warnings, and poll skip warnings — no routine chatter
Initial setup validationDebugSee every candidate event and matching decision to confirm rule IDs are correct

Build docs developers (and LLMs) love