0.6.0 Logger - dynamic control

How does one turn logging off and on under dynamic program control?

The following program:

SerialLogHandler logHandler;

void setup() {
    delay(2000L);
}

Outputs this:

0000002246 [system] INFO: ARM_WLAN_WD 2
0000002246 [hal.wlan] INFO: Bringing WiFi interface up with DHCP
0000002278 [system] INFO: CLR_WLAN_WD 1, DHCP success
0000002280 [system] INFO: Cloud: connecting
0000002284 [system] INFO: Resolved host device.spark.io to 52.23.193.249
0000002560 [system] INFO: connected to cloud 52.23.193.249:5683
0000002560 [system] INFO: Cloud socket connected
0000003618 [comm] INFO: Hanshake: completed
0000003620 [system] INFO: Cloud connected

which is fine if one wants this output, but if you don’t, how do you stop it?

You may find some info about the capabilities of the LogHandlers here

@ScruffR, this stops the trace output (just like the documentation says it would):

SerialLogHandler logHandler(LOG_LEVEL_NONE, {   // Logging level for non-application messages
        { "app", LOG_LEVEL_NONE },                  // Default logging level for all application messages
        { "app.network", LOG_LEVEL_TRACE },          // Logging level for networking messages
        { "app.setup", LOG_LEVEL_WARN }            // Logging level for setup messages
    });

The question remains however as to how to dynamically change the logging output from a running program, eg by a cloud function. The spark_wiring_logging.h does not give an clues here.

I must admit I haven’t done that myself yet, but I’d have thought of class LogManager to be doing that.
But I’ve not checked if that is exposed to user code.

  LogManager::instance()->addHandler(yourHandler);
  LogManager::instance()->removeHandler(yourHandler);

Did you have luck with it?

@Rikardov,

Yes, it was solved, but not quite in the that way I originally asked for (ie change the log level dynamically at will during the running of the program) because I changed my mind. I now just set it once via a config within Setup() and not change it again.

Am sure that @ScruffR’s suggestion above will work, but I did not need to make it “dynamic” in the end.

// ==== Dynamically set up logger =====

// Get log manager's instance
auto logManager = LogManager::instance();

// Configure and register log handler dynamically
LogCategoryFilters filters;

LogLevel logLevel;

  // Typically set from a config - just showing what options you have here to simplify
  // logLevel = LOG_LEVEL_NONE;
  // logLevel = LOG_LEVEL_ERROR;
  // logLevel = LOG_LEVEL_WARN;
  // logLevel = LOG_LEVEL_INFO;
  // logLevel = LOG_LEVEL_TRACE;
  logLevel = LOG_LEVEL_ALL;

filters.append({ "app", logLevel });   

// Select debug output destination
// -------------------------------
Print *pStream;

if (bUseUSBSerial1)
    pStream = &USBSerial1;
else
    pStream = &Serial;

auto logHandler1 = new StreamLogHandler(*pStream, LOG_LEVEL_WARN /* Default level */, filters);

logManager->addHandler(logHandler1);
2 Likes