0

Я создал службу поддержки Java EE 6 restfull и попытался интегрировать ее с Spring Security. Но все время я получаю разные странные исключения. Что не имеет никакого смысла или может иметь смысл, но, по крайней мере, не для меня.Spring Security с Java EE Restful Service

структура Направление моего приложения что-то вроде этого:

com.security 
    UserDetailsSecurityConfig.java 
com.service 
    ApplicationConfig.java 
    UserFacadeREST.java 
com.config 
    AppConfig.java 

Мои объекты сгенерированы автоматически поэтому ошибка не кажется, чтобы быть там. Но, да, три файла кажутся мне подозрительными, поскольку UserFacadeREST отлично работает, когда я не интегрирую свое приложение с Spring Security.

com.UserDetailsSecurityConfig.java

@Configuration 
@EnableWebSecurity 
@EnableGlobalMethodSecurity(securedEnabled = true) 
public class UserDetailsSecurityConfig extends WebSecurityConfigurerAdapter { 
    @Autowired 
    public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception { 
     auth.userDetailsService(userDetailsService()); 
    } 
    @Override 
    protected void configure(HttpSecurity http) throws Exception { 
     http 
      .httpBasic().and() 
      .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS).and() 
      .authorizeRequests().antMatchers("/**").hasRole("USER"); 
    } 
    @Bean 
    public UserDetailsService userDetailsService() { 
     return new UserDetailsService() { 
      @Override 
      public UserDetails loadUserByUsername(final String username) 
        throws UsernameNotFoundException { 
       if(username.equals("admin")) { 
        return new User(username, "password", true, true, true, true, 
          Arrays.asList(
          new SimpleGrantedAuthority("ROLE_USER"), 
          new SimpleGrantedAuthority("ROLE_ADMIN") 
         ) 
        ); 
       } else if (username.equals("user")) { 
        return new User(username, "password", true, true, true, true, 
         Arrays.asList(
          new SimpleGrantedAuthority("ROLE_USER") 
         ) 
        ); 
       } 

       return null; 
      } 
     }; 
    } 

} 

com.service.ApplicationConfig.java

@javax.ws.rs.ApplicationPath("webresources") 
public class ApplicationConfig extends Application { 

    @Override 
    public Set<Class<?>> getClasses() { 
     Set<Class<?>> resources = new java.util.HashSet<>(); 
     addRestResourceClasses(resources); 
     return resources; 
    } 

    /** 
    * Do not modify addRestResourceClasses() method. 
    * It is automatically populated with 
    * all resources defined in the project. 
    * If required, comment out calling this method in getClasses(). 
    */ 
    private void addRestResourceClasses(Set<Class<?>> resources) { 
     resources.add(com.service.UserFacadeREST.class); 
    } 

} 

com.service.UserFacadeREST.java

@Stateless 
@Path("user") 
public class UserFacadeREST extends AbstractFacade<UpUser> { 
    @PersistenceContext(unitName = "PU") 
    private EntityManager em; 

    public UserFacadeREST() { 
     super(User.class); 
    } 

    @POST 
    @Override 
    @Consumes({"application/xml", "application/json"}) 
    public void create(User entity) { 
     super.create(entity); 
    } 
    @GET 
    @Path("count") 
    @Produces("text/plain") 
    public String countREST() { 
     return String.valueOf(super.count()); 
    } 

} 

com.config.AppConfig.java

@Configuration 
@Import(UserDetailsSecurityConfig.class) 
public class AppConfig {  
    @Bean 
    public ApplicationConfig applicationConfig() { 
     return new ApplicationConfig(); 
    } 
     @Bean 
    public UserFacadeREST userRestService() { 
     return new UserFacadeREST(); 
    } 


} 

В целом коде я сделал несколько изменений для попадания и суда. И в настоящее время я получаю исключение.

java.lang.IllegalStateException: Нет WebApplicationContext найдено: нет ContextLoaderListener зарегистрирован?

Перед тем, что я получаю еще одно исключение, которое было

WebSecurityConfigurers должен быть уникальным. Заказ 100 был уже использован

Я не понимаю, что я делаю неправильно в интеграции Spring Security с Java EE 6. Я новичок в Spring, возможно, я делаю ошибку, которая кажется мне очевидной.

Мой файл web.xml является:

<?xml version="1.0" encoding="UTF-8"?> 
<web-app xmlns="http://java.sun.com/xml/ns/javaee" 
    xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" 
    id="rest-sec" version="3.0"> 

    <display-name>rest</display-name> 

    <!-- Spring security --> 
    <listener> 
     <listener-class>org.springframework.security.web.session.HttpSessionEventPublisher</listener-class> 
    </listener> 

    <filter> 
     <filter-name>springSecurityFilterChain</filter-name> 
     <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class> 
    </filter> 
    <filter-mapping> 
     <filter-name>springSecurityFilterChain</filter-name> 
     <url-pattern>/*</url-pattern> 
    </filter-mapping> 

    <filter> 
     <filter-name>etagFilter</filter-name> 
     <filter-class>org.springframework.web.filter.ShallowEtagHeaderFilter</filter-class> 
    </filter> 
    <filter-mapping> 
     <filter-name>etagFilter</filter-name> 
     <url-pattern>/api/*</url-pattern> 
    </filter-mapping> 

    <!-- rest --> 
    <servlet> 
     <servlet-name>rest</servlet-name> 
     <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> 
     <init-param> 
      <param-name>contextClass</param-name> 
      <param-value>org.springframework.web.context.support.AnnotationConfigWebApplicationContext</param-value> 
     </init-param> 
     <init-param> 
      <param-name>contextConfigLocation</param-name> 
      <param-value>com.labs.entities</param-value> <!-- won't find anything --> 
     </init-param> 
     <init-param> 
      <param-name>dispatchOptionsRequest</param-name> 
      <param-value>true</param-value> 
     </init-param> 

     <load-on-startup>1</load-on-startup> 
    </servlet> 
    <servlet-mapping> 
     <servlet-name>rest</servlet-name> 
     <url-pattern>/api/*</url-pattern> 
    </servlet-mapping> 

    <!-- Disables servlet container welcome file handling. Needed for compatibility 
     with Servlet 3.0 and Tomcat 7.0 --> 
    <welcome-file-list> 
     <welcome-file /> 
    </welcome-file-list> 

</web-app> 

ответ

0

java.lang.IllegalStateException: Нет WebApplicationContext найдено: нет зарегистрированных ContextLoaderListener?

Необходимо указать фильтр, где искать контекст (по умолчанию это поиск в месте, которое не используется созданным сервлетом). В фильтре добавить инициализации параметров:

<init-param> 
     <param-name>contextAttribute</param-name> 
     <param-value>org.springframework.web.servlet.FrameworkServlet.CONTEXT.spring</param-value> 
    </init-param> 

WebSecurityConfigurers должен быть уникальным.Приказ 100 был уже использован

У вас есть 2 бобы типа WebSecurityConfigurerAdapter? Или ваш UserDetailsSecurityConfig загружается дважды?

+0

Я сделал изменение и все еще получаю то же исключение. Я также просмотрел код и не нашел несколько записей в WebSecurityCOnfigurerAdapter. Но после применения этого изменения исключение немного изменилось: java.lang.IllegalStateException: нет обнаруженного WebApplicationContext: инициализатор не зарегистрирован? –

+0

Зачем вам нужен 'DispatcherServlet'? Может быть, вам просто нужно использовать 'ContextLoaderListener'? Я думаю, что Джерси 2 пытается сделать это за вас, поэтому, возможно, это проблема (Джерси загрузил контекст Spring для вас, а затем снова загрузил его)? –

+0

P.S. Я сказал вам поставить init-param в неправильном месте (он идет в фильтре). См. Обновленный ответ. Но если вам не нужен сервлет, тогда совет меняется. –