2010-07-12 3 views
8

Azure 테이블 스토리지에서 약 1 억 개의 데이터 행을 다운로드해야하는 임무가 있습니다. 여기서 중요한 것은 속도입니다.Azure 테이블 스토리지에서 1 억 개의 행을 다운로드하는 방법 FAST

우리가 사용중인 프로세스는 Azure 테이블 저장소에서 10,000 개의 행을 다운로드하고 있습니다. Sql Server의 로컬 인스턴스로 처리하십시오. 행을 처리하는 동안 Azure 테이블에서 한 번에 100 개의 행을 삭제합니다. 이 프로세스는 한 번에 10,000 개의 행을 다운로드하는 8 개의 스레드를 갖도록 스레드됩니다.

유일한 문제는 Google 계산에 따른 것입니다. 우리가 저장 한 약 1 억 개의 행을 다운로드하고 처리하는 데 약 40 일이 소요됩니다. 누구든지이 작업을 수행하는 더 빠른 방법을 알고 있습니까?

사이드 질문 : 다운로드 프로세스 중에 Azure는 방금 데이터가없는 xml을 되돌려 보냅니다. 오류를 다시 보내지 않습니다. 하지만 다음을 보냅니다.

<?xml version="1.0" encoding="utf-8" standalone="yes"?> 
<feed xml:base="azure-url/" xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices" xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" xmlns="http://www.w3.org/2005/Atom"> 
    <title type="text">CommandLogTable</title> 
    <id>azure-url/CommandLogTable</id> 
    <updated>2010-07-12T19:50:55Z</updated> 
    <link rel="self" title="CommandLogTable" href="CommandLogTable" /> 
</feed> 
0 

다른 사람이이 문제를 가지고 있으며 수정 사항이 있습니까?

+0

행당 데이터 양은 어느 정도입니까? 400 바이트, 400kb, meg? –

+0

최대 각 행은 1k입니다. – jWoose

+0

나는 Azure에서 일하지 않았다. 그래서 나는 SQL/네트워크 관점에서 문제를 해결하려고 노력하고있다. 그러나 일부 블로그를 통해 읽고 있는데 ATOM을 사용하면 대용량 데이터 집합에 대해 매우 장황하고 비효율적입니다. 자, 이걸 바꾸는 것이 얼마나 어려운지 모르겠습니다. 속도/데이터 차이의 예가 여기에 있습니다. http://weblogs.asp.net/rgillen/archive/2009/08/20/atompub-json-azure-and-large-datasets-part-2.aspx –

답변

15

Disabling Nagling의 제안 외에도 improving performance of Azure Table Storage에 매우 좋은 소식이 있습니다. 사실 은 ADO.NET 역 직렬화의 속도를 향상 시키며 Sqwarea (프레임 워크로 제작 된 거대한 온라인 멀티 플레이어 게임)에 대해 10 배의 속도 향상을 제공합니다.

그러나 테이블 저장소는 대용량 스토리지 시나리오 (수백만 개가 넘는 레코드)에 가장 적합한 솔루션이 아닐 수 있습니다. 대기 시간은 여기에있는 살인 요인입니다.이 문제를 해결하기 위해 파일 기반 데이터베이스 저장소를 사용하여 변경 사항을 로컬에서 (CLAP의 네트워크 대기 시간없이) 성공적으로 사용하고 파일을 다시 업로드하여 BLOB에 위임합니다 (병행 성 및 스케일 아웃은 여기에서 Lokad.CQRS Windows Azure 용 App Engine).

SQLite 데이터베이스에 레코드를 한 번에 (트랜잭션 내에서 각 레코드가 2 개의 필드로 인덱싱되고 ProtoBuf를 통해 임의의 스키마가없는 데이터가 직렬화 된) 레코드를 삽입하는 데 평균적으로 총 200 초 밖에 걸리지 않았습니다. 결과 파일 업로드/다운로드 - 평균 약 15 초. 인덱스에 의한 무작위 읽기 (즉, 파일이 로컬 저장소에 캐시되고 ETag가 일치하는 경우).

+0

귀하의 조언에 감사드립니다. 이것은 많은 도움이 될 것입니다. 그리고 그저 네가 테이블 스토리지가이 많은 레코드에 이상적이지 않다고 말하고 싶었습니다. SQL Azure에 의해 제한되는 작업이었습니다. SQL Azure 문제가 수정되어 더 이상 테이블 스토리지에 데이터를 저장하지 않지만 여전히 해당 테이블에 저장된 데이터를 원합니다. – jWoose

+0

도움이 된 것을 기쁘게 생각합니다.테이블 스토리지는 훌륭하지만 (API는 훨씬 뛰어 났을 수 있지만) 확장 성이 뛰어난 웹 애플리케이션의 뷰 데이터를 저장하는 것과 같이 바꿔 놓을 수는 없습니다. 그러나 극히 낮은 대기 시간과 높은 처리량을 요구하는 시나리오에서는 (SQL Azure와 마찬가지로) 최상의 것은 아닙니다 –

+1

Rinat 및 jWoose. Azure 테이블 스토리지는 관계형이 아닙니다. NoSQL, noschema, 분산 데이터베이스로서 아마도 당신이 설명하는 것과 유사한 방식으로 구현됩니다. Azure Table Storage는 Gazillions 기록을 위해 특별히 설계되었습니다. –

0

제한 요소는 처리 할 수없는 네트워크 대역폭입니다. 그렇다면 더 많은 스레드가 데이터를 다운로드하기 위해 더 많은 머신을 실행해야합니다.

사실, 모든 행을 수동으로 다운로드해야하는 필요성을 제거하는 "내보내기"메커니즘이 Azure에 노출되지 않았습니까?

+0

무엇부터 나는 제한 요소가 대역폭이 아니라고 말할 수 있습니다. Azure에서 행을 가져오고 삭제하는 지연 시간이 문제입니다. – jWoose

+0

@jWoose : 이것을 어떻게 결정합니까? I/O 경계가 아니라고 믿는 데 어려움이 있습니다. –

7

귀하의 측면 질문에 관해서는, 나는 당신이 "연속 토큰"을 얻고 있다고 기대합니다. .NET 저장소 클라이언트 라이브러리를 사용하는 경우 쿼리에 .AsTableServiceQuery()를 추가하십시오.

주요 질문에 관해서는, 당신이 할 수있는 최선의 일은 질문을 패닝하는 것입니다. 로컬 컴퓨터 (Windows Azure가 아님)에서 저장소에 액세스하는 것처럼 들립니다. 그렇다면 테이블 저장소에서 데이터를 가져 오는 작은 서비스를 Windows Azure에 배포하여 (데이터 센터 내에서 더 높은 대역폭과 낮은 대기 시간이 있기 때문에 훨씬 빠름) 작은 크기의 서비스를 배치 한 다음 결과를보고 로컬 컴퓨터로 다시 보냅니다. Windows Azure 테이블로 전송되는 XML에는 많은 오버 헤드가 있으므로 행을 묶어서 전송하면 많은 전송 시간이 절약됩니다.

+0

스티브의 제안 된 접근 방식에 동의합니다. 또한 압축 된 이미지를 BLOB 저장소에 쓰는 것을 고려하십시오. 따라서 사내 구축 환경에서 쉽게 검색 할 수 있습니다. –

+0

내 문제는 맞습니까? 요청이 5 초 이상 걸리면 연속 토큰이 다시 전송됩니다. – jWoose

1

대역폭 제한에 대한 제안 외에 각 테이블 파티션이 초당 약 500 회의 트랜잭션으로 제한되므로 스토리지 계정 제한을 쉽게 실행할 수 있습니다.

추가 정보 : 1K 데이터 읽기와 같이 작은 읽기 작업을 실제로 느리게 할 수있는 최적화가 구현되었습니다 (Nagle의 알고리즘). 여기에 blog post about disabling Nagling이 있습니다. 잠재적으로 읽기 속도를 크게 높일 수 있습니다. 특히 인터넷 대기 시간이없는 Azure 서비스에서 직접 실행하는 경우에는 특히 그렇습니다.

0

큰 요인은 데이터가 파티션간에 어떻게 퍼져 있는지입니다. 파티션 경계에 걸쳐있는 u 리는 해당 파티션이 0 행인 경우에도 다시 제출해야하는 각 경계에서 리턴됩니다. 데이터가 1 ​​Partition = 1 Row 인 경우 속도가 느리지 만 스레드 수를 8보다 크게 늘릴 수 있습니다. 데이터가 n 개의 파티션 = m 행에 있으면 다음 아이디어로 속도가 빨라집니다.

여러 개의 파티션이 있고 각 행의 번호가 있다고 가정 할 때 가장 빠른 방법은 .Net PLINQ 또는 Parallel.ForEach (파티션)를 사용하는 경우 또는 가능한 한 많은 스레드를 스핀하는 것입니다. QueueWorkItem())을 실행하고 스레드가 모든 행, 프로세스, SQL에 게시, & 삭제하기 전에 해당 파티션을 검사하도록하십시오.

대기 시간 (10 초)과 다중 왕복 이동 (8 개 스레드 포함)을 고려할 때 생각만큼 혼잡하지 않을 것입니다. 또한 사용중인 VM은 언급하지 않지만 다른 크기를 프로필로 지정할 수는 있습니다.

다른 방법으로 대기열과 일부 'n'직원을 활용하는 것입니다. 각 파티션 (또는 파티션 세트)에 대해 큐에 메시지를 넣으십시오. 작업자가 대기열 (멀티 스레드)에서 빠져 나와 쿼리/프로세스/게시/반복하도록합니다. 필요에 따라 많은 수의 직원을 배치하여 데이터 센터에 더 많이 배치 할 수 있습니다 (예 : 더 많은 처리량 등).

1

Amazon에서 지원하는 데이터를 얻는 가장 빠른 방법이지만 아직 Azure는 USB 디스크 (심지어 USB 스틱)를 배송하고 데이터를 디스크에 넣어 다시 배송합니다.

또 다른 옵션은 AppFabric Service Bus를 사용하여 데이터를 한 번에 모두 다운로드하지 않고 다른 시스템에 데이터를 가져 오는 것입니다.

관련 문제