feat: add redis

This commit is contained in:
2025-12-01 20:24:51 +09:00
parent c300771020
commit f6d5901300
7 changed files with 113 additions and 4 deletions

View File

@@ -52,6 +52,9 @@ dependencies {
// actuator // actuator
implementation 'org.springframework.boot:spring-boot-starter-actuator' implementation 'org.springframework.boot:spring-boot-starter-actuator'
// Redis
implementation 'org.springframework.boot:spring-boot-starter-data-redis'
// SpringDoc OpenAPI (Swagger) // SpringDoc OpenAPI (Swagger)
implementation 'org.springdoc:springdoc-openapi-starter-webmvc-ui:2.7.0' implementation 'org.springdoc:springdoc-openapi-starter-webmvc-ui:2.7.0'

View File

@@ -17,6 +17,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class TestDto { public static class TestDto {
private Long id; private Long id;
private Geometry polygon; private Geometry polygon;
private Double centroidX; private Double centroidX;
@@ -29,6 +30,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class CountDto { public static class CountDto {
private String classCd; // 영문코드 private String classCd; // 영문코드
private String className; // 한글명 private String className; // 한글명
private Long count; // 건수 private Long count; // 건수
@@ -40,6 +42,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class CogUrlReq { public static class CogUrlReq {
private Integer beforeYear; private Integer beforeYear;
private Integer afterYear; private Integer afterYear;
private String mapSheetNum; private String mapSheetNum;
@@ -51,6 +54,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class CogUrlDto { public static class CogUrlDto {
private String beforeCogUrl; private String beforeCogUrl;
private String afterCogUrl; private String afterCogUrl;
private Geometry bbox; private Geometry bbox;
@@ -62,6 +66,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class AnalYearList { public static class AnalYearList {
private Long analUid; private Long analUid;
private String analTitle; private String analTitle;
private Integer beforeYear; private Integer beforeYear;
@@ -75,6 +80,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class MapSheetList { public static class MapSheetList {
private String mapSheetNum; private String mapSheetNum;
private String mapSheetName; private String mapSheetName;
private String alias; private String alias;
@@ -86,6 +92,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PolygonFeatureList { public static class PolygonFeatureList {
private String type; private String type;
private List<PolygonFeature> features; // Point 값 private List<PolygonFeature> features; // Point 값
} }
@@ -96,6 +103,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PointFeatureList { public static class PointFeatureList {
private String type; private String type;
private List<PointFeature> features; // Point 값 private List<PointFeature> features; // Point 값
} }
@@ -106,6 +114,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PolygonFeature { public static class PolygonFeature {
private String type; private String type;
private JsonNode geometry; // after 분류 private JsonNode geometry; // after 분류
private PolygonProperties properties; // private PolygonProperties properties; //
@@ -117,6 +126,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PolygonQueryData { public static class PolygonQueryData {
private String type; private String type;
private String geometry; // geoJson String private String geometry; // geoJson String
private Long geoUid; private Long geoUid;
@@ -135,6 +145,7 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PointFeature { public static class PointFeature {
private String type; private String type;
private Geometry geometry; // point private Geometry geometry; // point
private PointProperties properties; // Point 정보 private PointProperties properties; // Point 정보
@@ -146,14 +157,18 @@ public class ChangeDetectionDto {
@NoArgsConstructor @NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PointProperties { public static class PointProperties {
private Long geoUid; private Long geoUid;
private String classCd; // after 분류 private String classCd; // after 분류
} }
@Schema(name = "PolygonProperties", description = "폴리곤 정보") @Schema(name = "PolygonProperties", description = "폴리곤 정보")
@Getter @Getter
@Setter
@NoArgsConstructor
@AllArgsConstructor @AllArgsConstructor
public static class PolygonProperties { public static class PolygonProperties {
private Long geoUid; private Long geoUid;
private Double area; // 면적 private Double area; // 면적
private Integer beforeYear; // 기준년도 private Integer beforeYear; // 기준년도

View File

@@ -5,6 +5,7 @@ import com.kamco.cd.kamcoback.changedetection.dto.ChangeDetectionDto;
import com.kamco.cd.kamcoback.postgres.core.ChangeDetectionCoreService; import com.kamco.cd.kamcoback.postgres.core.ChangeDetectionCoreService;
import java.util.List; import java.util.List;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
@Service @Service
@@ -34,11 +35,14 @@ public class ChangeDetectionService {
return changeDetectionCoreService.getChangeDetectionYearList(); return changeDetectionCoreService.getChangeDetectionYearList();
} }
@Cacheable(value = "changeDetectionPolygon", key = "#analUid + '_' + #mapSheetNum")
public ChangeDetectionDto.PolygonFeatureList getChangeDetectionPolygonList( public ChangeDetectionDto.PolygonFeatureList getChangeDetectionPolygonList(
Long analUid, String mapSheetNum) { Long analUid, String mapSheetNum) {
return changeDetectionCoreService.getChangeDetectionPolygonList(analUid, mapSheetNum); return changeDetectionCoreService.getChangeDetectionPolygonList(analUid, mapSheetNum);
} }
// Geometry 객체 순환 참조 문제로 캐싱 불가
public ChangeDetectionDto.PointFeatureList getChangeDetectionPointList( public ChangeDetectionDto.PointFeatureList getChangeDetectionPointList(
Long analUid, String mapSheetNum) { Long analUid, String mapSheetNum) {
return changeDetectionCoreService.getChangeDetectionPointList(analUid, mapSheetNum); return changeDetectionCoreService.getChangeDetectionPointList(analUid, mapSheetNum);

View File

@@ -0,0 +1,73 @@
package com.kamco.cd.kamcoback.config;
import java.time.Duration;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cache.CacheManager;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.cache.RedisCacheConfiguration;
import org.springframework.data.redis.cache.RedisCacheManager;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.connection.RedisStandaloneConfiguration;
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.RedisSerializationContext;
import org.springframework.data.redis.serializer.StringRedisSerializer;
@Configuration
@EnableCaching
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;
@Bean
public RedisConnectionFactory redisConnectionFactory() {
RedisStandaloneConfiguration redisConfig = new RedisStandaloneConfiguration();
redisConfig.setHostName(host);
redisConfig.setPort(port);
redisConfig.setPassword(password);
return new LettuceConnectionFactory(redisConfig);
}
@Bean
public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory connectionFactory) {
RedisTemplate<String, Object> template = new RedisTemplate<>();
template.setConnectionFactory(connectionFactory);
// Key는 String으로 직렬화
template.setKeySerializer(new StringRedisSerializer());
template.setHashKeySerializer(new StringRedisSerializer());
// Value는 JSON으로 직렬화
template.setValueSerializer(new GenericJackson2JsonRedisSerializer());
template.setHashValueSerializer(new GenericJackson2JsonRedisSerializer());
template.afterPropertiesSet();
return template;
}
// 기본 레디스 캐시 세팅
@Bean
public CacheManager cacheManager(RedisConnectionFactory connectionFactory) {
RedisCacheConfiguration config =
RedisCacheConfiguration.defaultCacheConfig()
.entryTtl(Duration.ofHours(1)) // 기본 TTL 1시간
.serializeKeysWith(
RedisSerializationContext.SerializationPair.fromSerializer(
new StringRedisSerializer()))
.serializeValuesWith(
RedisSerializationContext.SerializationPair.fromSerializer(
new GenericJackson2JsonRedisSerializer()));
return RedisCacheManager.builder(connectionFactory).cacheDefaults(config).build();
}
}

View File

@@ -25,10 +25,12 @@ spring:
idle-timeout: 300000 # 5분 유휴 타임아웃 idle-timeout: 300000 # 5분 유휴 타임아웃
max-lifetime: 1800000 # 30분 최대 수명 max-lifetime: 1800000 # 30분 최대 수명
leak-detection-threshold: 60000 # 연결 누수 감지 leak-detection-threshold: 60000 # 연결 누수 감지
transaction: transaction:
default-timeout: 300 # 5분 트랜잭션 타임아웃 default-timeout: 300 # 5분 트랜잭션 타임아웃
data:
redis:
host: 192.168.2.109
port: 6379
password: kamco

View File

@@ -22,3 +22,9 @@ spring:
minimum-idle: 1 minimum-idle: 1
maximum-pool-size: 5 maximum-pool-size: 5
data:
redis:
host: 192.168.2.109
port: 6379
password: kamco

View File

@@ -20,6 +20,12 @@ spring:
idle-timeout: 300000 idle-timeout: 300000
max-lifetime: 1800000 max-lifetime: 1800000
leak-detection-threshold: 60000 leak-detection-threshold: 60000
data:
redis:
host: localhost
port: 6379
password:
jpa: jpa:
hibernate: hibernate:
ddl-auto: update # 테이블이 없으면 생성, 있으면 업데이트 ddl-auto: update # 테이블이 없으면 생성, 있으면 업데이트