mgttlinger
mgttlinger

Reputation: 1435

Akka custom logger does not receive some messages

I have written a custom logger for to pass on log messages to a remote system. I have a second logger in place using with as backend to print to the console and a logfile.

The strange thing I noticed is that some messages are not being received by my custom logger but the slf4j one receives them just fine.

For example the error messages generated by a failing child actor that get logged as part of the supervision strategy:

[DEBUG][akka://Test/system/remote-deployment-watcher]: started (akka.remote.RemoteDeploymentWatcher@b342d63)
[DEBUG][akka://Test/system]: now supervising Actor[akka://Test/system/deadLetterListener#-286980524]
started (akka.remote.RemoteDeploymentWatcher@b342d63)
now supervising Actor[akka://Test/system/deadLetterListener#-286980524]
[DEBUG][akka://Test/system/deadLetterListener]: started (akka.event.DeadLetterListener@4a3c6344)
started (akka.event.DeadLetterListener@4a3c6344)
started (akka.remote.RemoteWatcher@14fbdfea)
[DEBUG][akka://Test/system/remote-watcher]: started (akka.remote.RemoteWatcher@14fbdfea)
now supervising TestActor[akka://Test/user/$$a]
[DEBUG][akka://Test/user]: now supervising TestActor[akka://Test/user/$$a]
started (package.Discoverer@24537c20)
now supervising Actor[akka://Test/user/$$a/refresher#-138594901]
[DEBUG][akka://Test/user/$$a]: started (package.Discoverer@24537c20)
[DEBUG][akka://Test/user/$$a]: now supervising Actor[akka://Test/user/$$a/refresher#-138594901]
akka.tcp://[email protected]:2552/user/$$a: im an error
[ERROR][akka.tcp://[email protected]:2552/user/$$a]: im an error
stopped
[ERROR][akka://Test/user/$$a/refresher]: exception during creation
akka.actor.ActorInitializationException: exception during creation
    at akka.actor.ActorInitializationException$.apply(Actor.scala:164) ~[akka-actor_2.10-2.3.5.jar:na]
    ...

For debugging purposes my custom logger prints the received messages to the console. The messages with the prefixed log level are generated by slf4j and the ones in between that contain just the message are generated by my custom logger.

As you can see my custom logger receives the debug messages just fine and even the error message "im an error" that I manually generated is received fine but not the automatic message generated by the exception.

Do I have to subscribe the logger to additional events to receive those? Or what is the issue here?

My logger:

class MonitoringLogger extends Actor {

  val mon = context.actorOf(Props[MonitorEndpoint], "MonitorEndpoint")

  def receive = {
    case InitializeLogger(bus) => sender ! LoggerInitialized
    case Error(cause, logSource, logClass, message: String) =>
      println(message)
      mon ! format(logSource, message, Console.RED)
    case Warning(logSource, logClass, message: String) => mon ! format(logSource, message, Console.YELLOW)
    case Info(logSource, logClass, message: String) => mon ! format(logSource, message, Console.GREEN)
    case Debug(logSource, logClass, message: String) =>
      println(message)
      mon ! format(logSource, message, Console.GREEN)
  }

  def format(src: String, msg: String, code: String) = s"${Console.BLUE}R> $code[${src.split('/').last}] ${Console.RESET}$msg"
}

Interresting part of application.conf:

akka {
  loggers = ["akka.event.slf4j.Slf4jLogger", "package.MonitoringLogger"]
  loglevel = "DEBUG"
  log-dead-letters-during-shutdown = off
  log-dead-letters = 10
  actor.debug {
    lifecycle = on
  }
}

Upvotes: 3

Views: 602

Answers (1)

mgttlinger
mgttlinger

Reputation: 1435

cmbaxter has lead me to my mistake. The case class Error that I match against is defined as:

case class Error(
  cause: Throwable, 
  logSource: String, 
  logClass: Class[_], 
  message: Any = "") extends LogEvent

Note that the message has type Any but I match against String. My own log messages get matched against because I use a string message. The auto generated event of that exception has message set to null so it doesn't satisfy the match.

Upvotes: 2

Related Questions