이번 프로젝트는 창고 중개 플랫폼 웹 애플리케이션을 개발하는 팀 프로젝트였다.
그중 나는 사용자, 공급자의 로그인, 회원가입, 수정, 삭제 구현과 더블어 세션 유지까지 하는 파트를 담당했다
사용자와 공급자의 코드 메커니즘은 유사하기 때문에 사용자 관점에서만 리뷰하는점 참고해주세요!
먼저 회원정보를 담는 DB는 MariaDB를 사용하였고, Java와 데이터베이스를 상호작용을 할 수 있는 MyBatis 프레임워크를 이용하고 Annotation 방식을 선택했다.
먼저 사용자 회원가입에 필요한 쿼리문이다.
CREATE TABLE user (
user_id VARCHAR(20) PRIMARY KEY NOT NULL,
user_pwd VARCHAR(20) NOT NULL,
user_name VARCHAR(10) NOT NULL,
user_tel VARCHAR(20),
user_email VARCHAR(30),
user_addr VARCHAR(50),
user_jumin VARCHAR(14) UNIQUE
);
이 쿼리문을 가지고 자바와 상호작용 할 수 있는 MyBatis Annotation 방식을 Interface파일에 코드 로직을 구현하였다.
import lombok.Data;
@Data
public class UserDto {
private String user_id, user_pwd, user_name;
private String user_tel, user_email, user_addr, user_jumin, user_repwd;
}
UserDto 클래스는 사용자 정보를 나타내는 데이터 객체로 사용되며, Lombok의 @Data 어노테이션을 통해 간단하게 필수 메소드들을 생성한다.
이러한 목적으로 만들어진 클래스로, 데이터를 보관하고 전송하기 위한 목적으로 만들었다.
@Mapper
public interface DataMapperInter {
@Insert("INSERT INTO user (user_id, user_pwd, user_name, user_tel, user_email, user_addr, user_jumin) \r\n"
+ "VALUES (#{user_id}, #{user_pwd}, #{user_name}, #{user_tel}, #{user_email}, #{user_addr}, #{user_jumin})")
int userInsertData(UserDto userDto);
MyBatis에서 제공 @Insert
을 사용해 데이터베이스에 새로운 사용자 정보를 삽입(INSERT)하기 위한 SQL 문이다.
userInsertData라는 이름의 메서드를 선언하며, 파라미터로 UserDto 객체인 userDto를 받는다.
메서드의 반환 값은 데이터를 삽입한 후 영향을 미친 행의 수를 나타내고 데이터베이스 작업의 성공 또는 실패를 판단하기 위해 반환 타입을 int로 선언
@Repository
public class UserDao {
@Autowired
private DataMapperInter dataMapperInter;
private boolean isEmpty(String value) {
return value == null || value.trim().isEmpty();
}
private boolean joinUserData(UserDto userDto) {
boolean b = false;
if (isEmpty(userDto.getUser_id()) ||
isEmpty(userDto.getUser_pwd()) ||
isEmpty(userDto.getUser_name()) ||
isEmpty(userDto.getUser_tel()) ||
isEmpty(userDto.getUser_email()) ||
isEmpty(userDto.getUser_addr()) ||
!userDto.getUser_id().matches("^[a-zA-Z\\d]{4,}$") ||
!userDto.getUser_tel().matches("^[0-9-]+$") ||
!userDto.getUser_jumin().matches("^\\d{6}-\\d{7}$") ||
!userDto.getUser_pwd().equals(userDto.getUser_repwd()) ||
!userDto.getUser_name().matches("^[가-힣]{2,}$") ||
!userDto.getUser_pwd().matches("^.{4,}$") ||
!userDto.getUser_email().matches("^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,4}$")) {
b = false;
} else {
b = true;
}
return b;
}
userDao에 @Repository
적용함으로서 이 클래스는 퍼시스턴스 레이어 역할을한다.
즉, DB나 파일같은 외부 I/O 작업을 처리함, DAO는 DB 서버에 접근하여 SQL문을 실행할 수 있는 객체이다.
@Autowired
어노테이션을 사용하여 dataMapperInter를 주입함으로써 데이터베이스와 상호작용할 수 있는 구현체를 UserDao 클래스에 제공한다.
회원가입 필드란이 공백이거나 JavaScript으로 작성한 정규식에 맞지 않았음에도 불구하고 데이터가 정상적으로 삽입되는 걸 확인했다.
userInsertData()
는 UserDto 객체에 대한 각 필드의 유효성을 확인하고, 모든 유효성 검사를 통과한 경우에만 true를 반환.
따라서 비정상적으로 작성했을 때는 데이터가 들어가는 걸 방지하기 위해 따로 로직을 추가하였다.
public boolean userInsertData(UserDto userDto) {
boolean b = false;
try {
if (joinUserData(userDto)) {
int re = dataMapperInter.userInsertData(userDto);
if (re > 0) {
b = true;
}
}
} catch (Exception e) {
e.printStackTrace();
}
eturn b;
}
UserDto 객체인 userDto를 파라미터로 받아 사용자가 입력한 회원가입 데이터를 처리하고 성공 여부를 boolean 값으로 반환한다.
joinUserData(userDto) 메서드를 호출하여 사용자가 입력한 데이터의 유효성을 검사하고
데이터가 유효할 때 (true 값일 때) 데이터베이스에 사용자의 회원가입 데이터를 삽입하기 위해 메서드 호출
re 변수의 값이 양수(보통 1)인 경우, 데이터베이스 삽입이 성공한 것으로 간주하고 b 변수를 true로 설정하여 회원가입 작업의 성공 여부를 나타낸다.
// 사용자 회원가입에서 가입 버튼을 클릭하고 성공 했을 때 (성공)
@PostMapping("userJoinClick")
public String userLoginOK(UserDto userDto) {
boolean b = userDao.userInsertData(userDto);
if(b) {
return "user/userlogin";
} else {
// 회원 가입 정보를 다시 입력하도록 유도하기 위해 userjoin.html 이동
return "user/userjoin";
}
}
userJoinClick 핸들러 매핑을 클라이언트가 Post방식으로 요청했을 때 메서드가 수행된다.
여기서 b는 앞서 userInsertData()
의 반환 값이다.
그 반환값이 true이면 회원가입에 성공하고 바로 로그인 페이지로 이동한다.