소셜 게임의 주요 특징
사용자 수가 기본적으로 많고 단번에 대폭 늘어날 수도 있다
- 사용자 수가 많으면 당연히 방문자 수와 생성되는 데이터 양이 방대해짐
주요 정보는 모두 서버가 가지고 있음
- 게임기와 달리 휴대전화는 그 자체로 게임 공략에 필요한 모든 정보를 유지하는 것이 곤란함. 따라서 던전 공략 정보, 소지 아이템 정보 등 주요 데이터는 모두 서버에서 유지함
- 그래서 서버가 해킹되면 모든 사용자가 영향을 받는다는 막대한 피해가 있을 수 있기에 세심한 주의가 필요함
사용자 ID를 키로 사용하는 처리가 많다
- 웹 서비스는 로그인 후 마이페이지를 비롯한 거의 모든 화면이 사용자와 연관
- 사용자 정보나 소지 아이템 리스트 같은 테이블에 거의 모두 사용자 ID(+alpha)를 기본 키로 갖게 됨
구조화된 데이터 항목이 많다
- 사용자 ID, 아이템 ID, 소지금, 체력 등 구조화된 데이터 항목이 대다수임
- 데이터베이스 이론인 정규화 이론의 노하우 충분히 활용가능함
영구적으로 필요한 데이터와 기간 한정의 데이터가 있음
- 기간 한정의 데이터는 계속해서 기본 데이터베이스 서버에 둘 필요는 없고, 불필요하게 된 시점에서 삭제하거나 백업 파일로 옮겨 놓는 등의 대응이 가능한 데이터
- 기간 중에 소실되면 곤란하므로 데이터로서는 일반 데이터베이스에 두지만, 기한 후에는 지운다는 의미에서 영구적인 데이터와 다름
- 세션 정보 등 매우 한정된 시간밖에 사용하지 않는 것도 있는데 이러한 경우는 캐시 서버나, 무정지성이 높지 않지만 빠른 처리가 가능한 NoSQL에 저장할 수도 있음
가용성과 무결성에 대한 요구가 의외로 높다
- 사용자에게 과금을 하는 유형의 서비스인지 그렇지 않은지에 따라 크게 다름
- 소셜 게임의 경우는 아이템 과금 등의 형태로 돈을 지불해 주는 사용자가 있기 때문에 네트워크 서비스에서의 품질 요구는 비약적으로 상승
- 장시간의 다운 타임은 과금 수익에 큰 영향이 있기 때문에 가능한 무중단 으로 복구 또는 수정해야 함
대규모 웹 서비스용 데이터베이스에 요구되는 기능
온라인(무중단)에서의 스키마 변경
- NoSQL 형태로 데이터를 관리(value 열에 값 다 때려넣는 형태) 혹은, MySQL 에서의 복제 구성을 잘 사용 혹은 커뮤니티에서 제공하는 테이블 정의 변경 툴을 사용함으로써 중단 없이 테이블 정의를 변경할 수 있음
수평 분산(Sharding)의 용이성
- 시스템이 커질수록 한 대의 (마스터) 서버에서 모든 요청을 처리하는 것은 불가능함
- 참조 처리는 슬레이브와 캐시 서버를 추가함으로써 분산시킬 수 있지만, 업데이트 프로세스는 모든 데이터베이스에 반드시 반영해야 하기 때문에 참조 처리의 분산만큼 간단하지 않음
- 웹 서비스에서 정석이 되고 있는 것이 데이터마다 여러 서버에 분할하여 각각 업데이트를 담당시키는 방법 ↔ Sharding(수평 분할)
- 어느 데이터가 어느 Shard에 속하는가 하는 정보를 어딘가에 갖게 할 필요가 있음 → 로직 구현이 필요 (MySQL은 표준 기능 갖고 있지 않아 애플리케이션 측에서 만들어서 넣어야 하고, MongoDB 같은 경우는 자동으로 해줌)
안정성
- 쉽게 크래쉬되거나 데이터가 망가지지 않을 것
- 갑자기 원인 불명의 성능 다운으로 장시간 보류되는 일이 없을 것
- 데이터베이스를 선택할 때 가장 확실한 기준은
실적
. 이 점에서 높이 평가받은 것이 MySQL - 애시당초 크래시 자체가 거의 발생하지 않으며 InnoDB에는 안정성에 빠뜨릴 수없는 트랜잭션 기능도 있기에 복구도 고속으로 가능함
단일 장애점의 제거
- 단일 장애점이란 이것이 다운되면 서비스 전체가 다운되는 부분을 말함
- 단일 장애점이 다운되면 신속하게 긴급 대응하지 않으면 안 되기 때문에 대량의 서버를 적은 인원으로 운용하는 것은 어려움
- 데이터베이스에 있어 단일 장애점이 되기 쉬운 것이 마스터
- 마스터 장애가 발생했을 때 어떻게 중단 없이 자동 장애 조치를 안정적으로 작동하는가가 단일 장애점을 제거하는 데에 있어 중요함
- 필자가 개발한 MySQL의 마스터 무정지 실현하는 툴 MHA for MySQL
두 곳 이상의 데이터 센터
- 데이터 센터 자체가 돌연사하는 경우도 생각해야 함
- 서비스를 처리하는 데는 여러 데이터 센터에서 운용하는 것을 생각해야 함
- 당연히 데이터베이스도 거기에 대응하고 있을 필요가 있음
단위 성능의 차이
- 대규모 웹 서비스에 있어 중요한 성능 면에서의 지표는 수평 분할 뿐만이 아니라, 동일한 트래픽을 처리한다면 서버 대수가 적은 것이 총 비용이 낮은 만큼 당연히 좋음
- 수평 분할이 되어도 단위 성능이 일반 RDBMS의 몇 분의 1정도 밖에 안되는 것도 있음
국소적인 초고속화
- 대규모 웹 서비스에서는 극히 일부의 처리에 대하여 액세스가 매우 집중되는 경향이 있음
- 해당 액세스에 대해 캐시 서버(Redis, Memcached)를 사용
- 사용자 ID를 키로 사용자 정보를 바로 취한다는 단순한 처리라면 NoSQL 프로토콜이 최적이라고 말할 수 있지만, 실제로는 이보다 더 복잡한 처리가 높은 빈도로 실행되는 경우도 있음
- 예로, Twitter에서 자신이 팔로우하고 있는 사람들의 최근 트윗 20건을 표시하기 와 같은 처리
- 이를 구현하기 위해서는 여러번의 SQL 문이 실행되어야 하는데 이런 상황에서
저장 프로시저
와 같이 데이터베이스 측면에서의 완벽한 처리를 구현하는 것이 효율적임
- 저장 프로그램이라면 유지보수성의 관점에서 안티 패턴이라고 불리기도 하지만, 초고속성이 요구되는 극히 제한된 용도라면 자원 소비를 줄이기 위해 오히려 적극적으로 사용해도 좋다고 할 수 있음
규모가 다르면 선정 기준도 바뀐다
- 1,000대 이상의 MySQL 서버를 이용하는 대규모 서비스의 경우 MySQL을 자신있게 권함
- 한편, 10대 정도의 소규모 환경에서 새로운 서비스를 만드는 경우는 MongoDB와 같은 NoSQL에도 우위성이 있음. (
자동 Sharding 메커니즘
이 큼) ⇒ 개발 공수 줄어듬
- 한 대당 실질적인 성능과 처리할 수 있는 데이터의 크기는 고속화 메커니즘(Change Buffering, Range partitioning)을 갖고 있는 MySQL 쪽이 높음
- MySQL은 구문 분석이 필요한 SQL로 액세스하고, NoSQL은 고속의 API에 액세스하기 때문에 NoSQL 쪽이 고속이다 라고 말하는 사람이 있다면, 한번 본격적으로 큰 트래픽을 취급하는 서비스를 운영해 보길 권한다. 실제 환경에서는 디스크 I/O에서 병목현상이 나타나므로 구문 해석과 같은 CPU 주변의 처리가 아닌 I/O 주변의 처리에 최적화된 제품 쪽이 더 빠름
소규모 웹 서비스는 MySQL에서는 5대로 끝나는 것이 다른 NoSQL은 10대 필요하게 되었다 하더라도 그 정도의 비용 차이라면 Sharding이나 페일오버가 자동으로 되는 NoSQL을 선택하는 의사결정이 충분히 납득가능
대규모 웹 서비스에서는 총 비용이 커지기 때문에 그것을 조금이라도 줄이기 위해 고속화 메커니즘이나 내결함성을 갖춘 MySQL을 선택하여 누락된 Sharding 등의 기능은 직접 개발한다는 방침 쪽으로 진행되고 있음
데이터베이스 제품 선정
DeNA(Mobage)에서는 위의 기준을 중시한 것은 물론 아래와 같은 이유로 MySQL을 사용하고 있다고 함
성능이 높을 것
- 대규모 서비스를 유지해 나가는 데 있어서 성능 관리는 매우 중요한 주제
- 수평 분할에만 눈이 멀어 한 대당 성능에 소홀해지면 안됨
시계열/이력계 데이터의 취급에 능할 것
- 시계열 데이터는 액세스 범위에 극단적인 편향이 있는 것이 보통. Twitter 등의 실시간 서비스에서 특히 현저한데, 사용자가 최근 올린 데이터로의 액세스는 많으나 몇 달 전에 올린 데이터로의 접근은 거의 없을 것
- MySQL의 레인지 파티셔닝 기능을 사용하면 하나의 테이블을 물리적으로 여러 파티션으로 나눌 수 있음. 인덱스는 파티션 단위로 만들어지기 때문에 테이블이 거대하게 되어도 개별 인덱스 크기는 일정 이하로 유지할 수 있음
- 대량 데이터라면 NoSQL로 분산 데이터베이스를 이라고 생각하는 사람도 많지만 NoSQL은 레인지 파티셔닝 기능이 거의 없기 때문에 필요 충분한 성능을 내기 위해 한 대당 탑재할 수 있는 데이터 양이 MySQL에 비해 훨씬 작아짐 → 더 많은 서버가 필요하여 비용 효과가 떨어짐
트랜잭션/무정지성 기능이 충실할 것
- 서비스가 쉽게 다운되지 않도록 하기 위해서는 단일 장애점을 없도록 하는 것이 중요함
- DeNA는 MySQL의 복제 기능을 채용하고 마스터 / 다중 슬레이브 구성을 취하고 있음
- 따라서 슬레이브 한 개가 고장나도 서비스를 계속할 수 있음