본문 바로가기

Spring 4/Security 3

Spring Security Custom Login-form

Spring Security 커스텀 로그인 폼 설정 예


커스텀 로그인 폼, 로그아웃 성공시 이동 URL을 지정하는 예


root-context.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/security"
    xmlns:beans="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:jee="http://www.springframework.org/schema/jee"
    xsi:schemaLocation="http://www.springframework.org/schema/security 
    	http://www.springframework.org/schema/security/spring-security-4.1.xsd
        http://www.springframework.org/schema/jee 
        http://www.springframework.org/schema/jee/spring-jee.xsd
        http://www.springframework.org/schema/beans 
        http://www.springframework.org/schema/beans/spring-beans.xsd">
    
    <beans:bean id="dataSource" class="oracle.jdbc.pool.OracleDataSource"> 
	    <beans:property name="dataSourceName" value="ds"/>
	    <beans:property name="URL" value="jdbc:oracle:thin:@localhost:1521:xe"/>
	    <beans:property name="user" value="scott"/>
	    <beans:property name="password" value="TIGER"/>
    </beans:bean>
         
    <http auto-config='true'  use-expressions="true">
        <intercept-url pattern="/admin/usermanager/**"  access="hasAuthority('USER_MANAGER')" />
        <intercept-url pattern="/manager/**"  access="hasRole('USER')" />
        <intercept-url pattern="/member/**"  access="isAuthenticated()" />
        <intercept-url pattern="/**"  access="permitAll" />
        <form-login
        	login-page="/sec/login" <!--로그인 폼을 화면에 출력하기 위한 요청경로-->
        	login-processing-url="/user/login"  <!--이 경로로 로그인 폼이 전송되면 스프링이 처리한다 -->
        	username-parameter="id"
        	password-parameter="pwd"
        	default-target-url="/index"
        	authentication-failure-url="/sec/login?error=true" <!-- 다시 로그인 폼을 출력하면서 오류 메시지 출력-->
        />
        <logout logout-success-url="/sec/welcome" />  <!--로그아웃 성공시 스프링이 요청할 URL-->
        <!-- <csrf disabled="true"/> -->
        <!-- Spring security automatically enables csrf, which automatically disabled GET logouts. 
        You can fix this by disabling csrf protection by settings <csrf disabled="true"/> in the <http> , 
        or just using a POST. -->
    </http>

    <authentication-manager>
        <authentication-provider>
        	<jdbc-user-service 
        		id="jdbcUserService"
        		data-source-ref="dataSource"
        		users-by-username-query="select id, pwd, enabled from member where id=?"
        		authorities-by-username-query="select id, authority from member where id=?"/>
        </authentication-provider>
    </authentication-manager>

</beans:beans>


콘트롤러 클래스 없이도 테스트 가능하도록 서블릿 설정파일에 다음과 같이 요청을 바로 뷰로 연결한다

servlet-context.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/mvc" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:beans="http://www.springframework.org/schema/beans"
    xmlns:websocket="http://www.springframework.org/schema/websocket"
    xmlns:mvc="http://www.springframework.org/schema/mvc" 
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/websocket
        http://www.springframework.org/schema/websocket/spring-websocket.xsd">

    <!-- DispatcherServlet Context: defines this servlet's request-processing infrastructure -->
	
    <!-- Process annotations on registered beans like @Autowired... -->
    <context:annotation-config/>
    
    <!-- Enables the Spring MVC @Controller programming model -->
    <mvc:annotation-driven />

	<view-controller path="/index" view-name="security/index" />
	<view-controller path="/sec/login" view-name="security/loginForm" />
	<view-controller path="/admin/usermanager/main" view-name="security/usermanagerMain" />
	<view-controller path="/member/main" view-name="security/memberMain" />
	
    <context:component-scan base-package="org.kdea.java" />
    <context:component-scan base-package="org.kdea.service" />
    <context:component-scan base-package="org.kdea.exception" />
    <context:component-scan base-package="org.kdea.interceptor" />
    <context:component-scan base-package="org.kdea.mybatis" />
    <context:component-scan base-package="org.kdea.security" />

    <!-- Handles HTTP GET requests for /resources/** by efficiently serving up static resources in the ${webappRoot}/resources directory -->
    <mvc:resources mapping="/resources/**" location="/resources/" />

    <!-- Resolves views selected for rendering by @Controllers to .jsp resources in the /WEB-INF/views directory -->
    <beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <beans:property name="prefix" value="/WEB-INF/views/" />
        <beans:property name="suffix" value=".jsp" />
        <beans:property name="contentType" value="text/html; charset=UTF-8"/>
    </beans:bean>

	<beans:bean id="messageSource" 
 		class="org.springframework.context.support.ResourceBundleMessageSource">
    	<beans:property name="basename" value="messages/messages"/> 
    </beans:bean>
    
	<beans:bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" />

	<beans:bean id="multipartResolver"  
  		class="org.springframework.web.multipart.commons.CommonsMultipartResolver" />
  	
  	 <beans:bean id="echoHandler" class="org.kdea.websocket.EchoHandler"/>
  	    
    <websocket:handlers>
        <websocket:mapping handler="echoHandler" path="/echo-ws" />
        <websocket:handshake-interceptors>
	       <beans:bean class="org.kdea.interceptor.WebsocketHandshakeInterceptor"/>
		</websocket:handshake-interceptors>
    </websocket:handlers>

<!-- 	<beans:bean id="dataSource" class="oracle.jdbc.pool.OracleDataSource"> 
	    <beans:property name="dataSourceName" value="ds"/>
	    <beans:property name="URL" value="jdbc:oracle:thin:@localhost:1521:xe"/>
	    <beans:property name="user" value="scott"/>
	    <beans:property name="password" value="TIGER"/>
    </beans:bean> -->
    
	<beans:bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
		<beans:property name="mapperLocations" value="classpath:org/kdea/mybatis/**/*.xml"/>
		<beans:property name="dataSource" ref="dataSource" />
	</beans:bean>
	
	<beans:bean id="sqlSessionTemplate" class="org.mybatis.spring.SqlSessionTemplate">
	        <beans:constructor-arg index="0" ref="sqlSessionFactory"/>
	</beans:bean>

</beans:beans>


loginForm.jsp

<%@ page contentType="text/html; charset=utf-8"  pageEncoding="utf-8"%>
<%@ taglib prefix="c"  uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>로그인 폼</title>
</head>
<body>
<c:if test="${param.error==true }">
	로그인 실패
</c:if>
<form action="<c:url value='/user/login' />" method="post">
<input type="hidden" name="${_csrf.parameterName }" value="${_csrf.token }">
ID : <input type="text" name="id"  value="user01">
PWD : <input type="password" name="pwd"  value="pwd01">
<button type="submit" >로그인</button>
</form>

</body>
</html>