본문 바로가기
코딩/수업 정리

21.02.18 [060] Thu

by 6^6 2021. 2. 18.
728x90

시큐리티 어제거 이어서~~ 

 

 

가장기본적인 셋팅(설명5)- 에러페이지 추가

================================================================
 가장기본적인 셋팅(설명5)- 에러페이지 추가	
================================================================
<http> 
	<intercept-url pattern="/security/all" access="permitAll" />
	<intercept-url pattern="/security/member" access="hasRole('ROLE_MEMBER')" />  
	<intercept-url pattern="/security/admin" access="hasRole('ROLE_ADMIN')" />  
	<form-login />
	<!-- 403 에러 처리 --403에러가나면 밑에주소를 던져줘라-->
	<access-denied-handler error-page="/security/accessError"/>
</http> 

<!-- provider --> 
<authentication-manager>
	<authentication-provider> 
		<user-service> 
			<user name="member" password="{noop}member" authorities="ROLE_MEMBER" /> 
			<user name="admin" password="{noop}admin" authorities="ROLE_MEMBER,ROLE_ADMIN" /> 
		</user-service> 
	</authentication-provider>
</authentication-manager>
================================================================

 

[SecurityController.java]
	@GetMapping("/accessError")
	public void accessError(Authentication auth, Model model) {
		log.info("accessd denied" + auth);
		model.addAttribute("msg", "Access Denied");
	}

<user name="admin" password="{noop}admin"
authorities="ROLE_MEMBER,ROLE_ADMIN" />

admin은 두개의 권한이 있다.(member와 admin)

 

 

 

 

 

 

 

 

 

가장기본적인 셋팅(설명6)-로그인 페이지 커스텀 화

가장기본적인 셋팅(설명6)-로그인 페이지 커스텀 화	
================================================================
<http> 
	<intercept-url pattern="/security/all" access="permitAll" />
	<intercept-url pattern="/security/member" access="hasRole('ROLE_MEMBER')" />  
	<intercept-url pattern="/security/admin" access="hasRole('ROLE_ADMIN')" />  
    
    <!-- 로그인 페이지 커스텀화 -- 로그인페이지가 로그인폴더 안에있다. -->
		<form-login login-page="/login/loginForm"
			default-target-url="/"
			authentication-failure-url="/login/loginForm?error"
			username-parameter="id" password-parameter="password" />

		<logout logout-url="/logout" logout-success-url="/" />
	
    <!-- 403 에러 처리 -->
	<access-denied-handler error-page="/security/accessError"/>
</http> 

<!-- provider --> 
<authentication-manager>
	<authentication-provider> 
		<user-service> 
			<user name="member" password="{noop}member" authorities="ROLE_MEMBER" /> 
		   <user name="admin" password="{noop}admin" authorities="ROLE_MEMBER,ROLE_ADMIN" /> 
		</user-service> 
	</authentication-provider>
</authentication-manager>
================================================================
 
spring security는 세션-쿠키방식으로 인증한다.
여기서는 전통적인 쿠키-세션 방식을 사용한다. (JWT이런거는 spring-security-oauth2를..)
 
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<!DOCTYPE html>
<html lang="ko">
<head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
    <title>로그인 페이지</title>
</head>

<body onload="document.f.id.focus();">

<h3>아이디와 비밀번호를 입력해주세요.</h3>

<c:url value="/login" var="loginUrl" />
<p>${loginUrl}</p>
<form:form name="f" action="${loginUrl}" method="POST">
    <c:if test="${param.error != null}">
        <p>아이디와 비밀번호가 잘못되었습니다.</p>
    </c:if>
    <c:if test="${param.logout != null}">
        <p>로그아웃 하였습니다.</p>
    </c:if>
    <p>
        <label for="username">아이디</label>
        <input type="text" id="id" name="id" />
    </p>
    <p>
        <label for="password">비밀번호</label>
        <input type="password" id="password" name="password"/>
    </p>
    <%-- <input type="hidden" name="${_csrf.parameterName}" value="${_csrf.token}" /> --%>
    <button type="submit" class="btn">로그인</button>
</form:form>

</body>
</html>

 

↑name:"id" name:"password"이거 맞춰주기

 

 

 

이거오류남

--오류해결 : jsp파일을 views에 안넣고 security폴더에 넣음

 

 

 

 

========================================================================================================================================================

이제db랑 연결해서 가져오기

 

sql developer에서 예전에 생성해줬던 user, 테이블

 

 

 

[security-db-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"
	xsi:schemaLocation="http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security.xsd
      http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

	<http>
		<intercept-url pattern="/security/all"
			access="permitAll" />
		<intercept-url pattern="/security/member"
			access="hasRole('ROLE_MEMBER')" />
		<intercept-url pattern="/security/admin"
			access="hasRole('ROLE_ADMIN')" />


		<!-- 로그인 페이지 커스텀화 -->
		<form-login login-page="/login/loginForm"
			default-target-url="/"
			authentication-failure-url="/login/loginForm?error"
			username-parameter="id" password-parameter="password" />

		<logout logout-url="/logout" logout-success-url="/" />

		<!-- 403 에러 처리 -->
		<access-denied-handler
			error-page="/security/accessError" />
	</http>

	<beans:bean id="userDetailsService"
		class="org.springframework.security.core.userdetails.jdbc.JdbcDaoImpl">
		<beans:property name="dataSource" ref="dataSource" />
	</beans:bean>

	<!-- provider -->
	<authentication-manager>
		<authentication-provider>
			<jdbc-user-service data-source-ref="dataSource"
				role-prefix=""
				users-by-username-query="select username, password, enabled from users where username = ?"
				authorities-by-username-query="select username, authority from authorities where username = ?" />
		</authentication-provider>
	</authentication-manager>
</beans:beans>
[web.xml] 수정하기
	<context-param>
		<param-name>contextConfigLocation</param-name>
		<param-value>/WEB-INF/spring/root-context.xml
					/WEB-INF/spring/security-db-context.xml
		</param-value>
	</context-param>
[admin.jsp]
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
    
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>    
<%@ taglib uri="http://www.springframework.org/security/tags" prefix="sec" %>
    
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
<h1>/sample/admin page</h1>
 
 
<p>principal : <sec:authentication property="principal"/></p>
<%-- <p>MemberVO : <sec:authentication property="principal.member"/></p>
<p>사용자이름 : <sec:authentication property="principal.member.userName"/></p> --%>
<p>사용자아이디 : <sec:authentication property="principal.username"/></p>
<%--<p>사용자 권한 리스트  : <sec:authentication property="principal.member.authList"/></p>--%>
 
 
<a href="/customLogout">Logout</a>
 
 
</body>
</html>

 

 

 

 

========================================================================================================================================================

 

[security-db-context.xml] 설명

[security-db-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"
	xsi:schemaLocation="http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security.xsd
      http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

	<http>
		<intercept-url pattern="/login/loginForm"
			access="permitAll" />
		<intercept-url pattern="/" access="permitAll" />
		<intercept-url pattern="/admin/**"
			access="hasRole('ADMIN')" />
		<intercept-url pattern="/**"
			access="hasAnyRole('USER, ADMIN')" />

		<!-- 로그인 페이지 커스텀화 -->
		<form-login login-page="/login/loginForm"
			default-target-url="/"
			authentication-failure-url="/login/loginForm?error"
			username-parameter="id" password-parameter="password" />

		<logout logout-url="/logout" logout-success-url="/" />

		<!-- 403 에러 처리 -->
		<access-denied-handler
			error-page="/login/accessDenied" />
	</http>

	<beans:bean id="userDetailsService"
		class="org.springframework.security.core.userdetails.jdbc.JdbcDaoImpl">
		<beans:property name="dataSource" ref="dataSource" />
	</beans:bean>

	<!-- 여기추가 -->
	<beans:bean id="customNoOpPasswordEncoder"
		class="edu.bit.ex.security.CustomNoOpPasswordEncoder" />

	<!-- provider -->
	<authentication-manager>
		<authentication-provider>

			<!-- 여기추가 -->
			<password-encoder ref="customNoOpPasswordEncoder" />
			<jdbc-user-service data-source-ref="dataSource"
				role-prefix=""
				users-by-username-query="select username, password, enabled from users where username = ?"
				authorities-by-username-query="select username, authority from authorities where username = ?" />
		</authentication-provider>
	</authentication-manager>
</beans:beans>

403에러 처리 수정

 

<!-- 403 에러 처리 -->
<access-denied-handler
error-page="/login/accessDenied" />
</http> //HomeController.java에 있는 폴더경로랑 똑같이 맞춰주기

 

 

인터셉터도 수정

<http>
<intercept-url pattern="/login/loginForm" access="permitAll" />
<intercept-url pattern="/" access="permitAll" />
<intercept-url pattern="/admin/**" access="hasRole('ADMIN')" />
<intercept-url pattern="/**" access="hasAnyRole('USER, ADMIN')" />

//반드시 제한이 제일 큰걸 위로 해서 순서대로 넣기

 

[home.jsp]에서

 [<a href="/ex/user/userHome">유저 홈</a>] 가 intercept-url "/**"에서 걸린다★★

(USER나 ADMIN)인증이 안되어있기때문에

user나 admin인증이 되면 유저홈 또는 관리자홈이 들어갈수있게 된다.

 

---member로 로그인하고 관리자홈을 들어가면 "Access Denied!"가 뜬다.

intercept에서 ADMIN만 /admin/**을 들어갈수 있게 했기 때문에

 

<logout logout-url="/logout" logout-success-url="/" />

↑이건 디폴트로 주기!

 

 

 

 

 

오늘의 과제

 

EMP에 있는 ename과 empno 활용해서 로그인하기

 

ex. blake 를 아이디로 넣고 empno인 7698로 비번을 넣으면 로그인되게하기
blake는 manager임.
manager은 관리자홈에 들어갈 수 있음
만약 smith , 7369로 로그인하면 clerk이기 때문에 유저홈은 들어가지지만 관리자홈은 들어갈수 없다.

 

 

정답이 나오기 전까지 오류 원인 :

1. 쿼리문 오류

"select ename as username, CASE WHEN job ='MANAGER' THEN 'ROLE_ADMIN' else 'ROLE_USER' END as authority from emp04 where ename = ?" 에 JOB CASE WHEN~~이런식으로 줌. 그리고 then admin이있으면 else로 무조건 user도 줬어야함. 그래야 user값을 가지기 때문

2.로그인할때 아이디 대문자로 써줘야함

--해결방법有 where UPPER(ename) LIKE UPPER(?) 를 추가한다.

users-by-username-query="select ename as username, empno 
		as password,enabled from emp04 where UPPER(ename) LIKE UPPER(?)" 
authorities-by-username-query="select ename as username, CASE WHEN job ='MANAGER' 
		THEN 'ROLE_ADMIN' else 'ROLE_USER' END as authority from emp04 where ename = ?" />

 

3. USER, ADMIN과 ROLE_USER, ROLE_ADIMIN의 차이

security-db-context.xml에서 access="hasAnyRole('ROLE_USER, ROLE_ADMIN')" /> 이런부분을 그냥 'USER', 'ADMIN' 이라고했더니 user든 admin이든 전부 유저홈 관리자홈에 접근 불가됨. 앞에 ROLE_ 붙여주니까 그제서야 매니저 권한과 유저권한 가짐

 

==========

enabled 테이블 생성

(생성안하고 그냥 쿼리문을 1 as enabled이나 그냥 1 로 줘도 상관없다.)

alter table emp04 add enable varchar2(200);
insert into emp04(enable) values('1');
[security-db-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"
	xsi:schemaLocation="http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security.xsd
      http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

	<http>
		<intercept-url pattern="/login/loginForm"
			access="permitAll" />
		<intercept-url pattern="/" access="permitAll" />
		<intercept-url pattern="/admin/**"
			access="hasRole('ROLE_ADMIN')" />
		<intercept-url pattern="/**"
			access="hasAnyRole('ROLE_USER, ROLE_ADMIN')" />

		<!-- 로그인 페이지 커스텀화 -->
		<form-login login-page="/login/loginForm"
			default-target-url="/"
			authentication-failure-url="/login/loginForm?error"
			username-parameter="id" password-parameter="password" />

		<logout logout-url="/logout" logout-success-url="/" />

		<!-- 403 에러 처리 -->
		<access-denied-handler
			error-page="/login/accessDenied" />
	</http>

	<beans:bean id="userDetailsService"
		class="org.springframework.security.core.userdetails.jdbc.JdbcDaoImpl">
		<beans:property name="dataSource" ref="dataSource" />
	</beans:bean>

	<!-- 여기추가 -->
	<beans:bean id="customNoOpPasswordEncoder"
		class="edu.bit.ex.security.CustomNoOpPasswordEncoder" />

	<!-- provider -->
	<authentication-manager>
		<authentication-provider>

			<!-- 여기추가 -->
			<password-encoder ref="customNoOpPasswordEncoder" />
			<jdbc-user-service data-source-ref="dataSource"
				role-prefix=""
				users-by-username-query="select ename as username, empno as password,enabled from emp04 where ename = ?"
				authorities-by-username-query="select ename as username, CASE WHEN job ='MANAGER' THEN 'ROLE_ADMIN' else 'ROLE_USER' END as authority from emp04 where ename = ?" />
		</authentication-provider>
	</authentication-manager>
</beans:beans>

해당소스파일↓

spring_security5_emp.zip
0.04MB

 

 

 

728x90

'코딩 > 수업 정리' 카테고리의 다른 글

21.02.22 [062] Mon  (0) 2021.02.22
21.02.19 [061] Fri  (0) 2021.02.19
21.02.17 [059] Wed  (0) 2021.02.17
21.02.16 [058] Tue  (0) 2021.02.16
21.02.15 [057] Mon  (0) 2021.02.15

댓글