/* * Looks up a component by its short name, or returns kNumLogComponents * if the shortName is invalid */ const LogComponent _getComponentForShortName(StringData shortName) { for (int i = 0; i < int(LogComponent::kNumLogComponents); ++i) { LogComponent component = static_cast<LogComponent::Value>(i); if (component.getShortName() == shortName) return component; } return static_cast<LogComponent::Value>(LogComponent::kNumLogComponents); }
// Log names of all components should have the same length. TEST_F(LogTestUnadornedEncoder, LogComponentNameForLog) { size_t defaultNameForLogLength = componentDefault.getNameForLog().toString().length(); ASSERT_NOT_EQUALS(0U, defaultNameForLogLength); for (int i = 0; i < int(LogComponent::kNumLogComponents); ++i) { LogComponent component = static_cast<LogComponent::Value>(i); ASSERT_EQUALS(defaultNameForLogLength, component.getNameForLog().toString().length()); } }
// Dotted name of component includes names of ancestors. TEST_F(LogTestUnadornedEncoder, LogComponentDottedName) { // Default -> ComponentD -> ComponentE ASSERT_EQUALS(componentDefault.getShortName(), LogComponent(LogComponent::kDefault).getDottedName()); ASSERT_EQUALS(componentD.getShortName(), componentD.getDottedName()); ASSERT_EQUALS(componentD.getShortName() + "." + componentE.getShortName(), componentE.getDottedName()); }
// Non-default log component short name should always be logged. TEST_F(LogTestUnadornedEncoder, MessageEventDetailsEncoderLogComponent) { Date_t d = Date_t::now(); StringData ctx("WHAT", StringData::LiteralTag()); StringData msg("HUH", StringData::LiteralTag()); for (int i = 0; i < int(LogComponent::kNumLogComponents); ++i) { LogComponent component = static_cast<LogComponent::Value>(i); testEncodedLogLine(MessageEventEphemeral(d, LogSeverity::Info(), component, ctx, msg), str::stream() << " I " << component.getNameForLog() << " ["); } }
// Non-default log component short name should always be logged. TEST_F(LogTestUnadornedEncoder, MessageEventDetailsEncoderLogComponent) { Date_t d = Date_t::now(); const auto ctx = "WHAT"_sd; const auto msg = "HUH"_sd; for (int i = 0; i < int(LogComponent::kNumLogComponents); ++i) { LogComponent component = static_cast<LogComponent::Value>(i); testEncodedLogLine(MessageEventEphemeral(d, LogSeverity::Info(), component, ctx, msg), str::stream() << " I " << component.getNameForLog() << " ["); } }
StatusWith<std::vector<LogComponentSetting>> parseLogComponentSettings(const BSONObj& settings) { typedef std::vector<LogComponentSetting> Result; std::vector<LogComponentSetting> levelsToSet; std::vector<BSONObjIterator> iterators; LogComponent parentComponent = LogComponent::kDefault; BSONObjIterator iter(settings); while (iter.moreWithEOO()) { BSONElement elem = iter.next(); if (elem.eoo()) { if (!iterators.empty()) { iter = iterators.back(); iterators.pop_back(); parentComponent = parentComponent.parent(); } continue; } if (elem.fieldNameStringData() == "verbosity") { if (!elem.isNumber()) { return StatusWith<Result>(ErrorCodes::BadValue, str::stream() << "Expected " << parentComponent.getDottedName() << ".verbosity to be a number, but found " << typeName(elem.type())); } levelsToSet.push_back((LogComponentSetting(parentComponent, elem.numberInt()))); continue; } const StringData shortName = elem.fieldNameStringData(); const LogComponent curr = _getComponentForShortName(shortName); if (curr == LogComponent::kNumLogComponents || curr.parent() != parentComponent) { return StatusWith<Result>( ErrorCodes::BadValue, str::stream() << "Invalid component name " << parentComponent.getDottedName() << "." << shortName); } if (elem.isNumber()) { levelsToSet.push_back(LogComponentSetting(curr, elem.numberInt())); continue; } if (elem.type() != Object) { return StatusWith<Result>(ErrorCodes::BadValue, str::stream() << "Invalid type " << typeName(elem.type()) << "for component " << parentComponent.getDottedName() << "." << shortName); } iterators.push_back(iter); parentComponent = curr; iter = BSONObjIterator(elem.Obj()); } // Done walking settings return StatusWith<Result>(levelsToSet); }
bool LogComponentSettings::shouldLog(LogComponent component, LogSeverity severity) const { dassert(int(component) >= 0 && int(component) < LogComponent::kNumLogComponents); // Should match parent component if minimum severity level is not configured for // component. dassert(_hasMinimumLoggedSeverity[component] || _minimumLoggedSeverity[component] == _minimumLoggedSeverity[component.parent()]); return severity >= LogSeverity::cast(_minimumLoggedSeverity[component]); }
void LogComponentSettings::clearMinimumLoggedSeverity(LogComponent component) { dassert(int(component) >= 0 && int(component) < LogComponent::kNumLogComponents); // LogComponent::kDefault must always be configured. if (component == LogComponent::kDefault) { setMinimumLoggedSeverity(component, LogSeverity::Log()); return; } // Set unconfigured severity level to match LogComponent::kDefault. setMinimumLoggedSeverity(component, getMinimumLogSeverity(component.parent())); _hasMinimumLoggedSeverity[component] = false; }
log() << "Logging A() -- " << A() << " -- done!" << std::endl; ASSERT_EQUALS(2U, _logLines.size()); ASSERT_EQUALS(std::string("Golly!\n"), _logLines[0]); ASSERT_EQUALS(std::string("Logging A() -- Golly! -- done!\n"), _logLines[1]); } // // Instantiating this object is a basic test of static-initializer-time logging. // class B { public: B() { log() << "Exercising initializer time logging."; } } b; // Constants for log component test cases. const LogComponent componentDefault = LogComponent::kDefault; const LogComponent componentA = LogComponent::kCommand; const LogComponent componentB = LogComponent::kAccessControl; const LogComponent componentC = LogComponent::kNetwork; const LogComponent componentD = LogComponent::kStorage; const LogComponent componentE = LogComponent::kJournal; // No log component declared at file scope. // Component severity configuration: // LogComponent::kDefault: 2 TEST_F(LogTestUnadornedEncoder, MongoLogMacroNoFileScopeLogComponent) { globalLogDomain()->setMinimumLoggedSeverity(LogSeverity::Debug(2)); LOG(2) << "This is logged"; LOG(3) << "This is not logged"; ASSERT_EQUALS(1U, _logLines.size());