From a74379942b2c672c9ba507093f27ead5693c1240 Mon Sep 17 00:00:00 2001 From: Diego Date: Tue, 13 Dec 2016 13:06:29 -0300 Subject: wip --- build.sbt | 11 +- .../util/executors/ExecutorMetricRecorder.scala | 26 +- .../kamon-annotation-example/java/pom.xml | 64 + .../main/java/kamon/KamonSpringApplication.java | 12 + .../main/java/kamon/akka/pingpong/PingPong.java | 22 + .../src/main/java/kamon/akka/pingpong/Pinger.java | 12 + .../src/main/java/kamon/akka/pingpong/Ponger.java | 12 + .../java/kamon/annotation/KamonController.java | 17 + .../java/src/main/resources/META-INF/aop.xml | 8 + .../java/src/main/resources/application.conf | 21 + .../java/src/main/resources/logback.xml | 19 + .../kamon-annotation-example/scala/build.sbt | 22 + .../scala/project/plugins.sbt | 1 + .../scala/src/main/resources/META-INF/aop.xml | 8 + .../scala/src/main/resources/application.conf | 10 + .../scala/src/main/resources/logback.xml | 19 + .../scala/kamon/annotation/KamonController.scala | 17 + .../kamon/annotation/KamonSpringApplication.scala | 10 + kamon-examples/kamon-autoweave-example/build.sbt | 62 + .../project/build.properties | 1 + .../kamon-autoweave-example/project/plugins.sbt | 6 + .../src/main/resources/application.conf | 18 + .../src/main/resources/logback.xml | 11 + .../scala/kamon/autoweave/example/PingPong.scala | 40 + kamon-examples/kamon-fluentd-example/README.md | 31 + kamon-examples/kamon-fluentd-example/build.sbt | 31 + .../kamon-fluentd-example/project/build.properties | 1 + .../kamon-fluentd-example/project/plugins.sbt | 6 + .../src/main/resources/application.conf | 73 + .../src/main/scala/KamonFluentdExample.scala | 60 + kamon-examples/kamon-newrelic-example/build.sbt | 26 + .../project/build.properties | 1 + .../kamon-newrelic-example/project/plugins.sbt | 9 + .../src/main/resources/application.conf | 10 + .../src/main/scala/NewRelicExample.scala | 40 + .../kamon-play-example-2.4.x/app/Filters.scala | 7 + .../app/controllers/KamonPlayExample.scala | 83 + .../app/filters/TraceLocalFilter.scala | 60 + .../kamon-play-example-2.4.x/conf/application.conf | 65 + .../kamon-play-example-2.4.x/conf/logger.xml | 27 + .../kamon-play-example-2.4.x/conf/routes | 5 + .../kamon-play-example-2.4.x/project/Build.scala | 52 + .../project/build.properties | 1 + .../kamon-play-example-2.4.x/project/plugins.sbt | 10 + .../public/images/favicon.png | Bin 0 -> 687 bytes .../public/images/glyphicons-halflings-white.png | Bin 0 -> 8777 bytes .../public/images/glyphicons-halflings.png | Bin 0 -> 12799 bytes .../public/javascripts/jquery-1.9.0.min.js | 4 + .../public/stylesheets/bootstrap.css | 6158 ++++++++++++++++++++ .../public/stylesheets/main.css | 0 kamon-examples/kamon-play-example/app/Global.scala | 30 + .../app/controllers/KamonPlayExample.scala | 83 + .../app/filters/TraceLocalFilter.scala | 60 + .../kamon-play-example/conf/application.conf | 67 + kamon-examples/kamon-play-example/conf/logger.xml | 27 + kamon-examples/kamon-play-example/conf/routes | 5 + .../kamon-play-example/project/Build.scala | 52 + .../kamon-play-example/project/build.properties | 1 + .../kamon-play-example/project/plugins.sbt | 10 + .../kamon-play-example/public/images/favicon.png | Bin 0 -> 687 bytes .../public/images/glyphicons-halflings-white.png | Bin 0 -> 8777 bytes .../public/images/glyphicons-halflings.png | Bin 0 -> 12799 bytes .../public/javascripts/jquery-1.9.0.min.js | 4 + .../public/stylesheets/bootstrap.css | 6158 ++++++++++++++++++++ .../kamon-play-example/public/stylesheets/main.css | 0 .../kamon-scalatra-example/project/AspectJ.scala | 28 + .../kamon-scalatra-example/project/Build.scala | 65 + .../project/build.properties | 1 + .../kamon-scalatra-example/project/plugins.sbt | 1 + .../src/main/resources/application.conf | 19 + .../src/main/resources/logback.xml | 11 + .../src/main/scala/ScalatraBootstrap.scala | 32 + .../main/scala/kamon/example/EmbeddedServer.scala | 39 + .../main/scala/kamon/example/KamonServlet.scala | 65 + .../main/scala/kamon/example/KamonSupport.scala | 34 + .../src/webapp/WEB-INF/web.xml | 9 + project/Dependencies.scala | 8 + project/Settings.scala | 13 +- 78 files changed, 14008 insertions(+), 23 deletions(-) create mode 100644 kamon-examples/kamon-annotation-example/java/pom.xml create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/java/kamon/KamonSpringApplication.java create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/PingPong.java create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Pinger.java create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Ponger.java create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/java/kamon/annotation/KamonController.java create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/resources/META-INF/aop.xml create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/resources/application.conf create mode 100644 kamon-examples/kamon-annotation-example/java/src/main/resources/logback.xml create mode 100644 kamon-examples/kamon-annotation-example/scala/build.sbt create mode 100644 kamon-examples/kamon-annotation-example/scala/project/plugins.sbt create mode 100644 kamon-examples/kamon-annotation-example/scala/src/main/resources/META-INF/aop.xml create mode 100644 kamon-examples/kamon-annotation-example/scala/src/main/resources/application.conf create mode 100644 kamon-examples/kamon-annotation-example/scala/src/main/resources/logback.xml create mode 100644 kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonController.scala create mode 100644 kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonSpringApplication.scala create mode 100644 kamon-examples/kamon-autoweave-example/build.sbt create mode 100644 kamon-examples/kamon-autoweave-example/project/build.properties create mode 100644 kamon-examples/kamon-autoweave-example/project/plugins.sbt create mode 100644 kamon-examples/kamon-autoweave-example/src/main/resources/application.conf create mode 100644 kamon-examples/kamon-autoweave-example/src/main/resources/logback.xml create mode 100644 kamon-examples/kamon-autoweave-example/src/main/scala/kamon/autoweave/example/PingPong.scala create mode 100644 kamon-examples/kamon-fluentd-example/README.md create mode 100644 kamon-examples/kamon-fluentd-example/build.sbt create mode 100644 kamon-examples/kamon-fluentd-example/project/build.properties create mode 100644 kamon-examples/kamon-fluentd-example/project/plugins.sbt create mode 100644 kamon-examples/kamon-fluentd-example/src/main/resources/application.conf create mode 100644 kamon-examples/kamon-fluentd-example/src/main/scala/KamonFluentdExample.scala create mode 100644 kamon-examples/kamon-newrelic-example/build.sbt create mode 100644 kamon-examples/kamon-newrelic-example/project/build.properties create mode 100644 kamon-examples/kamon-newrelic-example/project/plugins.sbt create mode 100644 kamon-examples/kamon-newrelic-example/src/main/resources/application.conf create mode 100644 kamon-examples/kamon-newrelic-example/src/main/scala/NewRelicExample.scala create mode 100644 kamon-examples/kamon-play-example-2.4.x/app/Filters.scala create mode 100644 kamon-examples/kamon-play-example-2.4.x/app/controllers/KamonPlayExample.scala create mode 100644 kamon-examples/kamon-play-example-2.4.x/app/filters/TraceLocalFilter.scala create mode 100644 kamon-examples/kamon-play-example-2.4.x/conf/application.conf create mode 100644 kamon-examples/kamon-play-example-2.4.x/conf/logger.xml create mode 100644 kamon-examples/kamon-play-example-2.4.x/conf/routes create mode 100644 kamon-examples/kamon-play-example-2.4.x/project/Build.scala create mode 100644 kamon-examples/kamon-play-example-2.4.x/project/build.properties create mode 100644 kamon-examples/kamon-play-example-2.4.x/project/plugins.sbt create mode 100644 kamon-examples/kamon-play-example-2.4.x/public/images/favicon.png create mode 100644 kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings-white.png create mode 100644 kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings.png create mode 100644 kamon-examples/kamon-play-example-2.4.x/public/javascripts/jquery-1.9.0.min.js create mode 100644 kamon-examples/kamon-play-example-2.4.x/public/stylesheets/bootstrap.css create mode 100644 kamon-examples/kamon-play-example-2.4.x/public/stylesheets/main.css create mode 100644 kamon-examples/kamon-play-example/app/Global.scala create mode 100644 kamon-examples/kamon-play-example/app/controllers/KamonPlayExample.scala create mode 100644 kamon-examples/kamon-play-example/app/filters/TraceLocalFilter.scala create mode 100644 kamon-examples/kamon-play-example/conf/application.conf create mode 100644 kamon-examples/kamon-play-example/conf/logger.xml create mode 100644 kamon-examples/kamon-play-example/conf/routes create mode 100644 kamon-examples/kamon-play-example/project/Build.scala create mode 100644 kamon-examples/kamon-play-example/project/build.properties create mode 100644 kamon-examples/kamon-play-example/project/plugins.sbt create mode 100644 kamon-examples/kamon-play-example/public/images/favicon.png create mode 100644 kamon-examples/kamon-play-example/public/images/glyphicons-halflings-white.png create mode 100644 kamon-examples/kamon-play-example/public/images/glyphicons-halflings.png create mode 100644 kamon-examples/kamon-play-example/public/javascripts/jquery-1.9.0.min.js create mode 100644 kamon-examples/kamon-play-example/public/stylesheets/bootstrap.css create mode 100644 kamon-examples/kamon-play-example/public/stylesheets/main.css create mode 100644 kamon-examples/kamon-scalatra-example/project/AspectJ.scala create mode 100644 kamon-examples/kamon-scalatra-example/project/Build.scala create mode 100644 kamon-examples/kamon-scalatra-example/project/build.properties create mode 100644 kamon-examples/kamon-scalatra-example/project/plugins.sbt create mode 100644 kamon-examples/kamon-scalatra-example/src/main/resources/application.conf create mode 100644 kamon-examples/kamon-scalatra-example/src/main/resources/logback.xml create mode 100644 kamon-examples/kamon-scalatra-example/src/main/scala/ScalatraBootstrap.scala create mode 100644 kamon-examples/kamon-scalatra-example/src/main/scala/kamon/example/EmbeddedServer.scala create mode 100644 kamon-examples/kamon-scalatra-example/src/main/scala/kamon/example/KamonServlet.scala create mode 100644 kamon-examples/kamon-scalatra-example/src/main/scala/kamon/example/KamonSupport.scala create mode 100644 kamon-examples/kamon-scalatra-example/src/webapp/WEB-INF/web.xml diff --git a/build.sbt b/build.sbt index a39041b9..8288efcc 100644 --- a/build.sbt +++ b/build.sbt @@ -26,18 +26,21 @@ lazy val kamon = (project in file(".")) lazy val core = (project in file("kamon-core")) + .settings(moduleName := "kamon-core") .settings(basicSettings: _*) .settings(formatSettings: _*) .settings( libraryDependencies ++= - compileScope(akkaActor, hdrHistogram, slf4jApi) ++ + compileScope(akkaDependency("actor").value, hdrHistogram, slf4jApi) ++ providedScope(aspectJ) ++ optionalScope(logback) ++ - testScope(scalatest, akkaTestKit, akkaSlf4j, logback)) + testScope(scalatest, akkaDependency("testkit").value, akkaDependency("slf4j").value, logback)) + lazy val autoweave = (project in file("kamon-autoweave")) .dependsOn(core) + .settings(moduleName := "kamon-autoweave") .settings(basicSettings: _*) .settings(formatSettings: _*) .settings( @@ -48,16 +51,18 @@ lazy val autoweave = (project in file("kamon-autoweave")) lazy val testkit = (project in file("kamon-testkit")) .dependsOn(core) + .settings(moduleName := "kamon-testkit") .settings(basicSettings: _*) .settings(formatSettings: _*) .settings( libraryDependencies ++= - compileScope(akkaActor, akkaTestKit) ++ + compileScope(akkaActor, akkaDependency("testkit").value) ++ providedScope(aspectJ) ++ testScope(slf4jApi, slf4jnop)) lazy val bench = (project in file("kamon-bench")) .dependsOn(core) + .settings(moduleName := "kamon-bench") .settings(basicSettings: _*) .settings(formatSettings: _*) .settings(noPublishing: _*) diff --git a/kamon-core/src/main/scala/kamon/util/executors/ExecutorMetricRecorder.scala b/kamon-core/src/main/scala/kamon/util/executors/ExecutorMetricRecorder.scala index 732e189e..a4bca570 100644 --- a/kamon-core/src/main/scala/kamon/util/executors/ExecutorMetricRecorder.scala +++ b/kamon-core/src/main/scala/kamon/util/executors/ExecutorMetricRecorder.scala @@ -1,6 +1,6 @@ /* * ========================================================================================= - * Copyright © 2013-2015 the kamon project + * Copyright © 2013-2016 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 @@ -23,7 +23,7 @@ import kamon.util.executors.ForkJoinPools.ForkJoinMetrics import scala.concurrent.forkjoin.ForkJoinPool -object ForkJoinPools { +object ForkJoinPools extends ForkJoinLowPriority { trait ForkJoinMetrics[T] { def getParallelism(fjp: T): Long def getPoolSize(fjp: T): Long @@ -33,16 +33,6 @@ object ForkJoinPools { def getQueuedSubmissionCount(fjp: T): Long } - implicit object ScalaForkJoin extends ForkJoinMetrics[ForkJoinPool] { - def getParallelism(fjp: ForkJoinPool) = fjp.getParallelism - def getPoolSize(fjp: ForkJoinPool) = fjp.getPoolSize.toLong - def getRunningThreadCount(fjp: ForkJoinPool) = fjp.getActiveThreadCount.toLong - def getActiveThreadCount(fjp: ForkJoinPool) = fjp.getRunningThreadCount.toLong - def getQueuedTaskCount(fjp: ForkJoinPool) = fjp.getQueuedTaskCount - def getQueuedSubmissionCount(fjp: ForkJoinPool) = fjp.getQueuedSubmissionCount - - } - implicit object JavaForkJoin extends ForkJoinMetrics[JavaForkJoinPool] { def getParallelism(fjp: JavaForkJoinPool) = fjp.getParallelism def getPoolSize(fjp: JavaForkJoinPool) = fjp.getPoolSize.toLong @@ -50,7 +40,17 @@ object ForkJoinPools { def getActiveThreadCount(fjp: JavaForkJoinPool) = fjp.getRunningThreadCount.toLong def getQueuedTaskCount(fjp: JavaForkJoinPool) = fjp.getQueuedTaskCount def getQueuedSubmissionCount(fjp: JavaForkJoinPool) = fjp.getQueuedSubmissionCount + } +} +trait ForkJoinLowPriority { + implicit object ScalaForkJoin extends ForkJoinMetrics[ForkJoinPool] { + def getParallelism(fjp: ForkJoinPool) = fjp.getParallelism + def getPoolSize(fjp: ForkJoinPool) = fjp.getPoolSize.toLong + def getRunningThreadCount(fjp: ForkJoinPool) = fjp.getActiveThreadCount.toLong + def getActiveThreadCount(fjp: ForkJoinPool) = fjp.getRunningThreadCount.toLong + def getQueuedTaskCount(fjp: ForkJoinPool) = fjp.getQueuedTaskCount + def getQueuedSubmissionCount(fjp: ForkJoinPool) = fjp.getQueuedSubmissionCount } } @@ -96,4 +96,4 @@ object ThreadPoolExecutorMetrics { def category: String = cat def createRecorder(instrumentFactory: InstrumentFactory) = new ThreadPoolExecutorMetrics(tpe, instrumentFactory) } -} \ No newline at end of file +} diff --git a/kamon-examples/kamon-annotation-example/java/pom.xml b/kamon-examples/kamon-annotation-example/java/pom.xml new file mode 100644 index 00000000..32f4f86b --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/pom.xml @@ -0,0 +1,64 @@ + + + 4.0.0 + + kamon.annotation + kamon-spring-boot + 0.1.0 + + + + org.springframework.boot + spring-boot-starter-parent + 1.4.0.RELEASE + + + + + org.springframework.boot + spring-boot-starter-web + + + io.kamon + kamon-core_2.11 + 0.6.2 + + + io.kamon + kamon-annotation_2.11 + 0.6.2 + + + io.kamon + kamon-akka_2.11 + 0.6.2 + + + io.kamon + kamon-log-reporter_2.11 + 0.6.2 + + + + + 1.8 + + + + + + + org.springframework.boot + spring-boot-maven-plugin + + + + + + + io.kamon + http://snapshots.kamon.io + + + diff --git a/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/KamonSpringApplication.java b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/KamonSpringApplication.java new file mode 100644 index 00000000..8103306b --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/KamonSpringApplication.java @@ -0,0 +1,12 @@ +package kamon; + +import kamon.akka.pingpong.PingPong; +import kamon.annotation.KamonController; +import org.springframework.boot.SpringApplication; + +public class KamonSpringApplication { + public static void main(String... args) { + Kamon.start(); + SpringApplication.run(new Object[] {KamonController.class, PingPong.class}, args); + } +} diff --git a/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/PingPong.java b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/PingPong.java new file mode 100644 index 00000000..8ef2f621 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/PingPong.java @@ -0,0 +1,22 @@ +package kamon.akka.pingpong; + +import akka.actor.ActorRef; +import akka.actor.ActorSystem; +import akka.actor.Props; +import org.springframework.stereotype.Component; + +import javax.annotation.PostConstruct; + +@Component +public class PingPong { + + @PostConstruct + public void initialize() { + final ActorSystem system = ActorSystem.create("kamon-spring-boot-actor-system"); + + final ActorRef pinger = system.actorOf(Props.create(Pinger.class), "pinger"); + final ActorRef ponger = system.actorOf(Props.create(Ponger.class), "ponger"); + + pinger.tell(new Ponger.PongMessage(), ponger); + } +} diff --git a/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Pinger.java b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Pinger.java new file mode 100644 index 00000000..dcab35b6 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Pinger.java @@ -0,0 +1,12 @@ +package kamon.akka.pingpong; + +import akka.actor.UntypedActor; + +class Pinger extends UntypedActor { + static final class PingMessage {} + + public void onReceive(Object message) throws Exception { + if (message instanceof Ponger.PongMessage) getSender().tell(new PingMessage(), getSelf()); + else unhandled(message); + } +} diff --git a/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Ponger.java b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Ponger.java new file mode 100644 index 00000000..b4e8ecfa --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/akka/pingpong/Ponger.java @@ -0,0 +1,12 @@ +package kamon.akka.pingpong; + +import akka.actor.UntypedActor; + +class Ponger extends UntypedActor { + static final class PongMessage {} + + public void onReceive(Object message) throws Exception { + if (message instanceof Pinger.PingMessage) getSender().tell(new PongMessage(), getSelf()); + else unhandled(message); + } +} diff --git a/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/annotation/KamonController.java b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/annotation/KamonController.java new file mode 100644 index 00000000..27eeda53 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/java/kamon/annotation/KamonController.java @@ -0,0 +1,17 @@ +package kamon.annotation; + +import org.springframework.boot.autoconfigure.*; +import org.springframework.stereotype.*; +import org.springframework.web.bind.annotation.*; + +@Controller +@EnableAutoConfiguration +@RequestMapping("/kamon") +@EnableKamon +public class KamonController { + + @RequestMapping("/counter") + @ResponseBody + @Count(name = "awesomeCounter") + public String counter() { return "count!!!"; } +} diff --git a/kamon-examples/kamon-annotation-example/java/src/main/resources/META-INF/aop.xml b/kamon-examples/kamon-annotation-example/java/src/main/resources/META-INF/aop.xml new file mode 100644 index 00000000..9b144860 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/resources/META-INF/aop.xml @@ -0,0 +1,8 @@ + + + + + + + + diff --git a/kamon-examples/kamon-annotation-example/java/src/main/resources/application.conf b/kamon-examples/kamon-annotation-example/java/src/main/resources/application.conf new file mode 100644 index 00000000..1755bfc5 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/resources/application.conf @@ -0,0 +1,21 @@ +############################### +# Kamon related configuration # +############################### + +kamon { + + metric { + filters { + trace.includes = [ "**" ] + akka-actor.includes = [ "**" ] + akka-actor.excludes = ["*/system/**", "*/user/IO-**" ] + akka-dispatcher.includes = [ "**" ] + akka-dispatcher.excludes = [ ] + } + } + + modules { + kamon-annotation.auto-start = yes + kamon-log-reporter.auto-start = yes + } +} diff --git a/kamon-examples/kamon-annotation-example/java/src/main/resources/logback.xml b/kamon-examples/kamon-annotation-example/java/src/main/resources/logback.xml new file mode 100644 index 00000000..fac5ad3d --- /dev/null +++ b/kamon-examples/kamon-annotation-example/java/src/main/resources/logback.xml @@ -0,0 +1,19 @@ + + + + + + + + + ${CONSOLE_LOG_PATTERN} + + + + + + + + + + diff --git a/kamon-examples/kamon-annotation-example/scala/build.sbt b/kamon-examples/kamon-annotation-example/scala/build.sbt new file mode 100644 index 00000000..2200ad6f --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/build.sbt @@ -0,0 +1,22 @@ +name := "spring-boot-kamon" + +version := "1.0" + +scalaVersion := "2.11.6" + +sbtVersion := "0.13.1" + +resolvers += "Kamon Repository Snapshots" at "http://snapshots.kamon.io" + +libraryDependencies ++= Seq( + "org.springframework.boot" % "spring-boot-starter-web" % "1.2.3.RELEASE", + "io.kamon" %% "kamon-core" % "0.5.2", + "io.kamon" %% "kamon-annotation" % "0.5.2", + "io.kamon" %% "kamon-log-reporter" % "0.5.2" +) + +aspectjSettings + +fork in run := true + +javaOptions in run <++= AspectjKeys.weaverOptions in Aspectj diff --git a/kamon-examples/kamon-annotation-example/scala/project/plugins.sbt b/kamon-examples/kamon-annotation-example/scala/project/plugins.sbt new file mode 100644 index 00000000..eba7b696 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/project/plugins.sbt @@ -0,0 +1 @@ +addSbtPlugin("com.typesafe.sbt" % "sbt-aspectj" % "0.10.0") diff --git a/kamon-examples/kamon-annotation-example/scala/src/main/resources/META-INF/aop.xml b/kamon-examples/kamon-annotation-example/scala/src/main/resources/META-INF/aop.xml new file mode 100644 index 00000000..9b144860 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/src/main/resources/META-INF/aop.xml @@ -0,0 +1,8 @@ + + + + + + + + diff --git a/kamon-examples/kamon-annotation-example/scala/src/main/resources/application.conf b/kamon-examples/kamon-annotation-example/scala/src/main/resources/application.conf new file mode 100644 index 00000000..595f9b89 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/src/main/resources/application.conf @@ -0,0 +1,10 @@ +############################### +# Kamon related configuration # +############################### + +kamon { + modules { + kamon-annotation.auto-start = yes + kamon-log-reporter.auto-start = yes + } +} \ No newline at end of file diff --git a/kamon-examples/kamon-annotation-example/scala/src/main/resources/logback.xml b/kamon-examples/kamon-annotation-example/scala/src/main/resources/logback.xml new file mode 100644 index 00000000..fac5ad3d --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/src/main/resources/logback.xml @@ -0,0 +1,19 @@ + + + + + + + + + ${CONSOLE_LOG_PATTERN} + + + + + + + + + + diff --git a/kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonController.scala b/kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonController.scala new file mode 100644 index 00000000..00c88715 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonController.scala @@ -0,0 +1,17 @@ +package kamon.annotation + +import org.springframework.boot.autoconfigure._ +import org.springframework.stereotype._ +import org.springframework.web.bind.annotation._ + +@Controller +@EnableAutoConfiguration +@RequestMapping(Array("/kamon")) +@EnableKamon +class KamonController { + + @RequestMapping(Array("/counter")) + @ResponseBody + @Count(name = "awesomeCounter") + def counter(): String = "count!!!" +} \ No newline at end of file diff --git a/kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonSpringApplication.scala b/kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonSpringApplication.scala new file mode 100644 index 00000000..595900a8 --- /dev/null +++ b/kamon-examples/kamon-annotation-example/scala/src/main/scala/kamon/annotation/KamonSpringApplication.scala @@ -0,0 +1,10 @@ +package kamon.annotation + +import kamon.Kamon +import org.springframework.boot.SpringApplication + +object KamonSpringApplication extends App { + Kamon.start() + + SpringApplication.run(classOf[KamonController]) +} diff --git a/kamon-examples/kamon-autoweave-example/build.sbt b/kamon-examples/kamon-autoweave-example/build.sbt new file mode 100644 index 00000000..ce36f064 --- /dev/null +++ b/kamon-examples/kamon-autoweave-example/build.sbt @@ -0,0 +1,62 @@ + +name := "kamon-autoweave-example" + +scalaVersion := "2.11.8" + +libraryDependencies += "org.aspectj" % "aspectjweaver" % "1.8.9" + +libraryDependencies += "com.typesafe.akka" %% "akka-actor" % "2.4.5" + +libraryDependencies += "com.typesafe.akka" %% "akka-testkit" % "2.4.5" % "test" + +libraryDependencies += "com.typesafe.akka" %% "akka-slf4j" % "2.4.11" + +libraryDependencies += "io.kamon" %% "kamon-core" % "0.6.3" + +libraryDependencies += "io.kamon" %% "kamon-autoweave" % "0.6.3" + +libraryDependencies += "io.kamon" %% "kamon-akka" % "0.6.3" + +libraryDependencies += "io.kamon" %% "kamon-log-reporter" % "0.6.3" + +libraryDependencies += "org.slf4j" % "slf4j-api" % "1.7.16" + +libraryDependencies += "ch.qos.logback" % "logback-classic" % "1.1.7" + +fork in run := true + +// Create a new MergeStrategy for aop.xml files +val aopMerge = new sbtassembly.MergeStrategy { + val name = "aopMerge" + import scala.xml._ + import scala.xml.dtd._ + + def apply(tempDir: File, path: String, files: Seq[File]): Either[String, Seq[(File, String)]] = { + val dt = DocType("aspectj", PublicID("-//AspectJ//DTD//EN", "http://www.eclipse.org/aspectj/dtd/aspectj.dtd"), Nil) + val file = MergeStrategy.createMergeTarget(tempDir, path) + val xmls: Seq[Elem] = files.map(XML.loadFile) + val aspectsChildren: Seq[Node] = xmls.flatMap(_ \\ "aspectj" \ "aspects" \ "_") + val weaverChildren: Seq[Node] = xmls.flatMap(_ \\ "aspectj" \ "weaver" \ "_") + val options: String = xmls.map(x => (x \\ "aspectj" \ "weaver" \ "@options").text).mkString(" ").trim + val weaverAttr = if (options.isEmpty) Null else new UnprefixedAttribute("options", options, Null) + val aspects = new Elem(null, "aspects", Null, TopScope, false, aspectsChildren: _*) + val weaver = new Elem(null, "weaver", weaverAttr, TopScope, false, weaverChildren: _*) + val aspectj = new Elem(null, "aspectj", Null, TopScope, false, aspects, weaver) + XML.save(file.toString, aspectj, "UTF-8", xmlDecl = false, dt) + IO.append(file, IO.Newline.getBytes(IO.defaultCharset)) + Right(Seq(file -> path)) + } +} + +assemblyMergeStrategy in assembly := { + case m if m.toLowerCase.endsWith("manifest.mf") => MergeStrategy.discard + case m if m.toLowerCase.matches("meta-inf.*\\.sf$") => MergeStrategy.discard + case m if m.toLowerCase.matches("meta-inf.*\\.properties") => MergeStrategy.discard + case PathList("META-INF", "aop.xml") => aopMerge + case PathList(ps @ _*) if ps.last endsWith ".txt.1" => MergeStrategy.first + case "reference.conf" => MergeStrategy.concat + case "application.conf" => MergeStrategy.concat + case x => + val oldStrategy = (assemblyMergeStrategy in assembly).value + oldStrategy(x) +} diff --git a/kamon-examples/kamon-autoweave-example/project/build.properties b/kamon-examples/kamon-autoweave-example/project/build.properties new file mode 100644 index 00000000..a6e117b6 --- /dev/null +++ b/kamon-examples/kamon-autoweave-example/project/build.properties @@ -0,0 +1 @@ +sbt.version=0.13.8 diff --git a/kamon-examples/kamon-autoweave-example/project/plugins.sbt b/kamon-examples/kamon-autoweave-example/project/plugins.sbt new file mode 100644 index 00000000..28ab3a86 --- /dev/null +++ b/kamon-examples/kamon-autoweave-example/project/plugins.sbt @@ -0,0 +1,6 @@ +// Comment to get more information during initialization +logLevel := Level.Warn + +resolvers += "Kamon Repository Snapshots" at "http://snapshots.kamon.io" + +addSbtPlugin("com.eed3si9n" % "sbt-assembly" % "0.14.3") diff --git a/kamon-examples/kamon-autoweave-example/src/main/resources/application.conf b/kamon-examples/kamon-autoweave-example/src/main/resources/application.conf new file mode 100644 index 00000000..51732890 --- /dev/null +++ b/kamon-examples/kamon-autoweave-example/src/main/resources/application.conf @@ -0,0 +1,18 @@ +kamon { + + trace { + level = simple-trace + } + + metric { + filters { + trace.includes = [ "**" ] + akka-actor.includes = [ "**" ] + akka-dispatcher.includes = [ "**" ] + } + } + + modules { + kamon-log-reporter.auto-start = yes + } +} \ No newline at end of file diff --git a/kamon-examples/kamon-autoweave-example/src/main/resources/logback.xml b/kamon-examples/kamon-autoweave-example/src/main/resources/logback.xml new file mode 100644 index 00000000..56f7f131 --- /dev/null +++ b/kamon-examples/kamon-autoweave-example/src/main/resources/logback.xml @@ -0,0 +1,11 @@ + + + + %date{HH:mm:ss.SSS} %-5level [%X{akkaSource}] [%thread] %logger{55} - %msg%n + + + + + + + \ No newline at end of file diff --git a/kamon-examples/kamon-autoweave-example/src/main/scala/kamon/autoweave/example/PingPong.scala b/kamon-examples/kamon-autoweave-example/src/main/scala/kamon/autoweave/example/PingPong.scala new file mode 100644 index 00000000..6457222d --- /dev/null +++ b/kamon-examples/kamon-autoweave-example/src/main/scala/kamon/autoweave/example/PingPong.scala @@ -0,0 +1,40 @@ +/* + * ========================================================================================= + * Copyright © 2013-2015 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.autoweave.example + +import akka.actor._ +import kamon.Kamon + +object PingPong extends App { + Kamon.start() + + val system = ActorSystem() + + val pinger = system.actorOf(Props(new Actor { + def receive: Actor.Receive = { case "pong" ⇒ sender ! "ping" } + }), "pinger") + + val ponger = system.actorOf(Props(new Actor { + def receive: Actor.Receive = { case "ping" ⇒ sender ! "pong" } + }), "ponger") + + pinger.tell("pong", ponger) +} + +//sbt run +//or +//sbt assembly && java -jar target/scala-2.11/kamon-autoweave-example-assembly-0.1-SNAPSHOT.jar diff --git a/kamon-examples/kamon-fluentd-example/README.md b/kamon-examples/kamon-fluentd-example/README.md new file mode 100644 index 00000000..0dc6a250 --- /dev/null +++ b/kamon-examples/kamon-fluentd-example/README.md @@ -0,0 +1,31 @@ +kamon-fluentd-example +------------------------------ + +An example Spray application with Kamon monitoring reporting to Fluentd Server. + +Prerequisites +--------------- +* fluentd: + ```sh + you@host:kamon-fluentd-example $ gem install fluentd + ``` + +* install kamon snapshots to local: + ```sh + you@host:kamon-fluentd-example $ cd ../../ + you@host:Kamon $ sbt "+ publishLocal" + ... snip... + [info] published ivy to /Users/___/.ivy2/local/io.kamon/kamon-akka-remote_2.11/0.5.2-021ffd253e104342e6b4c75ae42717b51e3b6b26/ivys/ivy.xml + [success] Total time: 248 s, completed 2015/10/04 0:27:53 + [info] Setting version to 2.10.4 + [info] Reapplying settings... + [info] Set current project to kamon (in build file:/Users/___/kamon-io/Kamon/) + ``` + +* edit build.sbt. edit `kamonV` variable with installed snapshot version (`0.5.2-021ffd253e104342e6b4c75ae42717b51e3b6b26` in the above example). + +How to run +------------ +1. just do it: `sbt aspectj-runner:run` +2. you'll see kamon-log-reporter outputs on console. +3. you'll also see kamon metrics sent to fluentd on files named `target/fluentd_out.****` diff --git a/kamon-examples/kamon-fluentd-example/build.sbt b/kamon-examples/kamon-fluentd-example/build.sbt new file mode 100644 index 00000000..a240fad3 --- /dev/null +++ b/kamon-examples/kamon-fluentd-example/build.sbt @@ -0,0 +1,31 @@ +import sbt._ +import sbt.Keys._ + +name := "kamon-fluentd-example" + +version := "1.0" + +scalaVersion := "2.11.6" + +resolvers += "Kamon repo" at "http://repo.kamon.io" + +resolvers += "spray repo" at "http://repo.spray.io" + +libraryDependencies ++= { + val akkaV = "2.3.5" + val sprayV = "1.3.1" + val kamonV = "EDIT_HERE" + Seq( + "io.spray" %% "spray-can" % sprayV, + "io.spray" %% "spray-routing" % sprayV, + "io.kamon" %% "kamon-core" % kamonV, + "io.kamon" %% "kamon-system-metrics" % kamonV, + "io.kamon" %% "kamon-akka" % kamonV, + "io.kamon" %% "kamon-scala" % kamonV, + "io.kamon" %% "kamon-spray" % kamonV, + "io.kamon" %% "kamon-fluentd" % kamonV, + "io.kamon" %% "kamon-log-reporter" % kamonV, + "org.aspectj" % "aspectjweaver" % "1.8.4" + ) +} + diff --git a/kamon-examples/kamon-fluentd-example/project/build.properties b/kamon-examples/kamon-fluentd-example/project/build.properties new file mode 100644 index 00000000..df58110a --- /dev/null +++ b/kamon-examples/kamon-fluentd-example/project/build.properties @@ -0,0 +1 @@ +sbt.version=0.13.6 \ No newline at end of file diff --git a/kamon-examples/kamon-fluentd-example/project/plugins.sbt b/kamon-examples/kamon-fluentd-example/project/plugins.sbt new file mode 100644 index 00000000..ab3750e2 --- /dev/null +++ b/kamon-examples/kamon-fluentd-example/project/plugins.sbt @@ -0,0 +1,6 @@ +resolvers += "Sonatype snapshots" at "http://oss.sonatype.org/content/repositories/snapshots/" + +resolvers += "Kamon Releases" at "http://repo.kamon.io" + +addSbtPlugin("io.kamon" % "aspectj-runner" % "0.1.2") + diff --git a/kamon-examples/kamon-fluentd-example/src/main/resources/application.conf b/kamon-examples/kamon-fluentd-example/src/main/resources/application.conf new file mode 100644 index 00000000..bb69abd3 --- /dev/null +++ b/kamon-examples/kamon-fluentd-example/src/main/resources/application.conf @@ -0,0 +1,73 @@ +# ===================================== # +# Kamon-Fluentd Reference Configuration # +# ===================================== # + +kamon { + metric.filters { + akka-actor { + includes = ["**"], + } + + akka-dispatcher { + includes = ["**"] + } + + akka-router { + includes = ["**"] + } + } + + fluentd { + # Hostname and port of fluentd server to which kamon fluentd sends metrics. + hostname = "localhost" + port = 24224 + + # tag prefix of metrics data which is sent to fluentd server + tag = "kamon.fluentd" + + # Interval between metrics data flushes to fluentd server. + # It's value must be equal or greater than the kamon.metric.tick-interval setting. + flush-interval = 10 seconds + + # Your app name + application-name = "kamon-fluentd-example" + + # Subscription patterns used to select which metrics will be pushed to Fluentd. Note that first, metrics + # collection for your desired entities must be activated under the kamon.metrics.filters settings. + subscriptions { + histogram = [ "**" ] + min-max-counter = [ "**" ] + gauge = [ "**" ] + counter = [ "**" ] + trace = [ "**" ] + trace-segment = [ "**" ] + akka-actor = [ "**" ] + akka-dispatcher = [ "**" ] + akka-router = [ "**" ] + system-metric = [ "**" ] + http-server = [ "**" ] + } + + # statistic values to be reported for histogram type metrics + # (i.e. Histogram, MinMaxCounter, Gauge). + histogram-stats { + # stats values: + # "count", "min", "max", "average", "percentiles" are supported. + # you can use "*" for wildcards. + subscription = [ "count", "min", "max", "average", "percentiles" ], + + # percentile points: + # this will be used when you set "percentiles" in "subscription" above. + # In this example, kamon-fluentd reports 50th 90th, 99th and 99.9th percentiles. + percentiles = [50.0, 90.0, 99.0, 99.9] + } + } + + modules { + kamon-fluentd { + auto-start = yes + requires-aspectj = no + extension-class = "kamon.fluentd.Fluentd" + } + } +} \ No newline at end of file diff --git a/kamon-examples/kamon-fluentd-example/src/main/scala/KamonFluentdExample.scala b/kamon-examples/kamon-fluentd-example/src/main/scala/KamonFluentdExample.scala new file mode 100644 index 00000000..bb1d0f7b --- /dev/null +++ b/kamon-examples/kamon-fluentd-example/src/main/scala/KamonFluentdExample.scala @@ -0,0 +1,60 @@ +/* ========================================================================================= + * Copyright © 2013-2015 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. + * ========================================================================================= + */ + +import akka.actor.ActorSystem +import kamon.Kamon +import spray.routing.SimpleRoutingApp +import xerial.fluentd.{ FluentdConfig, FluentdStandalone } + +import scala.util.Properties + +object KamonFluentdExample extends App with SimpleRoutingApp { + // Start fluentd server only for this sample app + // In real usecase, you will spawn fluentd server independently. + val fluentdServer = FluentdStandalone.start(FluentdConfig(configuration = + """ + | + | type forward + | port 24224 + | + | + | type file + | path target/fluentd-out + | + """.stripMargin)) + sys.addShutdownHook { + fluentdServer.stop + } + + // start Kamon + Kamon.start() + + implicit val system = ActorSystem("kamon-fluentd-example") + + // server endpoint + val interface = "0.0.0.0" + val port = Properties.envOrElse("PORT", "8080").toInt + + // resource endpoints + startServer(interface = interface, port = port) { + path("hello") { + get { + complete { +

Hello! Kamon Fluentd Example!

+ } + } + } + } +} diff --git a/kamon-examples/kamon-newrelic-example/build.sbt b/kamon-examples/kamon-newrelic-example/build.sbt new file mode 100644 index 00000000..89b1b3d3 --- /dev/null +++ b/kamon-examples/kamon-newrelic-example/build.sbt @@ -0,0 +1,26 @@ +import sbt._ +import sbt.Keys._ + +import com.typesafe.sbt.SbtAspectj._ + +aspectjSettings + +name := "kamon-newrelic-example" + +version := "1.0" + +scalaVersion := "2.10.2" + +resolvers += "Kamon repo" at "http://repo.kamon.io" + +resolvers += "spray repo" at "http://repo.spray.io" + +libraryDependencies += "kamon" %% "kamon-core" % "0.0.12" + +libraryDependencies += "kamon" %% "kamon-spray" % "0.0.12" + +libraryDependencies += "kamon" %% "kamon-newrelic" % "0.0.12" + +libraryDependencies += "io.spray" % "spray-can" % "1.2.0" + +javaOptions <++= AspectjKeys.weaverOptions in Aspectj diff --git a/kamon-examples/kamon-newrelic-example/project/build.properties b/kamon-examples/kamon-newrelic-example/project/build.properties new file mode 100644 index 00000000..db255c25 --- /dev/null +++ b/kamon-examples/kamon-newrelic-example/project/build.properties @@ -0,0 +1 @@ +sbt.version=0.12.3 \ No newline at end of file diff --git a/kamon-examples/kamon-newrelic-example/project/plugins.sbt b/kamon-examples/kamon-newrelic-example/project/plugins.sbt new file mode 100644 index 00000000..6e42c696 --- /dev/null +++ b/kamon-examples/kamon-newrelic-example/project/plugins.sbt @@ -0,0 +1,9 @@ +resolvers += "Sonatype snapshots" at "http://oss.sonatype.org/content/repositories/snapshots/" + +resolvers += "Kamon Releases" at "http://repo.kamon.io" + +addSbtPlugin("com.ivantopo.sbt" % "sbt-newrelic" % "0.0.1") + +addSbtPlugin("com.typesafe.sbt" % "sbt-aspectj" % "0.9.4") + +addSbtPlugin("com.github.mpeltonen" % "sbt-idea" % "1.5.2") \ No newline at end of file diff --git a/kamon-examples/kamon-newrelic-example/src/main/resources/application.conf b/kamon-examples/kamon-newrelic-example/src/main/resources/application.conf new file mode 100644 index 00000000..52944172 --- /dev/null +++ b/kamon-examples/kamon-newrelic-example/src/main/resources/application.conf @@ -0,0 +1,10 @@ +akka { + extensions = ["kamon.newrelic.NewRelic"] +} + +kamon { + newrelic { + app-name = "KamonNewRelicExample[Development]" + license-key = <> + } +} diff --git a/kamon-examples/kamon-newrelic-example/src/main/scala/NewRelicExample.scala b/kamon-examples/kamon-newrelic-example/src/main/scala/NewRelicExample.scala new file mode 100644 index 00000000..e111e473 --- /dev/null +++ b/kamon-examples/kamon-newrelic-example/src/main/scala/NewRelicExample.scala @@ -0,0 +1,40 @@ +/* =================================================== + * Copyright © 2013 2014 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. + * ========================================================== */ + +import akka.actor.ActorSystem +import spray.routing.SimpleRoutingApp + +object NewRelicExample extends App with SimpleRoutingApp { + + implicit val system = ActorSystem("kamon-system") + + startServer(interface = "localhost", port = 8080) { + path("helloKamon") { + get { + complete { +

Say hello to Kamon

+ } + } + } ~ + path("helloNewRelic") { + get { + complete { +

Say hello to NewRelic

+ } + } + } + } +} \ No newline at end of file diff --git a/kamon-examples/kamon-play-example-2.4.x/app/Filters.scala b/kamon-examples/kamon-play-example-2.4.x/app/Filters.scala new file mode 100644 index 00000000..0ae2747a --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/app/Filters.scala @@ -0,0 +1,7 @@ +import javax.inject.Inject +import play.api.http.HttpFilters +import filters.TraceLocalFilter + +class Filters extends HttpFilters { + val filters = Seq(TraceLocalFilter) +} \ No newline at end of file diff --git a/kamon-examples/kamon-play-example-2.4.x/app/controllers/KamonPlayExample.scala b/kamon-examples/kamon-play-example-2.4.x/app/controllers/KamonPlayExample.scala new file mode 100644 index 00000000..fd6f08e7 --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/app/controllers/KamonPlayExample.scala @@ -0,0 +1,83 @@ +/* =================================================== + * Copyright © 2013-2015 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 controllers + +import filters.{TraceLocalContainer, TraceLocalKey} +import kamon.play.action.TraceName +import kamon.play.di.Kamon +import kamon.trace.TraceLocal +import play.api.Logger +import play.api.libs.concurrent.Execution.Implicits.defaultContext +import play.api.mvc.{Action, Controller} +import javax.inject._ + +import scala.concurrent._ + +/** + * Run the following commands from console: + * + * aspectj-runner:run + * + * and finally testing: + * + * curl -i -H 'X-Trace-Token:kamon-test' -H 'MyTraceLocalStorageKey:extra-header' -X GET "http://localhost:9000/helloKamon" + * + * we should get: + * HTTP/1.1 200 OK + * Content-Type: text/plain; charset=utf-8 + * MyTraceLocalStorageKey: extra-header -> Extra Information + * X-Trace-Token: kamon-test -> default Trace-Token + * + * Say hello to Kamon + **/ +class KamonPlayExample @Inject() (kamon: Kamon) extends Controller { + + val logger = Logger(this.getClass) + val counter = kamon.metrics.counter("my-counter") + + def sayHello = Action.async { + Future { + logger.info("Say hello to Kamon") + Ok("Say hello to Kamon") + } + } + + //using the Kamon TraceName Action to rename the trace name in metrics + def sayHelloWithTraceName = TraceName("my-trace-name") { + Action.async { + Future { + logger.info("Say hello to Kamon with trace name") + Ok("Say hello to Kamon with trace name") + } + } + } + + def incrementCounter = Action.async { + Future { + logger.info("increment") + counter.increment() + Ok("increment") + } + } + + def updateTraceLocal() = Action.async { + Future { + TraceLocal.store(TraceLocalKey)(TraceLocalContainer("MyTraceToken","MyImportantHeader")) + logger.info("storeInTraceLocal") + Ok("storeInTraceLocal") + } + } +} diff --git a/kamon-examples/kamon-play-example-2.4.x/app/filters/TraceLocalFilter.scala b/kamon-examples/kamon-play-example-2.4.x/app/filters/TraceLocalFilter.scala new file mode 100644 index 00000000..523e2048 --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/app/filters/TraceLocalFilter.scala @@ -0,0 +1,60 @@ +/* =================================================== + * Copyright © 2013-2014 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 filters + +import kamon.trace.TraceLocal +import kamon.trace.TraceLocal.{AvailableToMdc, TraceLocalKey} +import play.api.Logger +import play.api.mvc.{Result, RequestHeader, Filter} +import play.api.libs.concurrent.Execution.Implicits.defaultContext +import scala.concurrent.Future + +case class TraceLocalContainer(traceToken:String, importantHeader:String) + +object TraceLocalKey extends TraceLocalKey[TraceLocalContainer] + +/* + By default kamon spreads the trace-token-header-name, but sometimes is necessary pass through the application requests with some information like + extra headers, with kamon it's possible using the TraceLocalStorage, in Play applications we can do an Action Filter or using Action Composition, + in this example we are using a simple filter where given a Header store the value and then put the value in the result headers.. + + More detailed usage of TraceLocalStorage: https://github.com/kamon-io/Kamon/blob/b17539d231da923ea854c01d2c69eb02ef1e85b1/kamon-core/src/test/scala/kamon/trace/TraceLocalSpec.scala + */ +object TraceLocalFilter extends Filter { + val logger = Logger(this.getClass) + val TraceLocalStorageKey = "MyTraceLocalStorageKey" + + val userAgentHeader = "User-Agent" + + //this value will be available in the MDC at the moment to call to Logger.*()s + val UserAgentHeaderAvailableToMDC = AvailableToMdc(userAgentHeader) + + override def apply(next: (RequestHeader) ⇒ Future[Result])(header: RequestHeader): Future[Result] = { + + def onResult(result:Result) = { + val traceLocalContainer = TraceLocal.retrieve(TraceLocalKey).getOrElse(TraceLocalContainer("unknown","unknown")) + result.withHeaders(TraceLocalStorageKey -> traceLocalContainer.traceToken) + } + + //update the TraceLocalStorage + TraceLocal.store(TraceLocalKey)(TraceLocalContainer(header.headers.get(TraceLocalStorageKey).getOrElse("unknown"), "unknown")) + TraceLocal.store(UserAgentHeaderAvailableToMDC)(header.headers.get(userAgentHeader).getOrElse("unknown")) + + //call the action + next(header).map(onResult) + } +} diff --git a/kamon-examples/kamon-play-example-2.4.x/conf/application.conf b/kamon-examples/kamon-play-example-2.4.x/conf/application.conf new file mode 100644 index 00000000..c42c6459 --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/conf/application.conf @@ -0,0 +1,65 @@ +#kamon related configuration + +kamon { + + metric { + tick-interval = 1 second + } + + statsd { + # Hostname and port in which your StatsD is running. Remember that StatsD packets are sent using UDP and + # setting unreachable hosts and/or not open ports wont be warned by the Kamon, your data wont go anywhere. + hostname = "127.0.0.1" + port = 8125 + + # Interval between metrics data flushes to StatsD. It's value must be equal or greater than the + # kamon.metrics.tick-interval setting. + flush-interval = 1 second + + # Max packet size for UDP metrics data sent to StatsD. + max-packet-size = 1024 bytes + + # Subscription patterns used to select which metrics will be pushed to StatsD. Note that first, metrics + # collection for your desired entities must be activated under the kamon.metrics.filters settings. + includes { + actor = [ "*" ] + trace = [ "*" ] + dispatcher = [ "*" ] + } + + simple-metric-key-generator { + # Application prefix for all metrics pushed to StatsD. The default namespacing scheme for metrics follows + # this pattern: + # application.host.entity.entity-name.metric-name + application = "activator-akka-kamon-statsd" + } + } + + play { + include-trace-token-header = true + trace-token-header-name = "X-Trace-Token" + } + + modules { + kamon-statsd.auto-start = no + kamon-log-reporter.auto-start = yes + kamon-system-metrics.auto-start = no + } +} + +# This is the main configuration file for the application. +# ~~~~~ + +# Secret key +# ~~~~~ +# The secret key is used to secure cryptographics functions. +# If you deploy your application to several instances be sure to use the same key! +application.secret = "3BLM`AZE9EOphrmf;;6JsAN" + +# The application languages +# ~~~~~ +play.i18n.langs = ["en"] + +# HttpRequestHandler +play.http.requestHandler = "play.http.DefaultHttpRequestHandler" + diff --git a/kamon-examples/kamon-play-example-2.4.x/conf/logger.xml b/kamon-examples/kamon-play-example-2.4.x/conf/logger.xml new file mode 100644 index 00000000..a4a10bd0 --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/conf/logger.xml @@ -0,0 +1,27 @@ + + + + + + + + %date{HH:mm:ss.SSS} %-5level [%traceToken][%X{User-Agent}] [%thread] %logger{55} - %msg%n + + + + + + + + + + + + + + + diff --git a/kamon-examples/kamon-play-example-2.4.x/conf/routes b/kamon-examples/kamon-play-example-2.4.x/conf/routes new file mode 100644 index 00000000..6aae1d8e --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/conf/routes @@ -0,0 +1,5 @@ +# Routes +GET /helloKamon @controllers.KamonPlayExample.sayHello +GET /helloKamonWithTraceName @controllers.KamonPlayExample.sayHelloWithTraceName +GET /incrementCounter @controllers.KamonPlayExample.incrementCounter +GET /updateTraceLocal @controllers.KamonPlayExample.updateTraceLocal \ No newline at end of file diff --git a/kamon-examples/kamon-play-example-2.4.x/project/Build.scala b/kamon-examples/kamon-play-example-2.4.x/project/Build.scala new file mode 100644 index 00000000..b96b2436 --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/project/Build.scala @@ -0,0 +1,52 @@ +import java.io.File +import sbt._ +import Keys._ +import play.Play.autoImport._ +import sbt.Keys._ +import sbt._ +import com.typesafe.sbt.web.SbtWeb + + +object ApplicationBuild extends Build { + + val appName = "Kamon-Play-Example" + val appVersion = "1.0-SNAPSHOT" + + val resolutionRepos = Seq( + "Typesafe repository" at "http://repo.typesafe.com/typesafe/releases/", + "Sonatype Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots", + "Sonatype Releases" at "https://oss.sonatype.org/content/repositories/releases", + "Kamon Repository Snapshots" at "http://snapshots.kamon.io" + ) + + val defaultSettings = Seq( + scalaVersion := "2.10.5", + resolvers ++= resolutionRepos, + scalacOptions := Seq( + "-encoding", + "utf8", + "-g:vars", + "-feature", + "-unchecked", + "-deprecation", + "-target:jvm-1.6", + "-language:postfixOps", + "-language:implicitConversions", + "-Xlog-reflective-calls" + )) + + val kamonVersion = "0.4.1-SNAPSHOT" + + val dependencies = Seq( + "io.kamon" %% "kamon-core" % kamonVersion, + "io.kamon" %% "kamon-play-24" % kamonVersion, + "io.kamon" %% "kamon-statsd" % kamonVersion, + "io.kamon" %% "kamon-log-reporter" % kamonVersion, + "io.kamon" %% "kamon-system-metrics" % kamonVersion, + "org.aspectj" % "aspectjweaver" % "1.8.6" + ) + + val main = Project(appName, file(".")).enablePlugins(play.PlayScala, SbtWeb) + .settings(libraryDependencies ++= dependencies) + .settings(defaultSettings: _*) +} diff --git a/kamon-examples/kamon-play-example-2.4.x/project/build.properties b/kamon-examples/kamon-play-example-2.4.x/project/build.properties new file mode 100644 index 00000000..a6e117b6 --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/project/build.properties @@ -0,0 +1 @@ +sbt.version=0.13.8 diff --git a/kamon-examples/kamon-play-example-2.4.x/project/plugins.sbt b/kamon-examples/kamon-play-example-2.4.x/project/plugins.sbt new file mode 100644 index 00000000..26bdf8cf --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/project/plugins.sbt @@ -0,0 +1,10 @@ +// Comment to get more information during initialization +logLevel := Level.Warn + +// The Typesafe repository +resolvers += "Typesafe repository" at "http://repo.typesafe.com/typesafe/releases/" + +// Use the Play sbt plugin for Play projects +addSbtPlugin("com.typesafe.play" % "sbt-plugin" % "2.4.2") + +addSbtPlugin("io.kamon" % "aspectj-play-24-runner" % "0.1.3") diff --git a/kamon-examples/kamon-play-example-2.4.x/public/images/favicon.png b/kamon-examples/kamon-play-example-2.4.x/public/images/favicon.png new file mode 100644 index 00000000..c7d92d2a Binary files /dev/null and b/kamon-examples/kamon-play-example-2.4.x/public/images/favicon.png differ diff --git a/kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings-white.png b/kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings-white.png new file mode 100644 index 00000000..3bf6484a Binary files /dev/null and b/kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings-white.png differ diff --git a/kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings.png b/kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings.png new file mode 100644 index 00000000..a9969993 Binary files /dev/null and b/kamon-examples/kamon-play-example-2.4.x/public/images/glyphicons-halflings.png differ diff --git a/kamon-examples/kamon-play-example-2.4.x/public/javascripts/jquery-1.9.0.min.js b/kamon-examples/kamon-play-example-2.4.x/public/javascripts/jquery-1.9.0.min.js new file mode 100644 index 00000000..50d1b22f --- /dev/null +++ b/kamon-examples/kamon-play-example-2.4.x/public/javascripts/jquery-1.9.0.min.js @@ -0,0 +1,4 @@ +/*! jQuery v1.9.0 | (c) 2005, 2012 jQuery Foundation, Inc. | jquery.org/license */(function(e,t){"use strict";function n(e){var t=e.length,n=st.type(e);return st.isWindow(e)?!1:1===e.nodeType&&t?!0:"array"===n||"function"!==n&&(0===t||"number"==typeof t&&t>0&&t-1 in e)}function r(e){var t=Tt[e]={};return st.each(e.match(lt)||[],function(e,n){t[n]=!0}),t}function i(e,n,r,i){if(st.acceptData(e)){var o,a,s=st.expando,u="string"==typeof n,l=e.nodeType,c=l?st.cache:e,f=l?e[s]:e[s]&&s;if(f&&c[f]&&(i||c[f].data)||!u||r!==t)return f||(l?e[s]=f=K.pop()||st.guid++:f=s),c[f]||(c[f]={},l||(c[f].toJSON=st.noop)),("object"==typeof n||"function"==typeof n)&&(i?c[f]=st.extend(c[f],n):c[f].data=st.extend(c[f].data,n)),o=c[f],i||(o.data||(o.data={}),o=o.data),r!==t&&(o[st.camelCase(n)]=r),u?(a=o[n],null==a&&(a=o[st.camelCase(n)])):a=o,a}}function o(e,t,n){if(st.acceptData(e)){var r,i,o,a=e.nodeType,u=a?st.cache:e,l=a?e[st.expando]:st.expando;if(u[l]){if(t&&(r=n?u[l]:u[l].data)){st.isArray(t)?t=t.concat(st.map(t,st.camelCase)):t in r?t=[t]:(t=st.camelCase(t),t=t in r?[t]:t.split(" "));for(i=0,o=t.length;o>i;i++)delete r[t[i]];if(!(n?s:st.isEmptyObject)(r))return}(n||(delete u[l].data,s(u[l])))&&(a?st.cleanData([e],!0):st.support.deleteExpando||u!=u.window?delete u[l]:u[l]=null)}}}function a(e,n,r){if(r===t&&1===e.nodeType){var i="data-"+n.replace(Nt,"-$1").toLowerCase();if(r=e.getAttribute(i),"string"==typeof r){try{r="true"===r?!0:"false"===r?!1:"null"===r?null:+r+""===r?+r:wt.test(r)?st.parseJSON(r):r}catch(o){}st.data(e,n,r)}else r=t}return r}function s(e){var t;for(t in e)if(("data"!==t||!st.isEmptyObject(e[t]))&&"toJSON"!==t)return!1;return!0}function u(){return!0}function l(){return!1}function c(e,t){do e=e[t];while(e&&1!==e.nodeType);return e}function f(e,t,n){if(t=t||0,st.isFunction(t))return st.grep(e,function(e,r){var i=!!t.call(e,r,e);return i===n});if(t.nodeType)return st.grep(e,function(e){return e===t===n});if("string"==typeof t){var r=st.grep(e,function(e){return 1===e.nodeType});if(Wt.test(t))return st.filter(t,r,!n);t=st.filter(t,r)}return st.grep(e,function(e){return st.inArray(e,t)>=0===n})}function p(e){var t=zt.split("|"),n=e.createDocumentFragment();if(n.createElement)for(;t.length;)n.createElement(t.pop());return n}function d(e,t){return e.getElementsByTagName(t)[0]||e.appendChild(e.ownerDocument.createElement(t))}function h(e){var t=e.getAttributeNode("type");return e.type=(t&&t.specified)+"/"+e.type,e}function g(e){var t=nn.exec(e.type);return t?e.type=t[1]:e.removeAttribute("type"),e}function m(e,t){for(var n,r=0;null!=(n=e[r]);r++)st._data(n,"globalEval",!t||st._data(t[r],"globalEval"))}function y(e,t){if(1===t.nodeType&&st.hasData(e)){var n,r,i,o=st._data(e),a=st._data(t,o),s=o.events;if(s){delete a.handle,a.events={};for(n in s)for(r=0,i=s[n].length;i>r;r++)st.event.add(t,n,s[n][r])}a.data&&(a.data=st.extend({},a.data))}}function v(e,t){var n,r,i;if(1===t.nodeType){if(n=t.nodeName.toLowerCase(),!st.support.noCloneEvent&&t[st.expando]){r=st._data(t);for(i in r.events)st.removeEvent(t,i,r.handle);t.removeAttribute(st.expando)}"script"===n&&t.text!==e.text?(h(t).text=e.text,g(t)):"object"===n?(t.parentNode&&(t.outerHTML=e.outerHTML),st.support.html5Clone&&e.innerHTML&&!st.trim(t.innerHTML)&&(t.innerHTML=e.innerHTML)):"input"===n&&Zt.test(e.type)?(t.defaultChecked=t.checked=e.checked,t.value!==e.value&&(t.value=e.value)):"option"===n?t.defaultSelected=t.selected=e.defaultSelected:("input"===n||"textarea"===n)&&(t.defaultValue=e.defaultValue)}}function b(e,n){var r,i,o=0,a=e.getElementsByTagName!==t?e.getElementsByTagName(n||"*"):e.querySelectorAll!==t?e.querySelectorAll(n||"*"):t;if(!a)for(a=[],r=e.childNodes||e;null!=(i=r[o]);o++)!n||st.nodeName(i,n)?a.push(i):st.merge(a,b(i,n));return n===t||n&&st.nodeName(e,n)?st.merge([e],a):a}function x(e){Zt.test(e.type)&&(e.defaultChecked=e.checked)}function T(e,t){if(t in e)return t;for(var n=t.charAt(0).toUpperCase()+t.slice(1),r=t,i=Nn.length;i--;)if(t=Nn[i]+n,t in e)return t;return r}function w(e,t){return e=t||e,"none"===st.css(e,"display")||!st.contains(e.ownerDocument,e)}function N(e,t){for(var n,r=[],i=0,o=e.length;o>i;i++)n=e[i],n.style&&(r[i]=st._data(n,"olddisplay"),t?(r[i]||"none"!==n.style.display||(n.style.display=""),""===n.style.display&&w(n)&&(r[i]=st._data(n,"olddisplay",S(n.nodeName)))):r[i]||w(n)||st._data(n,"olddisplay",st.css(n,"display")));for(i=0;o>i;i++)n=e[i],n.style&&(t&&"none"!==n.style.display&&""!==n.style.display||(n.style.display=t?r[i]||"":"none"));return e}function C(e,t,n){var r=mn.exec(t);return r?Math.max(0,r[1]-(n||0))+(r[2]||"px"):t}function k(e,t,n,r,i){for(var o=n===(r?"border":"content")?4:"width"===t?1:0,a=0;4>o;o+=2)"margin"===n&&(a+=st.css(e,n+wn[o],!0,i)),r?("content"===n&&(a-=st.css(e,"padding"+wn[o],!0,i)),"margin"!==n&&(a-=st.css(e,"border"+wn[o]+"Width",!0,i))):(a+=st.css(e,"padding"+wn[o],!0,i),"padding"!==n&&(a+=st.css(e,"border"+wn[o]+"Width",!0,i)));return a}function E(e,t,n){var r=!0,i="width"===t?e.offsetWidth:e.offsetHeight,o=ln(e),a=st.support.boxSizing&&"border-box"===st.css(e,"boxSizing",!1,o);if(0>=i||null==i){if(i=un(e,t,o),(0>i||null==i)&&(i=e.style[t]),yn.test(i))return i;r=a&&(st.support.boxSizingReliable||i===e.style[t]),i=parseFloat(i)||0}return i+k(e,t,n||(a?"border":"content"),r,o)+"px"}function S(e){var t=V,n=bn[e];return n||(n=A(e,t),"none"!==n&&n||(cn=(cn||st("