How to avoid the "lack of type" error when combining partial functions

I am currently studying Scala and Akka and developing a test application for it. In this application, almost all participants log raw messages to facilitate debugging:

import akka.actor._ class TestActor extends Actor with ActorLogging { def receive: Receive = { case Some(value) => // do something... case msg => log.debug("Unhandled message: {}.", msg) } } 

As I said, such code exists in almost all of my agents, and I began to think about moving it to hell:

 trait LogUnhandled { this: Actor with ActorLogging => def logUnhandled: Receive = { case msg => log.debug("Unhandled message: {}.", msg) } } 

and using it after

 class TestActor extends Actor with ActorLogging with LogUnhandled { def receive: Receive = { case Some(value) => // do something... } orElse logUnhandled } 

I was wondering if structural subtyping allows me to do this, or TestActor#Receive and LogUnhadled#Receive will be different types, but even before that I have

 error: missing parameter type for expanded function The argument types of an anonymous function must be fully known. (SLS 8.5) Expected type was: ? 

And while I could not figure out how to avoid this, except to transfer the first block {...} to a separate function:

 class TestActor extends Actor with ActorLogging with LogUnhandled { def doReceive: Receive = { case Some(value) => // do something... } def receive: Receive = doReceive orElse logUnhandled } 

The latter will do, of course, but it is "missing a point" and causes some other side effects, such as "thinking about the corresponding function name instead of receive " ...

So, I am wondering: is it possible to avoid the โ€œabsence of a type parameter errorโ€ by somehow declaring (Any) => Unit signature of the function โ€œin placeโ€?

+4
source share
1 answer
 class TestActor extends Actor with ActorLogging with LogUnhandled { def receive = ({ case Some(value) => // do something... }: Receive) orElse logUnhandled } 

Also consider this . LoggingReceive allows you to perform the following actions:

 class A extends Actor { def receive = LoggingReceive { case msg => ... } } 

And all received / rejected messages will be posted to the debug stream.

+4
source

All Articles