Reputation: 1435
I have written a custom logger for akka to pass on log messages to a remote system. I have a second logger in place using slf4j with logback 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
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