레디스에서 회원 데이터를 저장/조회
This commit is contained in:
28
README.md
28
README.md
@@ -226,6 +226,34 @@ springCloudBus
|
||||
-- 메시지 발행/수신 확인
|
||||
[POST] http://localhost:8090/member/assu
|
||||
|
||||
-- 레디스 설치확인
|
||||
C:\Users\ju>netstat -an|findstr 6379
|
||||
TCP 127.0.0.1:6379 0.0.0.0:0 LISTENING
|
||||
C:\Users\ju>redis-cli
|
||||
127.0.0.1:6379> ping
|
||||
PONG
|
||||
127.0.0.1:6379> set key value
|
||||
OK
|
||||
127.0.0.1:6379> get key
|
||||
"value"
|
||||
127.0.0.1:6379>
|
||||
|
||||
-- 레디스 실행
|
||||
redis-server.bat 실행
|
||||
|
||||
-- 모든 키 확인
|
||||
127.0.0.1:6379> keys *
|
||||
1) "member"
|
||||
|
||||
-- key-value 확인 (get 은 String 만 다루므로 여기선 에러로 표시)
|
||||
127.0.0.1:6379> get member
|
||||
(error) WRONGTYPE Operation against a key holding the wrong kind of value
|
||||
|
||||
-- 모든 키 삭제
|
||||
127.0.0.1:6379> flushall
|
||||
OK
|
||||
|
||||
|
||||
```
|
||||
|
||||
|
||||
|
||||
@@ -67,7 +67,6 @@ public class EventServiceApplication {
|
||||
|
||||
/**
|
||||
* 레디스 서버에 작업 수행 시 사용할 RedisTemplate 객체 생성
|
||||
* @return
|
||||
*/
|
||||
@Bean
|
||||
public RedisTemplate<String, Object> redisTemplate() {
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
package com.assu.cloud.eventservice.client;
|
||||
|
||||
import com.assu.cloud.eventservice.config.CustomConfig;
|
||||
import com.assu.cloud.eventservice.model.Member;
|
||||
import com.assu.cloud.eventservice.repository.MemberRedisRepository;
|
||||
import com.assu.cloud.eventservice.utils.CustomContext;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.http.HttpMethod;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
/**
|
||||
* 회원 데이터 필요 시 회원 서비스 호출 전 레디스 캐시 먼저 확인
|
||||
*/
|
||||
@Component
|
||||
public class MemberCacheRestTemplateClient {
|
||||
|
||||
private static final Logger logger = LoggerFactory.getLogger(MemberCacheRestTemplateClient.class);
|
||||
|
||||
private final RestTemplate restTemplate;
|
||||
private final MemberRedisRepository memberRedisRepository;
|
||||
private final CustomConfig customConfig;
|
||||
|
||||
public MemberCacheRestTemplateClient(RestTemplate restTemplate, MemberRedisRepository memberRedisRepository, CustomConfig customConfig) {
|
||||
this.restTemplate = restTemplate;
|
||||
this.memberRedisRepository = memberRedisRepository;
|
||||
this.customConfig = customConfig;
|
||||
}
|
||||
|
||||
String URL_PREFIX = "/api/mb/member/"; // 회원 서비스의 주울 라우팅경로와 회원 클래스 주소
|
||||
|
||||
/**
|
||||
* 회원 아이디로 레디스에 저장된 Member 클래스 조회
|
||||
*/
|
||||
private Member checkRedisCache(String userId) {
|
||||
try {
|
||||
return memberRedisRepository.findMember(userId);
|
||||
} catch (Exception e) {
|
||||
logger.error("======= Error encountered while trying to retrieve member {} check Redis Cache., Exception {}", userId, e);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 레디스 캐시에 데이터 저장
|
||||
*/
|
||||
private void cacheMemberObject(Member member) {
|
||||
try {
|
||||
memberRedisRepository.saveMember(member);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
logger.error("======= Unable to cache member {} in Redis. Exception {}", member.getId(), e);
|
||||
}
|
||||
}
|
||||
|
||||
public Member getMember(String userId) {
|
||||
|
||||
Member member = checkRedisCache(userId);
|
||||
|
||||
// 레디스에 데이터가 없다면 원본 데이터에서 데이터를 조회하기 위해 회원 서비스 호출
|
||||
if (member != null) {
|
||||
logger.debug("======= Successfully retrieved an Member {} from the redis cache: {}", userId, member);
|
||||
return member;
|
||||
}
|
||||
|
||||
logger.debug("======= Unable to locate member from the redis cache: {}", userId);
|
||||
|
||||
ResponseEntity<Member> restExchange =
|
||||
restTemplate.exchange(
|
||||
"http://" + customConfig.getServiceIdZuul() + URL_PREFIX + "{userId}", // http://localhost:5555/api/mb/member/userInfo/rinda
|
||||
HttpMethod.GET,
|
||||
null,
|
||||
Member.class,
|
||||
userId
|
||||
);
|
||||
|
||||
// 캐시 레코드 저장
|
||||
member = restExchange.getBody();
|
||||
|
||||
// 조회한 객체를 캐시에 저장
|
||||
if (member != null) {
|
||||
cacheMemberObject(member);
|
||||
}
|
||||
|
||||
return member;
|
||||
}
|
||||
}
|
||||
@@ -1,8 +1,10 @@
|
||||
package com.assu.cloud.eventservice.controller;
|
||||
|
||||
import com.assu.cloud.eventservice.client.MemberCacheRestTemplateClient;
|
||||
import com.assu.cloud.eventservice.client.MemberRestTemplateClient;
|
||||
import com.assu.cloud.eventservice.client.MemberFeignClient;
|
||||
import com.assu.cloud.eventservice.config.CustomConfig;
|
||||
import com.assu.cloud.eventservice.model.Member;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
@@ -15,11 +17,14 @@ public class EventController {
|
||||
private final CustomConfig customConfig;
|
||||
private final MemberFeignClient memberFeignClient;
|
||||
private final MemberRestTemplateClient memberRestTemplateClient;
|
||||
private final MemberCacheRestTemplateClient memberCacheRestTemplateClient;
|
||||
|
||||
public EventController(CustomConfig customConfig, MemberFeignClient memberFeignClient, MemberRestTemplateClient memberRestTemplateClient) {
|
||||
public EventController(CustomConfig customConfig, MemberFeignClient memberFeignClient, MemberRestTemplateClient memberRestTemplateClient,
|
||||
MemberCacheRestTemplateClient memberCacheRestTemplateClient) {
|
||||
this.customConfig = customConfig;
|
||||
this.memberFeignClient = memberFeignClient;
|
||||
this.memberRestTemplateClient = memberRestTemplateClient;
|
||||
this.memberCacheRestTemplateClient = memberCacheRestTemplateClient;
|
||||
}
|
||||
|
||||
@GetMapping(value = "name/{nick}")
|
||||
@@ -49,6 +54,14 @@ public class EventController {
|
||||
return "[EVENT] Gift is " + gift;
|
||||
}
|
||||
|
||||
/**
|
||||
* 레디스 캐싱 데이터 사용
|
||||
*/
|
||||
@GetMapping(value = "{userId}")
|
||||
public Member userInfo(@PathVariable("userId") String userId) {
|
||||
return memberCacheRestTemplateClient.getMember(userId);
|
||||
}
|
||||
|
||||
/*@GetMapping("userInfo/{name}")
|
||||
public String userInfo(@PathVariable("name") String name) {
|
||||
return "[EVENT-MEMBER] " + memberRestTemplateClient.userInfo(name);
|
||||
|
||||
@@ -2,6 +2,9 @@ package com.assu.cloud.eventservice.repository;
|
||||
|
||||
import com.assu.cloud.eventservice.model.Member;
|
||||
|
||||
/**
|
||||
* 레디스에 액세스해야 하는 클래스에 주입된 인터페이스
|
||||
*/
|
||||
public interface MemberRedisRepository {
|
||||
void saveMember(Member member);
|
||||
void updateMember(Member member);
|
||||
|
||||
@@ -1,30 +1,38 @@
|
||||
package com.assu.cloud.eventservice.repository;
|
||||
|
||||
import com.assu.cloud.eventservice.model.Member;
|
||||
import com.netflix.discovery.converters.Auto;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.redis.core.HashOperations;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
|
||||
import org.springframework.data.redis.serializer.StringRedisSerializer;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
|
||||
/**
|
||||
* 부트스트랩 클래스에서 정의한 RedisTemplate 빈을 사용하여 레디스 서버와 통신
|
||||
*/
|
||||
@Repository
|
||||
public class MemberRedisRepositoryImpl implements MemberRedisRepository {
|
||||
|
||||
private static final String HASH_NAME = "member"; // 회원 데이터가 저장되는 레디스 서버의 해시명
|
||||
private RedisTemplate<String, Member> redisTemplate;
|
||||
private final RedisTemplate<String, Member> redisTemplate;
|
||||
private HashOperations hashOperations; // HashOperation 클래스는 레디스 서버에 데이터 작업을 수행하는 스프링 헬퍼 메서드의 집합
|
||||
|
||||
public MemberRedisRepositoryImpl() {
|
||||
super();
|
||||
}
|
||||
|
||||
public MemberRedisRepositoryImpl(RedisTemplate<String, Member> redisTemplate) {
|
||||
public MemberRedisRepositoryImpl(RedisTemplate redisTemplate) {
|
||||
this.redisTemplate = redisTemplate;
|
||||
}
|
||||
|
||||
@PostConstruct
|
||||
public void init() {
|
||||
hashOperations = redisTemplate.opsForHash();
|
||||
|
||||
// 키와 값을 명시적으로 직렬화해주지 않으면 default serializer 로 JdkSerializationRedisSerializer 를 사용하는데
|
||||
// 그러면 \xac\xed\x00\x05t\x00\x06member 이런 식으로 저장됨
|
||||
redisTemplate.setKeySerializer(new StringRedisSerializer());
|
||||
redisTemplate.setValueSerializer(new GenericJackson2JsonRedisSerializer());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -15,5 +15,5 @@ spring:
|
||||
brokers: localhost
|
||||
#redis
|
||||
redis:
|
||||
server: redis
|
||||
server: localhost
|
||||
port: 6379
|
||||
@@ -3,6 +3,9 @@ package com.assu.cloud.memberservice.controller;
|
||||
import com.assu.cloud.memberservice.client.EventRestTemplateClient;
|
||||
import com.assu.cloud.memberservice.config.CustomConfig;
|
||||
import com.assu.cloud.memberservice.event.source.SimpleSourceBean;
|
||||
import com.assu.cloud.memberservice.model.Member;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import javax.servlet.ServletRequest;
|
||||
@@ -11,6 +14,8 @@ import javax.servlet.ServletRequest;
|
||||
@RequestMapping("/member")
|
||||
public class MemberController {
|
||||
|
||||
private static final Logger logger = LoggerFactory.getLogger(MemberController.class);
|
||||
|
||||
private final CustomConfig customConfig;
|
||||
private final EventRestTemplateClient eventRestTemplateClient;
|
||||
private final SimpleSourceBean simpleSourceBean;
|
||||
@@ -60,4 +65,17 @@ public class MemberController {
|
||||
simpleSourceBean.publishMemberChange("SAVE", userId);
|
||||
}
|
||||
|
||||
/**
|
||||
* 이벤트 서비스에서 캐시 용도로 회원 데이터 조회
|
||||
*/
|
||||
@GetMapping("{userId}")
|
||||
public Member userInfoCache(@PathVariable("userId") String userId) {
|
||||
logger.debug("====== 회원 서비스 호출!");
|
||||
|
||||
// DB 를 조회하여 회원 데이터 조회 (간편성을 위해 아래와 같이 리턴함)
|
||||
Member member = new Member();
|
||||
member.setId(userId);
|
||||
member.setName("rinda");
|
||||
return member;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,24 @@
|
||||
package com.assu.cloud.memberservice.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
public class Member implements Serializable {
|
||||
private String id;
|
||||
private String name;
|
||||
|
||||
public String getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(String id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user