如何基于用户属性创建Spring会话范围的bean

时间:2015-10-16 12:17:00

标签: java spring spring-mvc spring-bean session-scope

我开发了一个Spring Web-MVC应用程序。我的项目中有一些办公室。每个用户都属于一个办公室。 user.getOfficeType()返回表示用户办公室类型的整数。如果办公室类型为1,则用户属于Office1等。 但是,我想将经过身份验证的用户办公室注入我的服务类:

class MyService{
   @Autowired
   Office currentOffice;
   ...
}

我阅读了Spring文档。我需要一个会话范围的bean来将它注入我的服务类。

applicationContext.xml

<mvc:annotation-driven />
<tx:annotation-driven transaction-manager="hibernateTransactionManager"/>
<context:annotation-config />
<context:component-scan base-package="com.package.controller" />
<context:component-scan base-package="com.package.service" />
...
<bean id="office" class="com.package.beans.Office" scope="session">
    <aop:scoped-proxy/>
</bean>

enter image description here

我有Office接口的三个实现。一旦用户请求资源,我想知道他的Office。所以我需要将他的会话范围的Office注入我的服务类。但我根据用户的办公室不知道如何实例化它。请帮忙!

2 个答案:

答案 0 :(得分:3)

我找到了解决方案!我声明了OfficeContext包裹了Office并且还实现了它。

@Component
@Scope(value = "session", proxyMode = ScopedProxyMode.TARGET_CLASS)
public class OfficeContext implements InitializingBean, Office {

   private Office office;

   @Autowired
   private UserDao userDao;

   @Autowired
   private NoneOffice noneOffice;
   @Autowired
   private AllOffice allOffice;
   @Autowired
   private TariffOffice tariffOffice;
   @Autowired
   private ArzeshOffice arzeshOffice;

    public Office getOffice() {
       return this.office;
    }

   @Override
   public void afterPropertiesSet() throws Exception {
      Authentication auth = SecurityContextHolder.getContext().getAuthentication();
       if (auth.isAuthenticated()) {
           String name = auth.getName(); //get logged in username
           JUser user = userDao.findByUsername(name);
           if (user != null) {
               this.office = noneOffice;
           } else {
               OfficeType type = user.getOfficeType();
               switch (type) {
                   case ALL:
                       this.office = allOffice;
                       break;
                   case TARIFF:
                       this.office = tariffOffice;
                       break;
                   case ARZESH:
                       this.office = arzeshOffice;
                       break;
                   default:
                       this.office = noneOffice;
               }
           }
       } else {
           this.office = noneOffice;
       }

   }

   @Override
   public OfficeType getType() {
       return office.getType();
   }

   @Override
   public String getDisplayName() {
       return office.getDisplayName();
   }

}

在我的服务类中,我注入了OfficeContext

@Service
public class UserService {

   @Autowired
   UserDao userDao;

   @Autowired
   OfficeContext office;

   public void persist(JUser user) {
       userDao.persist(user);
   }

   public void save(JUser user) {
       userDao.save(user);
   }


}

答案 1 :(得分:0)

我只是提出了另一种方法

@Configuration
public class SessionScopeBeansConfig {

    @Bean
    @SessionScope(proxyMode = ScopedProxyMode.TARGET_CLASS)
    public User user( UserDAO userDAO ) {

        return userDAO.getUserByLoginName( SecurityContextHolder.getContext().getAuthentication().getName() );
    }


    @Bean
    @SessionScope(proxyMode = ScopedProxyMode.TARGET_CLASS)
    public Office office( User user ) {

        Office office = <<Code to initialize office>>;

        return office;
    }
}

通过这种方式可以直接注入Office

class MyService{
   @Autowired
   Office currentOffice;
   ...
}