Skip to content

Commit

Permalink
Extension methods to Logger as workaround for overload and varargs pr…
Browse files Browse the repository at this point in the history
…oblem, #26537 (#27605)

* "ambiguous reference to overloaded definition" for 2 arg method
* varargs not supported for primitive types
* providing extension methods info2 and infoN (and friends) via implicit class LoggerOps
  as more convenient workaround for these problems
  • Loading branch information
patriknw committed Sep 4, 2019
1 parent 2b8a5d8 commit 102e79b
Show file tree
Hide file tree
Showing 24 changed files with 591 additions and 96 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -188,18 +188,18 @@ class ActorLoggingSpec extends ScalaTestWithActorTestKit("""
LoggingEventFilter
.custom({
case _ => true // any is fine, we're just after the right count of statements reaching the listener
}, occurrences = 34)
}, occurrences = 36)
.intercept({
spawn(Behaviors.setup[String] {
context =>
context.log.debug("message")
context.log.debug("{}", "arg1")
context.log
.debug("{} {}", "arg1", "arg2": Any) //using Int to avoid ambiguous reference to overloaded definition
// using `: Any` to avoid "ambiguous reference to overloaded definition", see also LoggerOpsSpec
context.log.debug("{} {}", "arg1", "arg2": Any)
context.log.debug("{} {} {}", "arg1", "arg2", "arg3")
context.log.debug(marker, "message")
context.log.debug(marker, "{}", "arg1")
context.log.debug(marker, "{} {}", "arg1", "arg2": Any) //using Int to avoid ambiguous reference to overloaded definition
context.log.debug(marker, "{} {}", "arg1", "arg2": Any)
context.log.debug(marker, "{} {} {}", "arg1", "arg2", "arg3")

context.log.info("message")
Expand All @@ -225,10 +225,13 @@ class ActorLoggingSpec extends ScalaTestWithActorTestKit("""
context.log.error("{}", "arg1")
context.log.error("{} {}", "arg1", "arg2": Any)
context.log.error("{} {} {}", "arg1", "arg2", "arg3")
// using to avoid vararg problem for primitive type, see also LoggerOpsSpec
context.log.error("{} {} {}", "arg1", "arg2", 3.asInstanceOf[AnyRef])
context.log.error(marker, "message")
context.log.error(marker, "{}", "arg1")
context.log.error(marker, "{} {}", "arg1", "arg2": Any)
context.log.error(marker, "{} {} {}", "arg1", "arg2", "arg3")
context.log.error(marker, "{} {} {}", "arg1", "arg2", 3.asInstanceOf[AnyRef])
context.log.error("message", cause)

Behaviors.stopped
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
/*
* Copyright (C) 2009-2019 Lightbend Inc. <https://www.lightbend.com>
*/

package akka.actor.typed.scaladsl

import akka.actor.testkit.typed.scaladsl.LoggingEventFilter
import akka.actor.testkit.typed.scaladsl.ScalaTestWithActorTestKit
import org.scalatest.WordSpecLike
import org.slf4j.LoggerFactory

object LoggerOpsSpec {
case class Value1(i: Int)
case class Value2(i: Int)
case class Value3(i: Int)
}

class LoggerOpsSpec extends ScalaTestWithActorTestKit with WordSpecLike {
import LoggerOpsSpec._

val log = LoggerFactory.getLogger(getClass)

"LoggerOps" must {

"provide extension method for 2 arguments" in {
LoggingEventFilter.info(message = "[template a b]", occurrences = 1).intercept {
log.info2("[template {} {}]", "a", "b")
}
LoggingEventFilter.info(message = "[template a 2]", occurrences = 1).intercept {
log.info2("[template {} {}]", "a", 2)
}
LoggingEventFilter.info(message = "[template 1 2]", occurrences = 1).intercept {
log.info2("[template {} {}]", 1, 2)
}
LoggingEventFilter.info(message = "[template 1 b]", occurrences = 1).intercept {
log.info2("[template {} {}]", 1, "b")
}
LoggingEventFilter.info(message = "[template a Value2(2)]", occurrences = 1).intercept {
log.info2("[template {} {}]", "a", Value2(2))
}
LoggingEventFilter.info(message = "[template Value1(1) Value1(1)]", occurrences = 1).intercept {
log.info2("[template {} {}]", Value1(1), Value1(1))
}
LoggingEventFilter.info(message = "[template Value1(1) Value2(2)]", occurrences = 1).intercept {
log.info2("[template {} {}]", Value1(1), Value2(2))
}
}

"provide extension method for vararg arguments" in {
LoggingEventFilter.info(message = "[template a b c]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", "a", "b", "c")
}
LoggingEventFilter.info(message = "[template a b 3]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", "a", "b", 3)
}
LoggingEventFilter.info(message = "[template a 2 c]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", "a", 2, "c")
}
LoggingEventFilter.info(message = "[template 1 2 3]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", 1, 2, 3)
}
LoggingEventFilter.info(message = "[template 1 b c]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", 1, "b", "c")
}
LoggingEventFilter.info(message = "[template a Value2(2) Value3(3)]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", "a", Value2(2), Value3(3))
}
LoggingEventFilter.info(message = "[template Value1(1) Value1(1) Value1(1)]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", Value1(1), Value1(1), Value1(1))
}
LoggingEventFilter.info(message = "[template Value1(1) Value2(2) Value3(3)]", occurrences = 1).intercept {
log.infoN("[template {} {} {}]", Value1(1), Value2(2), Value3(3))
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,19 @@ package docs.akka.typed

import java.net.URI

import akka.NotUsed
import akka.actor.typed.{ ActorRef, ActorSystem, Behavior }
import akka.actor.typed.scaladsl.{ Behaviors, TimerScheduler }

import scala.concurrent.Future
import scala.concurrent.duration._
import scala.util.{ Failure, Success }
import scala.util.Failure
import scala.util.Success

import akka.NotUsed
import akka.actor.testkit.typed.scaladsl.ScalaTestWithActorTestKit
import akka.actor.typed.ActorRef
import akka.actor.typed.ActorSystem
import akka.actor.typed.Behavior
import akka.actor.typed.scaladsl.Behaviors
import akka.actor.typed.scaladsl.LoggerOps
import akka.actor.typed.scaladsl.TimerScheduler
import org.scalatest.WordSpecLike

class InteractionPatternsSpec extends ScalaTestWithActorTestKit with WordSpecLike {
Expand Down Expand Up @@ -120,10 +125,10 @@ class InteractionPatternsSpec extends ScalaTestWithActorTestKit with WordSpecLik
context.log.info("Started {}", taskId)
Behaviors.same
case Backend.JobProgress(taskId, progress) =>
context.log.info("Progress {}: {}", taskId, progress)
context.log.info2("Progress {}: {}", taskId, progress)
Behaviors.same
case Backend.JobCompleted(taskId, result) =>
context.log.info("Completed {}: {}", taskId, result)
context.log.info2("Completed {}: {}", taskId, result)
inProgress(taskId) ! result
active(inProgress - taskId, count)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ package docs.akka.typed
//#fiddle_code
//#imports
import akka.actor.typed.scaladsl.Behaviors
import akka.actor.typed.scaladsl.LoggerOps
import akka.actor.typed.{ ActorRef, ActorSystem, Behavior }
//#imports
//#fiddle_code
Expand Down Expand Up @@ -54,7 +55,7 @@ object IntroSpec {
Behaviors.receive { (context, message) =>
val n = greetingCounter + 1
//#fiddle_code
context.log.info("Greeting {} for {}", n, message.whom)
context.log.info2("Greeting {} for {}", n, message.whom)
//#fiddle_code
//#hello-world-bot
println(s"Greeting $n for ${message.whom}")
Expand Down Expand Up @@ -190,7 +191,7 @@ object IntroSpec {
handle ! PostMessage("Hello World!")
Behaviors.same
case MessagePosted(screenName, message) =>
context.log.info("message has been posted by '{}': {}", screenName, message: Any)
context.log.info2("message has been posted by '{}': {}", screenName, message)
Behaviors.stopped
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ package docs.akka.typed
//#imports
import akka.Done
import akka.actor.typed.{ ActorRef, ActorSystem, Behavior }
import akka.actor.typed.scaladsl.{ AbstractBehavior, ActorContext, Behaviors }
import akka.actor.typed.scaladsl.{ AbstractBehavior, ActorContext, Behaviors, LoggerOps }
//#imports

import akka.NotUsed
Expand Down Expand Up @@ -104,7 +104,7 @@ object OOIntroSpec {
handle ! PostMessage("Hello World!")
Behaviors.same
case MessagePosted(screenName, message) =>
context.log.info("message has been posted by '{}': {}", screenName, message: Any)
context.log.info2("message has been posted by '{}': {}", screenName, message)
Behaviors.stopped
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import com.github.ghik.silencer.silent
import akka.actor.typed.Behavior
import akka.actor.typed.SpawnProtocol
import akka.actor.typed.scaladsl.Behaviors
import akka.actor.typed.scaladsl.LoggerOps

//#imports1

Expand Down Expand Up @@ -67,7 +68,7 @@ class SpawnProtocolDocSpec extends ScalaTestWithActorTestKit with WordSpecLike {
system.ask(SpawnProtocol.Spawn(behavior = HelloWorld(), name = "greeter", props = Props.empty, _))

val greetedBehavior = Behaviors.receive[HelloWorld.Greeted] { (context, message) =>
context.log.info("Greeting for {} from {}", message.whom, message.from: Any)
context.log.info2("Greeting for {} from {}", message.whom, message.from)
Behaviors.stopped
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import scala.concurrent.Future

import akka.actor.typed.ActorSystem
import akka.actor.typed.ActorRef
import akka.actor.typed.scaladsl.LoggerOps
import akka.actor.typed.scaladsl.TimerScheduler
import scala.concurrent.duration.FiniteDuration

Expand Down Expand Up @@ -126,7 +127,7 @@ object StyleGuideDocExamples {
Behaviors.same
case Increment =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter to [{}]", name, newValue)
counter(name, timers, newValue)
case GetValue(replyTo) =>
replyTo ! Value(n)
Expand Down Expand Up @@ -160,16 +161,16 @@ object StyleGuideDocExamples {
private def counter(setup: Setup, n: Int): Behavior[Command] =
Behaviors.receiveMessage {
case IncrementRepeatedly(interval) =>
setup.context.log.debug(
setup.context.log.debugN(
"[{}] Starting repeated increments with interval [{}], current count is [{}]",
setup.name,
interval.toString,
n.toString)
interval,
n)
setup.timers.startTimerWithFixedDelay("repeat", Increment, interval)
Behaviors.same
case Increment =>
val newValue = n + 1
setup.context.log.debug("[{}] Incremented counter to [{}]", setup.name, newValue)
setup.context.log.debug2("[{}] Incremented counter to [{}]", setup.name, newValue)
counter(setup, newValue)
case GetValue(replyTo) =>
replyTo ! Value(n)
Expand Down Expand Up @@ -207,16 +208,16 @@ object StyleGuideDocExamples {
private def counter(n: Int): Behavior[Command] =
Behaviors.receiveMessage {
case IncrementRepeatedly(interval) =>
context.log.debug(
context.log.debugN(
"[{}] Starting repeated increments with interval [{}], current count is [{}]",
name,
interval.toString,
n.toString)
interval,
n)
timers.startTimerWithFixedDelay("repeat", Increment, interval)
Behaviors.same
case Increment =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter to [{}]", name, newValue)
counter(newValue)
case GetValue(replyTo) =>
replyTo ! Value(n)
Expand All @@ -243,16 +244,16 @@ object StyleGuideDocExamples {
def counter(n: Int): Behavior[Command] =
Behaviors.receiveMessage {
case IncrementRepeatedly(interval) =>
context.log.debug(
context.log.debugN(
"[{}] Starting repeated increments with interval [{}], current count is [{}]",
name,
interval.toString,
n.toString)
interval,
n)
timers.startTimerWithFixedDelay("repeat", Increment, interval)
Behaviors.same
case Increment =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter to [{}]", name, newValue)
counter(newValue)
case GetValue(replyTo) =>
replyTo ! Value(n)
Expand Down Expand Up @@ -353,11 +354,11 @@ object StyleGuideDocExamples {
Behaviors.receiveMessage {
case Increment =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter to [{}]", name, newValue)
counter(newValue)
case Tick =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter by background tick to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter by background tick to [{}]", name, newValue)
counter(newValue)
case GetValue(replyTo) =>
replyTo ! Value(n)
Expand Down Expand Up @@ -404,11 +405,11 @@ object StyleGuideDocExamples {
Behaviors.receiveMessage {
case Increment =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter to [{}]", name, newValue)
counter(newValue)
case Tick =>
val newValue = n + 1
context.log.debug("[{}] Incremented counter by background tick to [{}]", name, newValue)
context.log.debug2("[{}] Incremented counter by background tick to [{}]", name, newValue)
counter(newValue)
case GetValue(replyTo) =>
replyTo ! Value(n)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import scala.concurrent.duration.FiniteDuration
import akka.actor.Cancellable
import akka.actor.NotInfluenceReceiveTimeout
import akka.actor.typed.scaladsl.ActorContext
import akka.actor.typed.scaladsl.LoggerOps
import akka.annotation.InternalApi
import akka.dispatch.ExecutionContexts
import akka.util.JavaDurationConverters._
Expand Down Expand Up @@ -159,9 +160,11 @@ import org.slf4j.Logger
} else {
// it was from an old timer that was enqueued in mailbox before canceled
if (log.isDebugEnabled)
log.debug(
log.debugN(
"Received timer [{}] from old generation [{}], expected generation [{}], discarding",
Array(timerMsg.key, timerMsg.generation, t.generation))
timerMsg.key,
timerMsg.generation,
t.generation)
OptionVal.none // message should be ignored
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,14 @@

package akka.actor.typed.internal.receptionist

import akka.actor.typed.{ ActorRef, Behavior, Terminated }
import akka.actor.typed.ActorRef
import akka.actor.typed.Behavior
import akka.actor.typed.Terminated
import akka.actor.typed.receptionist.Receptionist._
import akka.actor.typed.receptionist.ServiceKey
import akka.actor.typed.scaladsl.{ ActorContext, Behaviors }
import akka.actor.typed.scaladsl.Behaviors.{ receive, same }
import akka.actor.typed.scaladsl.ActorContext
import akka.actor.typed.scaladsl.Behaviors
import akka.actor.typed.scaladsl.LoggerOps
import akka.annotation.InternalApi
import akka.util.TypedMultiMap

Expand Down Expand Up @@ -98,7 +101,7 @@ private[akka] object LocalReceptionist extends ReceptionistBehaviorProvider {

def onCommand(ctx: ActorContext[Any], cmd: Command): Behavior[Any] = cmd match {
case ReceptionistMessages.Register(key, serviceInstance, maybeReplyTo) =>
ctx.log.debug("Actor was registered: {} {}", key, serviceInstance: Any)
ctx.log.debug2("Actor was registered: {} {}", key, serviceInstance)
watchWith(ctx, serviceInstance, RegisteredActorTerminated(key, serviceInstance))
maybeReplyTo match {
case Some(replyTo) => replyTo ! ReceptionistMessages.Registered(key, serviceInstance)
Expand All @@ -108,7 +111,7 @@ private[akka] object LocalReceptionist extends ReceptionistBehaviorProvider {

case ReceptionistMessages.Find(key, replyTo) =>
replyWithListing(key, replyTo)
same
Behaviors.same

case ReceptionistMessages.Subscribe(key, subscriber) =>
watchWith(ctx, subscriber, SubscriberTerminated(key, subscriber))
Expand All @@ -121,14 +124,14 @@ private[akka] object LocalReceptionist extends ReceptionistBehaviorProvider {

def onInternal(ctx: ActorContext[Any], cmd: InternalCommand): Behavior[Any] = cmd match {
case RegisteredActorTerminated(key, serviceInstance) =>
ctx.log.debug("Registered actor terminated: {} {}", key, serviceInstance: Any)
ctx.log.debug2("Registered actor terminated: {} {}", key, serviceInstance)
updateRegistry(Set(key), _.removed(key)(serviceInstance))

case SubscriberTerminated(key, subscriber) =>
next(newSubscriptions = subscriptions.removed(key)(subscriber))
}

receive[Any] { (ctx, msg) =>
Behaviors.receive[Any] { (ctx, msg) =>
msg match {
case cmd: Command => onCommand(ctx, cmd)
case cmd: InternalCommand => onInternal(ctx, cmd)
Expand Down
Loading

0 comments on commit 102e79b

Please sign in to comment.