This commit is contained in:
Aaron Po
2026-05-15 14:11:34 -04:00
parent e6a20324e4
commit c58e4c1986
7 changed files with 24 additions and 44 deletions

View File

@@ -53,11 +53,6 @@ struct LogEntry {
std::chrono::system_clock::time_point timestamp =
std::chrono::system_clock::now();
std::thread::id calling_thread_id;
/// @brief The thread id of the logger
std::thread::id logging_thread_id =
std::this_thread::get_id(); // captured on construction
/// @brief Severity level of this entry.
LogLevel level;

View File

@@ -9,7 +9,7 @@
void BiergartenPipelineOrchestrator::GenerateBreweries(
std::span<const EnrichedCity> cities) {
logger_->Log(LogLevel::Info, PipelinePhase::BreweryAndBeerGeneration,
"\n=== SAMPLE BREWERY GENERATION ===");
"=== SAMPLE BREWERY GENERATION ===");
generated_breweries_.clear();
size_t skipped_count = 0;

View File

@@ -27,5 +27,5 @@ void BiergartenPipelineOrchestrator::LogResults() const {
++index;
}
logger_->Log(LogLevel::Info, PipelinePhase::Teardown, msg.str());
logger_->Log(LogLevel::Debug, PipelinePhase::Teardown, msg.str());
}

View File

@@ -7,6 +7,7 @@
#include <algorithm>
#include <filesystem>
#include <format>
#include <iterator>
#include <random>
@@ -15,14 +16,12 @@
std::vector<Location> BiergartenPipelineOrchestrator::QueryCitiesWithCountries() {
logger_->Log(LogLevel::Info, PipelinePhase::Startup,
"\n=== GEOGRAPHIC DATA OVERVIEW ===");
"=== GEOGRAPHIC DATA OVERVIEW ===");
const std::filesystem::path locations_path = "locations.json";
auto all_locations = JsonLoader::LoadLocations(locations_path, logger_);
logger_->Log(LogLevel::Info, PipelinePhase::Startup,
std::string(" Locations available: ") +
std::to_string(all_locations.size()));
const size_t sample_count = std::min(
static_cast<size_t>(application_options_.pipeline.location_count),
@@ -40,7 +39,8 @@ std::vector<Location> BiergartenPipelineOrchestrator::QueryCitiesWithCountries()
sample_count_signed, random_generator);
logger_->Log(LogLevel::Info, PipelinePhase::Startup,
std::string(" Sampled locations: ") +
std::to_string(sampled_locations.size()));
std::format(" Locations available: {}", all_locations.size()));
logger_->Log(LogLevel::Info, PipelinePhase::Startup,
std::format(" Sampled locations: {}", sampled_locations.size()));
return sampled_locations;
}

View File

@@ -105,13 +105,5 @@ std::vector<Location> JsonLoader::LoadLocations(
});
}
const std::string msg = std::string("[JsonLoader] Loaded ") +
std::to_string(locations.size()) + " locations from " +
filepath.string();
if (logger) {
logger->Log(LogLevel::Info, PipelinePhase::Startup, msg);
} else {
std::cout << msg << std::endl;
}
return locations;
}

View File

@@ -39,14 +39,8 @@ namespace di = boost::di;
static constexpr size_t kLogMaxCount = 512;
int main(const int argc, char** argv) {
// Configure global spdlog formatting: timestamp, level, and message.
// Use Unicode box-drawing characters to frame logs for improved readability.
// The LogDispatcher includes phase and thread info inside the message.
spdlog::set_pattern(R"(┌────────────────────────────────────────────────────────
%^%l%$ | %Y-%m-%d %H:%M:%S:%e
%v
)");
spdlog::set_level(spdlog::level::debug);
spdlog::set_pattern("│ %Y-%m-%d %H:%M:%S.%e │ %^%-7l%$ │ %v");
BoundedChannel<LogEntry> log_channel(kLogMaxCount);
auto log_dispatcher = std::make_unique<LogDispatcher>(log_channel);
std::thread log_thread([&log_dispatcher] { log_dispatcher->Run(); });
@@ -61,7 +55,7 @@ int main(const int argc, char** argv) {
#endif
log_producer->Log(LogLevel::Info, PipelinePhase::Startup,
"=== Starting Biergarten Pipeline ===");
"STARTING PIPELINE");
const std::optional<ApplicationOptions> parsed_options =
ParseArguments(argc, argv, log_producer);
@@ -83,9 +77,8 @@ int main(const int argc, char** argv) {
std::unique_ptr<IPromptDirectory> prompt_directory;
if (!options.generator.use_mocked) {
try {
prompt_directory =
std::make_unique<PromptDirectory>(options.pipeline.prompt_dir,
log_producer);
prompt_directory = std::make_unique<PromptDirectory>(
options.pipeline.prompt_dir, log_producer);
} catch (const std::exception& dir_error) {
log_producer->Log(
LogLevel::Error, PipelinePhase::Startup,
@@ -107,11 +100,11 @@ int main(const int argc, char** argv) {
di::bind<IExportService>().to<SqliteExportService>(),
di::bind<IPromptFormatter>().to<Gemma4JinjaPromptFormatter>(),
di::bind<IEnrichmentService>().to(
[options, &log_producer](const auto& inj)
-> std::unique_ptr<IEnrichmentService> {
if (options.generator.use_mocked) {
return std::make_unique<MockEnrichmentService>();
}
[options, &log_producer](
const auto& inj) -> std::unique_ptr<IEnrichmentService> {
// if (options.generator.use_mocked) {
// return std::make_unique<MockEnrichmentService>();
// }
return std::make_unique<WikipediaEnrichmentService>(
inj.template create<std::unique_ptr<WebClient>>(),
log_producer);
@@ -165,9 +158,9 @@ int main(const int argc, char** argv) {
// Attempt to use the logging infrastructure; if channel/dispatcher are
// compromised this is a best-effort fallback.
if (log_producer) {
log_producer->Log(LogLevel::Error, PipelinePhase::Teardown,
std::string("Unhandled fatal error in main: ") +
exception.what());
log_producer->Log(
LogLevel::Error, PipelinePhase::Teardown,
std::string("Unhandled fatal error in main: ") + exception.what());
}
log_channel.Close();
log_thread.join();

View File

@@ -3,6 +3,8 @@
* @brief LogProducer implementation for asynchronous pipeline logging.
*/
#include "services/logging/log_producer.h"
#include <chrono>
#include <optional>
#include <string>
@@ -10,15 +12,13 @@
#include "concurrency/bounded_channel.h"
#include "services/logging/log_entry.h"
#include "services/logging/log_producer.h"
LogProducer::LogProducer(BoundedChannel<LogEntry>& channel)
: channel_(channel) {}
void LogProducer::Log(LogLevel level, PipelinePhase phase,
const std::string_view message) {
const std::string_view message) {
channel_.Send(LogEntry{.timestamp = std::chrono::system_clock::now(),
.calling_thread_id = std::this_thread::get_id(),
.level = level,
.phase = phase,
.message = std::string(message)});