redis로 리더보드 만들기

짱구·2023년 1월 27일
0

redis

목록 보기
8/8

리더보드란?

게임에서 상위랭커, 쇼핑몰에서 인기상품과 같이 실시간 랭킹!

RDBMS로 구현?

RDB의 경우

update query는 한 행에 접근하므로 빠른 성능을 가짐

Update ranking Set score = 1550 Where userId = A;

조회 query는 데이터를 정렬하거나 Count query와 같은 집계 연산을 수행해야되므로 데이터가 많아질수록 속도가 엄청나게 느려짐!

ex) 상위 5개 출력

Select userId From ranking Ordery By score Desc Limit 0,5;

순위 컬럼을 만들어서 해결?

  • update시 순위가 변동 될경우 다른 모든 데이터 로우에서 순위 컬럼을 변경을 해줘야함 (비효율적)

Redis를 사용했을 때

장점

  • 순위 데이터에 적합한 Sorted-Set의 자료구조를 사용하면 score를 통해 자동으로
    정렬됨
  • 용도에 특화된 오퍼레이션(Set 삽입/업데이트, 조회)이 존재하므로 사용이 간단함
  • 자료구조의 특성으로 데이터 조회가 빠름(범위 검색, 특정 값의 순위 검색)
  • 빈번한 액세스에 유리한 In-memory DB의 속도
  • 비교적 매우 쉬운 구현

실습

선언

private final static String LEADER_BOARD_KEY = "leaderBoard"; //redis 변수명
private final StringRedisTemplate redisTemplate;

UserId와 점수 등록

public boolean setUserScore(String userId, int score){
   ZSetOperations zSetOps = redisTemplate.opsForZSet(); //Sorted Set 선언
   zSetOps.add(LEADER_BOARD_KEY,userId,score);
   return true;
}

UserId로 등수 확인

public Long getUserRanking(String userId){
    ZSetOperations zSetOps = redisTemplate.opsForZSet();
    return zSetOps.reverseRank(LEADER_BOARD_KEY, userId);
}

상위권 등수 확인

public List<String> getTopRank(int limit){
    ZSetOperations zSetOps = redisTemplate.opsForZSet();
    Set<String> range = zSetOps.reverseRange(LEADER_BOARD_KEY, 0, limit-1);
    return new ArrayList<>(range);
}

출처 및 링크 : fastcampus

profile
코드를 거의 아트의 경지로 끌어올려서 내가 코드고 코드가 나인 물아일체의 경지

0개의 댓글