티스토리 뷰
과제요구사항
- 회원 가입 페이지
- 회원가입 버튼을 클릭하기
- 닉네임, 비밀번호, 비밀번호 확인을 입력하기
- 닉네임은 최소 3자 이상, 알파벳 대소문자(a~z, A~Z), 숫자(0~9)로 구성하기
- 비밀번호는 최소 4자 이상이며, 닉네임과 같은 값이 포함된 경우 회원가입에 실패로 만들기
- 비밀번호 확인은 비밀번호와 정확하게 일치하기
- 데이터베이스에 존재하는 닉네임을 입력한 채 회원가입 버튼을 누른 경우 "중복된 닉네임입니다." 라는 에러메세지를 프론트엔드에서 보여주기
- 회원가입 버튼을 누르고 에러메세지가 발생하지 않는다면 로그인 페이지로 이동시키기
- 로그인 페이지
- 로그인, 회원가입 버튼을 만들기
- 닉네임, 비밀번호 입력란 만들기
- 로그인 버튼을 누른 경우 닉네임과 비밀번호가 데이터베이스에 등록됐는지 확인한 뒤, 하나라도 맞지 않는 정보가 있다면 "닉네임 또는 패스워드를 확인해주세요"라는 메세지를 프론트엔드에서 보여주기
- 로그인 버튼을 눌러서 에러 메세지가 발생하지 않는다면 전체 게시글 목록 조회 페이지로 이동시키기
- 로그인 검사
- 아래 페이지를 제외하고 모두 로그인 한 경우만 볼 수 있도록 하기
- 회원가입 페이지
- 로그인 페이지
- 게시글 목록 조회 페이지
- 게시글 조회 페이지
- 로그인을 하지 않거나 올바르지 않은 경로로 접속한 사용자가 로그인이 필요한 경로에 접속한 경우 "로그인이 필요합니다." 라는 메세지를 프론트엔드에서 띄워주고 로그인 페이지로 이동시키기
- 로그인 한 사용자가 로그인 페이지 또는 회원가입 페이지에 접속한 경우 "이미 로그인이 되어있습니다."라는 메세지를 띄우고 전체 게시글 목록 조회 페이지로 이동시키기
- 아래 페이지를 제외하고 모두 로그인 한 경우만 볼 수 있도록 하기
- 소셜 로그인 기능 만들기
- 카카오 소셜 로그인이 가능하도록 하기
- 게시글 조회 페이지 > 댓글 목록 조회
- 로그인 하지 않은 사용자도 댓글 목록 조회가 가능하도록 하기
- 현재 조회중인 게시글에 작성된 모든 댓글을 목록 형식으로 볼 수 있도록 하기
- 댓글 목록 위에 댓글 작성란 만들기
- 댓글 작성에 관한 기능은 5번 요구사항으로 연결하기
- 댓글 목록 중, 내가 작성한 댓글인 경우 댓글 수정, 댓글 삭제 버튼 만들기
- 댓글 수정 버튼을 누르면 6번 요구사항으로 연결하기
- 댓글 삭제 버튼을 누르면 7번 요구사항으로 연결하기
- 제일 최근 작성된 댓글을 맨 위에 띄우기
- 게시글 조회 페이지 > 댓글 작성
- 로그인 한 사용자만 댓글 작성이 가능하도록 하기
- 게시글 조회 페이지 하단에 댓글 내용을 입력할 수 있는 댓글 작성 버튼 만들기
- 로그인 하지 않은 사용자가 댓글 작성란을 누르면 "로그인이 필요한 기능입니다." 라는 메세지를 띄우고 로그인 페이지로 이동시키기
- 댓글 내용란을 비워둔 채 댓글 작성 버튼을 누르면 "댓글 내용을 입력해주세요" 라는 메세지를 띄우기
- 댓글 내용을 입력하고 댓글 작성 버튼을 누른 경우 작성한 댓글을 추가하기
- 게시글 조회 페이지 > 댓글 수정
- 내가 작성한 댓글만 수정 가능하도록 하기
- 댓글 본문이 사라지고, 댓글 내용, 저장 버튼 생성하기
- 댓글 내용에는 이전에 입력했던 댓글 내용을 기본 값으로 채우기
- 수정할 댓글 내용은 비어 있지 않도록 하기
- 저장 버튼을 누른 경우 기존 댓글의 내용을 새로 입력한 댓글 내용으로 바꾸기
- 게시글 조회 페이지 > 댓글 삭제
- 내가 작성한 댓글만 삭제 가능하도록 하기
- "정말로 삭제하시겠습니까?" 메세지를 띄우고, 확인/취소 버튼 중 "확인" 버튼을 누른 경우 목록에서 해당 댓글을 삭제하기
- 취소를 누른 경우 삭제되지 않고 그대로 유지하기
- 회원가입 테스트 코드 작성
- 회원가입시 구현한 아래 조건을 검사하는 테스트 코드를 작성하기
- 닉네임은 최소 3자 이상, 알파벳 대소문자(a~z, A~Z), 숫자(0~9)로 이루어져 있어야 합니다.
- 비밀번호는 최소 4자 이상이며, 닉네임과 같은 값이 포함된 경우 회원가입에 실패합니다.
- 비밀번호 확인은 비밀번호와 정확하게 일치해야 합니다.
- 데이터베이스에 존재하는 닉네임을 입력한 채 회원가입 버튼을 누른 경우 "중복된 닉네임입니다." 라는 에러메세지가 발생합니다.
- 테스트 코드 실행 시 실제로는 데이터베이스에 연결되지 않도록 하기
- 각 조건 별로 2개 이상의 테스트 케이스가 존재하도록 하기
- 회원가입시 구현한 아래 조건을 검사하는 테스트 코드를 작성하기
스프링 과제하면서 헷갈리는 내용 기록
상대경로, 절대경로
절대경로란 지정되어 있어 변경할 수 없는 경로를 뜻한다.
상대경로란 상대적으로 변경될 수 있는 경로를 말한다. (디렉토리, 파일명)
이상태에서 login.html에서 style.css를 link로 받을려면
<link rel="stylesheet" type="text/css" href="/css/style.css"> 경로를 이렇게 지정해주면 된다.
헷갈려서 처음에 href="/static/css/style.css" 이렇게 했었는데 css가 적용이 안되서 당황했었다.
현재 적용할려는 파일 기준으로 생각해보면 될것같다. (상위폴더로 갈경우에는 ../를 붙여주면 된다.)
Optional
Optional을 사용하면 객체에 null도 받을 수 있게되어서 따로 null일경우에 대한 예외처리를 할 필요가 없어지게 된다.
그리고 isPresent()를 사용하여 객체가 null인지 아닌지 알 수 있다.
패스워드 암호화
passwordEncoder 스프링 시큐리티에서 제공해주고, 권고되고있는 BCrypt 해시함수를 사용하여 암호화한다.
사용방법은 WebSecurityConfig에서 Bean등록을 해주고 사용하는 곳에서 DI 주입을 받아 사용하면된다.
스프링 유효성검사
validation을 이용해 백엔드 유효성 검사를 진행하였다.
validation에서 제공하는 어노테이션을 사용해 Dto에대해 유효성 검사를 해줬다.
@Valid 어노테이션을 통해 requestDto에 대해 유효성검사를 진행하고 에러가 존재할 시 다시 회원가입창을 불러내 에러를 표시해준다. 그리고 Dto에 지정된 유효성 검사 말고도 아이디, 이메일 중복체크와 비밀번호가 일치하는지 확인을 해줘야 하기 때문에 if문을 추가했다.
회원가입 form이고 여기서 th:if를 통해 에러가 존재할시 에러를 출력해주도록 해놨다.
Repository 함수 직접선언
JPA 내장함수를 사용할 경우에는 예외처리를 해줘야한다. (Optional을 사용해도됨)
List로 repository에 findByBoardId()를 선언한경우에는 null에 대한 예외처리를 안해줘도된다. (왜그런지는 정확히모르겠음..)
- (21.05.26 수정)
=> 컬렉션은 조회시 없을경우 null을 보내지않고 빈 컬렉션을 제공해주기 때문에 null처리를 안해줘도 된다.
자바스크립트에서 타임리프 문법
자바스크립트에서 타임리프 문법을 사용할려면 [ [ ${} ] ] 와 같은 문법으로 사용할 수 있다.
비밀번호에 닉네임과 같은값이 포함되어있으면 에러보내기
여기서는 indexof를 사용했다 -1이면 같은값이 없기때문에 -1을 제외한 모든 값에 에러를 보내게 해놨다.
문자열체크 contains를 사용해도 될것같다.
form 안에 onclick시 onsubmit 호출되는 현상
form안에 button 에서 onclick이 발동되면 form에 onsubmit이 같이 호출이되는 상황이 일어난다.
이걸 해결해주기 위해서는 button태그를 사용하는것이 아니라 input태그에서 type을 button으로 바꿨더니 onsubmit이 호출이 안된다.
form th:field로 인한 th:value값 안먹는 현상
th:field = "*{text}"는 th:object에 멤버변수 값인데 controller에서 넘겨준값이 빈 객체를 넘겨줬기 때문에 값이 아무것도 없어서 th:value를 넣어줘도 겹쳐서 그러는지 input에 value값이 안들어간다.
그래서 어쩔수 없이 자바스크립트를 통해서 넣어줬다.
작성일자 'yyyy-MM-dd'로 나타내기
Timestamped를 상속받아 createdAt, modifiedAt 게시글에 생성일자와 마지막변경시점을 db에 저장하고있는데 이것을 게시글 생성일자 'yyyy-MM-dd' 로 나타내주고 싶어서 #temporals.format() 함수를 사용하여 나타내었다. (MM만 대문자인 이유는 mm은 분 을 나타내고 MM이 월 을 나타낸다.)
타임리프 문법
객체에서 username이라는 맴버변수를 가지고 오고 싶을때는 자바에서는 객체.getUsername()이렇게 사용하는데 타임리프에서는 객체.username 이런식으로 사용하면된다. (빨간줄은 무시해도 된다.)
페이징
JPA에서 Pageable을 지원해줘서 페이징 처리와 sort처리를 쉽게할 수 있는데 sort는 따로 사용하지는 않았다.
페이징 번호를 처리해주기 위해서 startPage와 endPage를 구해서 model로 값을 보내준다.
전체 게시글 보여주는 페이지에서 model값을 받아 #number.sequnce 유틸리티 메서드를 사용해 startPage 부터 endPage까지 페이징 번호를 적용시켜준다. 그리고 각 번호를 누를때마다 이동할 수 있도록 href를 걸어준다.
그리고 classappend를 사용해 특정 조건일 경우만 class에 disabled가 먹도록 설정해줬다 왜냐하면 첫번째 페이지일 경우 previous가 눌리면 안되고 현재 자신의 page도 눌리면 안되기 때문이다.
i는 실제 보여지는 페이징 번호이기 때문에 1부터 시작해서 인덱스 값이랑 비교를 할 경우에는 -1을 해준다.
'항해99' 카테고리의 다른 글
[항해99] 6주차 회고 클론코딩 (리디셀렉트) (0) | 2021.04.11 |
---|---|
[항해99] 5주차 회고 주특기-2 (Spring) (0) | 2021.04.04 |
[항해99] 4주차 회고 주특기-1 (Spring) (0) | 2021.03.28 |
[항해99] Spring 심화반 강의 (4) 정리 (0) | 2021.03.27 |
[항해99] Spring 심화반 강의(3) 정리 (0) | 2021.03.27 |