redis 특강

brave_chicken·2024년 7월 8일

잇(IT)생 챌린지

목록 보기
84/90

build.gradle

dependencies {
	implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
	implementation 'org.springframework.boot:spring-boot-starter-data-redis'
	implementation 'org.springframework.boot:spring-boot-starter-thymeleaf'
	implementation group: 'org.modelmapper', name: 'modelmapper', version: '2.4.0'
	implementation 'org.springframework.boot:spring-boot-starter-web'
	compileOnly 'org.projectlombok:lombok'
	developmentOnly 'org.springframework.boot:spring-boot-devtools'
	runtimeOnly 'com.oracle.database.jdbc:ojdbc11'
	annotationProcessor 'org.projectlombok:lombok'
	testImplementation 'org.springframework.boot:spring-boot-starter-test'
	testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
}

application.properties

spring.application.name=erp
server.port=8088


#db ??? ?? ??
spring.datasource.driver-class-name=oracle.jdbc.driver.OracleDriver
spring.datasource.url=jdbc:oracle:thin:@127.0.0.1:1521:xe
spring.datasource.username=test
spring.datasource.password=test

#spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
#spring.datasource.url=jdbc:mysql://db-nt04n-kr.vpc-pub-cdb.ntruss.com:3306/myerp?serverTimezone=UTC
#spring.datasource.username=myerp
#spring.datasource.password=myerp2024!

#mybatis ??? ?? ??
mybatis.mapper-locations=classpath:/mapper/*.xml
mybatis.type-aliases-package=com.example.erp.dto

#redis
spring.data.redis.host=127.0.0.1
spring.data.redis.port=6379
#spring.data.redis.password=

#jpa????
#???? ??? ???? ?????. drop ??? ???? create
#spring.jpa.hibernate.ddl-auto=create
spring.jpa.hibernate.ddl-auto=none
spring.sql.init.encoding=UTF-8
spring.sql.init.mode=always


#sysout?? ??
spring.jpa.show-sql=true

#JPA log
#??????? ???? ???? sql??
logging.level.org.hibernate.sql=debug
logging.level.org.hibernate.type.descriptor.sql=trace

#JPA? ???? sql? ??? ????
spring.jpa.properties.hibernate.format_sql=true
spring.jpa.properties.hibernate.use_sql_comments=true

jpa.defer-datasource-initialization=true

config

RedisConfig

@Configuration
public class RedisConfig {
    @Value("${spring.data.redis.host}")
    private String host;
    @Value("${spring.data.redis.port}")
    private int port;
    /*@Value("{spring.data.redis.password}")
    private String password;*/

    //LettuceConnectionFactory는 Redis서버와 연결을 설정하고 관리하는 객체
    //이를 통해서 spring data redis내부에서 redis서버와 통신할 ㅅ 있다.
    @Bean
    public RedisConnectionFactory redisConnectionFactory(){
        //config객체를 만들고
        RedisStandaloneConfiguration config =
                new RedisStandaloneConfiguration(host,port);
        //config.setPassword(password);

        //config를 이용해서 factory객체를 만들어서 리턴
        return new LettuceConnectionFactory(config);
    }

    @Bean
    @Primary //빈을 만들때 우선순위 높게 지정
    public RedisTemplate<String,String> redisTemplate(){
        RedisTemplate<String,String> redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(redisConnectionFactory());
        redisTemplate.setKeySerializer(new StringRedisSerializer());
        redisTemplate.setValueSerializer(new StringRedisSerializer());
        //hashes operation을 사용하는 경우
        redisTemplate.setHashKeySerializer(new StringRedisSerializer());
        redisTemplate.setHashValueSerializer(new StringRedisSerializer());

        return redisTemplate;
    }
}

hashes

Subject

  • @RedisHash : redis에 저장할 클래스를 생성
  • value는 redis에 들어갈 객체의 key가 된디
  • 키는 value에 지정한 key:entityid
    =>mysubject : id
@Data
@NoArgsConstructor
@AllArgsConstructor
@RedisHash(value = "mysubject")
public class Subject {
    @Id
    private String id;
    private String name;
    private int price;
    private String info;
}

SubjectHashController

@RestController
@RequiredArgsConstructor
public class SubjectHashController {
    private final SubjectHashService service;
    //request용 response용 dto는 따로 만들어서 작업하기
    //redis에 저장하기
    @PostMapping("/hashtest")
    public Subject save(@RequestBody Subject subject){
        System.out.println(subject);
        return service.save(subject);
    }

    //redis에 저장된 데이터 불러오기
    @GetMapping("/hashtest")
    public Subject find(@RequestParam("id") String id){
        return service.findById(id);
    }
}

SubjectHashRepository

public interface SubjectHashRepository extends CrudRepository<Subject,String> {
}

SubjectHashService

public interface SubjectHashService {
    Subject save(Subject subject);
    Subject findById(String id);

}

SubjectHashServiceImpl

@Service
@RequiredArgsConstructor
public class SubjectHashServiceImpl implements SubjectHashService{
    private final SubjectHashRepository repository;

    @Override
    public Subject save(Subject subject) {
        return repository.save(subject);
    }

    @Override
    public Subject findById(String id) {
        return repository.findById(id).get();
    }
}

sortedset

Product

@Data
@NoArgsConstructor
@AllArgsConstructor
public class Product {
    private String categoryId;//key
    private String productId;//member(sortedset에 저장되는 각 요소)
    private int price;//score
}

SortedSetController

@RestController
@RequiredArgsConstructor
public class SortedSetController {
    private final SortedSetService service;

    @GetMapping("/getzset")
    public Set<ZSetOperations.TypedTuple<String>> getzsetvalues(@RequestParam("key") String key){
        return service.getZsetValues(key);
    }

    @PostMapping("/add")
    public int create(@RequestBody Product newProduct){
        service.createMember(newProduct);
        return service.getRank(newProduct);
    }
}

SortedSetService

public interface SortedSetService {
    //전체 sorted set의 멤버들 조회
    //ZSetOperations은 sortedset을 다루기 위해 여러가지 메소드를 제공하는 인터페이스
    //TypedTuple은 spring data redis에서 제공하는 인터페이스 - sortedset의 자료구조를 모델링한 객체
    Set<ZSetOperations.TypedTuple<String>> getZsetValues(String key);
    //새로운 member를 저장
    void createMember(Product newProduct);
    //매개변수로 정의한 상품의 rank구하기
    int getRank(Product newProduct);
}

SortedSetServiceImpl

@Service
@RequiredArgsConstructor
public class SortedSetServiceImpl implements SortedSetService{
    private final RedisTemplate<String,String> redisTemplate;

    //sortedset에 저장된 모든 member와 score를 조회
    @Override
    public Set<ZSetOperations.TypedTuple<String>> getZsetValues(String key) {
        ZSetOperations<String,String> zSetOperations = redisTemplate.opsForZSet();
        Set<ZSetOperations.TypedTuple<String>> sortedset = zSetOperations.rangeWithScores(key,0,-1);
        return sortedset;
    }

    @Override
    public void createMember(Product newProduct) {
        ZSetOperations<String,String> zSetOperations = redisTemplate.opsForZSet();
        //key,member,score
        zSetOperations.add(newProduct.getCategoryId(),
                newProduct.getProductId(), newProduct.getPrice());
    }

    //정의한 객체의 순위를 리턴
    @Override
    public int getRank(Product newProduct) {
        ZSetOperations<String,String> zSetOperations = redisTemplate.opsForZSet();
        int rank = zSetOperations.rank(newProduct.getCategoryId(),
                newProduct.getProductId()).intValue();
        return rank;
    }
}

C:\Users\주희>cd\

C:\>cd C:\Program Files\Redis

C:\Program Files\Redis>redis-cli

127.0.0.1:6379> keys *
1) "cate001"
2) "mysubject"
3) "mysubject:subject02"
4) "test1"
5) "mysubject:subject01"

127.0.0.1:6379> zrange cate001 0 -1
1) "prd02"

127.0.0.1:6379> zrange cate001 0 -1
1) "prd01"
2) "prd03"
3) "prd02"

본 포스팅은 멀티캠퍼스의 멀티잇 백엔드 개발(Java)의 교육을 수강하고 작성되었습니다.

0개의 댓글