참고
Redis Publish / Subscribe
NOTE
Pub/Sub ⇒ 특정한 주제(topic)에 대하여 해당 topic을 구독한 모두에게 메시지를 발행하는 방법이다!
ex) 한명이 채팅방에 채팅을 올리면, 채팅방의 모든 인원에게 메세지가 올라감!
메시징 미들웨어 사용의 장점
•
비동기
◦
통신의 비동기 처리가 가능하다.
•
낮은 결합도
◦
송신자와 수신자가 직접 서로 의존하지 않고 공통 미들웨어에 의존한다.
•
탄력성
◦
구성원들간에 느슨한 연결로 인해 일부 장애가 생겨도 영향이 최소화 된다.
Redis Pub/Sub의 특징
•
In-Memory 기반이라 매우 빠르게 메세지를 받을 수 있다!
•
메시지를 단순히 던지는 시스템이기 때문에, 메시지를 큐에서 따로 보관하지 않는다.
◦
수신자가 메시지를 받는것을 보장하지 않는다.
◦
수신자가 아무도 없어도 pub을 실행하면 메시지가 사라진다.
•
Kafka의 컨슈머 그룹같은 분산처리 개념이 없다.
◦
클라이언트가 늘어날수록 성능이 저하된다.
사용경우
•
실시간으로 빠르게 전송되어야 하는 메시지
•
메시지 유실을 감내할 수 있는 케이스
•
최대 1회 전송패턴이 적합한 경우
•
Subscriber들이 다양한 채널을 유동적으로 바꾸면서 한시적으로 구독하는 경우
Pub / Sub 명령어
NOTE
Redis 서버를 매개로, 통신하며 클라이언트는 Redis 서버내 채널을 생성한다.
이 채널을 구독(sub)하거나, 메시지(pub)를 보낼 수 있음
# 채널 구독
subscribe channel [채널 이름]
# 메시지를 지정한 채널로 송신
publish channel [메시지]
# subscribe로 등록한 채널 구독 해제
unsubscribe channle [채널 이름]
Bash
복사
스프링 부트 Redis 채팅방 구현
NOTE
@Configuration
public class RedisConfig {
@Bean
public RedisConnectionFactory redisConnectionFactory(){
return new LettuceConnectionFactory();
}
@Bean
RedisMessageListenerContainer redisContainer(){
final RedisMessageListenerContainer container = new RedisMessageListenerContainer();
container.setConnectionFactory(redisConnectionFactory());
return container;
}
}
Java
복사
Reids pub/sub 생성
@SpringBootApplication
public class HelloworldApplication implements CommandLineRunner {
@Autowired
private ChatService chatService;
public static void main(String[] args) {
SpringApplication.run(HelloworldApplication.class, args);
}
@Override
public void run(String... args) {
System.out.println("Application started..");
chatService.enterChatRoom("chat1");
}
}
Java
복사
Application 시작시 chat1 채팅방에 입장
@Service
public class ChatService implements MessageListener {
@Autowired
private RedisMessageListenerContainer container;
@Autowired
RedisTemplate<String, String> redisTemplate;
public void enterChatRoom(String chatRoomName) {
// 채널 등록
container.addMessageListener(this, new ChannelTopic(chatRoomName));
Scanner in = new Scanner(System.in);
while (in.hasNextLine()) {
String line = in.nextLine();
if (line.equals("q")) {
System.out.println("Quit...");
break;
}
redisTemplate.convertAndSend(chatRoomName, line);
}
// 끝나면료
container.removeMessageListener(this);
}
@Override
public void onMessage(Message message, byte[] pattern) {
System.out.println("Message: " + message.toString());
}
}
Java
복사
onMessage로 pub에 메시지가 오면 바로 받아서 출력한다!