개발자의 서재
Chaptor.04 - DTO, Repository, 로그인API 생성 본문
SpringBootProject/SringBoot_JWT_RestApi
Chaptor.04 - DTO, Repository, 로그인API 생성
ironmask431 2022. 4. 3. 19:01
<진행할 것>
- DTO 생성
- Repository 관련 코드 생성
- 로그인API, 관련 로직 생성
1. DTO 패키지 생성
2. LoginDto.java 생성
package com.leesh.springbootjwttutorial.dto;
import lombok.*;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
@Getter
@Setter
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class LoginDto {
//@NotNull = requestBody로 입력받을때 not null 체크
@NotNull
@Size(min=3, max=50)
private String email;
@NotNull
@Size(min=3, max=100)
private String password;
}
3. TokenDto.java 생성
package com.leesh.springbootjwttutorial.dto;
import lombok.*;
@Getter
@Setter
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class TokenDto {
private String token;
}
4. UserDto.java 생성
package com.leesh.springbootjwttutorial.dto;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.leesh.springbootjwttutorial.entity.User;
import lombok.*;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
@Getter
@Setter
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class UserDto {
private Long userId;
@NotNull //requestBody로 입력받을 때 null 비허용
@Size(min=3, max=50)
private String email;
//회원가입 테스트코드에서 오류발생 (password를 get하지 못함)하여 주석처리함.
//@JsonProperty(access = JsonProperty.Access.WRITE_ONLY)
@NotNull
@Size(min=3, max=100)
private String password;
public UserDto(User user){
this.userId = user.getUserId();
this.email = user.getEmail();
}
}
5. repository 패키지 생성 + UserRepository 인터페이스 생성
package com.leesh.springbootjwttutorial.repository;
import com.leesh.springbootjwttutorial.entity.User;
import org.springframework.data.jpa.repository.EntityGraph;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.Optional;
public interface UserRepository extends JpaRepository<User,Long> {
//유저정보를 조회할 때 권한(Authority)정보도 같이 조회함.
@EntityGraph(attributePaths = "authorities")
Optional<User> findOneWithAuthoritiesByEmail(String email);
}
7. service 패키지 생성 + CustomUserDetailsService.java 생성
package com.leesh.springbootjwttutorial.service;
import com.leesh.springbootjwttutorial.entity.User;
import com.leesh.springbootjwttutorial.repository.UserRepository;
import lombok.RequiredArgsConstructor;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Component;
import java.util.List;
import java.util.stream.Collectors;
@RequiredArgsConstructor
@Component("userDetailsService")
public class CustomUserDetailsService implements UserDetailsService {
private final UserRepository userRepository;
public UserDetails loadUserByUsername(final String email){
return userRepository.findOneWithAuthoritiesByEmail(email)
.map(user -> createUser(email,user))
.orElseThrow(()-> new UsernameNotFoundException(email+"-> DB에서 찾을 수 없습니다."));
}
private org.springframework.security.core.userdetails.User createUser
(String email, User user){
if(!user.isActivated()){
throw new RuntimeException(email + "-> 활성화되어 있지 않습니다.");
}
List<GrantedAuthority> grantedAuthorities = user.getAuthorities().stream()
.map(authority -> new SimpleGrantedAuthority(authority.getAuthorityName()))
.collect(Collectors.toList());
return new org.springframework.security.core.userdetails.User(user.getEmail()
,user.getPassword(), grantedAuthorities
);
}
}
8. 로그인을 처리할 AuthController.java 생성
package com.leesh.springbootjwttutorial.controller;
import com.leesh.springbootjwttutorial.dto.LoginDto;
import com.leesh.springbootjwttutorial.dto.TokenDto;
import com.leesh.springbootjwttutorial.jwt.JwtFilter;
import com.leesh.springbootjwttutorial.jwt.TokenProvider;
import lombok.RequiredArgsConstructor;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.validation.Valid;
/**
* 로그인 API 컨트롤러
*/
@RequiredArgsConstructor
@RestController
@RequestMapping("/api/auth")
public class AuthController {
private final TokenProvider tokenProvider;
private final AuthenticationManagerBuilder authenticationManagerBuilder;
//로그인api, 성공 시 JWT토큰 리턴
@PostMapping("/login")
public ResponseEntity<TokenDto> authorize(@Valid @RequestBody LoginDto loginDto){
//입력받은 email, password 로 UsernamePasswordAuthenticationToken 생성
UsernamePasswordAuthenticationToken authenticationToken =
new UsernamePasswordAuthenticationToken(loginDto.getEmail(), loginDto.getPassword());
//UsernamePasswordAuthenticationToken 으로 authentication 생성
//SecurityContext에 authentication set.
Authentication authentication = authenticationManagerBuilder.getObject().authenticate(authenticationToken);
SecurityContextHolder.getContext().setAuthentication(authentication);
//jwt토큰생성
String jwt = tokenProvider.createToken(authentication);
//header에 jwt토큰 추가 ("Bearer "+ jwt 토큰 형태로 입력됨.)
HttpHeaders httpHeaders = new HttpHeaders();
httpHeaders.add(JwtFilter.AUTHORIZATION_HEADER,"Bearer "+ jwt);
//토큰정보와 헤더를 response 리턴해줌.
return new ResponseEntity<>(new TokenDto(jwt), httpHeaders, HttpStatus.OK);
}
}
9. 구동 후 postman으로 로그인 테스트 > 토큰발급 정상 확인
10. postman 에서 response의 데이터를 전역변수에 저장해서 다른 request 시 사용 할 수있다.
(로그인시 response로 받은 토큰을 다른 request 요청 시 헤더에 넣어서 요청 할 수 있음.)
- 로그인 api 의 Tests 탭에 아래와 같이 입력
var jsonData = JSON.parse(responseBody)
pm.globals.set("jwt_tutorial_token",jsonData.token);
- 다른 request 에서 Authorization 탭에서 Type : Bearer Token 선택
Token 항목에 {{jwt_tutorial_token}} 이라고 입력
'SpringBootProject > SringBoot_JWT_RestApi' 카테고리의 다른 글
Chaptor.06 - 상품,주문 entity, repository, dto, servcie, controller (API) 추가 (0) | 2022.04.03 |
---|---|
Chaptor.05 - 회원가입 API 생성 , 권한검증 테스트 (0) | 2022.04.03 |
Chaptor.03 - JWT코드, Security 설정 추가 (0) | 2022.04.03 |
Chaptor.02 - JPA Entity생성 + h2 console 에서 확인 (0) | 2022.04.01 |
Chaptor.01 - 스프링부트 기초세팅 + 스프링 시큐리티 설정 + Hello API 생성 (0) | 2022.04.01 |
Comments