Цензурування логів
У цьому посібнику показано, як реалізувати цензурування конфіденційної інформації у ваших журналах OpenTelemetry .NET. Цензурування є важливою практикою для захисту конфіденційних даних, таких як інформація, що дозволяє ідентифікувати особу (PII), облікові дані та інша конфіденційна інформація.
Чому важливо цензурувати логи?
Цензурування чутливої інформації з логів є важливим для:
- Дотримання вимог: Дотримання нормативних вимог, таких як GDPR, HIPAA або PCI DSS
- Безпеки: Запобігання витоку чутливих даних у файлах журналів або системах управління журналами
- Конфіденційності: Захист конфіденційності користувачів шляхом видалення інформації, що дозволяє ідентифікувати особу (PII)
- Зниження ризиків: Мінімізація впливу потенційних витоків даних журналів
Реалізація базового процесора цензурування
OpenTelemetry дозволяє створювати власні процесори, які можуть змінювати записи журналів перед їх експортом. Ось як створити базовий процесор цензурування:
using System.Collections;
using OpenTelemetry;
using OpenTelemetry.Logs;
internal sealed class MyRedactionProcessor : BaseProcessor<LogRecord>
{
public override void OnEnd(LogRecord logRecord)
{
if (logRecord.Attributes != null)
{
logRecord.Attributes = new MyClassWithRedactionEnumerator(logRecord.Attributes);
}
}
internal sealed class MyClassWithRedactionEnumerator : IReadOnlyList<KeyValuePair<string, object?>>
{
private readonly IReadOnlyList<KeyValuePair<string, object?>> state;
public MyClassWithRedactionEnumerator(IReadOnlyList<KeyValuePair<string, object?>> state)
{
this.state = state;
}
public int Count => this.state.Count;
public KeyValuePair<string, object?> this[int index]
{
get
{
var item = this.state[index];
var entryVal = item.Value?.ToString();
if (entryVal != null && entryVal.Contains("<secret>"))
{
return new KeyValuePair<string, object?>(item.Key, "***REDACTED***");
}
return item;
}
}
public IEnumerator<KeyValuePair<string, object?>> GetEnumerator()
{
for (var i = 0; i < this.Count; i++)
{
yield return this[i];
}
}
IEnumerator IEnumerable.GetEnumerator()
{
return this.GetEnumerator();
}
}
}
Цей процесор перевіряє кожне значення атрибуту журналу і замінює всі, що містять рядок «
Використання процесора цензурування
Щоб використовувати процесор цензурування, додайте його до конфігурації журналювання OpenTelemetry:
using Microsoft.Extensions.Logging;
using OpenTelemetry.Logs;
// Припустимо, що MyRedactionProcessor визначено в іншому місці.
// public class MyRedactionProcessor : BaseProcessor<LogRecord> { ... }
var loggerFactory = LoggerFactory.Create(builder =>
{
builder.AddOpenTelemetry(logging =>
{
logging.AddProcessor(new MyRedactionProcessor());
logging.AddConsoleExporter();
});
});
var logger = loggerFactory.CreateLogger<Program>();
// Повідомлення буде відредаговано MyRedactionProcessor
logger.FoodPriceChanged("", 9.99);
loggerFactory.Dispose();
При виконанні цього коду будь-який атрибут журналу, що містить “
Розширені стратегії цензурування
У реальних застосунках вам знадобляться більш складні стратегії цензурування, або через SDK, або через процесори OTel Collector.
Ось кілька підходів, які використовують SDK:
1. Відповідність шаблонам за допомогою регулярних виразів
public KeyValuePair<string, object?> this[int index]
{
get
{
var item = this.state[index];
var entryVal = item.Value?.ToString();
if (entryVal != null)
{
// Redact credit card numbers
var redactedValue = Regex.Replace(
entryVal,
@"\b(?:\d{4}[-\s]?){3}\d{4}\b",
"***CARD-REDACTED***");
// Redact email addresses
redactedValue = Regex.Replace(
redactedValue,
@"\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Z|a-z]{2,}\b",
"***EMAIL-REDACTED***");
if (redactedValue != entryVal)
{
return new KeyValuePair<string, object?>(item.Key, redactedValue);
}
}
return item;
}
}
2. Цензурування на основі полів
Ви можете захотіти відредагувати конкретні назви полів незалежно від їх вмісту:
public KeyValuePair<string, object?> this[int index]
{
get
{
var item = this.state[index];
// Цензурування чутливих полів за назвою
var sensitiveFields = new[] { "password", "ssn", "creditcard", "api_key" };
if (sensitiveFields.Any(field => item.Key.Contains(field, StringComparison.OrdinalIgnoreCase)))
{
return new KeyValuePair<string, object?>(item.Key, "***REDACTED***");
}
return item;
}
}
3. Часткове цензурування
Для деяких типів даних ви можете захотіти показати частину значення:
public KeyValuePair<string, object?> this[int index]
{
get
{
var item = this.state[index];
var entryVal = item.Value?.ToString();
if (item.Key.Equals("email", StringComparison.OrdinalIgnoreCase) && entryVal != null)
{
var parts = entryVal.Split('@');
if (parts.Length == 2)
{
// Показати перший символ імені користувача та домен
var redactedEmail = $"{parts[0][0]}***@{parts[1]}";
return new KeyValuePair<string, object?>(item.Key, redactedEmail);
}
}
return item;
}
}
Інтеграція з ASP.NET Core
Для ASP.NET Core застосунків ви можете інтегрувати свій процесор цензурування:
builder.Services.AddOpenTelemetry()
.WithLogging(logging =>
{
logging.AddProcessor(new MyRedactionProcessor());
logging.AddConsoleExporter();
});
Дізнайтеся більше
Відгук
Чи це було корисним?
Дякуємо. Ми цінуємо ваші відгуки!
Будь ласка, дайте нам знати як ми можемо покращити цю сторінку. Ми цінуємо ваші відгуки!