Skip to content

Commit

Permalink
basic json logger
Browse files Browse the repository at this point in the history
  • Loading branch information
barinek committed May 31, 2024
1 parent 933c3c8 commit a887c35
Show file tree
Hide file tree
Showing 14 changed files with 206 additions and 9 deletions.
1 change: 1 addition & 0 deletions applications/basic-server/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ val ktorVersion: String by project

dependencies {
implementation(project(":components:data-analyzer"))
implementation(project(":support:logging-support"))
implementation(project(":support:workflow-support"))

implementation("io.ktor:ktor-server-core-jvm:$ktorVersion")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,14 @@ import io.ktor.server.response.respond
import io.ktor.server.routing.Routing
import io.ktor.server.routing.get
import io.ktor.util.pipeline.PipelineContext
import org.slf4j.LoggerFactory
import java.util.*

private val logger = LoggerFactory.getLogger(object {}.javaClass.enclosingClass)

fun Application.module() {
logger.info("starting the app")

install(FreeMarker) {
templateLoader = ClassTemplateLoader(this::class.java.classLoader, "templates")
}
Expand Down
11 changes: 3 additions & 8 deletions applications/basic-server/src/main/resources/logback.xml
Original file line number Diff line number Diff line change
@@ -1,11 +1,6 @@
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{YYYY-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</pattern>
</encoder>
</appender>

<root level="INFO">
<appender-ref ref="STDOUT"/>
<appender name="basic" class="io.initialcapacity.logging.BasicJSONServiceProvider"/>
<root level="info">
<appender-ref ref="basic"/>
</root>
</configuration>
2 changes: 2 additions & 0 deletions applications/data-analyzer-server/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ group = "io.initialcapacity.analyzer"
val ktorVersion: String by project

dependencies {
implementation("org.slf4j:slf4j-simple:2.0.7")

implementation(project(":components:data-analyzer"))
implementation(project(":support:workflow-support"))

Expand Down
2 changes: 2 additions & 0 deletions applications/data-collector-server/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ group = "io.initialcapacity.collector"
val ktorVersion: String by project

dependencies {
implementation("org.slf4j:slf4j-simple:2.0.7")

implementation(project(":components:data-collector"))
implementation(project(":support:workflow-support"))

Expand Down
1 change: 0 additions & 1 deletion build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ subprojects {

dependencies {
implementation("org.slf4j:slf4j-api:2.0.7")
implementation("org.slf4j:slf4j-simple:2.0.7")

testImplementation(kotlin("test-junit"))
}
Expand Down
1 change: 1 addition & 0 deletions settings.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -8,5 +8,6 @@ include(
"components:data-collector",
"components:data-analyzer",

"support:logging-support",
"support:workflow-support"
)
9 changes: 9 additions & 0 deletions support/logging-support/build.gradle.kts
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
plugins {
id("org.jetbrains.kotlin.plugin.serialization")
}

dependencies {
implementation("org.slf4j:slf4j-api:2.0.7")
implementation("org.jetbrains.kotlinx:kotlinx-serialization-json:1.5.1")
implementation("org.jetbrains.kotlinx:kotlinx-datetime:0.6.0-RC.2")
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
package io.initialcapacity.logging

import kotlinx.serialization.Serializable
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
import org.slf4j.Marker
import org.slf4j.event.Level
import org.slf4j.helpers.LegacyAbstractLogger
import org.slf4j.helpers.MessageFormatter
import org.slf4j.spi.LocationAwareLogger
import java.time.Instant
import java.time.ZoneId
import java.time.format.DateTimeFormatter


class BasicJSONLogger(val desiredName: String) : LegacyAbstractLogger() {
init {
this.name = desiredName
}

override fun isTraceEnabled(): Boolean {
return isLevelEnabled(LocationAwareLogger.TRACE_INT);
}

override fun isDebugEnabled(): Boolean {
return isLevelEnabled(LocationAwareLogger.DEBUG_INT);
}

override fun isInfoEnabled(): Boolean {
return isLevelEnabled(LocationAwareLogger.INFO_INT);
}

override fun isWarnEnabled(): Boolean {
return isLevelEnabled(LocationAwareLogger.WARN_INT);
}

override fun isErrorEnabled(): Boolean {
return isLevelEnabled(LocationAwareLogger.ERROR_INT);
}

override fun getFullyQualifiedCallerName(): String? {
return null
}

@Serializable
data class Entry(
val time: String,
val threadName: String,
val severity: String,
val loggerName: String,
val message: String
)

private val formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ssZ")

@Synchronized
override fun handleNormalizedLoggingCall(
level: Level?,
marker: Marker?,
messagePattern: String?,
arguments: Array<out Any>?,
throwable: Throwable?
) {

val time = Instant.now().atZone(ZoneId.of("UTC")).format(formatter)
val threadName = Thread.currentThread().name
val severity = renderLevel(level!!.toInt())
val loggerName = name
val message = MessageFormatter.basicArrayFormat(messagePattern, arguments)

// %r [%t] %level %logger - %m%n
// val builder = StringBuilder(32)
// builder.append(time);
// builder.append(" ")
// builder.append("[")
// builder.append(threadName)
// builder.append("] ")
// builder.append(levelString)
// builder.append(" ")
// builder.append(loggetName).append(" - ");
// builder.append(message);
// val entry = builder.toString()

val entry = Entry(time, threadName, severity, loggerName, message)
val encodeToString = Json.encodeToString(entry)

System.err.println(encodeToString)
throwable?.printStackTrace()
System.err.flush()
}

private fun isLevelEnabled(level: Int): Boolean {
return (level >= LocationAwareLogger.INFO_INT)
}

private fun renderLevel(level: Int): String {
when (level) {
LocationAwareLogger.TRACE_INT -> return "TRACE"
LocationAwareLogger.DEBUG_INT -> return "DEBUG"
LocationAwareLogger.INFO_INT -> return "INFO"
LocationAwareLogger.WARN_INT -> return "WARN"
LocationAwareLogger.ERROR_INT -> return "ERROR"
}
throw IllegalStateException("Unrecognized level [$level]")
}

private val json = Json {
isLenient = true
ignoreUnknownKeys = true
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package io.initialcapacity.logging

import org.slf4j.ILoggerFactory
import org.slf4j.Logger
import java.util.concurrent.ConcurrentHashMap


class BasicJSONLoggerFactory : ILoggerFactory {
private var loggerMap = ConcurrentHashMap<String, Logger>();

override fun getLogger(name: String): Logger {
return loggerMap.computeIfAbsent(name) {
BasicJSONLogger(it)
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package io.initialcapacity.logging

import org.slf4j.ILoggerFactory
import org.slf4j.IMarkerFactory
import org.slf4j.helpers.BasicMarkerFactory
import org.slf4j.helpers.NOPMDCAdapter
import org.slf4j.spi.MDCAdapter
import org.slf4j.spi.SLF4JServiceProvider


class BasicJSONServiceProvider : SLF4JServiceProvider {
var REQUESTED_API_VERSION: String = "2.0.99"

private var loggerFactory = BasicJSONLoggerFactory()
private var markerFactory = BasicMarkerFactory()
private var mdcAdapter = NOPMDCAdapter()

override fun getLoggerFactory(): ILoggerFactory {
return loggerFactory
}

override fun getMarkerFactory(): IMarkerFactory {
return markerFactory
}

override fun getMDCAdapter(): MDCAdapter {
return mdcAdapter
}

override fun getRequestedApiVersion(): String {
return REQUESTED_API_VERSION
}

override fun initialize() {
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
io.initialcapacity.logging.BasicJSONServiceProvider
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package test.initialcapacity.logging

import org.slf4j.LoggerFactory
import kotlin.test.Test

class BasicJSONServiceProviderTest {

@Test
fun test1() {
val logger = LoggerFactory.getLogger("test1")
logger.info("Hello world.")
}
}
6 changes: 6 additions & 0 deletions support/logging-support/src/test/resources/logback.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
<configuration>
<appender name="basic" class="io.initialcapacity.logging.BasicJSONServiceProvider"/>
<root level="info">
<appender-ref ref="basic"/>
</root>
</configuration>

0 comments on commit a887c35

Please sign in to comment.