Skip to content

Commit 67e8b78

Browse files
pankajagrawal16Pankaj Agrawal
and
Pankaj Agrawal
authored
feat: ability to override object mapper used for logging event (#302)
Co-authored-by: Pankaj Agrawal <[email protected]>
1 parent cedac3f commit 67e8b78

File tree

5 files changed

+89
-4
lines changed

5 files changed

+89
-4
lines changed

powertools-logging/src/main/java/software/amazon/lambda/powertools/logging/LoggingUtils.java

+16
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515

1616
import java.util.Map;
1717

18+
import com.fasterxml.jackson.databind.ObjectMapper;
1819
import org.apache.logging.log4j.ThreadContext;
1920

2021
/**
@@ -23,6 +24,7 @@
2324
* {@see Logging}
2425
*/
2526
public final class LoggingUtils {
27+
private static ObjectMapper objectMapper = new ObjectMapper();
2628

2729
private LoggingUtils() {
2830
}
@@ -48,4 +50,18 @@ public static void appendKey(String key, String value) {
4850
public static void appendKeys(Map<String, String> customKeys) {
4951
ThreadContext.putAll(customKeys);
5052
}
53+
54+
/**
55+
* Sets the instance of ObjectMapper object which is used for serialising event when
56+
* {@code @Logging(logEvent = true)}.
57+
*
58+
* @param objectMapper Custom implementation of object mapper to be used for logging serialised event
59+
*/
60+
public static void defaultObjectMapper(ObjectMapper objectMapper) {
61+
LoggingUtils.objectMapper = objectMapper;
62+
}
63+
64+
public static ObjectMapper objectMapper() {
65+
return objectMapper;
66+
}
5167
}

powertools-logging/src/main/java/software/amazon/lambda/powertools/logging/internal/LambdaLoggingAspect.java

+3-4
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@
2424
import java.util.Random;
2525

2626
import com.fasterxml.jackson.core.JsonProcessingException;
27-
import com.fasterxml.jackson.databind.ObjectMapper;
2827
import org.apache.logging.log4j.Level;
2928
import org.apache.logging.log4j.LogManager;
3029
import org.apache.logging.log4j.Logger;
@@ -50,12 +49,12 @@
5049
import static software.amazon.lambda.powertools.core.internal.LambdaHandlerProcessor.serviceName;
5150
import static software.amazon.lambda.powertools.logging.LoggingUtils.appendKey;
5251
import static software.amazon.lambda.powertools.logging.LoggingUtils.appendKeys;
52+
import static software.amazon.lambda.powertools.logging.LoggingUtils.objectMapper;
5353
import static software.amazon.lambda.powertools.logging.internal.SystemWrapper.getenv;
5454

5555
@Aspect
5656
public final class LambdaLoggingAspect {
5757
private static final Logger LOG = LogManager.getLogger(LambdaLoggingAspect.class);
58-
private static final ObjectMapper MAPPER = new ObjectMapper();
5958
private static final Random SAMPLER = new Random();
6059

6160
private static final String LOG_LEVEL = System.getenv("LOG_LEVEL");
@@ -176,7 +175,7 @@ private Object[] logFromInputStream(final ProceedingJoinPoint pjp) {
176175

177176
Logger log = logger(pjp);
178177

179-
asJson(pjp, MAPPER.readValue(bytes, Map.class))
178+
asJson(pjp, objectMapper().readValue(bytes, Map.class))
180179
.ifPresent(log::info);
181180

182181
} catch (IOException e) {
@@ -190,7 +189,7 @@ private Object[] logFromInputStream(final ProceedingJoinPoint pjp) {
190189
private Optional<String> asJson(final ProceedingJoinPoint pjp,
191190
final Object target) {
192191
try {
193-
return ofNullable(MAPPER.writeValueAsString(target));
192+
return ofNullable(objectMapper().writeValueAsString(target));
194193
} catch (JsonProcessingException e) {
195194
logger(pjp).error("Failed logging event of type {}", target.getClass(), e);
196195
return empty();
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
package software.amazon.lambda.powertools.logging.handlers;
2+
3+
import java.io.IOException;
4+
5+
import com.amazonaws.services.lambda.runtime.Context;
6+
import com.amazonaws.services.lambda.runtime.RequestHandler;
7+
import com.amazonaws.services.lambda.runtime.events.models.s3.S3EventNotification;
8+
import com.fasterxml.jackson.core.JsonGenerator;
9+
import com.fasterxml.jackson.databind.ObjectMapper;
10+
import com.fasterxml.jackson.databind.SerializerProvider;
11+
import com.fasterxml.jackson.databind.module.SimpleModule;
12+
import com.fasterxml.jackson.databind.ser.std.StdSerializer;
13+
import software.amazon.lambda.powertools.logging.Logging;
14+
import software.amazon.lambda.powertools.logging.LoggingUtils;
15+
16+
public class PowerToolLogEventEnabledWithCustomMapper implements RequestHandler<S3EventNotification, Object> {
17+
18+
static {
19+
ObjectMapper objectMapper = new ObjectMapper();
20+
SimpleModule module = new SimpleModule();
21+
module.addSerializer(S3EventNotification.class, new S3EventNotificationSerializer());
22+
objectMapper.registerModule(module);
23+
LoggingUtils.defaultObjectMapper(objectMapper);
24+
}
25+
26+
@Logging(logEvent = true)
27+
@Override
28+
public Object handleRequest(S3EventNotification input, Context context) {
29+
return null;
30+
}
31+
32+
static class S3EventNotificationSerializer extends StdSerializer<S3EventNotification> {
33+
34+
public S3EventNotificationSerializer() {
35+
this(null);
36+
}
37+
38+
public S3EventNotificationSerializer(Class<S3EventNotification> t) {
39+
super(t);
40+
}
41+
42+
@Override
43+
public void serialize(S3EventNotification o, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException {
44+
jsonGenerator.writeStartObject();
45+
jsonGenerator.writeStringField("eventSource", o.getRecords().get(0).getEventSource());
46+
jsonGenerator.writeEndObject();
47+
}
48+
}
49+
}

powertools-logging/src/test/java/software/amazon/lambda/powertools/logging/internal/LambdaLoggingAspectTest.java

+18
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@
4747
import software.amazon.lambda.powertools.logging.handlers.PowerToolDisabledForStream;
4848
import software.amazon.lambda.powertools.logging.handlers.PowerToolLogEventEnabled;
4949
import software.amazon.lambda.powertools.logging.handlers.PowerToolLogEventEnabledForStream;
50+
import software.amazon.lambda.powertools.logging.handlers.PowerToolLogEventEnabledWithCustomMapper;
5051

5152
import static com.amazonaws.services.lambda.runtime.events.models.s3.S3EventNotification.RequestParametersEntity;
5253
import static com.amazonaws.services.lambda.runtime.events.models.s3.S3EventNotification.ResponseElementsEntity;
@@ -183,6 +184,23 @@ void shouldLogEventForHandler() throws IOException, JSONException {
183184
assertEquals(expectEvent, event, false);
184185
}
185186

187+
@Test
188+
void shouldLogEventForHandlerWithOverriddenObjectMapper() throws IOException, JSONException {
189+
RequestHandler<S3EventNotification, Object> handler = new PowerToolLogEventEnabledWithCustomMapper();
190+
S3EventNotification s3EventNotification = s3EventNotification();
191+
192+
handler.handleRequest(s3EventNotification, context);
193+
194+
Map<String, Object> log = parseToMap(Files.lines(Paths.get("target/logfile.json")).collect(joining()));
195+
196+
String event = (String) log.get("message");
197+
198+
String expectEvent = new BufferedReader(new InputStreamReader(this.getClass().getResourceAsStream("/customizedLogEvent.json")))
199+
.lines().collect(joining("\n"));
200+
201+
assertEquals(expectEvent, event, false);
202+
}
203+
186204
@Test
187205
void shouldLogEventForStreamAndLambdaStreamIsValid() throws IOException, JSONException {
188206
requestStreamHandler = new PowerToolLogEventEnabledForStream();
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"eventSource": "aws:s3"
3+
}

0 commit comments

Comments
 (0)