HiC*_*123 2 scala slf4j interceptor mdc akka
Akka和Scala新手在这里,请随时编辑这个问题,以便清楚地表达我在Scala和Akka领域的意图.
在我展示代码片段之前,这是我想要解决的问题:我本质上想要为我的团队开发一个通用模块,以便在他们使用Akka actor开发应用程序时使用.我想让它们混合一个特性,它将在运行时扩展它们的接收功能,主要用于记录目的.我遇到了编译错误,我很快就会解释.
但首先,举一个简单的主要内容:
object Test extends App {
val system = ActorSystem("system")
val myActor = system.actorOf(Props(new MyActor), "myActor")
myActor ! "Hello world!"
}
Run Code Online (Sandbox Code Playgroud)
以下是团队成员可能在其应用程序中实现的actor的示例实现:
class MyActor extends Actor with ActorLogger {
override def receive: Receive = {
case msg => {
log.info("testing ...")
}
case _ => throw new RuntimeException("Runtime Ex")
}
}
Run Code Online (Sandbox Code Playgroud)
这是一个如何为他们提供混合的共同特征的例子:
trait ActorLogger extends Actor {
val log: DiagnosticLoggingAdapter = Logging(this)
abstract override def receive: Receive = {
case msg: Any => {
if (msg.isInstanceOf[String]) {
println("enter")
log.mdc(Map[String, Any]("someKey" -> 123))
super.receive(msg)
log.clearMDC()
println("exit")
}
}
case _ => throw new RuntimeException("Runtime Ex")
}
}
Run Code Online (Sandbox Code Playgroud)
正如你所看到的,我正在尝试将数据添加到MDC,如果消息恰好是String(一个基本的例子,实际上,我会检查我们自己的一些自定义类型).
我得到的错误是:
Error:(29, 16) overriding method receive in trait ActorLogger of type =>
MyActor.this.Receive;
method receive needs `abstract override' modifiers
override def receive: Receive = {
^
Run Code Online (Sandbox Code Playgroud)
这有什么不对?并且堆叠特性是否有权通过消失来实现这样的目标?如果不是,那么最惯用的方式是什么?
更一般地说,除了"拦截器"模式之外还有其他模式吗?
感谢您的帮助!
一个没有黑客akka包的解决方案:
import akka.actor.{Actor, ActorSystem, Props}
trait MyActorExtension extends Actor {
def receiveExtension: Receive = PartialFunction.empty
}
abstract class MyActor extends MyActorExtension {
protected def receiveMsg: Receive
def receive: Receive = receiveExtension orElse receiveMsg
}
trait ActorLogger1 extends MyActor with MyActorExtension {
abstract override def receiveExtension = {
case msg =>
println(s"********** Logging # 1: $msg")
super.receiveExtension.applyOrElse(msg, receiveMsg)
}
}
trait ActorLogger2 extends MyActor with MyActorExtension {
abstract override def receiveExtension = {
case msg =>
println(s"########## Logging # 2: $msg")
super.receiveExtension.applyOrElse(msg, receiveMsg)
}
}
class SpecificActor extends MyActor with ActorLogger1 with ActorLogger2 {
def receiveMsg = {
case someMsg =>
println(s"SpecificActor: $someMsg")
}
}
object Test extends App {
val system = ActorSystem("system")
val mySpecificActor = system.actorOf(Props(new SpecificActor), "SpecificActor")
mySpecificActor ! "Hello world!"
}
Run Code Online (Sandbox Code Playgroud)
####记录#2:Hello world!
******记录#1:你好世界!
SpecificActor:Hello world!
| 归档时间: |
|
| 查看次数: |
2743 次 |
| 最近记录: |