Egloos | Log-in


"프랜드피드는 어떻게 MySQL을 사용해서 스키마 없는 데이터를 저장하나" 요약


상황

프랜드피드는 약 2억 5천만 개의 피드 항목을 저장하고 있으며 다른 데이터도 많다. 서비스가 성장하면서 스케일링 문제 겪었고 복제, 캐시, 분할 등을 도입하여 해결했다. 하지만 성장을 거듭할수록 기존 기능을 더 많은 트래픽에서 사용할 수 있게 하는 것보다 새 기능을 추가하기가 더 어려워졌다.

문제

특히 스키마 변경과 인덱스 추가 시에는 몇 시간씩 데이터베이스를 멈춰야 했다. 쓰지 않는 인덱스를 제거하는 것도 시간이 걸렸고 제거하지 않으면 INSERT 마다 사용하지도 않는 인덱스 블럭을 읽고 써야 해서 중요한 데이터가 캐시에서 밀려나 성능 저하를 가져왔다. 슬레이브에서 새 인덱스를 만들어서 슬레이브와 마스터를 교체하는 등의 방법도 써보았지만 복잡한 작업이라 실수하기 쉽다. 그래서 스키마나 인덱스 변경이 필요한 새로운 기능은 암묵적으로 제제되었다.

해결책

데이터베이스는 상당히 분할되어 있어서 RDBMS의 JOIN 등은 전혀 쓸모가 없었다. CouchDB 등 유연한 스키마와 온라인 인덱스 변경이 가능한 비관계형 데이터베이스를 살펴봤으나 아직 대규모 사이트에서 널리 사용되지도 않고, 충분히 안정적이지도 않았다. MySQL은 안정적이고, 이미 장단점을 잘 알고 있어서 MySQL을 저장소로 쓰는데 아무 불만이 없다. MySQL 위에 스키마가 없는 데이터베이스를 구현하기로 했다.

새 데이터베이스 API는 다음과 같이 동작한다.

  • 객체를 담을 테이블을 만들고 PK로 UUID를 쓴다. 객체는 테이블에 인코딩하여 저장한다.
  • 검색를 위한 인덱스가 필요하면 인덱스 테이블을 만들고 검색에 필요한 필드만 컬럼으로 추가한다.
  • 객체가 추가, 변경, 삭제 되면 데이터 테이블과 인덱스 테이블들에 객체와 인덱스들을 추가, 변경, 삭제한다.
  • 오류로 인해 인덱스 테이블이 데이터 테이블과 일치하지 않을 수 있다. 이는 별도의 인덱스 동기화 프로세스를 돌려서 즉시 복구될 수 있도록 한다.

기존 구성과의 차이점을 그림으로 나타내면 다음과 같다.

결과

안정적이고 편리한 관계형 데이터베이스를 쓰면서도 데이터베이스를 멈추지 않고 스키마 변경이나 인덱스 추가, 삭제를 할 수 있게 되었다. 객체를 JSON 등으로 인코딩하여 한 컬럼에 저장하기 때문에 스키마 변경은 전적으로 어플리케이션에서 다룰 수 있다. 인덱스도 별도의 인덱스 테이블로 관리되기 때문에 가동 중에 추가하고 삭제할 수 있다.

추가로 다음과 같은 장점도 얻을 수 있다.
  • 성능 향상. 평균 대기 시간이 짧아졌으며 대기 시간의 편차도 줄었다.
  • 객체 단위의 캐시 적용이 아주 쉽다.
  • 인덱스마다 다른 컬럼을 기준으로 분할 할 수 있다.

by 이피 | 2009/10/25 11:32 | 트랙백 | 덧글(2)

Undercover 0.8을 출시했습니다.

Undercover 0.8을 출시했습니다. IE8에서 그래프가 안나오는 문제를 고쳤습니다. 고쳤다고 해봐야 Flot 최신 버전을 적용한 것 뿐이지만 ㅎㅎ.

by 이피 | 2009/09/11 20:02 | Java | 트랙백 | 덧글(2)

Undercover 0.7을 출시했습니다.

0.6과 0.7 버전에서는 Undercover가 더 널리 쓰일 수 있게 만드는데 중점을 두었습니다. 아직 Undercover를 직접 지원하는 도구들이 없기 때문에 Continuous Integration 등의 기존 도구와 연동할 수 있도록 Cobertura, Emma 호환 XML 레포트를 만들 수 있습니다. Ant 사용자가 조금 더 쉽게 사용할 수 있도록 의존성을 줄였습니다. 이제는 Undercover와 함께 ASM과 commons-lang만 있으면 동작합니다.

설명서를 보강하고 코드를 정리한 후에 1.0을 출시할 예정입니다. 1.x 에서는 멀티 모듈 프로젝트를 위한 데이터 병합과 Scala 지원, 그리고 온라인 커버리지 수집 기능을 구현할 예정입니다.

by 이피 | 2009/08/09 15:03 | Java | 트랙백(1) | 덧글(0)

Undercover 0.5 출시

지정한 클래스를 커버리지 측정에서 제외할 수 있도록 필터를 추가했습니다. 앤트메이븐 모두에서 쓸 수 있습니다.

제가 필요한 필수 기능은 모두 구현했습니다. 어떤 기능이 필요하신가요?

by 이피 | 2009/06/29 20:16 | Java | 트랙백 | 덧글(4)

Undercover 0.4 출시

Apache Ant 에서도 사용할 수 있습니다.

다음 버전에는 지정한 클래스 무리를 제외 기능을 추가할 예정입니다. 제외까지 되면 필수 기능은 모두 구현이 되네요. 자 이제 돈을 벌어 볼까요 ㅋ 한 달에 3 천원, 일 년에 3 만원 정도면 괜잖나요? 너무 싼가.

by 이피 | 2009/06/26 13:03 | Java | 트랙백 | 덧글(0)

Undercover 0.3 출시



저번 버전에 비해서 리포트가 많이 보강되었습니다. 특히 이름 없는 클래스를 분리된 클래스로 취급하지 않고 그 클래스가 속한 메소드나 클래스에 포함하여 각종 지표를 계산합니다. GUI나 이벤트 기반 모델을 사용할 경우에 유용합니다.

다음 버전에는 앤트 빌드에서도 쓸 수 있도록 앤트 태스크를 추가하고 그 다음 버전에서는 측정 제외 기능을 추가할 예정입니다.

by 이피 | 2009/06/17 20:26 | Java | 트랙백 | 덧글(3)

살이 차오른다, 뛰자

살이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자

이 맨 처음 찌기 시작할 때부터
준비했던 뜀박질을
매번
이 차오를 때마다
포기했던 그 다짐을

이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자

말을 하면 아무도 못 알아들을 지 몰라
지레 겁 먹고 벙어리가 된 소년은
모두 잠든 새벽 네시 반 홀로 일어나
허리에 쪄 있는
을 보았네

하루밖에 남질 않았어
살은 내일이면 다 차올라
이번이 마지막 기회야
그걸 놓치면 영영 못 빼

이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자

뛰자

오늘도 여태것처럼 그냥 잠 들어 버려서
못 뺄지도 몰라

하지만 그러기엔 소년의 눈에는
저기 찐 살이 너무나 떨리더라

아 아 아
은 내일이면 다 차올라
아 아 아
그걸 놓치면 절대로 못 빼

이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자
이 차오른다, 뛰자

뛰자

by 이피 | 2009/06/15 00:28 | 트랙백 | 덧글(3)

Undercover 커버리지 분석기 0.2 출시했습니다

프로젝트 상태를 한 눈에 볼 수 있도록 대시보드를 추가했습니다. 클로버에 있는 커버리지 분포와 커버리지-복잡도를 보여줍니다. 커버리지-복잡도를 보면 어떤 클래스가 위험한지 한 눈에 알 수 있습니다. 커버리지가 낮으면서 복잡도가 높은 클래스는 위험한 클래스이니 리팩토링하여 복잡도를 낮추던지 테스트를 하여 커버리지를 높이던지 조치를 취해야 하는 클래스입니다.

다음 버전에서는 익명 클래스는 독립적인 클래스로 인정하지 않고, 익명 클래스를 만든 메소드나 클래스에 포함 시킬 예정입니다.

자세한 사항은 프로젝트 홈페이지에서 보세요.


by 이피 | 2009/06/06 17:44 | Java | 트랙백(1) | 덧글(0)

tokyotyrant-java 메이븐 저장소와 undercover 코드 커버리지 분석기

tokyotyrant-java 쓰는 사람이 있는지나 모르겠지만, 좀 더 편하게 쓸 수 있도록 메이븐 저장소를 마련하였습니다. misc 명령만 구현하고 1.0 릴리즈를 하려고 하는데 misc가 어떤 용도로 쓰이는지 몰라서 어떻게 구현해야 할지 모르겠네요.

요즘 만들고 있는 자바 코드 커버리지 분석기도 소개 합니다. 오픈 소스로는 Emma, Cobertura가 있고 상용으로는 Clover가 있는데 모두 조금씩 아쉬운 점이 있습니다. emma은 커버리지 분석에는 뛰어나지만 커버리지만 다루기 때문에 복잡도 등 다른 지표와 종합 분석을 할 수가 없습니다. cobertura는 복잡도도 같이 보여주지만 커버리지 분석에 부하가 큽니다. 그리고 둘 다 clover의 대시보드 같은 전체 상황 파악을 위한 요약 정보를 제공하지 않습니다. clover는 리포트는 훌륭하지만 소스 코드를 조작하여 커버리지를 측정하기 때문에 간혹 컴파일 에러가 난다던지 인코딩 문제를 일이키고 전체 빌드를 다시 해야하기 때문에 느리고 코드 생성 등으로 빌드가 복잡한 경우 동작하지 않습니다.

그리고 스칼라 코드의 커버리지와 복잡도도 알고 싶었습니다.

아직은 Maven 플러그인만 있고 커버리지와 복잡도 정보를 보여주는 이외의 기능은 전혀 없습니다. 그래도 스크린샷을 보면 쓸만해 보이죠? 스크린샷 주도 개발입니다. 메이븐 저장소를 이용하시면 개발 버전을 써볼 수 있습니다.



평소 코드 커버리지 분석기를 사용하시면서 좋아하는 점이나 싫어하는 점, 보여 주었으면 하는 지표나 지표를 보여주는 방법에 대해 의견 주시면 고맙겠습니다.

다른 툴의 불편함도 있었지만 (회사 안다니고) 내가 만들고 싶은 프로그램을 만들면서 살 수 있는 방법을 찾아보려고 시작한 프로젝트입니다.하지만 Clover 같은 상용 제품도 아주 싸더군요. 무제한 라이센스가 일년 무료 업그레이드에 $16,000 밖에 안하네요. 서버 1대 라이센스도 $1,200 이 정도 가격인데 안사는 회사라면 돈이 없어서 못사는게 아니라 관심이 없어서 안사는 회사이기 때문에 가격을 싸게 한다고 해도 팔리지는 않겠네요. 흑흑흑.

전략을 바꾸어 코드 커버리지 상승에 오르가즘을 느끼는 오덕 개발자를 위해서 일년에 $50 이하로 싸게 팔면 장사가 될까요. ㅎㅎㅎ 오덕 개발자 많지 않아서 이마저도 시장성은 없어 보이네요. 아니면 JUnit Max 와 연동하여 실시간 커버리지 분석으로 갈 때까지 가는 방법도 시도해볼 수 있겠죠.

아니면 어떤 코드의 커버리지를 측정하더라도 커버리지 100%라고 해주는 거짓 거울을 코드 커버리지 때문에 쪼이는 일선 관리자와 개발자에게 파는 방법도있겠군요.

by 이피 | 2009/05/28 00:19 | Java | 트랙백 | 덧글(4)

Tokyo Tyrant Java Client 0.8 출시

0.8 버전 출시!

0.7 이후로 달라진 점:

  • fwmkey의 결과 값이 리스트에서 배열로 바꼈습니다.

  • 테스트가 더 많아졌습니다.

  • 내부 구조가 변경되었습니다.

    • 키와 값의 인코딩과과 디코딩을 입출력 쓰레드가 아닌 클라이언트 쓰레드에서 수행합니다.

    • 인코딩, 디코딩 오류 발생 때 연결을 끊고 재접속하지 않습니다.

    • 인코딩, 디코딩 오류가 클라이언트 쓰레드에서 발생합니다.

    • 다중 CPU 환경에서 좀 더 유리하리라 기대합니다.




by 이피 | 2009/04/21 17:21 | Java | 트랙백(1) | 덧글(1)

◀ 이전 페이지          다음 페이지 ▶