基于 Spring Security Java 的配置不起作用。它会一直显示 index.jsp 页面

Posted

技术标签:

【中文标题】基于 Spring Security Java 的配置不起作用。它会一直显示 index.jsp 页面【英文标题】:Spring Seccurity Java based Configuration not working. It will always show index.jsp page 【发布时间】:2017-11-12 19:17:49 【问题描述】:

我正在将我的简单演示项目从 bean 配置转换为基于纯 java 的配置。有些地方有小问题,但我找不到它发生的地方,请帮助我。我使用本教程来构建我的项目 Spring Security 4 Hello World Annotation+XML Example

但是这个项目和我的项目 maven 原型项目之间有一点不同,我的项目是多模块 maven 项目。

这是我的项目原型

以下文件是我用于配置的文件

这个 pom 是根 pom,每个模块都有自己的 pom。这个pom在sms模块里面

pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" 
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 
http://maven.apache.org/xsd/maven-4.0.0.xsd">

<modelVersion>4.0.0</modelVersion>
<groupId>com.geek</groupId>
<artifactId>sms</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>pom</packaging>
<name>sms</name>

<properties>
    <spring.version>4.2.0.RELEASE</spring.version>
    <spring-security.version>4.0.2.RELEASE</spring-security.version>
    <jstl.version>1.2</jstl.version>
    <junit.version>3.8.1</junit.version>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

<build>
    <defaultGoal>install</defaultGoal>
    <pluginManagement>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.2</version>
                <configuration>
                    <source>1.8</source>
                    <target>1.8</target>
                </configuration>
            </plugin>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-war-plugin</artifactId>
                <version>2.4</version>
                <configuration>
                <warSourceDirectory>webapp</warSourceDirectory>
                <warName>sms-web</warName>
                <failOnMissingWebXml>false</failOnMissingWebXml>
                </configuration>
            </plugin>
        </plugins>
    </pluginManagement>
    <finalName>smsweb</finalName>
</build>

<modules>
  <module>sms-core</module>
  <module>sms-web</module>
</modules>


<dependencies>

    <!-- Spring framework -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>3.2.2.RELEASE</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-context</artifactId>
        <version>3.2.2.RELEASE</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring</artifactId>
        <version>2.5.6</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-web</artifactId>
        <version>$spring.version</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>$spring.version</version>
    </dependency>

    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-web</artifactId>
        <version>$spring-security.version</version>
    </dependency>

    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-config</artifactId>
        <version>$spring-security.version</version>
    </dependency>

    <!-- mongodb java driver -->
    <dependency>
        <groupId>org.mongodb</groupId>
        <artifactId>mongo-java-driver</artifactId>
        <version>2.11.0</version>
    </dependency>

    <!-- Spring data mongodb -->
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-mongodb</artifactId>
        <version>1.2.0.RELEASE</version>
    </dependency>

    <dependency>
        <groupId>cglib</groupId>
        <artifactId>cglib</artifactId>
        <version>2.2.2</version>
    </dependency>

     <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
        <version>$jstl.version</version>
    </dependency>

    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>servlet-api</artifactId>
        <version>2.5</version>
    </dependency>

    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>javax.servlet-api</artifactId>
        <version>3.0.1</version>
         <scope>provided</scope>
    </dependency>

    <dependency>
        <groupId>javax.servlet.jsp</groupId>
        <artifactId>javax.servlet.jsp-api</artifactId>
        <version>2.3.1</version>
    </dependency>

    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>$junit.version</version>
        <scope>test</scope>
    </dependency>

    <dependency>
        <groupId>commons-digester</groupId>
        <artifactId>commons-digester</artifactId>
        <version>2.1</version>
    </dependency>

  </dependencies>


 </project>

AppConfig.java

package com.geek.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.view.InternalResourceViewResolver;
import org.springframework.web.servlet.view.JstlView;

@EnableWebMvc
@Configuration
@ComponentScan(basePackages = "com.geek.*" )
public class AppConfig 

@Bean
public InternalResourceViewResolver viewResolver() 
    InternalResourceViewResolver viewResolver
                       = new InternalResourceViewResolver();
    viewResolver.setViewClass(JstlView.class);
    viewResolver.setPrefix("/WEB-INF/pages/");
    viewResolver.setSuffix(".jsp");
    return viewResolver;



SecurityConfig.java

package com.geek.config;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter 

@Autowired
public void configureGlobalSecurity(AuthenticationManagerBuilder auth) throws Exception 
    auth.inMemoryAuthentication().withUser("bill").password("abc123").roles("USER");
    auth.inMemoryAuthentication().withUser("admin").password("root123").roles("ADMIN");
    auth.inMemoryAuthentication().withUser("dba").password("root123").roles("ADMIN","DBA");//dba have two roles.


@Override
protected void configure(HttpSecurity http) throws Exception 

  http.authorizeRequests()
    .antMatchers("/", "/home").permitAll() 
    .antMatchers("/admin/**").access("hasRole('ADMIN')")
    .antMatchers("/db/**").access("hasRole('ADMIN') and hasRole('DBA')")
    .and().formLogin()
    .and().exceptionHandling().accessDeniedPage("/Access_Denied");




SpringMvcInitializer.java

package com.geek.config;

import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;

public class SpringMvcInitializer extends AbstractAnnotationConfigDispatcherServletInitializer 

@Override
protected Class<?>[] getRootConfigClasses() 
    return new Class[]  AppConfig.class ;


@Override
protected Class<?>[] getServletConfigClasses() 
    return null;


@Override
protected String[] getServletMappings() 
    return new String[]  "/" ;



SpringSecurityInitializer.java

package com.geek.config;

import org.springframework.security.web.context.AbstractSecurityWebApplicationInitializer;

public class SpringSecurityInitializer extends AbstractSecurityWebApplicationInitializer 


LoginController.java

package com.geek.controller;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.web.authentication.logout.SecurityContextLogoutHandler;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class LoginController 

@RequestMapping(value =  "/", "/home" , method = RequestMethod.GET)
public String homePage(ModelMap model) 
    model.addAttribute("greeting", "Hi, Welcome to mysite. ");
    return "welcome";


@RequestMapping(value = "/admin", method = RequestMethod.GET)
public String adminPage(ModelMap model) 
    model.addAttribute("user", getPrincipal());
    return "admin";


@RequestMapping(value = "/db", method = RequestMethod.GET)
public String dbaPage(ModelMap model) 
    model.addAttribute("user", getPrincipal());
    return "dba";


@RequestMapping(value="/logout", method = RequestMethod.GET)
   public String logoutPage (HttpServletRequest request, HttpServletResponse response) 
      Authentication auth = SecurityContextHolder.getContext().getAuthentication();
      if (auth != null)    
         new SecurityContextLogoutHandler().logout(request, response, auth);
      
      return "welcome";
   

@RequestMapping(value = "/Access_Denied", method = RequestMethod.GET)
public String accessDeniedPage(ModelMap model) 
    model.addAttribute("user", getPrincipal());
    return "accessDenied";


private String getPrincipal()
    String userName = null;
    Object principal = SecurityContextHolder.getContext().getAuthentication().getPrincipal();

    if (principal instanceof UserDetails) 
        userName = ((UserDetails)principal).getUsername();
     else 
        userName = principal.toString();
    
    return userName;



我的预期是当我尝试使用它登录我的应用程序时

http://localhost:8080/sms-web 我需要重定向到 login.jsp 页面或任何其他页面,但这将重定向到 index.jsp。

当我尝试使用外部 tomcat 运行这个 sms-web.war 并将我的 war 文件放入 webapps 文件夹时,它最终会出现这样的错误

 > uring scanning can improve startup time and JSP compilation time.
 SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
 SLF4J: Defaulting to no-operation (NOP) logger implementation
 SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further 
 details.
 11-Jun-2017 14:18:55.435 SEVERE [localhost-startStop-1] 
 org.apache.catalina.core.ContainerBase.addChildInternal 
 ContainerBase.addChild: start:
 org.apache.catalina.LifecycleException: Failed to start component 
 [StandardEngine[Catalina].StandardHost[localhost].StandardContext[/sms-web]]
    at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:167)
    at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:752)
    at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:728)
    at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:734)
    at org.apache.catalina.startup.HostConfig.deployWAR(HostConfig.java:952)
    at org.apache.catalina.startup.HostConfig$DeployWar.run(HostConfig.java:1823)
    at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
    at java.util.concurrent.FutureTask.run(FutureTask.java:266)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
    at java.lang.Thread.run(Thread.java:745)
 Caused by: java.lang.NoSuchMethodError: 

org.springframework.core.annotation.AnnotationAwareOrderComparator.sort(Ljava/util/List;)V 在

org.springframework.web.SpringServletContainerInitializer.onStartup(SpringServletContainerInitializer.java:171) 在

org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5178 ) 在 org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150) ... 10 更多

11-Jun-2017 14:18:55.435 SEVERE [localhost-startStop-1] 
org.apache.catalina.startup.HostConfig.deployWAR Error deploying web 
application archive F:\Pe
rsonal\Cingle Eve\Server\apache-tomcat-8.5.9\webapps\sms-web.war
java.lang.IllegalStateException: ContainerBase.addChild: start: 
org.apache.catalina.LifecycleException: Failed to start component 
[StandardEngine[Cat
alina].StandardHost[localhost].StandardContext[/sms-web]]
    at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:756)
    at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:728)
    at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:734)
    at org.apache.catalina.startup.HostConfig.deployWAR(HostConfig.java:952)
    at org.apache.catalina.startup.HostConfig$DeployWar.run(HostConfig.java:1823)
    at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
    at java.util.concurrent.FutureTask.run(FutureTask.java:266)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
    at java.lang.Thread.run(Thread.java:745)

 11-Jun-2017 14:18:55.455 INFO [localhost-startStop-1] 
 org.apache.catalina.startup.HostConfig.deployWAR Deployment of web 
 application archive F:\Person
al\Cingle Eve\Server\apache-tomcat-8.5.9\webapps\sms-web.war has finished in 
3,913 ms

我做错了什么请帮我找出答案...

【问题讨论】:

【参考方案1】:

看起来您的依赖项混合了不同的 Spring 版本时一团糟。尝试使用以下依赖项:

<dependencies>
    <!-- Spring framework -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>$spring.version</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-web</artifactId>
        <version>$spring-security.version</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-config</artifactId>
        <version>$spring-security.version</version>
    </dependency>
    <!-- mongodb java driver -->
    <dependency>
        <groupId>org.mongodb</groupId>
        <artifactId>mongo-java-driver</artifactId>
        <version>$mongo-driver.version</version>
    </dependency>
    <!-- Spring data mongodb -->
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-mongodb</artifactId>
        <version>$spring-data.version</version>
    </dependency>
    <dependency>
        <groupId>cglib</groupId>
        <artifactId>cglib</artifactId>
        <version>$cglib.version</version>
    </dependency>
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
        <version>$jstl.version</version>
    </dependency>
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>javax.servlet-api</artifactId>
        <version>$servlet-api.version</version>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>javax.servlet.jsp</groupId>
        <artifactId>javax.servlet.jsp-api</artifactId>
        <version>$servlet-jsp-api.version</version>
    </dependency>
    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>$junit.version</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-digester3</artifactId>
        <version>$commons-digester.version</version>
    </dependency>
</dependencies>

具有以下属性:

<properties>
    <spring.version>4.3.9.RELEASE</spring.version>
    <spring-security.version>4.2.3.RELEASE</spring-security.version>
    <mongo-driver.version>3.4.2</mongo-driver.version>
    <spring-data.version>1.10.4.RELEASE</spring-data.version>
    <cglib.version>3.2.5</cglib.version>
    <servlet-api.version>3.1.0</servlet-api.version>
    <servlet-jsp-api.version>2.3.1</servlet-jsp-api.version>
    <commons-digester.version>3.2</commons-digester.version>
    <jstl.version>1.2</jstl.version>
    <junit.version>4.12</junit.version>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

我使用了最新的 spring 版本并更新了一些其他依赖项。

此外,为了从索引重定向到登录页面,请执行以下操作:

.antMatchers("/", "/home").access("hasRole('ADMIN')")

【讨论】:

@randikaisuru 不客气。刚刚注意到如果未经授权,您想将您的应用程序直接从索引重定向到登录页面,因此您必须使用它:.antMatchers("/", "/home").access("hasRole('ADMIN')")

以上是关于基于 Spring Security Java 的配置不起作用。它会一直显示 index.jsp 页面的主要内容,如果未能解决你的问题,请参考以下文章

使用 Spring Security 和 Redis 对带有 Java 配置的 RESTFul api 进行基于 Cookie 的身份验证

基于 Spring Security Java 的配置不起作用。它会一直显示 index.jsp 页面

Spring Boot,Spring Security - 基于 XML 的配置

Spring Security - 基于所有权的访问

spring boot系列--spring security (基于数据库)登录和权限控制

spring boot系列--spring security (基于数据库)登录和权限控制