5

Использование Spring У меня были некоторые проблемы с выполнением инъекции зависимостей в аннотированном классе Aspect. CacheService вводится при запуске контекста Spring, но когда происходит переплетение, в нем говорится, что cacheService имеет значение null. Поэтому я вынужден перестроить весенний контекст вручную и получить из него компонент. Есть ли другой способ обойти это?Spring Dependency Injecting anotated Aspect

Вот пример моего Аспект:

import org.apache.log4j.Logger; 
import org.aspectj.lang.ProceedingJoinPoint; 
import org.aspectj.lang.annotation.Around; 
import org.aspectj.lang.annotation.Aspect; 
import com.mzgubin.application.cache.CacheService; 

@Aspect 
public class CachingAdvice { 

    private static Logger log = Logger.getLogger(CachingAdvice.class); 

    private CacheService cacheService; 

    @Around("execution(public *com.mzgubin.application.callMethod(..)) &&" 
      + "args(params)") 
    public Object addCachingToCreateXMLFromSite(ProceedingJoinPoint pjp, InterestingParams params) throws Throwable { 
    log.debug("Weaving a method call to see if we should return something from the cache or create it from scratch by letting control flow move on"); 

    Object result = null; 
    if (getCacheService().objectExists(params))}{ 
     result = getCacheService().getObject(params); 
    } else { 
     result = pjp.proceed(pjp.getArgs()); 
     getCacheService().storeObject(params, result); 
    } 
    return result; 
    } 

    public CacheService getCacheService(){ 
    return cacheService; 
    } 

    public void setCacheService(CacheService cacheService){ 
    this.cacheService = cacheService; 
    } 
} 

ответ

3

Проблема, как я понимаю, что Spring создает компонент этого типа для вас, но основа AspectJ также создание экземпляра этот тип, потому что он не знает, что Spring это сделала.

Я считаю, что вы хотите, чтобы Spring заводскую-метод, используемый для создания экземпляра бина, который также позволяет AspectJ знать Аспект создается:

<!-- An @Aspect-annotated class --> 
<bean id="bar" class="com.foo.bar" factory-method="aspectOf"> 
    <property name="meaning" value="42" /> 
</bean> 

Чтобы отдать должное, я наткнулся на этот вопрос ранее сегодня а затем нашел ответ elsewhere позже, поэтому я возвращаюсь, чтобы закрыть цикл.

Я не совсем понимаю, что происходит здесь, но я вижу, что есть класс Аспектов, который предоставляет некоторые статические конструкторы этого вкуса. Предположительно, AspectJ соткает статические методы с тем же именем на каждом аспекте, чтобы облегчить такую ​​конструкцию.

2

Я также столкнулся с такой проблемой.

Вот как это было исправлено:

@Aspect 
public class MyAspect { 
    @Resource // telling spring that at first look up bean by name; 
    Session session; // resource that won't of being setup; 

    private static class MyAspectHolder { 
    static final MyAspect instance = new MyAspect(); 
    } 

    ... 

    // special purpose method w/o it - stuff doesnt work; 
    public static MyAspect aspectOf() { 
    return MyAspectHolder.instance; 
    } 
} 

И конечно не забывайте <aop:aspectj-autoproxy /> в вашей конфигурации наряду с определением аспект боба.

+0

так просто установить метод aspectOf в моем классе аспектов, кажется, исправить это. Не уверен, почему это просто работает, потому что большинство других исправлений, которые я видел, не имеют. BTW попробовал @Configurable через пружинные аспекты и некоторые другие, но никто, казалось, не подключил bean-компонент к аспектному singleton. – PJH

+0

Если вы пишете классический аспект аспекта, статический аксессор aspecOf генерируется компилятором aspectj: –

4

Поскольку аспект создан перед контейнером Spring, вам необходимо извлечь этот аспект из аспекта фабричного метода AspectOf (ExampleClass.class).

Из конфигурации Spring XML, вы можете получить аспект (объект), как это:

<bean id="traceAspect" class="aspects.trace.TraceAspect" 
    factory-method="aspectOf" /> 

Фабричные методы являются обычным способом извлечения объектов, созданных за пределами Spring контейнера, как Enum.

Смежные вопросы