기존에 세션 데이터 캐싱을 위해 사용하던, TwemProxy - Multiple Redis 구조가
Redis 중 하나가 죽으면, TwemProxy에서 죽은 Redis를 제거해주기 까지, 서비스가 불안정한 문제가 있어서,
Moxi - Multiple Memcached 로 바꿔봤는데.. 역시나 동일했다.
그러다보니 발견 한게, XMemcached라는 라이브러리 였고, 해당 라이브러리에 failover를 자체 지원하는 옵션이 있었다.
Moxi, Redis, Twemproxy 모두 드러내고, Memcached만 여러개 띄워서,
XMemcached를 이용하기로 하였다.
아래 library는 메이븐 중앙저장소에서도 검색이 된다.
이거 하나만 있으면 됨.
<dependency>
<groupId>com.googlecode.xmemcached</groupId>
<artifactId>xmemcached</artifactId>
<version>2.0.0</version>
</dependency>
아래는 간단한 설정. Spring 설정이다. detroyMethod도 제공해줌.
@Bean(destroyMethod="shutdown")
public MemcachedClient memcachedClient() throws Exception {
XMemcachedClientBuilder memcachedClientBuilder = new XMemcachedClientBuilder(messageSourceAccessor.getMessage("memcached.host")); // IP:Port IP1:Port1 IP2:Port2 형식으로 띄어쓰기로 여러대의 서버를 등록이 가능함.
memcachedClientBuilder.setConnectionPoolSize(50);
// Command protocol 정의 (기본 : Text Protocol) - Binary가 Text보다 10배 더 빠르다는 결과가 있음.
memcachedClientBuilder.setCommandFactory(new BinaryCommandFactory());
// Hashing 방식 지정 (기본 : ketama) - 분산 처리(sharding)를 위한 옵션 (이걸 등록하지 않으면 한 곳으로 부하가 몰린다.)
KetamaMemcachedSessionLocator sessionLocator = new KetamaMemcachedSessionLocator();
// fail over를 할 것인가, 말 것 인가
sessionLocator.setFailureMode(true);
memcachedClientBuilder.setSessionLocator(sessionLocator);
memcachedClientBuilder.setTranscoder(new SerializingTranscoder());
return memcachedClientBuilder.build();
}
일단 이렇게 서비스하고, 서비스 중 memcached가 한대도 죽지 않는다면,
앞에 Moxi를 붙여서 사용하는 것도 나쁘지 않을 것 같다.
하지만, XMemcached에도 addServer, removeServer등의 API가 있어서 동적으로 서버를 추가가 가능하기 때문에, 오히려 이게 안정적일 것도 같은데..
이건 유저가 더 많아지면 생각해 볼일 같다.
jmx연동하여 모니터링도 가능하고, phpMemcacheAdmin이라는 툴로 Web UI에서 데이터 확인도 가능 한 것 같은데..
이건 조만간 추가로 진행해봐야 되겠다.