jsp보안 (1)

💻 Programming/JSP

[JSP] Security ( 보안 )

JSP와 servlets 은 Web 개발자들을 위해서 보안(인증)을 처리할 수 있는 다양한 방법을 제공합니다.  

오늘은 그 중 두가지에 대해서만 알아보도록 하겠습니다. 

 

역할 기반 인증

servlet 에서 제공하는 역할 기반 인증은 사용자 레벨에서 리소스를 제한하는 것이 아니라 사용자에게 역할을 부여하고 특정 역할을 가진 모든 사용자에 대해서 리소스를 제한하는 방법입니다.  

톰캣 홈 디렉토리의 conf디렉토리에 tomcat-users.xml 파일을 만들고 아래코드를 넣어주세요.

<?xml version='1.0' encoding='utf-8'?> 
<tomcat-users> 
	<role rolename="tomcat"/> 
	<role rolename="role1"/> 
	<role rolename="manager"/> 
	<role rolename="admin"/> 
	<user username="tomcat" password="tomcat" roles="tomcat"/> 
	<user username="role1" password="tomcat" roles="role1"/> 
	<user username="both" password="tomcat" roles="tomcat,role1"/> 
	<user username="admin" password="secret" roles="admin,manager"/> 
</tomcat-users>

위 코드가 뭘 하고있는지는 대충 봐도 아시겠죠? 역할을 생성하고 사용자를 만들때 역할을 부여하고 있습니다.

 

이제  web.xml파일에 <security-constraint> 태그를 추가하고 아래처럼 넣어보세요. 물론 url-pattern은 여러분이 가지고 있는 웹애플리케이션에 실제로 존재하는 url이어야게죠? 그래야 테스트가 가능합니다~ 

 

<web-app> 
    ... 
    <security-constraint> 
    	<web-resource-collection> 
        	<web-resource-name> SecuredBookSite </web-resource-name> 
            <url-pattern>/secured/*</url-pattern> 
            <http-method>GET</http-method> 
            <http-method>POST</http-method> 
        </web-resource-collection> 
        <auth-constraint> 
        	<description> Let only managers use this app </description> 
            <role-name>manager</role-name> 
        </auth-constraint> 
    </security-constraint> 
    <security-role> 
    	<role-name>manager</role-name> 
    </security-role> 
    <login-config> 
    	<auth-method>BASIC</auth-method> 
    </login-config> 
    ... 
</web-app>

위 소스코드가 의미하는 것이 무언인가 하면 다음과 같습니다. 

  • HTTP GET 이나 POST 방식의 요청에 대해서 /secured/* URL에 대한 요청이 들어오면 보안설정의 제약을 받게됩니다.

  • 매니저 역할을 가지고 있는 사용자에 대해서만 /secured/* 리소스에 접근이 가능합니다.

  • 마지막으로 login-config 태그가 기본형태의 인증을 위해서 사용되었습니다. 

이제 /security내부의 페이지로 접근을 하려면 사용자명과 비밀번호를 입력하라는 창이 뜨게됩니다. 접속할 수 있는 역할을 가지고 있지 않거나 인증에 실패하면 접속이 불가능하나 페이지가 되는 것이죠. 

 

Form을 이용한 인증

FORM 인증을 사용하려면 사용자에게 로그인 폼을 제공해주어야 합니다.  

<html>

<body bgcolor="#ffffff">
    <form method="POST" action="j_security_check">
        <table border="0">
            <tr>
                <td>Login</td>
                <td><input type="text" name="j_username"></td>
            </tr>
            <tr>
                <td>Password</td>
                <td><input type="password" name="j_password"></td>
            </tr>
        </table> <input type="submit" value="Login!"> </center>
    </form>
</body>

</html>

위 코드를 login.jsp에 넣어주세요. <form> 태그 안에있는 action의 값은  j_security_check 여야 합니다. POST 방식이 사용되어야 한다는 것은 알고 계시겠죠? 자 이제 web.xml의 <login-config> 태그를 FORM을 이용하도록 수정해야합니다.

<web-app> 
    ... 
    <security-constraint>
        <web-resource-collection>
            <web-resource-name> SecuredBookSite </web-resource-name>
            <url-pattern>/secured/*</url-pattern>
            <http-method>GET</http-method>
            <http-method>POST</http-method>
        </web-resource-collection>
        <auth-constraint>
            <description> Let only managers use this app </description>
            <role-name>manager</role-name>
        </auth-constraint>
    </security-constraint>
    <security-role>
        <role-name>manager</role-name>
    </security-role>
    <login-config>
        <auth-method>FORM</auth-method>
        <form-login-config>
            <form-login-page>/login.jsp</form-login-page>
            <form-error-page>/error.jsp</form-error-page>
        </form-login-config>
    </login-config> 
    ...
</web-app>

이제  /secured/* 주소로 접속을 시도해 보세요. 사용자 ID와 패스워드를 입력하라고 할겁니다. 컨테이너가  "j_security_check" 액션을 만나면요청을 인증하기위한 내부 메카니즘을 실행합니다.

로그인이 성공하고 리소스를 조회할 수 있는 역할을 가지고 있다면 컨테이너는 사용자를 확인하기위해서 session-id 를 비교합니다. 컨테이너는 세션아이디를 가지고있는 쿠키와 함께 세션을 유지하게됩니다. 서버가 이 쿠키를 클라이언트로 되돌려보내고 이후 요청때마다 이 쿠키를 서버로 전송하게되면 컨테이너는 요청하는 클라이언트를 식별할 수 있습니다.

로그인이 실패하면 서버는 에러페이지를 전송하게 됩니다.  

 

j_security_check 가 톰캣 컨테이너에서 어떻게 동작하는지에 대해서 더 자세한 정보를 보시려면 Standard Realm Implementations 이곳에 가보세요. 

 

Servlet/JSP의 코드로 보안적용하기

HttpServletRequest 객체가 보안관련해서 제공하는 메소드들은 다음과 같습니다.

 

SN Method and Description
1 String getAuthType()
The getAuthType() method returns a String object that represents the name of the authentication scheme used to protect the Servlet.
2 boolean isUserInRole(java.lang.String role)
The isUserInRole() method returns a boolean value: true if the user is in the given role or false if they are not.
3 String getProtocol()
The getProtocol() method returns a String object representing the protocol that was used to send the request. This value can be checked to determine if a secure protocol was used.
4 boolean isSecure()
The isSecure() method returns a boolean value representing if the request was made using HTTPS. A value of true means it was and the connection is secure. A value of false means the request was not.
5 Principle getUserPrinciple()
The getUserPrinciple() method returns a java.security.Principle object that contains the name of the current authenticated user.

 

예를들어 매니저 권한을 갖고있는 사용자들을 위한 링크를 제공하는 JavaServer Page 를 만들려면 아래 코드를 삽입해주시면 되는거죠 

<% if (request.isUserInRole("manager")) { %> 
    <a href="managers/mgrreport.jsp">Manager Report</a> 
    <a href="managers/personnel.jsp">Personnel Records</a> 
<% } %>

그러면 사용자 역할을 검사한 뒤 매니저역할을 가지고 있는 사용자에게만 링크를 보여주게 됩니다. 만약 로그인 폼에서 입력한 사용자명이 필요한 경우에는 getRemoteUser 메소드를 호출하면 됩니다.

 

 

 

Reference : http://www.tutorialspoint.com/jsp/jsp_security.htm