From 521807f4f4b51ff3fced7dd4ee3bd3a1fd2a8f87 Mon Sep 17 00:00:00 2001 From: PJ Fanning Date: Sun, 18 May 2025 12:14:47 +0100 Subject: [PATCH 1/6] add typed actor --- build.sbt | 3 +- .../instrumentation/pekko/TypedActor.scala | 30 +++++++++++++++++++ 2 files changed, 32 insertions(+), 1 deletion(-) create mode 100644 instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActor.scala diff --git a/build.sbt b/build.sbt index b8ca0b110..e17116179 100644 --- a/build.sbt +++ b/build.sbt @@ -525,7 +525,8 @@ lazy val `kamon-pekko` = (project in file("instrumentation/kamon-pekko")) .settings(Seq( crossScalaVersions := Seq(`scala_2.12_version`, `scala_2.13_version`, scala_3_version), libraryDependencies ++= Seq( - "org.apache.pekko" %% "pekko-actor" % "1.0.1" % "provided" + "org.apache.pekko" %% "pekko-actor" % "1.0.1" % "provided", + "org.apache.pekko" %% "pekko-actor-typed" % "1.0.1" % "test" ) )) .dependsOn( diff --git a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActor.scala b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActor.scala new file mode 100644 index 000000000..5ae40dc76 --- /dev/null +++ b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActor.scala @@ -0,0 +1,30 @@ +/* ========================================================================================= + * Copyright © 2013-2017 the kamon project + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, + * either express or implied. See the License for the specific language governing permissions + * and limitations under the License. + * ========================================================================================= + */ + +package kamon.instrumentation.pekko + +import org.apache.pekko.actor.typed.{ActorRef, Behavior} +import org.apache.pekko.actor.typed.scaladsl.Behaviors + +object TypedActor { + final case class Greet(whom: String, replyTo: ActorRef[Greeted]) + final case class Greeted(whom: String, from: ActorRef[Greet]) + + def apply(): Behavior[Greet] = Behaviors.receive { (context, message) => + context.log.info("Hello {}!", message.whom) + message.replyTo ! Greeted(message.whom, context.self) + Behaviors.same + } +} From f1dac331361254d37dc8a8f52d0250a6add45110 Mon Sep 17 00:00:00 2001 From: PJ Fanning Date: Sun, 18 May 2025 12:44:51 +0100 Subject: [PATCH 2/6] add test --- .../src/test/resources/application.conf | 2 +- .../pekko/TypedActorMetricsSpec.scala | 68 +++++++++++++++++++ 2 files changed, 69 insertions(+), 1 deletion(-) create mode 100644 instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala diff --git a/instrumentation/kamon-pekko/src/test/resources/application.conf b/instrumentation/kamon-pekko/src/test/resources/application.conf index ca685c1f3..f278cde78 100644 --- a/instrumentation/kamon-pekko/src/test/resources/application.conf +++ b/instrumentation/kamon-pekko/src/test/resources/application.conf @@ -44,7 +44,7 @@ kamon { actors { track { - includes = [ "*/user/tracked-*", "*/user/measuring-*", "*/user/clean-after-collect", "*/user/stop", "*/user/repointable*", "*/" ] + includes = [ "*/user/tracked-*", "*/user/measuring-*", "*/user/clean-after-collect", "*/user/stop", "*/user/repointable*", "*/", "greet-service/*" ] excludes = [ "*/system/**", "*/user/tracked-explicitly-excluded", "*/user/non-tracked-actor" ] } diff --git a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala new file mode 100644 index 000000000..4f5a118a2 --- /dev/null +++ b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala @@ -0,0 +1,68 @@ +/* ========================================================================================= + * Copyright © 2013 the kamon project + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, + * either express or implied. See the License for the specific language governing permissions + * and limitations under the License. + * ========================================================================================= + */ + +package kamon.instrumentation.pekko + +import org.apache.pekko.actor.typed.ActorSystem +import org.apache.pekko.actor.typed.scaladsl.AskPattern.Askable +import org.apache.pekko.util.Timeout +import kamon.instrumentation.pekko.ActorMetricsTestActor._ +import kamon.instrumentation.pekko.PekkoMetrics._ +import kamon.instrumentation.pekko.TypedActor._ +import kamon.tag.TagSet +import kamon.testkit.{InitAndStopKamonAfterAll, InstrumentInspection, MetricInspection} +import org.scalactic.TimesOnInt._ +import org.scalatest.BeforeAndAfterAll +import org.scalatest.matchers.should.Matchers +import org.scalatest.wordspec.AnyWordSpec + +import scala.concurrent.Await +import scala.concurrent.duration._ + +class TypedActorMetricsSpec extends AnyWordSpec + with MetricInspection.Syntax with InstrumentInspection.Syntax with Matchers + with InitAndStopKamonAfterAll { + + private val system: ActorSystem[Greet] = ActorSystem(TypedActor(), "greet-service") + + "the Kamon typed actor metrics" should { + "respect the configured include and exclude filters" in new ActorMetricsFixtures { + sendMessage("world") + ActorProcessingTime.tagValues("path") should contain("greet-service/user") + } + } + + override protected def afterAll(): Unit = { + system.terminate() + super.afterAll() + } + + def actorTags(path: String): TagSet = + TagSet.from( + Map( + "path" -> path, + "system" -> "ActorMetricsSpec", + "dispatcher" -> "pekko.actor.default-dispatcher" + ) + ) + + trait ActorMetricsFixtures { + + def sendMessage(name: String): Unit = { + val fut = system.ask[Greeted](Greet(name, _))(Timeout(10.seconds), system.scheduler) + Await.result(fut, 10.seconds) + } + } +} From cd97a9f258d0a1e8fcb6551c9cb49fffe4c0c65b Mon Sep 17 00:00:00 2001 From: PJ Fanning Date: Sun, 18 May 2025 12:55:23 +0100 Subject: [PATCH 3/6] Update TypedActorMetricsSpec.scala --- .../instrumentation/pekko/TypedActorMetricsSpec.scala | 9 --------- 1 file changed, 9 deletions(-) diff --git a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala index 4f5a118a2..3ee4b9425 100644 --- a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala +++ b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala @@ -49,15 +49,6 @@ class TypedActorMetricsSpec extends AnyWordSpec super.afterAll() } - def actorTags(path: String): TagSet = - TagSet.from( - Map( - "path" -> path, - "system" -> "ActorMetricsSpec", - "dispatcher" -> "pekko.actor.default-dispatcher" - ) - ) - trait ActorMetricsFixtures { def sendMessage(name: String): Unit = { From 2b9cabd0ca5d0681677b2536ea1d1875bcb528aa Mon Sep 17 00:00:00 2001 From: PJ Fanning Date: Sun, 18 May 2025 17:23:34 +0100 Subject: [PATCH 4/6] wip --- .../pekko/instrumentations/ActorCellInfo.scala | 6 +++++- .../kamon/instrumentation/pekko/TypedActorMetricsSpec.scala | 5 ++++- 2 files changed, 9 insertions(+), 2 deletions(-) diff --git a/instrumentation/kamon-pekko/src/main/scala/kamon/instrumentation/pekko/instrumentations/ActorCellInfo.scala b/instrumentation/kamon-pekko/src/main/scala/kamon/instrumentation/pekko/instrumentations/ActorCellInfo.scala index cee8cef56..194c13412 100644 --- a/instrumentation/kamon-pekko/src/main/scala/kamon/instrumentation/pekko/instrumentations/ActorCellInfo.scala +++ b/instrumentation/kamon-pekko/src/main/scala/kamon/instrumentation/pekko/instrumentations/ActorCellInfo.scala @@ -35,7 +35,6 @@ object ActorCellInfo { val actorName = ref.path.name val pathString = ref.path.elements.mkString("/") - val isRootSupervisor = pathString.length == 0 || pathString == "user" || pathString == "system" val isRouter = hasRouterProps(props) val isRoutee = PekkoPrivateAccess.isRoutedActorRef(parent) val isTemporary = PekkoPrivateAccess.isUnstartedActorCell(cell) @@ -48,6 +47,11 @@ object ActorCellInfo { else (props.actorClass(), None) + val isRootSupervisor = if (!isRouter && !isRoutee && isTyped(actorOrRouterClass)) + pathString != "user" + else + pathString.isEmpty || pathString == "user" || pathString == "system" + val fullPath = if (isRoutee) cellName(system, parent) else cellName(system, ref) val dispatcherName = if (isRouter) { if (props.routerConfig.isInstanceOf[BalancingPool]) { diff --git a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala index 3ee4b9425..8404f15a7 100644 --- a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala +++ b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala @@ -40,7 +40,10 @@ class TypedActorMetricsSpec extends AnyWordSpec "the Kamon typed actor metrics" should { "respect the configured include and exclude filters" in new ActorMetricsFixtures { sendMessage("world") - ActorProcessingTime.tagValues("path") should contain("greet-service/user") + val pathValues = ActorProcessingTime.tagValues("path") + pathValues should not contain("greet-service/") + pathValues should contain("greet-service/user") + } } From 37e23810bb398cbcf17f453b8129b700df37e95c Mon Sep 17 00:00:00 2001 From: PJ Fanning Date: Sun, 18 May 2025 17:37:10 +0100 Subject: [PATCH 5/6] Update TypedActorMetricsSpec.scala --- .../kamon/instrumentation/pekko/TypedActorMetricsSpec.scala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala index 8404f15a7..53de2a0c5 100644 --- a/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala +++ b/instrumentation/kamon-pekko/src/test/scala/kamon/instrumentation/pekko/TypedActorMetricsSpec.scala @@ -41,7 +41,7 @@ class TypedActorMetricsSpec extends AnyWordSpec "respect the configured include and exclude filters" in new ActorMetricsFixtures { sendMessage("world") val pathValues = ActorProcessingTime.tagValues("path") - pathValues should not contain("greet-service/") + pathValues should not contain ("greet-service/") pathValues should contain("greet-service/user") } From 8723962a2545b366e395097914482a64fcad555a Mon Sep 17 00:00:00 2001 From: PJ Fanning Date: Sun, 18 May 2025 20:30:52 +0100 Subject: [PATCH 6/6] Update build.sbt --- instrumentation/kamon-pekko/build.sbt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/instrumentation/kamon-pekko/build.sbt b/instrumentation/kamon-pekko/build.sbt index 4a0c78a63..8c7c99a80 100644 --- a/instrumentation/kamon-pekko/build.sbt +++ b/instrumentation/kamon-pekko/build.sbt @@ -12,11 +12,13 @@ libraryDependencies ++= { scalatest % Test, logbackClassic % Test, "org.apache.pekko" %% "pekko-actor" % pekkoVersion % "provided,test", + "org.apache.pekko" %% "pekko-actor-typed" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-testkit" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-slf4j" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-remote" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-cluster" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-cluster-sharding" % pekkoVersion % "provided,test", + "org.apache.pekko" %% "pekko-cluster-typed" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-protobuf" % pekkoVersion % "provided,test", "org.apache.pekko" %% "pekko-testkit" % pekkoVersion % Test )