diff options
| author | andrew-rykov <[email protected]> | 2022-09-15 16:44:36 +0300 |
|---|---|---|
| committer | andrew-rykov <[email protected]> | 2022-09-15 16:44:36 +0300 |
| commit | 67ddc7744f2c537a293745383c33e324fbf08928 (patch) | |
| tree | 596c2c382226b2cdaf9913e32a4fe41e7f0f1dda /library/cpp/actors/core/log_buffer.cpp | |
| parent | 343f348b324943ca4364be11cad7c9e69fec348c (diff) | |
add log buffer 3
Diffstat (limited to 'library/cpp/actors/core/log_buffer.cpp')
| -rw-r--r-- | library/cpp/actors/core/log_buffer.cpp | 136 |
1 files changed, 73 insertions, 63 deletions
diff --git a/library/cpp/actors/core/log_buffer.cpp b/library/cpp/actors/core/log_buffer.cpp index 4a05f9a8c25..8c80f1d054b 100644 --- a/library/cpp/actors/core/log_buffer.cpp +++ b/library/cpp/actors/core/log_buffer.cpp @@ -6,93 +6,103 @@ using namespace NActors::NLog; namespace NActors { -TLogBufferMessage::TLogBufferMessage(NLog::TEvLog::TPtr& ev) - : Formatted(ev->Get()->Line) - , Time(ev->Get()->Stamp) - , Component(ev->Get()->Component) - , Priority(ev->Get()->Level.ToPrio()) -{} - -TLogBuffer::TLogBuffer(ILoggerMetrics *metrics) +TLogBuffer::TLogBuffer(ILoggerMetrics &metrics, const NLog::TSettings &settings) : Metrics(metrics) + , Settings(settings) {} -bool TLogBuffer::TryAddMessage(TLogBufferMessage message) { - Buffer.push_back(std::move(message)); - BufferSize += sizeof(message); - PrioStats[message.Priority]++; +size_t TLogBuffer::GetLogCostInBytes(NLog::TEvLog *log) const { + return LOG_STRUCTURE_BYTES + log->Line.length(); +} - return true; +ui16 TLogBuffer::GetPrioIndex(NLog::EPrio prio) { + return Min(ui16(prio), ui16(LOG_PRIORITIES_NUMBER - 1)); } -TLogBufferMessage TLogBuffer::GetMessage() { - auto message = Buffer.front(); +TIntrusiveList<NLog::TEvLog, NLog::TEvLogBufferLevelListTag> &TLogBuffer::GetPrioLogs(NLog::EPrio prio) { + return PrioLogsList[GetPrioIndex(prio)]; +} - ui64 messageSize = sizeof(message); - BufferSize -= messageSize; - Buffer.pop_front(); - PrioStats[message.Priority]--; +void TLogBuffer::AddLog(NLog::TEvLog *log) { + NLog::EPrio prio = log->Level.ToPrio(); + if (!CheckSize(log) && prio > NLog::EPrio::Emerg) { // always keep logs with prio Emerg = 0 + HandleIgnoredLog(log); + return; + } - return message; + SizeBytes += GetLogCostInBytes(log); + Logs.PushBack(log); + GetPrioLogs(prio).PushBack(log); } -bool TLogBuffer::IsEmpty() const { - return Buffer.empty(); +NLog::TEvLog* TLogBuffer::Pop() { + NLog::TEvLog* log = Logs.PopFront(); + static_cast<TIntrusiveListItem<TEvLog, TEvLogBufferLevelListTag>&>(*log).Unlink(); + + SizeBytes -= GetLogCostInBytes(log); + + return log; } -size_t TLogBuffer::GetLogsNumber() const { - return Buffer.size(); +bool TLogBuffer::IsEmpty() const { + return Logs.Empty(); } -ui64 TLogBuffer::GetSizeBytes() const { - return BufferSize; +bool TLogBuffer::CheckLogIgnoring() const { + return IgnoredCount > 0; } -void TLogBuffer::FilterByLogPriority(NLog::EPrio prio) { - bool isFirstRemoving = true; - auto it = Buffer.begin(); - while (it != Buffer.end()) - { - if (it->Priority >= prio) { - ui64 messageSize = sizeof(*it); - BufferSize -= messageSize; - Metrics->IncIgnoredMsgs(); - PrioStats[it->Priority]--; +bool TLogBuffer::CheckSize(NLog::TEvLog *log) { + size_t startSizeBytes = SizeBytes; - if (isFirstRemoving && prio > NLog::EPrio::Error) { - it->Priority = NLog::EPrio::Error; - it->Formatted = Sprintf("Ignored log records due to log buffer overflow! IgnoredCount# %" PRIu32 " ", PrioStats[prio]); + size_t logSize = GetLogCostInBytes(log); + if (SizeBytes + logSize <= Settings.BufferSizeLimitBytes) { + return true; + } - PrioStats[NLog::EPrio::Error]++; - BufferSize += sizeof(*it); - it++; - isFirstRemoving = false; + ui16 scanHighestPrio = Max((ui16)1, GetPrioIndex(log->Level.ToPrio())); // always keep logs with prio Emerg = 0 + for (ui16 scanPrio = LOG_PRIORITIES_NUMBER - 1; scanPrio >= scanHighestPrio; scanPrio--) { + TIntrusiveList<NLog::TEvLog, NLog::TEvLogBufferLevelListTag> &scanLogs = PrioLogsList[scanPrio]; + while (!scanLogs.Empty()) { + NLog::TEvLog* log = scanLogs.PopFront(); + SizeBytes -= GetLogCostInBytes(log); + HandleIgnoredLog(log); + + if (SizeBytes + logSize <= Settings.BufferSizeLimitBytes) { + return true; } - else { - it = Buffer.erase(it); - } - } - else { - it++; } } -} -bool inline TLogBuffer::CheckMessagesNumberEnoughForClearing(ui32 number) { - return number * 10 > Buffer.size(); + if (startSizeBytes > SizeBytes) { + return true; + } + + return false; } -bool TLogBuffer::TryReduceLogsNumber() { - ui32 removeLogsNumber = 0; - for (ui16 p = ui16(NLog::EPrio::Trace); p > ui16(NLog::EPrio::Alert); p--) - { - NLog::EPrio prio = static_cast<NLog::EPrio>(p); - removeLogsNumber += PrioStats[prio]; - if (CheckMessagesNumberEnoughForClearing(removeLogsNumber)) { - FilterByLogPriority(prio); - return true; - } +void TLogBuffer::HandleIgnoredLog(NLog::TEvLog *log) { + ui16 logPrio = GetPrioIndex(log->Level.ToPrio()); + Metrics.IncIgnoredMsgs(); + if (IgnoredHighestPrio > logPrio) { + IgnoredHighestPrio = logPrio; } - return false; + IgnoredCount++; + delete log; +} + +ui64 TLogBuffer::GetIgnoredCount() { + return IgnoredCount; +} + +NLog::EPrio TLogBuffer::GetIgnoredHighestPrio() { + NLog::EPrio prio = static_cast<NLog::EPrio>(IgnoredHighestPrio); + return prio; } + +void TLogBuffer::ClearIgnoredCount() { + IgnoredHighestPrio = LOG_PRIORITIES_NUMBER - 1; + IgnoredCount = 0; +} + } |
