2

Hi am not able to apply advice to third party library (log4g - Logger.getLogger call) using Spring LoadTimeWeaving?

1. SpringConfig.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">

    <!-- Spring Application Context holder that is used by code that can not be injected by spring.
    One example is the log4j appender called LogEventAppender.
     -->
     <!-- <context:property-placeholder location="classpath:/hello_${env}.properties"/> -->

    <context:load-time-weaver/>


    <context:spring-configured/>

    <context:component-scan base-package="com.app.svc">
        <!-- In the case the IFA is in the same class path that this spring context is being loaded from exclude this
        generator from including IPA classes. This happens in the fusion-util module. -->
    </context:component-scan>

    <aop:aspectj-autoproxy/>

</beans>

2. aop.xml in META-INF directory.

<!DOCTYPE aspectj PUBLIC "-//AspectJ//DTD//EN" "http://www.eclipse.org/aspectj/dtd/aspectj.dtd">
<aspectj>

    <weaver>
        <!-- only weave classes in our application-specific packages -->
        <include within="com.app.svc.*" />
        <include within="org.apache.log4j.*" />
    </weaver>

    <aspects>
        <!-- weave in just this aspect -->
        <aspect name="com.app.svc.MyLoggingAspect" />
    </aspects>

</aspectj>

3. Aspect class

package com.app.svc;

import org.apache.log4j.Logger;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;

@Aspect
public class MyLoggingAspect {

    @Around("getLoggerPointCut()")
    public Object changeFileAppender(ProceedingJoinPoint pjp) throws Throwable {
        System.err.println("---------------- MyLoggingAspect ##--------------------");
        Object proceed = pjp.proceed();
        return proceed;
    }

    //This is not working - Pointcuts for classes in 3rd party jar. 
    @Pointcut("execution(public org.apache.log4j.Logger org.apache.log4j.Logger.*(..))")
    public void getLoggerPointCut(){}   

    //This works - Pointcuts for classes in application.
    //@Pointcut("execution(public * com.app.svc.NewHello.info(..))")
    //public void getLoggerPointCut(){} 

}

Note: Provided following java VM argument. -javaagent:D:\devel\spring\spring-instrument-3.2.3.RELEASE.jar

It is not printing anyhing on console. If i change the pointcut definition to some package in my app then it works.

So looks like it's not able to apply the aspect to Log4j.xml

Any suggestion plz.

  • Getting loadtime weaving right is tricky... And basically you aspect is destroying the ability to loadtime weave... You are depending on Log4j, which already loads log4j before loadtime weaving can be applied. Loadtime weaving will only work for classes that aren't yet already loaded in the classloader. – M. Deinum Nov 08 '13 at 11:24
  • 1
    I often find it useful to code with the AspectJ's eclipse plugin. Its cross reference window comes in handy to see if the aspect's being applied or not --works with both annotation and "pure" aspects. As for your problem, consider trying "call" instead of "execution". – Apoorv Sep 07 '14 at 13:28

0 Answers0