Table of Contents

Bodu.Text.Filtering - Getting started

Unfamiliar with terms like action, evaluation mode, or deciding pattern? Read Core concepts first.

Install

dotnet add package Bodu.Text.Filtering

Targets net8.0. The package has a single dependency on Bodu.Core.

Minimal samples

Filter a list with include/exclude globs

using Bodu.Text.Filtering;

var filter = TextFilter.Build(
[
    TextFilterPattern.Include("error*"),
    TextFilterPattern.Include("warn*"),
    TextFilterPattern.Exclude("*debug*"),
]);

string[] lines = ["error: disk full", "warn: retrying", "error-debug-trace", "info: started"];
var kept = filter.FilterToList(lines);
// → "error: disk full", "warn: retrying"

Parse gitignore-style lines

var filter = TextFilter.Parse(
[
    "# log selection",
    "error*",
    "!*debug*",       // '!' flips the pattern to an exclude
]);

bool match = filter.IsMatch("error-7");        // → true
bool vetoed = filter.IsMatch("error-debug");   // → false

Ordered rules with re-inclusion (gitignore semantics)

var ordered = new TextFilterOptions { Mode = TextFilterEvaluationMode.LastMatchWins };
var filter = TextFilter.Parse(["!*.log", "important.log"], ordered);

filter.IsMatch("app.log");        // → false - excluded by "!*.log"
filter.IsMatch("important.log");  // → true  - re-included by the later rule
filter.IsMatch("readme.txt");     // → true  - unmatched values are included

Ask which pattern decided

var result = filter.Evaluate("app.log");
// → result.Decision == TextFilterDecision.Excluded, result.Pattern is the "!*.log" rule

Read the telemetry

var stats = filter.GetStatistics();
// → stats.ItemsEvaluated, stats.ItemsAccepted, stats.ItemsExcluded,
//   stats.Patterns[i].HitCount - decisions credited to each pattern

Fluent assembly with the builder

var filter = new TextFilterBuilder()
    .AddInclude("{error,warn}*")                 // brace alternation → two cheap prefix matchers
    .AddIncludeRegex(@"^audit-\d+$")
    .AddExclude("*retry*")
    .Build();

Where to go next