Skip to content

Commit

Permalink
Apache Log4j new version support (#88)
Browse files Browse the repository at this point in the history
* [INSTRUMENTATION] Apache-log4j 3.0.0-alpha1 to latest (new version released)

* [TEST] Added unit test cases for Apache-log4j 3.0.0-alpha1 to latest (new version released)

* Updated Changelog.md
  • Loading branch information
monu-k2io authored Aug 16, 2023
1 parent 8994065 commit 2cb3b36
Show file tree
Hide file tree
Showing 7 changed files with 249 additions and 0 deletions.
1 change: 1 addition & 0 deletions Changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [1.0.5-public-preview] - To Be Decided
### Changes
- [INSTRUMENTATION] Support for Apache log4j 3.0.0-alpha1 (new version released on 21 June 2023)

## [1.0.4-public-preview] - 2023-06-20
### Changes
Expand Down
25 changes: 25 additions & 0 deletions instrumentation-security/apache-log4j-3.0.0/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
jar {
manifest { attributes 'Implementation-Title': 'com.newrelic.instrumentation.security.apache-log4j' }
}

dependencies {
implementation(project(":newrelic-security-api"))
implementation("com.newrelic.agent.java:newrelic-api:${nrAPIVersion}")
implementation("com.newrelic.agent.java:newrelic-weaver-api:${nrAPIVersion}")
implementation("org.apache.logging.log4j:log4j-core:3.0.0-alpha1")
}

verifyInstrumentation {
passes("org.apache.logging.log4j:log4j-core:[3.0.0-alpha1,)")
}

site {
title 'Log4j'
type 'Framework'
}

java {
toolchain {
languageVersion.set(JavaLanguageVersion.of(11))
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package org.apache.logging.log4j.core.lookup;

import com.newrelic.api.agent.security.NewRelicSecurity;
import com.newrelic.api.agent.security.schema.JDBCVendor;
import com.newrelic.api.agent.security.schema.helper.Log4JStrSubstitutor;
import com.newrelic.api.agent.security.utils.UserDataTranslationHelper;
import com.newrelic.api.agent.weaver.MatchType;
import com.newrelic.api.agent.weaver.Weave;
import com.newrelic.api.agent.weaver.Weaver;
import org.apache.logging.log4j.core.LogEvent;

@Weave(type = MatchType.BaseClass, originalName = "org.apache.logging.log4j.core.lookup.StrSubstitutor")
public class StrSubstitutor_Instrumentation {

protected String resolveVariable(final LogEvent event, final String variableName, final StringBuilder buf,
final int startPos, final int endPos) {
if (NewRelicSecurity.isHookProcessingActive() && !NewRelicSecurity.getAgent().getSecurityMetaData().getRequest().isEmpty()) {
Log4JStrSubstitutor substitutor = new Log4JStrSubstitutor(variableName, buf, startPos, endPos);
NewRelicSecurity.getAgent().getSecurityMetaData().addCustomAttribute(UserDataTranslationHelper.getAttributeName(Log4JStrSubstitutor.class.getName()), substitutor);
}
return Weaver.callOriginal();
}


}
Original file line number Diff line number Diff line change
@@ -0,0 +1,175 @@
package com.nr.instrumentation.security.log4j;

import com.newrelic.agent.security.introspec.InstrumentationTestConfig;
import com.newrelic.agent.security.introspec.SecurityInstrumentationTestRunner;
import com.newrelic.agent.security.introspec.SecurityIntrospector;
import com.newrelic.api.agent.security.schema.helper.Log4JStrSubstitutor;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.lookup.StrSubstitutor;
import org.junit.Assert;
import org.junit.BeforeClass;
import org.junit.FixMethodOrder;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.MethodSorters;

import java.util.HashMap;
import java.util.Map;
import java.util.Properties;

@RunWith(SecurityInstrumentationTestRunner.class)
@FixMethodOrder(MethodSorters.NAME_ASCENDING)
@InstrumentationTestConfig(includePrefixes = "org.apache.logging.log4j.core", configName = "application_logging_context_data_enabled.yml")
public class Log4jTest {
private final Logger logger = LogManager.getLogger(Log4jTest.class);
private static final Map<String, String> MAP = new HashMap<>();
private final String SOURCE = " ${Key} ";
private final Log4JStrSubstitutor EXPECTED = new Log4JStrSubstitutor("Key", new StringBuilder(" value "), 1, 7);

@BeforeClass
public static void setLogLevel() {
MAP.put("Key", "value");
}

@Test
public void testResolveVariable() {
Properties info = new Properties();
info.setProperty("Key", "value");
String str = StrSubstitutor.replace(SOURCE, info);
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable1() {
String str = StrSubstitutor.replace(SOURCE, MAP);
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable2() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(SOURCE);
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actaul = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actaul);
}

@Test
public void testResolveVariable3() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(SOURCE, 0, SOURCE.length());
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable4() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(SOURCE.toCharArray());
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable5() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(SOURCE.toCharArray(), 0, SOURCE.length());
logger.error(str);


SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable6() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(new StringBuffer(SOURCE));
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable7() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(new StringBuffer(SOURCE), 0, SOURCE.length());
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable8() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(new StringBuilder(SOURCE));
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable9() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
String str = substitutor.replace(new StringBuilder(SOURCE), 0, SOURCE.length());
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable10() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
boolean str = substitutor.replaceIn(new StringBuilder(SOURCE));
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}

@Test
public void testResolveVariable11() {
StrSubstitutor substitutor = new StrSubstitutor(MAP);
boolean str = substitutor.replaceIn(new StringBuilder(SOURCE), 1, SOURCE.length()-1);
logger.error(str);

SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector();
Log4JStrSubstitutor actual = introspector.getLog4JStrSubstitutor();
assertLog4JStrSubstitutor(EXPECTED, actual);
}


private void assertLog4JStrSubstitutor(Log4JStrSubstitutor expected, Log4JStrSubstitutor actual) {
Assert.assertEquals("Invalid variable name", expected.getVariableName(), actual.getVariableName());
Assert.assertEquals("Invalid buffer value", expected.getBuf().toString(), actual.getBuf().toString());
Assert.assertEquals("Wrong Start position of variable", expected.getStartPos(), actual.getStartPos());
Assert.assertEquals("Wrong end position of variable", expected.getEndPos(), actual.getEndPos());
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
common: &default_settings
application_logging:
enabled: true
forwarding:
enabled: true
max_samples_stored: 10000
context_data:
enabled: true
metrics:
enabled: true
local_decorating:
enabled: false
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
common: &default_settings
application_logging:
enabled: true
forwarding:
enabled: true
max_samples_stored: 10000
metrics:
enabled: true
local_decorating:
enabled: false
1 change: 1 addition & 0 deletions settings.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@ include 'instrumentation:graalvm-jsinjection-19.0.0'
include 'instrumentation:graalvm-jsinjection-22.0.0'
include 'instrumentation:apache-log4j-2.0'
include 'instrumentation:apache-log4j-2.17.2'
include 'instrumentation:apache-log4j-3.0.0'
include 'instrumentation:saxpath'
include 'instrumentation:javax-xpath'
include 'instrumentation:akka-http-core-2.11_10.0.11'
Expand Down

0 comments on commit 2cb3b36

Please sign in to comment.