본문 바로가기
멀티캠퍼스 풀스택 과정/백엔드

Spring:7 로그인(DB연동), 로그아웃, 회원정보수정(DB연동) -4

by 이쟝 2022. 3. 17.

1. DB에 있는 회원정보와 일치하면 로그인 성공시키기

1. MemberDAO에 로그인을 확인할 수 있는 loginCheck( ) 생성한다.

package com.mycampus.myappy.dao;

import com.mycampus.myappy.vo.MemberVO;

public interface MemberDAO {
	// 로그인
	public MemberVO loginCheck(MemberVO vo); // 사용자가 입력한 정보가 MemberVO에 
}

2. MemberService에 로그인을 확인할 수 있는 loginCheck( ) 생성한다. 

package com.mycampus.myappy.service;

import com.mycampus.myappy.vo.MemberVO;

public interface MemberService {
	// 로그인
	public MemberVO loginCheck(MemberVO vo);
}

3. MemberServiceImpl에 MemberService를 구현하기 위한 loginCheck( )를 생성한다. 

package com.mycampus.myappy.service;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.mycampus.myappy.dao.MemberDAO;
import com.mycampus.myappy.vo.MemberVO;

@Service
public class MemberServiceImpl implements MemberService {
	
	@Autowired 
	MemberDAO dao; // DAO의 memberInsert를 사용하기 위해서 DAO를 객체 생성
	
	@Override
	public MemberVO loginCheck(MemberVO vo) {
		return dao.loginCheck(vo);
	}

}

4. MemberMapper.xml에 쿼리문을 작성한다. 

- 데이터를 가져오는 것이기 때문에 <select> 문을 사용한다.
- select userid, username from member where userid="사용자가 입력한 id" and userpwd="사용자가 입력한 pwd";
- 사용자가 입력한 userid, userpwd와 일치하는 레코드의 userid와 username을 최종 Controller로 보낸다. 
[resultType]
- xml에 select 문을 선언할 때는 output을 받아줄 객체를 꼭 선언해야 한다. select문을 실행하면 결과가 생성되는데 이 결과를 담을 객체를 resultType 속성에 지정한다. 
- resultType에는 패키지 이름을 포함한 전체 클래스명을 지정하던지 객체의 alias를 지정할 수 있다. 
    - 만약 자바 클래스로 매핑하려면 매핑하려는 자바 클래스의 전체 경로를 입력한다.
    ex) resultType="com.mycampus.myappy.vo.MemberVO"
    - 만약 int형 객체로 쿼리 실행 결과값을 받는다면 int형으로 입력한다. 
    ex) resultType="int"
<?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.mycampus.myappy.dao.MemberDAO">
	<select id="loginCheck" resultType="com.mycampus.myappy.vo.MemberVO">
		select userid, username from member
		where userid=#{userid} and userpwd=#{userpwd}
	</select>
</mapper>

5. loginOk를 MemberController에 맵핑하기

signIn.jsp의 폼의 액션

<form method="post" action="/myappy/member/loginOk" id="loginFrm" onsubmit="return LoginFrmCheck()">

MemberController

package com.mycampus.myappy.controller;

import javax.servlet.http.HttpSession;

@Controller
public class MemberController {
	
	@Autowired
	MemberService service;
	
	// 로그인
	@RequestMapping(value="/member/loginOk", method=RequestMethod.POST)
	public ModelAndView loginFormOk(MemberVO vo, HttpSession session) {
		// request userid, userpwd와 일치하는 레코드의 userid와 username을 선택한다.
		MemberVO mVO = service.loginCheck(vo);
		ModelAndView mav = new ModelAndView();
		
		if(mVO!=null) {
			session.setAttribute("logId", mVO.getUserid());
			session.setAttribute("logName", mVO.getUsername());
			session.setAttribute("logInStatus", "Y");
			mav.setViewName("redirect:/");
		}else {
			mav.setViewName("redirect:signIn");
		}
		return mav;
	}
	
}

 

더보기

- 여러 데이터를 받기 때문에 MemberVO를 첫 번째 매개변수로 받고, Session에 아이디와 이름을 저장해야 하기 때문에 HttpSession을 두 번째 매개변수로 받았다.

- Model파라미터 방식으로 메서드에(Model model) 파라미터를 넣어주고 String형태로 리턴한다. 값을 넣을 때 addAttribute()를 사용한다. 

 

- ModelAndView컴포넌트 방식으로 ModelAndView 객체를 생성해서 객체형태로 리턴한다. 값을 넣을때 addObject()를 사용하고, setViewName()으로 보낼 곳 View를 세팅한다.

- header.jspf에 logInstatus로 로그인 로그아웃 상태를 받는다.(로그인일때 로그아웃, 회원수정이 보이고 로그아웃일 때 로그인, 회원가입이보인다.)


2. 로그아웃 구현하기

header.jspf

a href="myappy/member/signOut"이다. DB와 상관없기 때문에 바로 controller에 맵핑!

<li><a href="${url}/member/signOut">로그아웃</a></li>

MemberController

	// 로그아웃
	@GetMapping(value="/member/signOut")
	public ModelAndView logout(HttpSession session) {
		// 세션 객체를 지우면 세션에 저장된 로그인정보 등 모든데이터가 삭제되고 새로운 세션을 할당한다. 
		// 새로운 세션을 할당한다. 
		session.invalidate();   // 세션 내용 삭제 
		ModelAndView mav = new ModelAndView();
		mav.setViewName("redirect:/");  // 삭제 되면 홈으로 이동
		return mav;
	}

3. 회원정보 수정하기 폼 만들기

- 회원 정보(회원 가입할 때 넣었던 정보)폼이 나와야 한다. 
- 로그인 되었을 때만 회원정보를 수정 가능하게 한다. 
- 선택 기준: userid(pk)가 유일한 값이기 때문에 session에 저장되어 있는 userid를 매개변수로 가져와서 정보를 수정할 수 있게 한다. 메서드는 memberSelect( )
- 정보를 가져와야하니까 select문 사용한다.

header.jspf

a href="myappy/member/signInEdit"이다. 

<a href="${url}/member/signInEdit">회원정보수정</a>

 

1. MemberDAO에 회원정보를 가져올 수 있는 memberSelect( ) 생성한다.

package com.mycampus.myappy.dao;

import com.mycampus.myappy.vo.MemberVO;

public interface MemberDAO {
	// 회원정보수정 폼
	public MemberVO memberSelect(String userid);
}

2. MemberService에 회원정보를 가져올 수 있는 memberSelect( ) 생성한다.

package com.mycampus.myappy.service;

import com.mycampus.myappy.vo.MemberVO;

public interface MemberService {
	// 회원정보수정 폼
	public MemberVO memberSelect(String userid);
}

3. MemberServiceImpl에 MemberService를 구현하기 위한  memberSelect( )를 생성한다.

package com.mycampus.myappy.service;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.mycampus.myappy.dao.MemberDAO;
import com.mycampus.myappy.vo.MemberVO;

@Service
public class MemberServiceImpl implements MemberService {
	
	@Autowired 
	MemberDAO dao; // DAO의 memberInsert를 사용하기 위해서 DAO를 객체 생성

	@Override
	public MemberVO memberSelect(String userid) {
		return dao.memberSelect(userid);
	}

}

4. MemberMapper.xml에 쿼리문을 작성한다. 

- 데이터를 가져오는 것이기 때문에 <select> 문을 사용한다.
- select userid, username, tel, email from member where userid="사용자의 아이디";
- userid, userpwd, username, tel
<?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.mycampus.myappy.dao.MemberDAO">
	<select id="memberSelect" resultType="com.mycampus.myappy.vo.MemberVO">
		select userid, username, tel, email from member
		where userid=#{param1}
	</select>
</mapper>

5. signInEdit를 MemberController에 맵핑하기

package com.mycampus.myappy.controller;

import javax.servlet.http.HttpSession;

@Controller
public class MemberController {
	
	@Autowired
	MemberService service;
	
	// 회원정보수정폼
	@GetMapping("/member/signInEdit")
	public ModelAndView memberEdit(HttpSession session) {
		
		String userid = (String)session.getAttribute("logId");
		MemberVO vo = service.memberSelect(userid);
		ModelAndView mav = new ModelAndView();
		
		mav.addObject("vo", vo);    // signInEdit에게 vo안에 데이터를 넘겨준다.
		mav.setViewName("/member/signInEdit");
		
		return mav;
	}
}

 

더보기

String userid = (String)session.getAttribute("logId")

- String userid에는 현재 로그인 되어 있는 아이디가 들어간다.(세션에서 가져오기), 세션은 object이기 때문에 String으로 형변환을 해줘야 한다. 

MemberVO mVO = new MemberVO();
session.setAttribute("logId", mVO.getUserid());

- 위 코드와 동일하다!

mav.addObject("vo", vo)

- vo는 새로 생성되는 변수이다. (뷰페이지에서 사용) 이름 임의 지정

6. signEdit.jsp 폼을 생성한다.

- 회원가입할 때 했던 비밀번호와 일치하지 않으면 수정이 안되게한다!
- vo를 쓸 수 있는 이유는 controller에서 임의 생성해주었기 때문이다!
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<link rel="stylesheet" href="/myappy/css/signInEditStyle.css" type="text/css"/>
<script src="/myappy/js/signInEditJs.js"></script>
<div class="container">
	<h1>회원정보수정 폼</h1>
	<form method="post" action="/myappy/member/signEditOk" id="eForm">
	<ul>
		<li>아이디</li>
		<li>${vo.userid}</li>
		<li>비밀번호</li> <!-- 회원가입할 때 했던 비밀번호를 모르면 못고치게 한다.-->
		<li><input type="password" name="userpwd" id="userpwd" placeholder="비밀번호입력"/></li>
		<li>이름</li>
		<li><input type="text" name="username" id="username" value="${vo.username}"/></li>
		<li>연락처</li>
		<li>
			<select name="tel1">
				<option value="010" <c:if test="${vo.tel1=='010'}">selected</c:if> > 010</option>
				<option value="02" <c:if test="${vo.tel1=='02'}">selected</c:if> > 02</option>
				<option value="031" <c:if test="${vo.tel1=='031'}">selected</c:if> > 031</option>
				<option value="051" <c:if test="${vo.tel1=='051'}">selected</c:if> > 051</option>
			</select> -
			<input type="text" name="tel2" id="tel2" maxlength="4" value="${vo.tel2}"/> -
			<input type="text" name="tel3" id="tel3" maxlength="4" value="${vo.tel3}"/>
		</li>
		<li>이메일</li>
		<li><input type="text" name="email" id="email" value="${vo.email}"/></li>
		<li><input type="submit" value="회원정보수정하기"/></li>
	</ul>
	</form>
</div>
더보기

signInEditStyle.css

@charset "UTF-8";
#eForm li{
	float:left; 
	height:40px; 
	line-height:40px;
	width:20%;
	border-bottom: 1px solid #ddd;
}
#eForm li:nth-child(2n){
	width:80%;
}
#eForm li:last-of-type{
	width:100%;
}

signInEditJs.js 

$(function(){
	$("#eForm").submit(function(){
		if($("#userpwd").val()==''){
			alert("비밀번호 입력 후 수정하세요");
			return false;
		}
		if($("#username").val()==''){ //DB에서 username -> not null
			alert("이름을 입력하세요");
			return false;
		}
		let reg = /^[0-9]{3,4}$/;
		let reg2 = /^[0-9]{4}$/;
		if(!reg.test($("#tel2").val()) || !reg2.test($("#tel3").val())){
			alert("전화번호를 입력하세요");
			return false;
		}
		return true;
	});
});

4. 회원정보 수정 폼을 DB와 연결하기

- 회원정보수정 폼에서 회원정보수정하기를 눌렀을 때 DB와 연결되어서 수정되어야 한다.(signInEdit.jsp의 action인 signInEditOk으로 이동!)
- 정보를 업데이트해야하니까 update문을 사용한다. 
- 회원정보 수정에 성공하면 바뀐 수정 폼이 나오고 수정에 실패하면 바뀌지 않은 수정 전 폼이 나온다.
- insert나 update는 int형 반환! 

1. MemberDAO에 회원정보를 수정할 수 있는 memberUpdate( ) 생성한다.

package com.mycampus.myappy.dao;

import com.mycampus.myappy.vo.MemberVO;

public interface MemberDAO {
	// 회원정보수정DB
	public int memberUpdate(MemberVO vo);
}

2. MemberService에 회원정보를 수정할 수 있는 memberUpdate( ) 생성한다.

package com.mycampus.myappy.service;

import com.mycampus.myappy.vo.MemberVO;

public interface MemberService {
	// 회원정보수정DB
	public int memberUpdate(MemberVO vo);
}

3. MemberServiceImpl에 MemberService를 구현하기 위한  memberUpdate( ) 생성한다.

package com.mycampus.myappy.service;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.mycampus.myappy.dao.MemberDAO;
import com.mycampus.myappy.vo.MemberVO;

@Service
public class MemberServiceImpl implements MemberService {
	
	@Autowired 
	MemberDAO dao; // DAO의 memberInsert를 사용하기 위해서 DAO를 객체 생성
	
	@Override
	public int memberUpdate(MemberVO vo) {
		return dao.memberUpdate(vo);
	}
}

4. MemberMapper.xml에 쿼리문을 작성한다. 

- 데이터를 업데이트 하는 것이기 때문에 update문을 사용한다.
- update member set username='사용자가 입력한 username', tel='사용자가 입력한 tel', email='사용자가 입력한 email' where userid='userid' and userpwd='userpwd'; => userid와 userpwd는 변경되면 xx
<?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.mycampus.myappy.dao.MemberDAO">
	<update id="memberUpdate">
		update member set username=#{username}, tel=#{tel}, email=#{email}
		where userid=#{userid} and userpwd=#{userpwd}
	</update>
</mapper>

5. signEditOk를 MemberController에 맵핑하기

package com.mycampus.myappy.controller;

import javax.servlet.http.HttpSession;

@Controller
public class MemberController {
	
	@Autowired
	MemberService service;
	
	// 회원정보수정(DB와 연결)
	@PostMapping("/member/signEditOk")
	public ModelAndView memberEditOk(MemberVO vo, HttpSession session) {
		vo.setUserid((String)session.getAttribute("logId")); //session 로그인 아이디
		service.memberUpdate(vo);
		ModelAndView mav = new ModelAndView();
		mav.setViewName("redirect:signInEdit");
		return mav;
	}
}