스프링 MVC

준비중..

스프링 MVC

스프링을 사용한 웹서비스 만들기

17 권한 제한

# 권한 제한 권한이 있는 사용자에게만 해당 기능을 사용할 수 있도록 해봅시다. --- ## 버튼 가리기 일반 사용자에게는 도서의 등록/수정/삭제를 보여지지 않도록 해봅시다. ![Imgur](http://i.imgur.com/9nVV84V.png) 위 화면의 소스코드는 아래와 같습니다. **views/books/index.jsp** ```jsp <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%> <%@ page pageEncoding="utf-8" session="false"%> <div class="jumbotron"> <h1>Books INDEX</h1> <p>views/books/index.jsp</p> <a href="<c:url value="/books/new" />" class="btn btn-lg btn-primary">도서등록</a> </div> <div class="container"> <div class="row"> <c:forEach var="book" items="${books}" varStatus="status"> <div class="col-md-4"> <div class="card"> <img src="<c:url value="${ book.image }" />" class="card-img-top" /> <div class="card-body"> <h3 class="card-title">${ book.title }</h3> <p class="card-text">Some quick example text to build on the card title and make up the bulk of the card's content.</p> <a href="#" class="btn btn-primary">상세보기</a> <a href="<c:url value='/books/edit/${ book.id }' />" class="btn btn-info">수정</a> <a href="<c:url value='/books/delete/${ book.id }' />" class="btn btn-danger">삭제</a> </div> </div> </div> </c:forEach> </div> </div> ``` 위 코드에서 등록/수정/삭제 기능을 하는 버튼들을 가리도록 하겠습니다. 먼저 권한에 따라 뷰 페이지를 보여주고 가릴 수 있도록 태그 라이브러리를 추가해야합니다. 해당 페이지에 아래의 태그라리브러리를 추가해주세요. **views/books/index.jsp** ```jsp <%@ taglib uri="http://www.springframework.org/security/tags" prefix="s"%> ... (이하 소스코드 생략) ``` 이제 spring security에서 제공하는 태그를 쉽게 사용할 수 있게 되었습니다. 도서 등록 버튼을 일반 사용자에게 보여주지 않도록 해보겠습니다. `s:authorize` 태그를 아래와 같이 추가해줍니다. **views/books/index.jsp** ```jsp ... <s:authorize access="hasRole('ADMIN')"> <a href="<c:url value="/books/new" />" class="btn btn-lg btn-primary">도서등록</a> </s:authorize> ``` 코드를 적용하여 도서 등록 버튼을 가리도록 하였습니다. ![Imgur](http://i.imgur.com/INuGaMy.png) 추가적으로 수정/삭제 버튼에 대해서도 같은 작업을 수행합니다. **views/books/index.jsp** ```jsp ... <s:authorize access="hasRole('ADMIN')"> <a href="<c:url value='/books/edit/${ book.id }' />" class="btn btn-lg btn-default">수정</a> <a href="<c:url value='/books/delete/${ book.id }' />" class="btn btn-lg btn-danger">삭제</a> </s:authorize> ... ``` ![Imgur](http://i.imgur.com/0HB2ch7.png) ## 버튼 가리기의 한계 위에서 버튼을 보이지 않도록 하였습니다. 하지만 그렇다고 해서 해당 기능을 완전히 사용할 수 없는 것은 아닙니다. 예를 들면 관리 기능의 버튼(등록/수정/삭제 등..)의 링크주소를 알고있는 경우, 직접 타이핑 해서 기능을 사용할 수 있습니다. ## URL 접근 제한하기 위의 문제를 해결하기 위해, 추가적으로 url 권한 인증을 설정해야 합니다. url 접근 인증은 스프링 시큐리티 xml을 통하여 할 수 있습니다. **security-context.xml** ```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" 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"> <!-- 스프링 시큐리티 설정의 거의 모든 것 --> <sec:http pattern="/css/**" security="none" /> <sec:http pattern="/img/**" security="none" /> <sec:http pattern="/js/**" security="none" /> <sec:http pattern="/uploads/**" security="none" /> <sec:http auto-config='true' use-expressions="true"> <sec:intercept-url pattern="/" access="permitAll" /> <sec:intercept-url pattern="/login" access="permitAll" /> <sec:intercept-url pattern="/signup" access="permitAll" /> <sec:intercept-url pattern="/**" access="hasRole('USER')" /> <sec:form-login login-page="/login" login-processing-url="/user/login" default-target-url="/" username-parameter="email" password-parameter="password" authentication-failure-url="/login?error" always-use-default-target='true' /> <sec:logout invalidate-session="true" logout-url="/logout" logout-success-url="/login?logout" /> <!-- disable csrf protection --> <sec:csrf disabled="true"/> </sec:http> <sec:authentication-manager> <sec:authentication-provider> <sec:jdbc-user-service data-source-ref="dataSource" users-by-username-query="SELECT email, password, enabled FROM users WHERE email = ?" authorities-by-username-query="SELECT email, authority FROM authorities WHERE email = ?" /> </sec:authentication-provider> </sec:authentication-manager> </beans> ``` 위 코드에 관리자 권한에 대한 url을 아래와 같이 추가해 줍니다. ```xml ... <sec:http auto-config='true' use-expressions="true"> <!-- 관리자 --> <sec:intercept-url pattern="/admin/**" access="hasRole('ADMIN')" /> <sec:intercept-url pattern="/books/new/**" access="hasRole('ADMIN')" /> <sec:intercept-url pattern="/books/edit/**" access="hasRole('ADMIN')" /> <sec:intercept-url pattern="/books/delete/**" access="hasRole('ADMIN')" /> <!-- 게스트 --> <sec:intercept-url pattern="/" access="permitAll" /> <sec:intercept-url pattern="/login" access="permitAll" /> <sec:intercept-url pattern="/signup" access="permitAll" /> <!-- 가입자 --> <sec:intercept-url pattern="/**" access="hasRole('USER')" /> ... ``` xml 설정을 완료하였다면 서버를 재시작해주세요. 이제 일반 유저가 관리자 권한 url을 실행시키면 아래와 같이 실행이 거부 됩니다. ![Imgur](http://i.imgur.com/jwuwvmE.png)