Spring

Spring STEP 12 - Spring Security 2

2023. 6. 21. 12:21
728x90

★ 회원가입

 

■ 파일 생성

com.test.controller > MemberController.java
com.test.mapper > MemberMapper.java(I)
com.test.domain > MemberDTO.java
                > AuthDTO.java

- src/main/resources > com > test > mapper > MemverMapper.xml

- views > register.jsp
        > registerok.jsp

 

■ 기초 셋팅

  • MemberMapper.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.test.mapper.MemberMapper">

</mapper>
  • MemberDTO.java
import java.util.List;

import lombok.Data;

@Data
public class MemberDTO {

	private String userid;
	private String userpw;
	private String username;
	private String regdate;
	private String updatedate;
	private String enabled;
	
	private List<AuthDTO> authlist;
}
  • AuthDTO.java
import lombok.Data;

@Data
public class AuthDTO {
	private String userid;
	private String auth;
}
  • MemberController.java
@Controller
public class MemberController {

	@Autowired
	private MemberMapper mapper;
	
	@Autowired
	private PasswordEncoder encoder;

	@GetMapping("/register.do")
	public String register() {
		
		return "register";
	}
	
	@PostMapping("/registerok.do")
	public String registerok() {
		
		return "registerok";
	}
}
  • 스캔 추가 -> root-context.xml -> namespace -> mybatis -> 스캔추가
<mybatis-spring:scan base-package="com.test.mapper"/>

 

■ 회원가입 Form 만들기 -> register.jsp

<%@ include file="/WEB-INF/views/inc/header.jsp" %>

<h2>Register Page</h2>

<form method="post" action="/security/registerok.do">
    <table class="vertical">
        <tr>
            <th>아이디</th>
            <td><input type="text" name="userid" required></td>
        </tr>
        <tr>
            <th>암호</th>
            <td><input type="password" name="userpw" required></td>
        </tr>
        <tr>
            <th>이름</th>
            <td><input type="text" name="username" required></td>
        </tr>
        <tr>
            <th>권한</th>
            <td>
                <select name="auth">
                    <option value="1">일반회원</option>
                    <option value="2">관리자</option>					
                </select>
            </td>
        </tr>
    </table>
    <div>
        <input type="submit" value="등록하기">
    </div>
    <!-- CSRF 토큰 -->
    <input type="hidden" name="${_csrf.parameterName}" value="${_csrf.token}">
</form>

 

■ 회원 가입 처리 -> MemberController.java

----------------- MemberController.java---------------------
@PostMapping("/registerok.do")
public String registerok(Model model, MemberDTO dto, int auth) {

    //암호 인코딩
    dto.setUserpw(encoder.encode(dto.getUserpw()));

    int result = mapper.register(dto);
    
    if (auth >= 1) {
        AuthDTO adto = new AuthDTO();
        adto.setUserid(dto.getUserid());
        adto.setAuth("ROLE_MEMBER");
        mapper.registerAuth(adto);
    }
    
    if (auth >= 2) {
        AuthDTO adto = new AuthDTO();
        adto.setUserid(dto.getUserid());
        adto.setAuth("ROLE_ADMIN");
        mapper.registerAuth(adto);
    }

	model.addAttribute("result", result);

    return "registerok";
}
------------------- MemberMapper.java -----------------------
int register(MemberDTO dto);
void registerAuth(AuthDTO adto);
------------------- MemberMapper.xml ------------------------
<insert id="register">

    insert into tbl_member(userid, userpw, username) values (#{userid}, #{userpw}, #{username})

</insert>

<insert id="registerAuth">
    insert into tbl_member_auth(userid, auth) values (#{userid), #{auth})
</insert>

 

■ registerok.jsp

<%@ include file="/WEB-INF/views/inc/header.jsp" %>

<h2>Register OK Page</h2>

<div>${result}</div>

 

★ UserDetailService > 커스텀 UserDetailService

- 여태까지.. username(id), userpassword, enabled, authority
- 추가로 관리하고 싶은 정보가 있으면 직접 UserDetailsService를 구현
  • index.jsp -> 태그 추가
<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>
  • 우리가 가져오고 싶은 정보 > SQL
1. MemberDTO
2. AuthDTO
3. MemberMapper(I)
4. MemberMapper.xml
  • MemberMapper.xml -> select 작성
<resultMap type="com.test.domain.MemberDTO" id="memberMap">
  <id property="userid" column="userid" />
  <result property="userid" column="userid" />
  <result property="userpw" column="userpw" />
  <result property="username" column="username" />
  <result property="enabled" column="enabled" />
  <result property="regdate" column="regdate" />
  <result property="updatedate" column="updatedate" />
  <collection property="authlist" resultMap="authMap"></collection>
</resultMap>

<resultMap type="com.test.domain.AuthDTO" id="authMap">
  <result property="userid" column="userid" />
  <result property="auth" column="auth" />
</resultMap>

<select id="read" resultMap="memberMap">
  select
     m.userid,
     m.userpw,
     m.username,
     m.enabled,
     m.regdate,
     m.updatedate,
     a.auth
  from tbl_member m
     left outer join tbl_member_auth a
        on m.userid = a.userid
           where m.userid = #{userid}
</select>

 

■ 파일 생성

src/test/java > "com.test.mapper" > MapperTest.java
  • 코드작성
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("file:src/main/webapp/WEB-INF/spring/root-context.xml")
@Log4j
public class MapperTest {

	@Autowired
	private MemberMapper mapper;
	
	@Test
	public void testRead() {
		
		MemberDTO dto = mapper.read("dong");
		
		log.info(dto);
		
		dto.getAuthlist().forEach(adto -> log.info(adto));
		
	}
}

 

■ CustomUserDetailServie 구성

- com.test.auth > "CustomUserDetailsService.java"
- com.test.domain > "CustomUser.java"
  • 코드 작성
@Log4j
public class CustomUserDetailsService implements UserDetailsService {@Override
	public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
		
		//기본 > username, password, enabled, authority
		//재정의 > 기본 + 추가 정보
	
		return null;
	}

}
  • Security-context.xml -> bean 추가 
<!-- 유저 정보 객체 -->
<bean id="customUserDetailsService" class="com.test.auth.CustomUserDetailsService"></bean>
  • Security-context.xml -> security 추가
<security:authentication-manager>
    <security:authentication-provider user-service-ref="customUserDetailsService">
        <security:password-encoder ref="bcryptPasswordEncoder"/>
    </security:authentication-provider>
</security:authentication-manager>
  • CustomUser.java -> 코드 작성
@Getter
public class CustomUser extends User {

	public MemberDTO member;
	
	public CustomUser(String username, String password
            , Collection<? extends GrantedAuthority> authorities) {
      super(username, password, authorities);
   }
   
   public CustomUser(MemberDTO dto) {
	   
	   //MemberDTO > Customer(User)
      
      super(dto.getUserid(), dto.getUserpw(), dto.getAuthlist().stream().map(auth -> new SimpleGrantedAuthority(auth.getAuth())).collect(Collectors.toList()));
      
      this.member = dto;
   }
	
}

 

■ info -> 만들기

  • MemberController.java -> 추가
@GetMapping("/info.do")
public String info() {

    return "info";
}
  • info.jsp
<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>  

<%@ include file="/WEB-INF/views/inc/header.jsp" %>

<h2>Info Page</h2>

<div class="message" title="principal">
    <sec:authentication property="principal"/>
</div>

<div class="message" title="MemberDTO">
    <sec:authentication property="principal.member"/>
</div>

<div class="message" title="사용자 아이디">
    <sec:authentication property="principal.username"/>
</div>

<div class="message" title="사용자 아이디">
    <sec:authentication property="principal.member.userid"/>
</div>

<div class="message" title="사용자 이름">
    <sec:authentication property="principal.member.username"/>
</div>

<div class="message" title="사용자 권한">
    <sec:authentication property="principal.member.authlist"/>
</div>
  • 결과

 

■ 스프링 시큐리티 > JSP 페이지 + 권한 적용 > 스프링 시큐리티 표현식

  • hasRole()
  • isAnonymous()
  • isAuthenticated()
  • header.jsp -> 작업
<%@ 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="sec" uri="http://www.springframework.org/security/tags" %>  

<!-- header.jsp -->
<header>
	<h1>Spring Security</h1>
	<ul>
		<li><a href="/security/index.do">Index</a></li>
		
		<sec:authorize access="hasRole('ROLE_MEMBER')">
		<li><a href="/security/member.do">Member</a></li>
		</sec:authorize>
		
		<sec:authorize access="hasRole('ROLE_ADMIN')">
		<li><a href="/security/admin.do">Admin</a></li>
		</sec:authorize>
		<li class="divider"></li>
		
		<sec:authorize access="isAnonymous()">
		<li><a href="/security/customlogin.do">Login</a></li>
		<li class="divider"></li>	
		<li><a href="/security/register.do">Register</a>
		</sec:authorize>
		
		<sec:authorize access="isAuthenticated()">
		<li><a href="/security/customlogout.do">Logout</a></li>
		<li class="divider"></li>
		<li><a href="/security/info.do">Info</a>
		</sec:authorize>
		
		
		
	</ul>
</header>

 

★ 자동 로그인(Remember-me)

  • 스프링 시큐리티에 기본으로 탑재
  • 정해진 테이블 구현
  • DB 생성
create table persistent_logins (
   username varchar(64) not null,
   series varchar(64) primary key,
   token varchar(64) not null,
   last_used timestamp not null
);
  • Security-context.xml -> 자동로그인 설정
<!-- 자동 로그인 -->
<security:remember-me data-source-ref="dataSource" token-validity-seconds="8640000" />
728x90
저작자표시 비영리 변경금지 (새창열림)

'Spring' 카테고리의 다른 글

Spring STEP 13 - Board 2  (0) 2023.06.22
Spring STEP 13 - Board  (0) 2023.06.21
Spring STEP 11 - Spring Security  (0) 2023.06.20
Spring STEP 10 - MyBatisSimple  (0) 2023.06.19
Spring STEP 9 - AOP  (0) 2023.06.19
'Spring' 카테고리의 다른 글
  • Spring STEP 13 - Board 2
  • Spring STEP 13 - Board
  • Spring STEP 11 - Spring Security
  • Spring STEP 10 - MyBatisSimple
IT의 큰손
IT의 큰손
IT계의 큰손이 되고 싶은 개린이의 Log 일지
Developer Story HouseIT계의 큰손이 되고 싶은 개린이의 Log 일지
IT의 큰손
Developer Story House
IT의 큰손
전체
오늘
어제
  • 분류 전체보기 (457)
    • 정보처리기사 필기 (18)
    • 정보처리기사 실기 (12)
    • 정보처리기사 통합 QUIZ (12)
    • 빅데이터 (11)
    • 안드로이드 (11)
    • 웹페이지 (108)
    • 자바 (49)
    • SQLD (3)
    • 백준 알고리즘 (76)
    • 데이터베이스 (41)
    • 깃허브 (2)
    • Library (14)
    • Server (31)
    • 크롤링&스크래핑 (3)
    • Spring (23)
    • Vue.js (13)
    • React (27)

블로그 메뉴

  • 홈
  • 태그
  • 방명록

공지사항

  • Developer Stroy House

인기 글

태그

  • 프론트엔드
  • java
  • IT개발자
  • 개발자
  • 정보보안전문가
  • IT자격증공부
  • 웹개발자
  • 데이터베이스
  • html
  • 알고리즘
  • DBA
  • jsp
  • React
  • 웹페이지
  • ajax
  • 앱개발자
  • 자바
  • jquery
  • it
  • 백엔드
  • JavaScript
  • css
  • IT자격증
  • DB
  • 코딩테스트
  • 백준
  • 정보처리기사
  • 정보처리기사필기
  • 웹개발
  • 개발블로그

최근 댓글

최근 글

Designed By hELLO
IT의 큰손
Spring STEP 12 - Spring Security 2
상단으로

티스토리툴바

단축키

내 블로그

내 블로그 - 관리자 홈 전환
Q
Q
새 글 쓰기
W
W

블로그 게시글

글 수정 (권한 있는 경우)
E
E
댓글 영역으로 이동
C
C

모든 영역

이 페이지의 URL 복사
S
S
맨 위로 이동
T
T
티스토리 홈 이동
H
H
단축키 안내
Shift + /
⇧ + /

* 단축키는 한글/영문 대소문자로 이용 가능하며, 티스토리 기본 도메인에서만 동작합니다.