From JCFWiKi
|
|
- 산출물 :Spring security 2.0 따라하기
- 작성자: 나윤주
- 최초작성일 : 2008/05/03
- 최종작성일 : 2008/05/21
Copyright © 2008 Daewoo Information Systems Co., Ltd.
|
|
|
- 이 가이드를 따라하시면 아래의 기능을 추가할 수 있습니다.
- 유저 권한 체계 생성 및 유저에 권한 부여
- 로그인 및 로그아웃
- 특정 url에 권한 부여
- 특정 메소드에 권한 부여
|
[편집] 라이브러리 등록하기
- 아래의 2개의 라이브러리를 /WEB-INF/lib/ 에 임포트한다.
- spring-security-core-2.0.0.jar
- spring-security-taglibs-2.0.0.jar
- 라이브러리 다운받기: 다운로드
- Spring security 2.0이 원활하게 동작하기 위해서는 spring framework 버전을 2.5 이상으로 한다.
[편집] web.xml 등록하기
- web/WEB-INF/web.xml에서 DelegatingFilterProxy filter를 추가해줌 (Filter 설정 순서에 주의하세요.)
<filter>
<filter-name>springSecurityFilterChain</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter>
<filter-name>struts-cleanup</filter-name>
<filter-class>
org.apache.struts2.dispatcher.ActionContextCleanUp</filter-class>
</filter>
<filter>
<filter-name>struts2</filter-name>
<filter-class>
org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>
<filter-mapping>
<filter-name>springSecurityFilterChain</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>struts-cleanup</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
[편집] Security 2.0 적용 table 생성하기
[편집] USERINFO table 만들기
CREATE TABLE userinfo (
username VARCHAR(50) NOT NULL PRIMARY KEY,
password VARCHAR(50) NOT NULL,
ENABLED int DEFAULT '0' NOT NULL
);
[편집] AUTHORITIES table 만들기
CREATE TABLE AUTHORITIES (
USERNAME VARCHAR(12) NOT NULL,
AUTHORITY VARCHAR(20) NOT NULL)
[편집] sample query 넣기
INSERT INTO userinfo VALUES ('marissa', 'koala', 0);
INSERT INTO userinfo VALUES ('dianne', 'emu', 1);
INSERT INTO authorities VALUES ('marissa', 'ROLE_ADMINISTRATOR');
INSERT INTO authorities VALUES ('dianne', 'ROLE_USER');
INSERT INTO authorities VALUES ('dianne', 'ROLE_GUEST');
- USERINFO의 ENABLED 값이 1인 경우만 로그인이 가능하다.
[편집] 그외 blog 샘플 쿼리 넣기
CREATE TABLE IF NOT EXISTS `blog` (
`id` int(11) NOT NULL DEFAULT '0',
`title` varchar(50) DEFAULT NULL,
`writer` varchar(50) DEFAULT NULL,
`description` varchar(500) DEFAULT NULL,
`regDate` date DEFAULT NULL,
`isPublic` char(1) DEFAULT NULL,
`categoryId` varchar(50) DEFAULT NULL,
`attach` varchar(50) DEFAULT NULL,
`attachBlob` blob,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
CREATE TABLE IF NOT EXISTS `code` (
`id` int(11) NOT NULL DEFAULT '0',
`name` varchar(20) DEFAULT NULL,
`description` varchar(50) DEFAULT NULL,
`category` varchar(20) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
INSERT INTO `code` (`id`, `name`, `description`, `category`) VALUES
(1, 'SEOUL', '서울', 'user_address_code'),
(2, 'INCHEN', '인천', 'user_address_code'),
(3, 'PUSAN', '부산', 'user_address_code'),
(4, 'ULSAN', '울산', 'user_address_code'),
(5, 'SEOUL', '서울', 'blog_category_code'),
(6, 'INCHEN', '인천', 'blog_category_code'),
(7, 'PUSAN', '부산', 'blog_category_code'),
(8, 'ULSAN', '울산', 'blog_category_code');
[편집] applicationContext-security.xml 설정하기
- security 설정을 담당하는 applicationContext 파일을 생성한다.
- src/config 밑에 applicationContext-security.xml 생성
- applicationContext-security.xml 시작하기
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:sec="http://www.springframework.org/schema/security"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security.xsd">
</beans:beans>
[편집] 로그인 form 설정하기
- <http> 설정으로 허용된 사용자만 접근이 가능하게 할 수 있다.
- spring security 2.0에서는 로그인 폼을 제공하므로 별도의 로그인 폼을 작성하지 않아도 사용할 수 있다.
<sec:http auto-config="true">
<intercept-url pattern="/**" access="ROLE_USER" />
</sec:http>
- <intercept-url>은 여러개를 정의할 수 있으며, 위에서부터 차례로 해당되는 url pattern이 적용된다.
- 직접 작성한 로그인 폼을 쓰고자 한다면, <http> 설정을 다음과 같이 할 수 있다.
- 직접 작성한 로그인 폼을 쓸 경우, 직접 작성한 로그인 폼은 누구나 접근할 수 있어야 하기 때문에 /** pattern의 사용에 주의한다.
<sec:http auto-config='true'>
<sec:form-login login-page="/public/blog/login.jsp"
authentication-failure-url="/public/blog/login.jsp" default-target-url="/blog/findBlogs.action"
always-use-default-target='true' />
<sec:logout logout-success-url="/public/blog/login.jsp" />
<sec:intercept-url pattern="/"
access="IS_AUTHENTICATED_ANONYMOUSLY" />
<sec:intercept-url pattern="/public/blog/login.jsp" filters='none' />
<sec:intercept-url pattern="/blog/**" access="ROLE_USER" />
</sec:http>
[편집] JDBC를 이용한 사용자 인증
- 사용자 정보를 xml에 등록하여 사용할 수도 있지만, 여기서는 데이터베이스에 저장된 사용자 정보를 이용하여 사용자 인증을 한다.
<sec:global-method-security secured-annotations="enabled">
<!--
AspectJ pointcut expression that locates our "post" method and
applies security that way <protect-pointcut expression="execution(*
bigbank.*Service.post*(..))" access="ROLE_TELLER"/>
-->
</sec:global-method-security>
<sec:authentication-provider>
<sec:jdbc-user-service data-source-ref="dataSource"
users-by-username-query="SELECT username, password, enabled FROM USERS where username = ?"
authorities-by-username-query="SELECT username, authority from authorities where username = ?"
group-authorities-by-username-query="SELECT g.id, g.group_name, ga.authority
FROM groups g, group_members gm, group_authorities ga
WHERE gm.username = ? AND g.id = ga.group_id AND g.id = gm.group_id" />
</sec:authentication-provider>
[편집] 인증 view page 만들기
- 사용자 인증에 사용할 로그인 폼은 직접 작성하여 사용 할 수 있다.
<%@ page contentType="text/html; charset=UTF-8" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<html>
<head>
<title>JCF EDUCATION::BLOG</title>
</head>
<body>
<div align="center">
<h1>JCF EDUCATION - BLOG</h1>
<hr width="600">
<h2>블로그 로그인</h2>
<form action="<s:url value='/j_spring_security_check'/>" method="POST">
<table>
<tr><td>User:</td><td><input type='text' name='j_username'></td></tr>
<tr><td>Password:</td><td><input type='password' name='j_password'></td></tr>
<tr><td colspan='2' align="center"><input name="submit" type="submit" value="로그인">
<input name="reset" type="reset" value="취소"></td></tr>
</table>
</form>
</div>
</body>
</html>
[편집] Spring seucrity 2.0 태그 사용하기
- 앞서 추가한 spring-security-taglibs-2.0.0.jar를 참조한다.
- findBlogs.jsp
<%@ page contentType="text/html; charset=UTF-8" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<%@ taglib uri="/WEB-INF/tld/app.tld" prefix="app" %>
<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>
<!-- 중간생략 -->
<!-- 권한에 따라 페이지에서 보여주는 것을 달리하기 위해 authorize 태그를 사용할 수 있다. -->
<sec:authorize ifNotGranted="ROLE_USER">
<a href="<s:url value="/public/blog/login.jsp"/>">로그인</a>
</sec:authorize>
<sec:authorize ifAnyGranted="ROLE_USER, ROLE_ADMIN">
<b><sec:authentication property="principal.username"/></b>님 반갑습니다. <br>
<a href="<s:url value="/j_spring_security_logout"/>">로그아웃</a>
</sec:authorize>
<!-- 이하생략 -->
- 수정 및 삭제 버튼도 위에서 사용한 authorize 태그를 사용해서 로그인 상태에 따라 보여주거나 보여주지 않을 수 있다.
- authentication 태그를 사용하여 현재 로그인된 사용자의 정보를 확인할 수 있다.
[편집] Spring Security Tag Library
- authentication 태그
- property="principal.username" 설정으로 현재 로그인 된 사용자의 username을 확인 할 수 있다.
- authorize 태그
- 현재 로그인 된 사용자가 해당되는 권한에 따라, 태그 안에 포함된 내용을 보여주거나 보여주지 않을 수 있다.
- ifAllGranted 속성: 사용자가 나열된 모든 권한에 해당할 경우 태그 안에 포함된 내용을 보여준다.
- ifAnyGranted 속성: 사용자가 나열된 권한 중 한가지에라도 해당할 경우 태그 안에 포함된 내용을 보여준다.
- ifNotGranted 속성: 사용자가 나열된 권한 중 한가지에라도 해당할 경우 태그 안에 포함된 내용을 보여주지 않는다.