8 Replies Latest reply on Mar 15, 2017 10:57 AM by jamezp

    JBoss Log4j LoggingEvent getThrowableInformation never returns null

    mclough

      I am implementing Microsoft Azure Application Insights logging following these instructions for Log4j 1.2:

      https://docs.microsoft.com/en-gb/azure/application-insights/app-insights-java-trace-logs

       

      I have created a module and added ApplicationInsights to my Wildfly 10 standalone.xml like this:

      <custom-handler name="APPLICATION_INSIGHTS" class="com.microsoft.applicationinsights.log4j.v1_2.ApplicationInsightsAppender" module="com.microsoft.applicationinsights"/>

      The purpose of Application Insights logging is to add log messages (as traces) or exceptions into the Application Insights monitoring application. However every log message appears as an exception instead of a trace.

       

      This is because in the Application Insights Appender code, (available here: https://github.com/Microsoft/ApplicationInsights-Java)  in the ApplicationInsightsLogEvent class is an isException method:

          public boolean isException() {

              return this.loggingEvent.getThrowableInformation() != null;

          }

      So the appender decides if the logging event is a message or exception depending on if the throwable information is null or not.

       

      In the standard implementation of Log4j LoggingEvent, (https://github.com/apache/log4j/blob/v1_2-branch/src/main/java/org/apache/log4j/spi/LoggingEvent.java), the getThrowableInformation is implemented as:

          public ThrowableInformation getThrowableInformation() {

              return throwableInfo;

          }

      This returns null if the event is for a non-exception message.

       

      JBoss Log4j LoggingEvent from https://github.com/jboss-logging/log4j-jboss-logmanager/blob/master/src/main/java/org/apache/log4j/spi/LoggingEvent.java is documented as "Our LoggingEvent class which is designed to look and act just like log4j's".

      The getThrowableInformation is implemented as:

          public ThrowableInformation getThrowableInformation() {

              if (cachedThrowableInformation == null) {

                  cachedThrowableInformation = new

                       ThrowableInformation(logRecord.getThrown(), logger);

              }

              return cachedThrowableInformation;

          }

      This method never returns null, even if the event is a normal log message. This does not "look and act" like Log4j, and it causes Application Insights to see every message as an exception.

       

      I think that getThrowableInformation should return null if the event is not an exception, i.e. if logRecord.getThrown is null.

       

      How can this be resolved?

      Thanks

        • 1. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
          jamezp

          I would agree this is a bug in the log4j-jboss-logmanager. It should use the same behavior that log4j uses. I've created a PR to fix that Null should be returned from the LoggingEvent.getThrowableInformation… by jamezp · Pull Request #13 · jboss-logging/log4… .

           

          If I get a chance I might see if they'll accept a PR for a JUL handler too. I'm somewhat surprised there isn't one for JUL by default.

           

          --

          James R. Perkins

          1 of 1 people found this helpful
          • 2. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
            mclough

            Thank you for your prompt and efficient reply.

             

            --

            Martin Clough

            • 3. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
              okelet

              Hi, I am trying to configure Application Insights too, but I am not able to do it. I have the same configuration than you in the standalone.xml file, but I get this error:

               

              2017/03/10 13:01:09,089 ERROR [org.jboss.as.controller.management-operation] (Controller Boot Thread) WFLYCTL0013: Operación ("add") falló - dirección: ([
                  ("subsystem" => "logging"),
                  ("custom-handler" => "ApplicationInsights")
              ]): java.lang.IllegalArgumentException: Failed to load class "com.microsoft.applicationinsights.log4j.v1_2.ApplicationInsightsAppender" for handler "ApplicationInsights"
              

               

              This is my module.xml:

               

              <module xmlns="urn:jboss:module:1.3" name="com.microsoft.applicationinsights.log4j">
                <resources>
                  <resource-root path="."/>
                  <resource-root path="applicationinsights-logging-log4j1_2-1.0.7.jar"/>
                  <resource-root path="applicationinsights-core-1.0.7.jar"/>
                  <resource-root path="applicationinsights-web-1.0.7.jar"/>
                  <resource-root path="commons-codec-1.6.jar"/>
                  <resource-root path="commons-io-2.4.jar"/>
                  <resource-root path="commons-lang3-3.1.jar"/>
                  <resource-root path="commons-logging-1.1.3.jar"/>
                  <resource-root path="guava-12.0.1.jar"/>
                  <resource-root path="httpclient-4.3.5.jar"/>
                  <resource-root path="httpcore-4.3.2.jar"/>
                  <resource-root path="jsr305-1.3.9.jar"/>
                  <resource-root path="log4j-1.2.17.jar"/>
                </resources>
              </module>
              

               

              And the ApplicationInsights.xml, in that module directory.

              • 4. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
                jamezp

                Is there a stack trace in the log file or on the console? What does the CLI command look like your using or your standalone.xml configuration?

                 

                --

                James R. Perkins

                • 5. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
                  okelet

                  Hi jamezp,

                   

                  You can find attached the full stack trace and the standalone.xml. This is the module structure:

                   

                  [root@siidevbatch01 ~]# tree /opt/jboss-eap-7.0/modules/system/layers/base/com/microsoft/applicationinsights/
                  /opt/jboss-eap-7.0/modules/system/layers/base/com/microsoft/applicationinsights/
                  └── log4j
                      └── main
                          ├── applicationinsights-core-1.0.7.jar
                          ├── applicationinsights-logging-log4j1_2-1.0.7.jar
                          ├── applicationinsights-web-1.0.7.jar
                          ├── ApplicationInsights.xml
                          ├── commons-codec-1.6.jar
                          ├── commons-io-2.4.jar
                          ├── commons-lang3-3.1.jar
                          ├── commons-logging-1.1.3.jar
                          ├── guava-12.0.1.jar
                          ├── httpclient-4.3.5.jar
                          ├── httpcore-4.3.2.jar
                          ├── jsr305-1.3.9.jar
                          ├── log4j-1.2.17.jar
                          └── module.xml
                  
                  2 directories, 14 files
                  

                   

                  This is the module file (i know I could exclude some local jars and include them as dependencies, but I have added all them just to test):

                   

                  [root@siidevbatch01 ~]# cat /opt/jboss-eap-7.0/modules/system/layers/base/com/microsoft/applicationinsights/log4j/main/module.xml 
                  <module xmlns="urn:jboss:module:1.3" name="com.microsoft.applicationinsights.log4j">
                    <resources>
                      <resource-root path="."/>
                      <resource-root path="applicationinsights-logging-log4j1_2-1.0.7.jar"/>
                      <resource-root path="applicationinsights-core-1.0.7.jar"/>
                      <resource-root path="applicationinsights-web-1.0.7.jar"/>
                      <resource-root path="commons-codec-1.6.jar"/>
                      <resource-root path="commons-io-2.4.jar"/>
                      <resource-root path="commons-lang3-3.1.jar"/>
                      <resource-root path="commons-logging-1.1.3.jar"/>
                      <resource-root path="guava-12.0.1.jar"/>
                      <resource-root path="httpclient-4.3.5.jar"/>
                      <resource-root path="httpcore-4.3.2.jar"/>
                      <resource-root path="jsr305-1.3.9.jar"/>
                      <resource-root path="log4j-1.2.17.jar"/>
                    </resources>
                    <dependencies>
                      <module name="org.apache.log4j"/>
                      <module name="org.slf4j"/>
                      <module name="javax.api"/>
                      <module name="org.jboss.logmanager"/>
                    </dependencies>
                  </module>
                  

                   

                  And this the ApplicationInsights.xml:

                   

                  [root@siidevbatch01 ~]# cat /opt/jboss-eap-7.0/modules/system/layers/base/com/microsoft/applicationinsights/log4j/main/ApplicationInsights.xml 
                  <?xml version="1.0" encoding="utf-8"?>
                  <ApplicationInsights xmlns="http://schemas.microsoft.com/ApplicationInsights/2013/Settings" schemaVersion="2014-05-30">
                    <SDKLogger />
                    <InstrumentationKey>my_instrumentation_key_from_azure_insights</InstrumentationKey>
                    <TelemetryModules>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.modules.WebRequestTrackingTelemetryModule"/>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.modules.WebSessionTrackingTelemetryModule"/>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.modules.WebUserTrackingTelemetryModule"/>
                    </TelemetryModules>
                    <TelemetryInitializers>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.initializers.WebOperationIdTelemetryInitializer"/>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.initializers.WebOperationNameTelemetryInitializer"/>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.initializers.WebSessionTelemetryInitializer"/>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.initializers.WebUserTelemetryInitializer"/>
                      <Add type="com.microsoft.applicationinsights.web.extensibility.initializers.WebUserAgentTelemetryInitializer"/>
                    </TelemetryInitializers>
                  </ApplicationInsights>
                  

                   

                  With this configuration, the previuos error would be thrown.

                  • 6. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
                    jamezp

                    You need to remove the <resource-root path="log4j-1.2.17.jar"/>. You just need the org.apache.log4j module dependency which you already have.

                     

                    --

                    James R. Perkins

                    • 7. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
                      okelet

                      Thanks! It works fine now, but I also have had to add another dependency:

                       

                      <module name="javax.xml.bind.api"/>
                      

                       

                      The final module.xml is like this:

                       

                      <module xmlns="urn:jboss:module:1.3" name="com.microsoft.applicationinsights.log4j">
                        <resources>
                          <resource-root path="."/>
                          <resource-root path="applicationinsights-logging-log4j1_2-1.0.7.jar"/>
                          <resource-root path="applicationinsights-core-1.0.7.jar"/>
                          <resource-root path="applicationinsights-web-1.0.7.jar"/>
                          <resource-root path="commons-codec-1.6.jar"/>
                          <resource-root path="commons-io-2.4.jar"/>
                          <resource-root path="commons-lang3-3.1.jar"/>
                          <resource-root path="commons-logging-1.1.3.jar"/>
                          <resource-root path="guava-12.0.1.jar"/>
                          <resource-root path="httpclient-4.3.5.jar"/>
                          <resource-root path="httpcore-4.3.2.jar"/>
                          <resource-root path="jsr305-1.3.9.jar"/>
                        </resources>
                        <dependencies>
                          <module name="org.apache.log4j"/>
                          <module name="org.slf4j"/>
                          <module name="javax.api"/>
                          <module name="org.jboss.logmanager"/>
                          <module name="javax.xml.bind.api"/>
                        </dependencies>
                      </module>
                      

                       

                      The only problem now is the original one in this thread; all messages appear as exceptions.... Could I replace the original jar with the one with the path applied, if any? Which is the version? Where can I download it?

                      • 8. Re: JBoss Log4j LoggingEvent getThrowableInformation never returns null
                        jamezp

                        You'd have to build this project, GitHub - jboss-logging/log4j-jboss-logmanager: JBoss Log4j Emulation , and replace the org.jboss.log4j.logmanager module. I'll try to get a new release of it out this week.

                         

                        --

                        James R. Perkins