2014-01-26 4 views
0

У меня есть набор Акка Актеров, и я даю около нескольких сотен сообщений каждому из них. Я хочу отслеживать, сколько раз каждый экземпляр этого Актера принимал для обработки всех полученных им сообщений. То, что я делаю в настоящее время иметь государство в экземпляре Актер как:Akka Актеры регистрации времени обработки

var startTime 
var firstCall 

я поставил обе переменные, когда экземпляр актера сначала вызывается. Есть ли другой способ, который я мог бы использовать для отслеживания времени обработки для моих экземпляров Actor? Я хочу избежать локального состояния в моем экземпляре Актера.

ответ

4

Это хороший вариант использования для context.become.

Помните, что блок приема в аккорде Akka - это всего лишь PartialFunction[Any, Unit], поэтому мы можем обернуть это в другую частичную функцию. Это тот же подход, который сделал встроенный Akka LoggingReceive.

class TimingReceive(r: Receive, totalTime: Long)(implicit ctx: ActorContext) extends Receive { 
    def isDefinedAt(o: Any): Boolean = { 
    r.isDefinedAt(o) 
    } 
    def apply(o: Any): Unit = { 
    val startTime = System.nanoTime 
    r(o) 
    val newTotal = totalTime + (System.nanoTime - startTime) 
    log.debug("Total time so far: " + totalTime + " nanoseconds") 
    ctx.become(new TimingReceive(r, newTotal)) 
    } 
} 

object TimingReceive { 
    def apply(r: Receive)(implicit ctx: ActorContext): Receive = new TimingReceive(r, 0) 
} 

Затем вы можете использовать его как это:

class FooActor extends Actor { 
    def receive = TimingReceive { 
    case x: String => println("got " + x) 
    } 
} 

После каждого сообщения, актер будет регистрировать время, затрачиваемое до сих пор. Конечно, если вы хотите сделать что-то еще с этой переменной, вам придется адаптировать это.

Этот подход не измеряет время, в течение которого актер жив, и только время, затрачиваемое на обработку сообщений. Не будет и точной, если ваша функция получения создаст будущее.

Смежные вопросы