문제

우리는 약 70GB 규모의 InnoDB 데이터베이스를 보유하고 있으며 향후 2~3년 내에 수백 GB로 성장할 것으로 예상합니다.데이터의 약 60%가 단일 테이블에 속합니다.현재는 64GB RAM을 갖춘 서버를 보유하고 있어 데이터베이스가 꽤 잘 작동하고 있어 데이터베이스 전체가 거의 메모리에 들어가지만, 앞으로는 데이터 양이 훨씬 더 많아질 것이 걱정됩니다.지금 우리는 테이블(특히 데이터의 가장 큰 부분을 차지하는 테이블)을 분할하는 방법을 고려하고 있으며 이를 수행하는 가장 좋은 방법이 무엇인지 궁금합니다.

현재 제가 알고 있는 옵션은 다음과 같습니다.

  • 버전 5.1과 함께 제공되는 MySQL 파티셔닝 사용
  • 데이터 분할을 캡슐화하는 일종의 타사 라이브러리 사용(예: 최대 절전 모드 샤드)
  • 애플리케이션 내에서 직접 구현하기

우리 애플리케이션은 J2EE 및 EJB 2.1을 기반으로 구축되었습니다(언젠가 EJB 3으로 전환하길 바랍니다).

무엇을 제안하시겠습니까?

편집 (2011-02-11):
업데이트 사항:현재 데이터베이스 크기는 380GB이고, "큰" 테이블의 데이터 크기는 220GB, 인덱스 크기는 36GB입니다.따라서 전체 테이블은 더 이상 메모리에 맞지 않지만 인덱스는 맞습니다.
시스템은 여전히 ​​동일한 하드웨어에서 제대로 작동하고 있으며 우리는 여전히 데이터 분할을 고려하고 있습니다.

편집 (2014-06-04):한 가지 추가 업데이트:전체 데이터베이스의 크기는 1.5TB이고 "큰" 테이블의 크기는 1.1TB입니다.우리는 서버를 128GB RAM을 갖춘 4 프로세서 시스템(Intel Xeon E7450)으로 업그레이드했습니다.시스템은 여전히 ​​잘 작동하고 있습니다.다음에 할 계획은 큰 테이블을 별도의 데이터베이스 서버에 배치하는 동시에(소프트웨어에서 필요한 변경을 완료했습니다) 동시에 256GB RAM이 있는 새 하드웨어로 업그레이드하는 것입니다.

이 설정은 2년 동안 지속될 것으로 예상됩니다.그런 다음 마침내 샤딩 솔루션 구현을 시작하거나 1TB RAM이 있는 서버를 구입해야 한동안 계속 사용할 수 있습니다.

편집(2016-01-18):

그 이후로 우리는 별도의 서버에 있는 자체 데이터베이스에 큰 테이블을 넣었습니다.현재 이 데이터베이스의 크기는 약 1.9TB이고, 다른 데이터베이스("큰" 데이터베이스를 제외한 모든 테이블 포함)의 크기는 1.1TB입니다.

현재 하드웨어 설정:

  • HP 프로라이언트 DL 580
  • 인텔(R) 제온(R) CPU E7-4830 4개
  • 256GB RAM

이 설정에서는 성능이 좋습니다.

도움이 되었습니까?

해결책

IO/메모리에 묶여 있을 것이라고 생각한다면 파티셔닝이 도움이 되지 않을 것이라고 생각합니다.늘 그렇듯이 먼저 벤치마킹을 하면 최선의 방향을 찾는 데 도움이 됩니다.64GB 메모리를 갖춘 예비 서버가 없다면 언제든지 공급업체에 '데모 장치'를 요청할 수 있습니다.

1개의 쿼리 집계 보고를 기대하지 않는다면 샤딩을 사용하겠습니다.나는 당신이 큰 테이블뿐만 아니라 전체 데이터베이스를 분할한다고 가정합니다.전체 엔터티를 함께 유지하는 것이 가장 좋습니다.글쎄, 어쨌든 모델이 잘 분할된다면.

다른 팁

42GB 테이블이 더 이상 메모리에 맞지 않으면 확실히 문제가 발생하기 시작합니다.실제로 더 이상 메모리에 맞지 않으면 성능이 매우 빠르게 저하됩니다.테스트하는 한 가지 방법은 해당 테이블을 RAM이 적은 다른 컴퓨터에 놓고 성능이 얼마나 떨어지는지 확인하는 것입니다.

우선, 테이블 중 일부를 별도의 물리적 볼륨으로 이동하지 않는 한 테이블을 많이 분할하는 것은 중요하지 않습니다.

이것은 잘못된 것입니다.파티셔닝(MySQL 5.1의 기능을 통하거나 MERGE 테이블을 사용하는 것과 동일한 기능을 통해)은 테이블이 동일한 드라이브에 있더라도 상당한 성능 이점을 제공할 수 있습니다.

예를 들어, 날짜 범위를 사용하여 큰 테이블에서 SELECT 쿼리를 실행한다고 가정해 보겠습니다.테이블이 전체인 경우 쿼리는 강제로 전체 테이블을 검색하게 됩니다(그리고 해당 크기에서는 인덱스를 사용하는 경우에도 속도가 느려질 수 있습니다).분할의 장점은 쿼리가 반드시 필요한 파티션에서만 실행된다는 것입니다.각 파티션의 크기가 1GB이고 쿼리가 자체 실행을 위해 5개의 파티션에만 액세스하면 되는 경우 결합된 5GB 테이블은 MySQL이 42GB의 거대한 버전보다 처리하기가 훨씬 쉽습니다.

스스로에게 물어봐야 할 한 가지는 데이터를 쿼리하는 방법입니다.쿼리가 특정 데이터 덩어리에만 액세스해야 할 가능성이 있는 경우(예:날짜 범위 또는 ID 범위), 일종의 분할이 도움이 될 것입니다.

MySQL 5.1 파티셔닝에는 여전히 일부 버그가 있다고 들었습니다. 특히 MySQL이 올바른 키를 선택하는 것과 관련이 있습니다.MERGE 테이블은 약간 더 많은 오버헤드가 필요하지만 동일한 기능을 제공할 수 있습니다.

도움이 되었기를 바랍니다...행운을 빕니다!

이는 거대한 데이터 흐름의 실제 예에서 MySql 파티셔닝이 수행할 수 있는 작업에 대한 훌륭한 예입니다.

http://web.archive.org/web/20101125025320/http://www.tritux.com/blog/2010/11/19/partitioning-mysql-database-with-high-load-solutions/11/1

귀하의 사건에 도움이 되기를 바랍니다.

얼마 전 Microsoft ArcReady 이벤트에서 귀하에게 유용할 수 있는 확장 패턴에 대한 프레젠테이션을 보았습니다.당신은 할 수 있습니다 슬라이드 보기 온라인으로.

나는 MariaDB InnoDB + Partitions(귀하의 쿼리에 따라 키 또는 날짜 기준)로 갈 것입니다.

이렇게 했는데 이제 더 이상 데이터베이스 문제가 없습니다.

MySQL은 몇 초 만에 MariaDB로 대체될 수 있습니다. 모든 데이터베이스 파일은 동일하게 유지됩니다.

우선, 테이블 중 일부를 별도의 물리적 볼륨으로 이동하지 않는 한 테이블을 많이 분할하는 것은 중요하지 않습니다.

둘째, 이동하려는 물리적 크기가 가장 큰 테이블일 필요는 없습니다.더 많은 활동을 수행하는 훨씬 작은 테이블이 있을 수 있지만 큰 테이블은 상당히 일정하게 유지되거나 데이터만 추가할 수 있습니다.

무엇을 하든 직접 구현하지 마세요.데이터베이스 시스템이 이를 처리하도록 하십시오.

큰 테이블은 무엇을 하는가?

분할하려는 경우 몇 가지 옵션이 있습니다.
- 데이터베이스 시스템을 사용하여 분할합니다. (그건 잘 모르겠습니다.)
- 행별로 나누어 보세요.
- 컬럼별로 나누어 보세요.

행별로 분할하는 것은 데이터를 청크로 쉽게 분리할 수 있는 경우에만 가능합니다.예를 들어같은 것 베이스 캠프 완전히 별개의 여러 계정이 있습니다.계정의 50%를 한 테이블에 보관하고 50%를 다른 시스템의 다른 테이블에 보관할 수 있습니다.

열로 분할은 행 크기에 큰 텍스트 필드나 BLOBS가 포함된 상황에 적합합니다.예를 들어 사용자 이미지와 큰 텍스트 블록이 포함된 테이블이 있는 경우 이미지를 완전히 다른 테이블로 구성할 수 있습니다.(다른 컴퓨터에서)

여기서 정규화를 깨뜨렸지만 너무 많은 문제가 발생할 것이라고는 생각하지 않습니다.

늘 그렇듯이 먼저 벤치마킹을 하면 최선의 방향을 찾는 데 도움이 됩니다.

대부분의 사람들이 그렇게 말하니까 결국 그 약을 먹어야 할 것 같아요...

결국에는 큰 테이블을 분할하고 싶을 수도 있습니다.두 번째 서버를 생각하기 전에 별도의 하드 디스크에 저장하는 것이 좋습니다.MySQL을 사용하는 것이 가장 편리한 옵션입니다.능력이 있다면 가십시오.

하지만

모든 것은 실제로 데이터베이스가 어떻게 사용되는지에 따라 달라집니다.통계.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top