Skip to content

Commit

Permalink
Add support for Logback 1.3.x and 1.4.x (#2820)
Browse files Browse the repository at this point in the history
  • Loading branch information
joschi committed Sep 4, 2022
1 parent 6c6f6b7 commit cf3cb93
Show file tree
Hide file tree
Showing 7 changed files with 641 additions and 0 deletions.
88 changes: 88 additions & 0 deletions metrics-logback13/pom.xml
@@ -0,0 +1,88 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<parent>
<groupId>io.dropwizard.metrics</groupId>
<artifactId>metrics-parent</artifactId>
<version>4.2.12-SNAPSHOT</version>
</parent>

<artifactId>metrics-logback13</artifactId>
<name>Metrics Integration for Logback 1.3.x</name>
<packaging>bundle</packaging>
<description>
An instrumented appender for Logback 1.3.x.
</description>

<properties>
<javaModuleName>io.dropwizard.metrics.logback14</javaModuleName>
<logback13.version>1.3.0</logback13.version>
<slf4j.version>2.0.0</slf4j.version>
</properties>

<dependencyManagement>
<dependencies>
<dependency>
<groupId>io.dropwizard.metrics</groupId>
<artifactId>metrics-bom</artifactId>
<version>${project.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>

<dependencies>
<dependency>
<groupId>io.dropwizard.metrics</groupId>
<artifactId>metrics-core</artifactId>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>${logback13.version}</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>${logback13.version}</version>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.assertj</groupId>
<artifactId>assertj-core</artifactId>
<version>${assertj.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-core</artifactId>
<version>${mockito.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>${slf4j.version}</version>
<scope>test</scope>
</dependency>
</dependencies>
</project>
@@ -0,0 +1,91 @@
package io.dropwizard.metrics.logback13;

import ch.qos.logback.classic.Level;
import ch.qos.logback.classic.spi.ILoggingEvent;
import ch.qos.logback.core.Appender;
import ch.qos.logback.core.UnsynchronizedAppenderBase;
import com.codahale.metrics.Meter;
import com.codahale.metrics.MetricRegistry;
import com.codahale.metrics.SharedMetricRegistries;

import static com.codahale.metrics.MetricRegistry.name;

/**
* A Logback {@link Appender} which has six meters, one for each logging level and one for the total
* number of statements being logged. The meter names are the logging level names appended to the
* name of the appender.
*/
public class InstrumentedAppender extends UnsynchronizedAppenderBase<ILoggingEvent> {
private final MetricRegistry registry;
public static final String DEFAULT_REGISTRY = "logback-metrics";
public static final String REGISTRY_PROPERTY_NAME = "metrics.logback.registry";

private Meter all;
private Meter trace;
private Meter debug;
private Meter info;
private Meter warn;
private Meter error;


/**
* Create a new instrumented appender using the given registry name.
*/
public InstrumentedAppender() {
this(System.getProperty(REGISTRY_PROPERTY_NAME, DEFAULT_REGISTRY));
}

/**
* Create a new instrumented appender using the given registry name.
*
* @param registryName the name of the registry in {@link SharedMetricRegistries}
*/
public InstrumentedAppender(String registryName) {
this(SharedMetricRegistries.getOrCreate(registryName));
}

/**
* Create a new instrumented appender using the given registry.
*
* @param registry the metric registry
*/
public InstrumentedAppender(MetricRegistry registry) {
this.registry = registry;
setName(Appender.class.getName());
}

@Override
public void start() {
this.all = registry.meter(name(getName(), "all"));
this.trace = registry.meter(name(getName(), "trace"));
this.debug = registry.meter(name(getName(), "debug"));
this.info = registry.meter(name(getName(), "info"));
this.warn = registry.meter(name(getName(), "warn"));
this.error = registry.meter(name(getName(), "error"));
super.start();
}

@Override
protected void append(ILoggingEvent event) {
all.mark();
switch (event.getLevel().toInt()) {
case Level.TRACE_INT:
trace.mark();
break;
case Level.DEBUG_INT:
debug.mark();
break;
case Level.INFO_INT:
info.mark();
break;
case Level.WARN_INT:
warn.mark();
break;
case Level.ERROR_INT:
error.mark();
break;
default:
break;
}
}
}
@@ -0,0 +1,142 @@
package io.dropwizard.metrics.logback13;

import ch.qos.logback.classic.Level;
import ch.qos.logback.classic.spi.ILoggingEvent;
import com.codahale.metrics.MetricRegistry;
import com.codahale.metrics.SharedMetricRegistries;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

public class InstrumentedAppenderTest {

public static final String METRIC_NAME_PREFIX = "ch.qos.logback.core.Appender";

private final MetricRegistry registry = new MetricRegistry();
private final InstrumentedAppender appender = new InstrumentedAppender(registry);
private final ILoggingEvent event = mock(ILoggingEvent.class);

@Before
public void setUp() {
appender.start();
}

@After
public void tearDown() {
SharedMetricRegistries.clear();
}

@Test
public void metersTraceEvents() {
when(event.getLevel()).thenReturn(Level.TRACE);

appender.doAppend(event);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".all").getCount())
.isEqualTo(1);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".trace").getCount())
.isEqualTo(1);
}

@Test
public void metersDebugEvents() {
when(event.getLevel()).thenReturn(Level.DEBUG);

appender.doAppend(event);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".all").getCount())
.isEqualTo(1);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".debug").getCount())
.isEqualTo(1);
}

@Test
public void metersInfoEvents() {
when(event.getLevel()).thenReturn(Level.INFO);

appender.doAppend(event);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".all").getCount())
.isEqualTo(1);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".info").getCount())
.isEqualTo(1);
}

@Test
public void metersWarnEvents() {
when(event.getLevel()).thenReturn(Level.WARN);

appender.doAppend(event);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".all").getCount())
.isEqualTo(1);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".warn").getCount())
.isEqualTo(1);
}

@Test
public void metersErrorEvents() {
when(event.getLevel()).thenReturn(Level.ERROR);

appender.doAppend(event);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".all").getCount())
.isEqualTo(1);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".error").getCount())
.isEqualTo(1);
}

@Test
public void usesSharedRegistries() {

String registryName = "registry";

SharedMetricRegistries.add(registryName, registry);
final InstrumentedAppender shared = new InstrumentedAppender(registryName);
shared.start();

when(event.getLevel()).thenReturn(Level.INFO);

shared.doAppend(event);

assertThat(registry.meter(METRIC_NAME_PREFIX + ".info").getCount())
.isEqualTo(1);
}

@Test
public void usesDefaultRegistry() {
SharedMetricRegistries.add(InstrumentedAppender.DEFAULT_REGISTRY, registry);
final InstrumentedAppender shared = new InstrumentedAppender();
shared.start();
when(event.getLevel()).thenReturn(Level.INFO);
shared.doAppend(event);

assertThat(SharedMetricRegistries.names()).contains(InstrumentedAppender.DEFAULT_REGISTRY);
assertThat(registry.meter(METRIC_NAME_PREFIX + ".info").getCount())
.isEqualTo(1);
}

@Test
public void usesRegistryFromProperty() {
SharedMetricRegistries.add("something_else", registry);
System.setProperty(InstrumentedAppender.REGISTRY_PROPERTY_NAME, "something_else");
final InstrumentedAppender shared = new InstrumentedAppender();
shared.start();
when(event.getLevel()).thenReturn(Level.INFO);
shared.doAppend(event);

assertThat(SharedMetricRegistries.names()).contains("something_else");
assertThat(registry.meter(METRIC_NAME_PREFIX + ".info").getCount())
.isEqualTo(1);
}

}

0 comments on commit cf3cb93

Please sign in to comment.