I am newbie to implement log4j2 with my aws java lambda cloud watch. I need custom log instead of cloud watch logs. I am uploading a csv of large size record using step function.So the built in cloud watch logs the same thing repeatedly. So I am planning to add log4j2 with my java lambda. For this I added below dependency in my pom.xml
<dependency>
<groupId>com.amazonaws</groupId>
<artifactId>aws-lambda-java-log4j2</artifactId>
<version>1.0.0</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.8.2</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
<version>2.8.2</version>
</dependency>
Then added the log4j2.xml under src/main/resources. The log4j2.xml is like below
<?xml version="1.0" encoding="UTF-8"?>
<Configuration packages="com.amazonaws.services.lambda.runtime.log4j2.LambdaAppender">
<Appenders>
<Lambda name="Lambda">
<PatternLayout>
<pattern>%d{yyyy-MM-dd HH:mm:ss} %X{AWSRequestId} %-5p %c{1}:%L - %m%n</pattern>
</PatternLayout>
</Lambda>
</Appenders>
<Loggers>
<Root level="debug">
<AppenderRef ref="Lambda" />
</Root>
</Loggers>
</Configuration>
After that to check the log i have created one aws java lambda project and my code looks like below.
package com.amazonaws.lambda.demo;
import com.amazonaws.services.lambda.runtime.Context;
import com.amazonaws.services.lambda.runtime.RequestHandler;
import com.amazonaws.services.lambda.runtime.events.S3Event;
import com.amazonaws.services.s3.AmazonS3;
import com.amazonaws.services.s3.AmazonS3ClientBuilder;
import com.amazonaws.services.s3.model.GetObjectRequest;
import com.amazonaws.services.s3.model.S3Object;
import com.amazonaws.services.stepfunctions.AWSStepFunctions;
import com.amazonaws.services.stepfunctions.AWSStepFunctionsClientBuilder;
import com.amazonaws.services.stepfunctions.model.StartExecutionRequest;
import com.amazonaws.services.lambda.runtime.Context;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
public class log4jTest implements RequestHandler<S3Event, String> {
static final Logger logger = LogManager.getLogger(log4jTest.class);
private AmazonS3 s3 = AmazonS3ClientBuilder.standard().build();
public log4jTest() {}
log4jTest(AmazonS3 s3) {
this.s3 = s3;
}
@Override
public String handleRequest(S3Event event, Context context) {
String bucket = event.getRecords().get(0).getS3().getBucket().getName();
String key = event.getRecords().get(0).getS3().getObject().getKey();
try {
for(int i=0;i<10;i++)
{
if(i==10)
{
logger.error("log data Error");
}
}
} catch (Exception e) {
context.getLogger().log(String.format(
"Error getting object %s from bucket %s. Make sure they exist and"
+ " your bucket is in the same region as this function.", key, bucket));
}
return null;
}
}
According to the aws document Logging (Java). Everything I did as the doc says. But when I am run the lambda I am getting an error like below
ERROR StatusLogger No log4j2 configuration file found. Using default configuration: logging only errors to the console. Set system property 'org.apache.logging.log4j.simplelog.StatusLogger.level' to TRACE to show Log4j2 internal initialization logging.
I am checking the log in lambda -> Monitoring -> jump to logs [Screen shot given below]
I googled and went through below sites.
No log4j2 configuration file found. Using default configuration: logging only errors to the console
No log4j2 configuration file found. Using default configuration: logging only errors to the console
But I dont know I can't fix this error anyway. Please anyone can help me on this. It would be really grateful if u can do this.
Thanks in advance
I found I did not have any luck placing my log4j2.xml file at either src/main/resources or at src/main/resources/path/to/my/Lambda/log4j2.xml. So I did a little digging. In my case, Lambda deploys my handler with a classpath whose first entry is a folder /var/task. The class files are rooted directly at /var/task - but the resource files are placed in /var/task/resources - so Log4J2 cannot find log4j2.xml in the classpath. The solution for me was to use the log4j.configurationFile property to specify the location of the file within the resources folder:
static {
// System.setProperty("org.apache.logging.log4j.simplelog.StatusLogger.level","TRACE");
System.setProperty("java.util.logging.manager", "org.apache.logging.log4j.jul.LogManager");
System.setProperty("log4j.configurationFile", "resources/lambda-log4j2.xml");
}
I also renamed the file "lambda-log4j2.xml" - to make sure it was reading my file, during debugging this... This static block is at the top of my handler class.