[ 
https://issues.apache.org/jira/browse/WW-3127?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=12864328#action_12864328
 ] 

Yannick le Restif commented on WW-3127:
---------------------------------------

Even if this discussion is getting a bit old now I thought it would still be of 
some use to give you some answers on this :
- First and most important, **** The problem above does NOT appear when 
struts.objectFactory.spring.autoWire.alwaysRespect option is set to true**** => 
that might be the reason you struts2 guys haven't had it + this is for almost 
everybody (including us) the solution to the problem. Maybe also this option 
should be set to "true" by default.
- ALL beans advised by Spring AOP, whether using JDK or CGLIB, will be proxied. 
BUT, beans that are not advised won't be proxied (at least if no other 
postprocessor proxies them), even if AOP is enabled.
- The problem happens when the above option is set to false because autowiring 
is done AFTER bean postprocessing. What this means is that autowiring is done 
on the proxy rather than on the class, which can't be done because proxy just 
doesn't have the fields !! I changed the order of the lines in 
SpringObjectFactory and it worked.

This is the original code snippet (in 
com.opensymphony.xwork2.spring.SpringObjectFactory, l. 146 to 170 in xwork 
2.1.6) :
    @Override
    public Object buildBean(Class clazz, Map<String, Object> extraContext) 
throws Exception {
        Object bean;

        try {
            // Decide to follow autowire strategy or use the legacy approach 
which mixes injection strategies
            if (alwaysRespectAutowireStrategy) {
                // Leave the creation up to Spring
                bean = autoWiringFactory.createBean(clazz, autowireStrategy, 
false);
                injectApplicationContext(bean);
                return injectInternalBeans(bean);
            } else {
                bean = autoWiringFactory.autowire(clazz, 
AutowireCapableBeanFactory.AUTOWIRE_CONSTRUCTOR, false);
                bean = 
autoWiringFactory.applyBeanPostProcessorsBeforeInitialization(bean, 
bean.getClass().getName());
                // We don't need to call the init-method since one won't be 
registered.
                bean = 
autoWiringFactory.applyBeanPostProcessorsAfterInitialization(bean, 
bean.getClass().getName());
                return autoWireBean(bean, autoWiringFactory);
            }
        } catch (UnsatisfiedDependencyException e) {
            if (LOG.isErrorEnabled())
                LOG.error("Error building bean", e);
            // Fall back
            return autoWireBean(super.buildBean(clazz, extraContext), 
autoWiringFactory);
        }
    }


So all I did was to change the last 2 lines before the catch :

BEFORE :
                bean = 
autoWiringFactory.applyBeanPostProcessorsAfterInitialization(bean, 
bean.getClass().getName());
                return autoWireBean(bean, autoWiringFactory);

AFTER :
                //autowiring first
                bean = autoWireBean(bean, autoWiringFactory);
                //doing the post processing (this is where aop is performed)
                bean = 
autoWiringFactory.applyBeanPostProcessorsAfterInitialization(bean, 
bean.getClass().getName());
                return bean;


Hoping this will be of some use to someone !

> Autoware fails on proxied objects
> ---------------------------------
>
>                 Key: WW-3127
>                 URL: https://issues.apache.org/jira/browse/WW-3127
>             Project: Struts 2
>          Issue Type: Bug
>          Components: Plugin - Spring
>    Affects Versions: 2.1.6
>            Reporter: Vasiliy Gagin
>             Fix For: Future
>
>
> com.opensymphony.xwork2.spring.SpringObjectFactory#buildBean method calls 
> autoWiringFactory.applyBeanPostProcessorsAfterInitialization() method.
> In some cases this method can return a JDK Proxy instead of action. Following 
> call to autoWireBean method attempts to autowire proxy itself instead of the 
> action.
> As a result the action remains "not-wired".
> May be autowiring should happen before applying post processors 
> "AfterInitialization".

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.

Reply via email to