SlideShare a Scribd company logo
1 of 21
どう使う? Windows Azure テーブル ~ SQL Azure に挑む ~ 山本 昭宏 (Akihiro Yamamoto) Twitter : A_Ym
プロフィール Microsoft 系テクノロジーコンサルタント会社勤務 興味のあるテクノロジー Windows Azure, C# 4, LINQ, WPF, WCF, WF, Silverlight  Software Factories WindowsAzure の活動 Windows AzureCommunity トレーニングキットの翻訳や技術検証、情報の整理をしていました。 Web メディア @IT  「Windows Azure Platform速習シリーズ:SQL Azure-SQL Azureの機能と制約を理解する」 の記事を執筆させていただきました。 セミナー TechDays2010 「Windows AzurePlatform 徹底検証」 にて技術検証を行い、スピーカーとして登壇させていただきました。
テーブル ストレージのスペックおさらい
トランザクションスペック (Windows Azure Storage Team Blog より) 1 entity 追加= 1 トランザクション 100entity に対する変更の反映 (エンティティ グループ トランザクション ⇒ EGT を使用しない場合)= 100 トランザクション 100entity に対する変更の反映(EGT を使用する場合) = 1 トランザクション PartitionKeyとRowKeyが一致した場合のクエリ = 1 トランザクション 1クエリ で 500 entity 返された場合(継続トークンが発生しない場合) = 1 トランザクション 1 クエリで 5 リクエスト 発生した場合 (4つの継続トークンが発生した場合) = 5 トランザクション
パフォーマンススペック (Windows Azure Storage Team Blog より) 1パーティションあたりのパフォーマンス 最大 500 トランザクション /sec 極力パーティションが均等に分散するような設計によりパフォーマンスが向上する 理論値 ? 参照 500entity×500 トランザクション =250,000entity/sec 追加 100entity×500 トランザクション =50,000entity/sec
出ません でした。
並列処理実装方法
追加の並列処理 (1/3) 使用法 var contexts = new TestTableContext[10000];Parallel.For(0, contexts.Count(),(idx) =>{    contexts[idx] = EntityController.CreateTestTableContext();    contexts[idx].SaveChangesDefaultOptions =     SaveChangesOptions.ContinueOnError | SaveChangesOptions.ReplaceOnUpdate        ;}Int64 from = 0;Int64 to   = 1000000;int counter      = 0;int parallelUnit = 100;using(var manualEvent = new ManualResetEvent(false)){    for (Int64 rowIdx = from; rowIdx < to; rowIdx++)    {var entity =            new TestTableEntity()            {                  PartitionKey = ((Int64)(Math.Floor((double)rowIdx / 1000))).ToString("0000000000")                , RowKey       = rowIdx.ToString("0000000000")                , Id           = rowIdx                , Text         = "Text_" + rowIdx.ToString("0000000000")            };        var context = contexts[(int)Math.Floor((double)rowIdx / to * contexts.Count())];        context.AddTestTableEntity(entity); 追加に使用する TableServiceContext を生成します。EGT のトランザクション単位は 100entity に制限されていますので、1000,000 entity 追加する場合は 10,000 の TableServiceContext を使用します。 ManualResetEvent を並列処理の同期に使用します。
追加の並列処理 (2/3) 使用法 (つづき)         if (rowIdx % parallelUnit == parallelUnit - 1 || rowIdx == to - 1)        {            context.SaveChangesAsParallel(            (exception) =>                {                    if (exception != null)                    {                     }                    if (Interlocked.Increment(ref counter) >= (int)(to / parallelUnit))                    {                        manualEvent.Set();                    }                }                );        }    } manualEvent.WaitOne();} EGT 単位 (100entity) で非同期追加処理を行います。 例外発生時の処理を行います。 EGT 単位で追加完了時にカウンターを同期インクリメントし、全件追加が完了したらメインスレッドの待機状態を解除します。 メインスレッドを待機状態にします。
追加の並列処理 (3/3) public static IAsyncResult SaveChangesAsParallel(      this TableServiceContext context    , Action<Exception> completeAction ){    var asyncCallback =        new AsyncCallback(            (asyncResult) =>            {                DataServiceResponse response;                try                {                    response = context.EndSaveChanges(asyncResult);                 completeAction(null);                }                catch (Exception exception)                {                 }            }            );    var ret =         context.BeginSaveChanges(              SaveChangesOptions.Batch            , asyncCallback            , null            );    return ret;} TableServiceContext.BeginSaveChanges メソッドの第1パラメーターに SaveChangesOptions.Batch オプションを指定して EGT 追加処理を行います。
クエリの並列処理 (1/3) 使用法 var context = EntityController.CreateTestTableContext();var query =    from        entity in context.TestTableEntity    select        entity    ;var entities =query.QueryAsParallel<TestTableEntity>( GetWhereExpressions(), null); IEnumerable<Expression<Func<TestTableEntity, bool>>> GetWhereExpressions(){    for (int pIdx = 0; pIdx <= 999; pIdx++)    {        yield return (TestTableEntity entity) => entity.PartitionKey == pIdx.ToString("0000000000");    }} where に使用する式は yieldreturn で返します。 これを使用しないと列挙の最後の式しか処理されません。
クエリの並列処理 (2/3) public static IEnumerable<TEntity> QueryAsParallel<TEntity>(      this IQueryable<TEntity> query    , IEnumerable<Expression<Func<TEntity, bool>>> whereExpressions    ) {    int whereExpressionsCount = whereExpressions.Count();    var entities = new List<TEntity>();    var syncRoot = (entities as ICollection).SyncRoot;    using (var manualResetEvent = new ManualResetEvent(false))    {        ThreadPool.RegisterWaitForSingleObject(              manualResetEvent            , new WaitOrTimerCallback( (_state, timeout) => { manualResetEvent.Set(); } )            , null            , 300000            , false            );        foreach (var whereExpression in whereExpressions)        {            var dataServiceQuery = (DataServiceQuery<TEntity>) query.Where(whereExpression);             var asyncCallback =                new AsyncCallback(                    (asyncResult) =>                    {                        try                        {                            var response = dataServiceQuery.EndExecute(asyncResult);                            lock (syncRoot) { entities.AddRange(response.ToArray()); }                        }                        catch (Exception exception)                        {                                                    } ManualResetEvent を並列処理の同期に使用します。 タイムアウトの設定を行います。 Select 式と Wehere 式を組み合わせてクエリを作ります。 結果を lockで同期してリストに追加します。(4. は次ページ) 例外を処理します。
クエリの並列処理 (3/3)                         finally                        {                            if (Interlocked.Decrement(ref whereExpressionsCount) == 0)                            {                                manualResetEvent.Set();                            }                        }                    }                    )                    ;                    dataServiceQuery.BeginExecute(asyncCallback, null);                }                manualResetEvent.WaitOne();            }            return entities;        } 全てのクエリが完了したらメイン スレッドの待機状態を解除します。 メイン スレッドを待機状態にします。
テーブル サービス エンティティの基本形 WCF の データコントラクトとして使用できないので TableServiceEntity クラスは継承せずに、DataServiceKey 属性を設定します。 [DataContract][DataServiceKey("PartitionKey", "RowKey")]public class TestTableEntity{    public TestTableEntity()    {    }    [DataMember]    public string PartitionKey { get; set; }    [DataMember]    public string RowKey { get; set; }     [DataMember]    public DateTime Timestamp { get; set; }    [DataMember]    public string TypeAssemblyQualifiedName { get; set; }     public string ETag    {        get;        private set;    }    public void SetETag(string etag)    {        ETag = etag;    }     [DataMember]    public Int64 Id { get; set; }    [DataMember]    public string Text { get; set; }} テーブル サービス エンティティとして必須のプロパティを用意します。 CLR にマッピングするためのキーを格納するプロパティを用意します。 Etag を保持するプロパティと設定するメソッドを用意します。 (テーブル格納対象外)
継続トークン処理の拡張メソッド化 (1/2) 使用法 var context = EntityController.CreateTestTableContext();var query =    from        entity in context.TestTableEntity    select        entity    ;var entities = query.QueryContinuously();
継続トークン処理の拡張メソッド化 (2/2) public static IEnumerable<TEntity> QueryContinuously<TEntity>(this IQueryable<TEntity> query) {   var resultList = new List<TEntity>();    string nextPartitionKey = null;    string nextRowKey       = null;    do {        var dataServiceQuery = query as DataServiceQuery<TEntity>;        if (dataServiceQuery == null) { break; }        if (nextPartitionKey != null)  {            dataServiceQuery = dataServiceQuery.AddQueryOption("NextPartitionKey", nextPartitionKey);            if (nextRowKey != null)            {                dataServiceQuery = dataServiceQuery.AddQueryOption("NextRowKey", nextRowKey);            }        }        var result   = dataServiceQuery.Execute();        var response = result as QueryOperationResponse;        resultList.AddRange(result);        nextPartitionKey = null;        nextRowKey       = null;        response.Headers.TryGetValue("x-ms-continuation-NextPartitionKey", out nextPartitionKey);        response.Headers.TryGetValue("x-ms-continuation-NextRowKey"      , out nextRowKey);    }    while (nextPartitionKey != null);    return resultList;}
まとめ
WindowsAzure テーブル vs.SQLAzure 並列処理を行えばパフォーマンスで SQL Azure に迫ることができます。 追加処理ではエンティティ グループ トランザクション (EGT) を組み合わせるとスループットが向上し、場合によっては SQLAzure を上回ります。 膨大なデータに対し、インスタンスサイズを大きくしたり、インスタンス数を増やすことによりリニアに対応できます。 ただし、PartitionKey の設計や並列処理の実装、メンテナンスのコストを考えると SQLAzure で対応可能なことを無理にテーブルで実現するメリットは小さいと言えます。 数10GB 以上のデータを扱うケースで有効だと考えます。⇒ 現在のところ Dallas との連携が有望だとみています。
参考情報 (1/2) Web メディア Windows Azure Storage Team Blog Understanding Windows Azure Storage Billing – Bandwidth, Transactions, and Capacity(http://blogs.msdn.com/b/windowsazurestorage/archive/2010/07/09/understanding-windows-azure-storage-billing-bandwidth-transactions-and-capacity.aspx) Windows Azure Storage Abstractions and their Scalability Targets(http://blogs.msdn.com/b/windowsazurestorage/archive/2010/05/10/windows-azure-storage-abstractions-and-their-scalability-targets.aspx) @IT  「Windows Azureストレージ開発入門(前編) -初めてのWindows Azureテーブル・ストレージ開発」(http://www.atmarkit.co.jp/fdotnet/dnfuture/winazurestorage_01/winazurestorage_01_01.html)
参考情報 (2/2) Windows Azure ベンチマーク サイト Azurescope: Benchmarking and Guidance for Windows Azure http://azurescope.cloudapp.net/ 書籍 (並列処理関連) More Effective C#(翔泳社) .NETのクラスライブラリ設計 (日経BPソフトプレス) 究極のC#プログラミング (技術評論社)
おわり ご静聴ありがとうございました。

More Related Content

What's hot

Writing and using Hamcrest Matchers
Writing and using Hamcrest MatchersWriting and using Hamcrest Matchers
Writing and using Hamcrest MatchersShai Yallin
 
Selenium Webdriver with data driven framework
Selenium Webdriver with data driven frameworkSelenium Webdriver with data driven framework
Selenium Webdriver with data driven frameworkDavid Rajah Selvaraj
 
Testing, Performance Analysis, and jQuery 1.4
Testing, Performance Analysis, and jQuery 1.4Testing, Performance Analysis, and jQuery 1.4
Testing, Performance Analysis, and jQuery 1.4jeresig
 
Understanding JavaScript Testing
Understanding JavaScript TestingUnderstanding JavaScript Testing
Understanding JavaScript Testingjeresig
 
JUnit & Mockito, first steps
JUnit & Mockito, first stepsJUnit & Mockito, first steps
JUnit & Mockito, first stepsRenato Primavera
 
The uniform interface is 42
The uniform interface is 42The uniform interface is 42
The uniform interface is 42Yevhen Bobrov
 
xUnit Style Database Testing
xUnit Style Database TestingxUnit Style Database Testing
xUnit Style Database TestingChris Oldwood
 
JUnit Kung Fu: Getting More Out of Your Unit Tests
JUnit Kung Fu: Getting More Out of Your Unit TestsJUnit Kung Fu: Getting More Out of Your Unit Tests
JUnit Kung Fu: Getting More Out of Your Unit TestsJohn Ferguson Smart Limited
 
33rd Degree 2013, Bad Tests, Good Tests
33rd Degree 2013, Bad Tests, Good Tests33rd Degree 2013, Bad Tests, Good Tests
33rd Degree 2013, Bad Tests, Good TestsTomek Kaczanowski
 
JAVASCRIPT TDD(Test driven Development) & Qunit Tutorial
JAVASCRIPT TDD(Test driven Development) & Qunit TutorialJAVASCRIPT TDD(Test driven Development) & Qunit Tutorial
JAVASCRIPT TDD(Test driven Development) & Qunit TutorialAnup Singh
 
The Ring programming language version 1.5.3 book - Part 78 of 184
The Ring programming language version 1.5.3 book - Part 78 of 184The Ring programming language version 1.5.3 book - Part 78 of 184
The Ring programming language version 1.5.3 book - Part 78 of 184Mahmoud Samir Fayed
 
Android testing
Android testingAndroid testing
Android testingSean Tsai
 
C++ Unit Test with Google Testing Framework
C++ Unit Test with Google Testing FrameworkC++ Unit Test with Google Testing Framework
C++ Unit Test with Google Testing FrameworkHumberto Marchezi
 
GeeCON 2012 Bad Tests, Good Tests
GeeCON 2012 Bad Tests, Good TestsGeeCON 2012 Bad Tests, Good Tests
GeeCON 2012 Bad Tests, Good TestsTomek Kaczanowski
 
Confitura 2012 Bad Tests, Good Tests
Confitura 2012 Bad Tests, Good TestsConfitura 2012 Bad Tests, Good Tests
Confitura 2012 Bad Tests, Good TestsTomek Kaczanowski
 
NSOperation objective-c
NSOperation objective-cNSOperation objective-c
NSOperation objective-cPavel Albitsky
 

What's hot (20)

Writing and using Hamcrest Matchers
Writing and using Hamcrest MatchersWriting and using Hamcrest Matchers
Writing and using Hamcrest Matchers
 
Selenium Webdriver with data driven framework
Selenium Webdriver with data driven frameworkSelenium Webdriver with data driven framework
Selenium Webdriver with data driven framework
 
Testing, Performance Analysis, and jQuery 1.4
Testing, Performance Analysis, and jQuery 1.4Testing, Performance Analysis, and jQuery 1.4
Testing, Performance Analysis, and jQuery 1.4
 
Understanding JavaScript Testing
Understanding JavaScript TestingUnderstanding JavaScript Testing
Understanding JavaScript Testing
 
JUnit & Mockito, first steps
JUnit & Mockito, first stepsJUnit & Mockito, first steps
JUnit & Mockito, first steps
 
The uniform interface is 42
The uniform interface is 42The uniform interface is 42
The uniform interface is 42
 
xUnit Style Database Testing
xUnit Style Database TestingxUnit Style Database Testing
xUnit Style Database Testing
 
JUnit Kung Fu: Getting More Out of Your Unit Tests
JUnit Kung Fu: Getting More Out of Your Unit TestsJUnit Kung Fu: Getting More Out of Your Unit Tests
JUnit Kung Fu: Getting More Out of Your Unit Tests
 
JUnit Pioneer
JUnit PioneerJUnit Pioneer
JUnit Pioneer
 
33rd Degree 2013, Bad Tests, Good Tests
33rd Degree 2013, Bad Tests, Good Tests33rd Degree 2013, Bad Tests, Good Tests
33rd Degree 2013, Bad Tests, Good Tests
 
Migrating to JUnit 5
Migrating to JUnit 5Migrating to JUnit 5
Migrating to JUnit 5
 
JAVASCRIPT TDD(Test driven Development) & Qunit Tutorial
JAVASCRIPT TDD(Test driven Development) & Qunit TutorialJAVASCRIPT TDD(Test driven Development) & Qunit Tutorial
JAVASCRIPT TDD(Test driven Development) & Qunit Tutorial
 
The Ring programming language version 1.5.3 book - Part 78 of 184
The Ring programming language version 1.5.3 book - Part 78 of 184The Ring programming language version 1.5.3 book - Part 78 of 184
The Ring programming language version 1.5.3 book - Part 78 of 184
 
Android testing
Android testingAndroid testing
Android testing
 
Junit With Eclipse
Junit With EclipseJunit With Eclipse
Junit With Eclipse
 
C++ Unit Test with Google Testing Framework
C++ Unit Test with Google Testing FrameworkC++ Unit Test with Google Testing Framework
C++ Unit Test with Google Testing Framework
 
GeeCON 2012 Bad Tests, Good Tests
GeeCON 2012 Bad Tests, Good TestsGeeCON 2012 Bad Tests, Good Tests
GeeCON 2012 Bad Tests, Good Tests
 
Confitura 2012 Bad Tests, Good Tests
Confitura 2012 Bad Tests, Good TestsConfitura 2012 Bad Tests, Good Tests
Confitura 2012 Bad Tests, Good Tests
 
JUnit 5
JUnit 5JUnit 5
JUnit 5
 
NSOperation objective-c
NSOperation objective-cNSOperation objective-c
NSOperation objective-c
 

Similar to どう使う? Windows azure テーブル

Unit testing en iOS @ MobileCon Galicia
Unit testing en iOS @ MobileCon GaliciaUnit testing en iOS @ MobileCon Galicia
Unit testing en iOS @ MobileCon GaliciaRobot Media
 
Using xUnit as a Swiss-Aarmy Testing Toolkit
Using xUnit as a Swiss-Aarmy Testing ToolkitUsing xUnit as a Swiss-Aarmy Testing Toolkit
Using xUnit as a Swiss-Aarmy Testing ToolkitChris Oldwood
 
State of entity framework
State of entity frameworkState of entity framework
State of entity frameworkDavid Paquette
 
Cassandra Day NY 2014: Getting Started with the DataStax C# Driver
Cassandra Day NY 2014: Getting Started with the DataStax C# DriverCassandra Day NY 2014: Getting Started with the DataStax C# Driver
Cassandra Day NY 2014: Getting Started with the DataStax C# DriverDataStax Academy
 
Getting Started with Datatsax .Net Driver
Getting Started with Datatsax .Net DriverGetting Started with Datatsax .Net Driver
Getting Started with Datatsax .Net DriverDataStax Academy
 
Unit testing in iOS featuring OCUnit, GHUnit & OCMock
Unit testing in iOS featuring OCUnit, GHUnit & OCMockUnit testing in iOS featuring OCUnit, GHUnit & OCMock
Unit testing in iOS featuring OCUnit, GHUnit & OCMockRobot Media
 
Java Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner WalkthroughJava Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner WalkthroughMahfuz Islam Bhuiyan
 
Testing And Drupal
Testing And DrupalTesting And Drupal
Testing And DrupalPeter Arato
 
A testing framework for Microsoft SQL-Server
A testing framework for Microsoft SQL-ServerA testing framework for Microsoft SQL-Server
A testing framework for Microsoft SQL-Serverelliando dias
 
Unit & Automation Testing in Android - Stanislav Gatsev, Melon
Unit & Automation Testing in Android - Stanislav Gatsev, MelonUnit & Automation Testing in Android - Stanislav Gatsev, Melon
Unit & Automation Testing in Android - Stanislav Gatsev, MelonbeITconference
 
Grails unit testing
Grails unit testingGrails unit testing
Grails unit testingpleeps
 
Describe's Full of It's
Describe's Full of It'sDescribe's Full of It's
Describe's Full of It'sJim Lynch
 
Introduction to nsubstitute
Introduction to nsubstituteIntroduction to nsubstitute
Introduction to nsubstituteSuresh Loganatha
 
API Performance Testing
API Performance TestingAPI Performance Testing
API Performance Testingrsg00usa
 
Intro to Unit Testing in AngularJS
Intro to Unit Testing in AngularJSIntro to Unit Testing in AngularJS
Intro to Unit Testing in AngularJSJim Lynch
 

Similar to どう使う? Windows azure テーブル (20)

Unit testing en iOS @ MobileCon Galicia
Unit testing en iOS @ MobileCon GaliciaUnit testing en iOS @ MobileCon Galicia
Unit testing en iOS @ MobileCon Galicia
 
Using xUnit as a Swiss-Aarmy Testing Toolkit
Using xUnit as a Swiss-Aarmy Testing ToolkitUsing xUnit as a Swiss-Aarmy Testing Toolkit
Using xUnit as a Swiss-Aarmy Testing Toolkit
 
State of entity framework
State of entity frameworkState of entity framework
State of entity framework
 
Cassandra Day NY 2014: Getting Started with the DataStax C# Driver
Cassandra Day NY 2014: Getting Started with the DataStax C# DriverCassandra Day NY 2014: Getting Started with the DataStax C# Driver
Cassandra Day NY 2014: Getting Started with the DataStax C# Driver
 
Getting Started with Datatsax .Net Driver
Getting Started with Datatsax .Net DriverGetting Started with Datatsax .Net Driver
Getting Started with Datatsax .Net Driver
 
Unit testing in iOS featuring OCUnit, GHUnit & OCMock
Unit testing in iOS featuring OCUnit, GHUnit & OCMockUnit testing in iOS featuring OCUnit, GHUnit & OCMock
Unit testing in iOS featuring OCUnit, GHUnit & OCMock
 
Java Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner WalkthroughJava Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner Walkthrough
 
Junit_.pptx
Junit_.pptxJunit_.pptx
Junit_.pptx
 
Mxunit
MxunitMxunit
Mxunit
 
Testing And Drupal
Testing And DrupalTesting And Drupal
Testing And Drupal
 
A testing framework for Microsoft SQL-Server
A testing framework for Microsoft SQL-ServerA testing framework for Microsoft SQL-Server
A testing framework for Microsoft SQL-Server
 
Unit & Automation Testing in Android - Stanislav Gatsev, Melon
Unit & Automation Testing in Android - Stanislav Gatsev, MelonUnit & Automation Testing in Android - Stanislav Gatsev, Melon
Unit & Automation Testing in Android - Stanislav Gatsev, Melon
 
ERRest
ERRestERRest
ERRest
 
Rx workshop
Rx workshopRx workshop
Rx workshop
 
Grails unit testing
Grails unit testingGrails unit testing
Grails unit testing
 
Harton-Presentation
Harton-PresentationHarton-Presentation
Harton-Presentation
 
Describe's Full of It's
Describe's Full of It'sDescribe's Full of It's
Describe's Full of It's
 
Introduction to nsubstitute
Introduction to nsubstituteIntroduction to nsubstitute
Introduction to nsubstitute
 
API Performance Testing
API Performance TestingAPI Performance Testing
API Performance Testing
 
Intro to Unit Testing in AngularJS
Intro to Unit Testing in AngularJSIntro to Unit Testing in AngularJS
Intro to Unit Testing in AngularJS
 

Recently uploaded

Driving Behavioral Change for Information Management through Data-Driven Gree...
Driving Behavioral Change for Information Management through Data-Driven Gree...Driving Behavioral Change for Information Management through Data-Driven Gree...
Driving Behavioral Change for Information Management through Data-Driven Gree...Enterprise Knowledge
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountPuma Security, LLC
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...Neo4j
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptxHampshireHUG
 
[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdfhans926745
 
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking MenDelhi Call girls
 
IAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsIAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsEnterprise Knowledge
 
GenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day PresentationGenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day PresentationMichael W. Hawkins
 
CNv6 Instructor Chapter 6 Quality of Service
CNv6 Instructor Chapter 6 Quality of ServiceCNv6 Instructor Chapter 6 Quality of Service
CNv6 Instructor Chapter 6 Quality of Servicegiselly40
 
08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking Men08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking MenDelhi Call girls
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...apidays
 
Presentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreterPresentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreternaman860154
 
Automating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps ScriptAutomating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps Scriptwesley chun
 
08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking Men08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking MenDelhi Call girls
 
Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024The Digital Insurer
 
Artificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and MythsArtificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and MythsJoaquim Jorge
 
Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...
Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...
Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...Igalia
 
The Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdf
The Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdfThe Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdf
The Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdfEnterprise Knowledge
 
Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024The Digital Insurer
 
Boost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfBoost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfsudhanshuwaghmare1
 

Recently uploaded (20)

Driving Behavioral Change for Information Management through Data-Driven Gree...
Driving Behavioral Change for Information Management through Data-Driven Gree...Driving Behavioral Change for Information Management through Data-Driven Gree...
Driving Behavioral Change for Information Management through Data-Driven Gree...
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path Mount
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
 
[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf
 
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
 
IAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsIAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI Solutions
 
GenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day PresentationGenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day Presentation
 
CNv6 Instructor Chapter 6 Quality of Service
CNv6 Instructor Chapter 6 Quality of ServiceCNv6 Instructor Chapter 6 Quality of Service
CNv6 Instructor Chapter 6 Quality of Service
 
08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking Men08448380779 Call Girls In Greater Kailash - I Women Seeking Men
08448380779 Call Girls In Greater Kailash - I Women Seeking Men
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 
Presentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreterPresentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreter
 
Automating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps ScriptAutomating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps Script
 
08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking Men08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking Men
 
Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024
 
Artificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and MythsArtificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and Myths
 
Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...
Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...
Raspberry Pi 5: Challenges and Solutions in Bringing up an OpenGL/Vulkan Driv...
 
The Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdf
The Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdfThe Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdf
The Role of Taxonomy and Ontology in Semantic Layers - Heather Hedden.pdf
 
Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024
 
Boost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfBoost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdf
 

どう使う? Windows azure テーブル

  • 1. どう使う? Windows Azure テーブル ~ SQL Azure に挑む ~ 山本 昭宏 (Akihiro Yamamoto) Twitter : A_Ym
  • 2. プロフィール Microsoft 系テクノロジーコンサルタント会社勤務 興味のあるテクノロジー Windows Azure, C# 4, LINQ, WPF, WCF, WF, Silverlight Software Factories WindowsAzure の活動 Windows AzureCommunity トレーニングキットの翻訳や技術検証、情報の整理をしていました。 Web メディア @IT 「Windows Azure Platform速習シリーズ:SQL Azure-SQL Azureの機能と制約を理解する」 の記事を執筆させていただきました。 セミナー TechDays2010 「Windows AzurePlatform 徹底検証」 にて技術検証を行い、スピーカーとして登壇させていただきました。
  • 4. トランザクションスペック (Windows Azure Storage Team Blog より) 1 entity 追加= 1 トランザクション 100entity に対する変更の反映 (エンティティ グループ トランザクション ⇒ EGT を使用しない場合)= 100 トランザクション 100entity に対する変更の反映(EGT を使用する場合) = 1 トランザクション PartitionKeyとRowKeyが一致した場合のクエリ = 1 トランザクション 1クエリ で 500 entity 返された場合(継続トークンが発生しない場合) = 1 トランザクション 1 クエリで 5 リクエスト 発生した場合 (4つの継続トークンが発生した場合) = 5 トランザクション
  • 5. パフォーマンススペック (Windows Azure Storage Team Blog より) 1パーティションあたりのパフォーマンス 最大 500 トランザクション /sec 極力パーティションが均等に分散するような設計によりパフォーマンスが向上する 理論値 ? 参照 500entity×500 トランザクション =250,000entity/sec 追加 100entity×500 トランザクション =50,000entity/sec
  • 8. 追加の並列処理 (1/3) 使用法 var contexts = new TestTableContext[10000];Parallel.For(0, contexts.Count(),(idx) =>{    contexts[idx] = EntityController.CreateTestTableContext();    contexts[idx].SaveChangesDefaultOptions =   SaveChangesOptions.ContinueOnError | SaveChangesOptions.ReplaceOnUpdate ;}Int64 from = 0;Int64 to   = 1000000;int counter    = 0;int parallelUnit = 100;using(var manualEvent = new ManualResetEvent(false)){    for (Int64 rowIdx = from; rowIdx < to; rowIdx++) {var entity =         new TestTableEntity()            {                  PartitionKey = ((Int64)(Math.Floor((double)rowIdx / 1000))).ToString("0000000000")                , RowKey       = rowIdx.ToString("0000000000")                , Id           = rowIdx                , Text         = "Text_" + rowIdx.ToString("0000000000")            };        var context = contexts[(int)Math.Floor((double)rowIdx / to * contexts.Count())];        context.AddTestTableEntity(entity); 追加に使用する TableServiceContext を生成します。EGT のトランザクション単位は 100entity に制限されていますので、1000,000 entity 追加する場合は 10,000 の TableServiceContext を使用します。 ManualResetEvent を並列処理の同期に使用します。
  • 9. 追加の並列処理 (2/3) 使用法 (つづき)     if (rowIdx % parallelUnit == parallelUnit - 1 || rowIdx == to - 1)        {            context.SaveChangesAsParallel(            (exception) =>                {                    if (exception != null)                    {                     }                 if (Interlocked.Increment(ref counter) >= (int)(to / parallelUnit))                 {                     manualEvent.Set();                 }                }                );        } } manualEvent.WaitOne();} EGT 単位 (100entity) で非同期追加処理を行います。 例外発生時の処理を行います。 EGT 単位で追加完了時にカウンターを同期インクリメントし、全件追加が完了したらメインスレッドの待機状態を解除します。 メインスレッドを待機状態にします。
  • 10. 追加の並列処理 (3/3) public static IAsyncResult SaveChangesAsParallel( this TableServiceContext context , Action<Exception> completeAction ){    var asyncCallback =        new AsyncCallback(         (asyncResult) =>         {             DataServiceResponse response;             try             {                 response = context.EndSaveChanges(asyncResult);              completeAction(null);             }             catch (Exception exception)             {              }         }            );    var ret =   context.BeginSaveChanges(             SaveChangesOptions.Batch         , asyncCallback            , null            );    return ret;} TableServiceContext.BeginSaveChanges メソッドの第1パラメーターに SaveChangesOptions.Batch オプションを指定して EGT 追加処理を行います。
  • 11. クエリの並列処理 (1/3) 使用法 var context = EntityController.CreateTestTableContext();var query =    from        entity in context.TestTableEntity    select        entity    ;var entities =query.QueryAsParallel<TestTableEntity>( GetWhereExpressions(), null); IEnumerable<Expression<Func<TestTableEntity, bool>>> GetWhereExpressions(){    for (int pIdx = 0; pIdx <= 999; pIdx++)    {        yield return (TestTableEntity entity) => entity.PartitionKey == pIdx.ToString("0000000000");    }} where に使用する式は yieldreturn で返します。 これを使用しないと列挙の最後の式しか処理されません。
  • 12. クエリの並列処理 (2/3) public static IEnumerable<TEntity> QueryAsParallel<TEntity>(      this IQueryable<TEntity> query    , IEnumerable<Expression<Func<TEntity, bool>>> whereExpressions    ) {    int whereExpressionsCount = whereExpressions.Count();    var entities = new List<TEntity>();    var syncRoot = (entities as ICollection).SyncRoot;    using (var manualResetEvent = new ManualResetEvent(false))    {        ThreadPool.RegisterWaitForSingleObject(              manualResetEvent            , new WaitOrTimerCallback( (_state, timeout) => { manualResetEvent.Set(); } )            , null            , 300000            , false            );        foreach (var whereExpression in whereExpressions)        {            var dataServiceQuery = (DataServiceQuery<TEntity>) query.Where(whereExpression);             var asyncCallback =                new AsyncCallback(                    (asyncResult) =>                    {                        try                        {                            var response = dataServiceQuery.EndExecute(asyncResult);                            lock (syncRoot) { entities.AddRange(response.ToArray()); }                        } catch (Exception exception)                        {                                                    } ManualResetEvent を並列処理の同期に使用します。 タイムアウトの設定を行います。 Select 式と Wehere 式を組み合わせてクエリを作ります。 結果を lockで同期してリストに追加します。(4. は次ページ) 例外を処理します。
  • 13. クエリの並列処理 (3/3)                         finally                        {                            if (Interlocked.Decrement(ref whereExpressionsCount) == 0)                            {                                manualResetEvent.Set();                            }                        }                    }                    )                    ;                    dataServiceQuery.BeginExecute(asyncCallback, null);                }                manualResetEvent.WaitOne();            }            return entities;        } 全てのクエリが完了したらメイン スレッドの待機状態を解除します。 メイン スレッドを待機状態にします。
  • 14. テーブル サービス エンティティの基本形 WCF の データコントラクトとして使用できないので TableServiceEntity クラスは継承せずに、DataServiceKey 属性を設定します。 [DataContract][DataServiceKey("PartitionKey", "RowKey")]public class TestTableEntity{    public TestTableEntity()    {    }    [DataMember]    public string PartitionKey { get; set; }    [DataMember]    public string RowKey { get; set; }     [DataMember]    public DateTime Timestamp { get; set; }    [DataMember]    public string TypeAssemblyQualifiedName { get; set; }     public string ETag    {        get;        private set;    }    public void SetETag(string etag)    {        ETag = etag;    }     [DataMember]    public Int64 Id { get; set; }    [DataMember]    public string Text { get; set; }} テーブル サービス エンティティとして必須のプロパティを用意します。 CLR にマッピングするためのキーを格納するプロパティを用意します。 Etag を保持するプロパティと設定するメソッドを用意します。 (テーブル格納対象外)
  • 15. 継続トークン処理の拡張メソッド化 (1/2) 使用法 var context = EntityController.CreateTestTableContext();var query =    from        entity in context.TestTableEntity    select        entity    ;var entities = query.QueryContinuously();
  • 16. 継続トークン処理の拡張メソッド化 (2/2) public static IEnumerable<TEntity> QueryContinuously<TEntity>(this IQueryable<TEntity> query) {   var resultList = new List<TEntity>();    string nextPartitionKey = null;    string nextRowKey       = null;    do {        var dataServiceQuery = query as DataServiceQuery<TEntity>;        if (dataServiceQuery == null) { break; }        if (nextPartitionKey != null) {            dataServiceQuery = dataServiceQuery.AddQueryOption("NextPartitionKey", nextPartitionKey);            if (nextRowKey != null) {                dataServiceQuery = dataServiceQuery.AddQueryOption("NextRowKey", nextRowKey); }        }        var result   = dataServiceQuery.Execute();        var response = result as QueryOperationResponse;        resultList.AddRange(result);        nextPartitionKey = null;        nextRowKey       = null;        response.Headers.TryGetValue("x-ms-continuation-NextPartitionKey", out nextPartitionKey);        response.Headers.TryGetValue("x-ms-continuation-NextRowKey"      , out nextRowKey);    }    while (nextPartitionKey != null);    return resultList;}
  • 18. WindowsAzure テーブル vs.SQLAzure 並列処理を行えばパフォーマンスで SQL Azure に迫ることができます。 追加処理ではエンティティ グループ トランザクション (EGT) を組み合わせるとスループットが向上し、場合によっては SQLAzure を上回ります。 膨大なデータに対し、インスタンスサイズを大きくしたり、インスタンス数を増やすことによりリニアに対応できます。 ただし、PartitionKey の設計や並列処理の実装、メンテナンスのコストを考えると SQLAzure で対応可能なことを無理にテーブルで実現するメリットは小さいと言えます。 数10GB 以上のデータを扱うケースで有効だと考えます。⇒ 現在のところ Dallas との連携が有望だとみています。
  • 19. 参考情報 (1/2) Web メディア Windows Azure Storage Team Blog Understanding Windows Azure Storage Billing – Bandwidth, Transactions, and Capacity(http://blogs.msdn.com/b/windowsazurestorage/archive/2010/07/09/understanding-windows-azure-storage-billing-bandwidth-transactions-and-capacity.aspx) Windows Azure Storage Abstractions and their Scalability Targets(http://blogs.msdn.com/b/windowsazurestorage/archive/2010/05/10/windows-azure-storage-abstractions-and-their-scalability-targets.aspx) @IT 「Windows Azureストレージ開発入門(前編) -初めてのWindows Azureテーブル・ストレージ開発」(http://www.atmarkit.co.jp/fdotnet/dnfuture/winazurestorage_01/winazurestorage_01_01.html)
  • 20. 参考情報 (2/2) Windows Azure ベンチマーク サイト Azurescope: Benchmarking and Guidance for Windows Azure http://azurescope.cloudapp.net/ 書籍 (並列処理関連) More Effective C#(翔泳社) .NETのクラスライブラリ設計 (日経BPソフトプレス) 究極のC#プログラミング (技術評論社)