How to inject session scope bean in interceptor using java config with Spring

I'm developping a full Spring 3.1 and servlet 3.0 application. But my interceptor has a private properties scoped as proxy:

public class MyInterceptor extends HandlerInterceptorAdapter {

    @Ressource
    private UserSession userSession;
}

The user session is defined as:

@Component 
@Scope(value = "session", proxyMode = ScopedProxyMode.TARGET_CLASS) 
public class UserSession implements Serializable {
   ....
}

When using this user session in the interceptor, java throws a NullPointerException for userSession.

I think the problem comes from my javaconfig oriented spring configuration:

@EnableWebMvc
@ComponentScan(basePackages = {"com.whatever"})
@Configuration
public class WebAppConfig extends WebMvcConfigurerAdapter {

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new MyInterceptor());
    }

    ...
}

The problem is that interceptor is manually instantied, so without instrumentation for the session proxy mechanism. Thus, the question is: "how can I let Spring detect and instance the scope session proxy bean in the java config of my application ?

Answers


What you posted works, but you aren't taking advantage of Spring's autowiring capabilities. What if you had many services or other beans to inject into your MyInterceptor bean.

Instead just make a @Bean method for your MyInterceptor

@EnableWebMvc
@ComponentScan(basePackages = {"com.whatever"})
@Configuration
public class WebAppConfig extends WebMvcConfigurerAdapter {

    @Bean
    @Scope(value = "session", proxyMode = ScopedProxyMode.TARGET_CLASS)
    public UserSession userSession() {
        return new UserSession();
    }

    @Bean
    public MyInterceptor myInterceptor() {
        return new MyInterceptor(); // let Spring go nuts injecting stuff
    }

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(myInterceptor()); // will always refer to the same object returned once by myInterceptor()
    }

    ...
}

The solution is to use annotation in the java config class:

@EnableWebMvc
@ComponentScan(basePackages = {"com.whatever"})
@Configuration
public class WebAppConfig extends WebMvcConfigurerAdapter {

    @Bean
    @Scope(value = "session", proxyMode = ScopedProxyMode.TARGET_CLASS)
    public UserSession userSession() {
        return new UserSession();
    }

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        MyInterceptor interceptor = new MyInterceptor();
        interceptor.setUserSession(userSession());
        registry.addInterceptor(interceptor);
    }

    ...
}

And you need to remove @Scope and @Bean annotation from UserSession class.


Need Your Help

Creating a jar from a maven project in intellij

java maven intellij-idea

I created a new maven project in IntelliJ and set packaging to jar but when I build it, the target folder does not contain a jar. I'm sure its something really dumb on my part but there are just so...

Subsonic, SharedDbConnectionScope and ApplicationState

caching subsonic shareddbconnectionscope

I'm looking at using Subsonic with a multi-tenant ASP.net web application. There are multiple DB's (one per client/instance). The user logs in with a domain suffix to their username (e.g. user@tena...