<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/atom10full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><feed xmlns="http://www.w3.org/2005/Atom" xmlns:media="http://search.yahoo.com/mrss/" xmlns:gr="http://www.google.com/schemas/reader/atom/" xmlns:idx="urn:atom-extension:indexing" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" idx:index="no" gr:dir="ltr"><!--
Content-type: Preventing XSRF in IE.

--><generator uri="http://www.google.com/reader">Google Reader</generator><id>tag:google.com,2005:reader/user/13668608591451703896/state/com.google/broadcast</id><title>Arnon's shared items in Google Reader</title><gr:continuation>CJvc1863tagC</gr:continuation><author><name>Arnon</name></author><updated>2011-09-18T22:32:47Z</updated><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/atom+xml" href="http://feeds.feedburner.com/ARGOReadings" /><feedburner:info uri="argoreadings" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><entry gr:crawl-timestamp-msec="1316385167124"><id gr:original-id="http://www.udidahan.com/?p=1527">tag:google.com,2005:reader/item/7095945f310e7150</id><category term="Architecture" /><category term="Autonomous Services" /><category term="Business Rules" /><category term="CQRS" /><category term="DDD" /><category term="Data Access" /><category term="Databases" /><category term="Reliability" /><category term="SOA" /><title type="html">Inconsistent data, poor performance, or SOA – pick one</title><published>2011-09-18T16:52:17Z</published><updated>2011-09-18T16:52:17Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/61iPCtBMvaM/" type="text/html" /><content xml:base="http://www.udidahan.com/" type="html">&lt;p&gt;One of the things that surprises some developers that I talk to is that you don’t always get consistency even with end-to-end synchronous communication and a single database. This goes beyond things like isolation levels that some developers are aware of and is particularly significant in multi-user collaborative domains.&lt;/p&gt;
&lt;h3&gt;The problem&lt;/h3&gt;
&lt;p&gt;Let’s start with an image to describe the scenario:&lt;/p&gt;
&lt;p&gt;&lt;img src="http://www.udidahan.com/wp-content/uploads/Inconsistency1.gif" alt="Inconsistency" title="Inconsistency" width="600" height="285"&gt;&lt;br&gt;
&lt;center&gt;Image 1. 3 transactions working in parallel on 3 entities&lt;/center&gt;&lt;/p&gt;
&lt;p&gt;The main issue we have here is that the values transaction 2 gets for A and B are those from T0 – before either transaction 1 or 3 completed. The reason this is an issue is that these old values (usually together with some message data) are used to calculate what the new state of C should be. &lt;/p&gt;
&lt;p&gt;Traditional optimistic concurrency techniques won’t detect any problem if we don’t touch A or B in transaction 2.&lt;/p&gt;
&lt;p&gt;In short, systems today are causing inconsistency.&lt;/p&gt;
&lt;h3&gt;Some solutions&lt;/h3&gt;
&lt;p&gt;1. Don’t have transactions which operate on multiple entities (which probably isn’t possible for some of your most important business logic).&lt;/p&gt;
&lt;p&gt;2. Turn on &lt;a href="http://en.wikipedia.org/wiki/Multiversion_concurrency_control"&gt;multi-version concurrency control&lt;/a&gt; – this is called snapshot isolation in MS Sql Server.&lt;/p&gt;
&lt;p&gt;Yes, you need to turn it on. It’s off by default.&lt;/p&gt;
&lt;p&gt;The good news is that this will stop the writing of inconsistent data to your database.&lt;br&gt;
The bad news is that it will probably cause your system many more exceptions when going to persist.&lt;/p&gt;
&lt;p&gt;For those of you who are using transaction messaging with automatic retrying, this will end up as “just” a performance problem (unless you follow the recommendations below). For those of you who are using regular web/wcf services (over tcp/http), you’re “cross cutting” exception management will likely end up discarding all the data submitted in those requests (but since that’s what you’re doing when you run into deadlocks this shouldn’t be news to you).&lt;/p&gt;
&lt;h3&gt;The solution to the performance issues&lt;/h3&gt;
&lt;p&gt;Eventual consistency.&lt;/p&gt;
&lt;p&gt;Funny isn’t it – all those people who were afraid of eventual consistency got &lt;b&gt;inconsistency&lt;/b&gt; instead.&lt;/p&gt;
&lt;p&gt;Also, it’s not enough to just have eventual consistency (like between the command and query sides of CQRS). You need to drastically decrease the size of your entities. And the best way of doing that is to partition those entities across multiple business services (also known in DDD lingo as Bounded Contexts) each with its own database.&lt;/p&gt;
&lt;p&gt;This is yet another reason why I say that CQRS shouldn’t be the top level architectural breakdown. Very useful within a given business service, yes – though sometimes as small as just some sagas.&lt;/p&gt;
&lt;h3&gt;Next steps&lt;/h3&gt;
&lt;p&gt;It may seem unusual that the title of this post implies that SOA is the solution, yet the content clearly states that traditional HTTP-based web services are a problem. Even REST wouldn’t change matters as it doesn’t influence how transactions are managed against a database.&lt;/p&gt;
&lt;p&gt;The SOA solution I’m talking about here is the one I’ve spent the last several years &lt;a href="http://www.udidahan.com/category/soa/"&gt;blogging about&lt;/a&gt;. It’s a different style of SOA which has services stretch up to contain parts of the UI as well as down to contain parts of the database, resulting in a composite UI and multiple databases. This is a drastically different approach than much of the literature on the topic – especially Thomas Erl’s books.&lt;/p&gt;
&lt;p&gt;Unfortunately there isn’t a book out there with all of this in it (that I’ve found), and I’m afraid that with my schedule (and family) writing a book is pretty much out of the question. Let’s face it – I’m barely finding time to blog.&lt;/p&gt;
&lt;p&gt;The one thing I’m trying to do more of is provide training on these topics. I’ve just finished a course in London, doing another this week in Aarhus Denmark, and another next month in San Francisco (which is now sold out). The next openings this year will be in Stockholm, London; Sydney Australia and Austin Texas will be coming in January of next year. I’ll be coming over to the US more next year so if you missed San Francisco, keep an eye out.&lt;/p&gt;
&lt;p&gt;I wish there was more I could do, but I’m only one guy.&lt;/p&gt;
&lt;p&gt;Hmm, maybe it’s time to change that.&lt;/p&gt;
&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/UdiDahan-TheSoftwareSimplist?a=c_mMy1CDq-Y:7jlasWfDtPU:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/UdiDahan-TheSoftwareSimplist?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/UdiDahan-TheSoftwareSimplist?a=c_mMy1CDq-Y:7jlasWfDtPU:F7zBnMyn0Lo"&gt;&lt;img src="http://feeds.feedburner.com/~ff/UdiDahan-TheSoftwareSimplist?i=c_mMy1CDq-Y:7jlasWfDtPU:F7zBnMyn0Lo" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/UdiDahan-TheSoftwareSimplist?a=c_mMy1CDq-Y:7jlasWfDtPU:V_sGLiPBpWU"&gt;&lt;img src="http://feeds.feedburner.com/~ff/UdiDahan-TheSoftwareSimplist?i=c_mMy1CDq-Y:7jlasWfDtPU:V_sGLiPBpWU" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/UdiDahan-TheSoftwareSimplist/~4/c_mMy1CDq-Y" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/61iPCtBMvaM" height="1" width="1"/&gt;</content><author><name>udidahan</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/UdiDahan-TheSoftwareSimplist"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/UdiDahan-TheSoftwareSimplist</id><title type="html">Udi Dahan - The Software Simplist</title><link rel="alternate" href="http://www.udidahan.com" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/UdiDahan-TheSoftwareSimplist/~3/c_mMy1CDq-Y/</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1314651591820"><id gr:original-id="426227:4867632:12658540">tag:google.com,2005:reader/item/2a9c30d665e7348b</id><category term="Strategy" /><category term="google" /><title type="html">The Three Ages of Google - Batch, Warehouse, Instant</title><published>2011-08-29T16:22:46Z</published><updated>2011-08-29T16:22:46Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/TeZhwg1pMhk/the-three-ages-of-google-batch-warehouse-instant.html" type="text/html" /><summary xml:base="http://highscalability.com/blog/" type="html">&lt;p&gt;&lt;a href="http://highscalability.com/blog/2009/12/16/building-super-scalable-systems-blade-runner-meets-autonomic.html"&gt;&lt;img src="http://farm7.static.flickr.com/6193/6091368869_dc65aa3ed9_m.jpg" alt="" width="200" height="200" align="right"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt; The world has changed. And some things that should not have been forgotten, were lost.&lt;/em&gt; I found these words from the Lord of the Rings echoing in my head as I listened to a fascinating presentation by &lt;a href="http://research.google.com/pubs/LuizBarroso.html"&gt;Luiz André Barroso&lt;/a&gt;, Distinguished Engineer at Google, concerning Google&amp;#39;s legendary past, golden present, and apocryphal future. His talk, &lt;a href="http://dl.acm.org/citation.cfm?id=2019527&amp;amp;CFID=39785911&amp;amp;CFTOKEN=33778723"&gt;Warehouse-Scale Computing: Entering the Teenage Decade&lt;/a&gt;, was given at the &lt;a href="http://www.acm.org/fcrc/plenary_2011.html"&gt;Federated Computing Research Conference&lt;/a&gt;. Luiz clearly knows his stuff and was early at Google, so he has a deep and penetrating perspective on the technology. There's much to learn from, think about, and build.&lt;/p&gt;
&lt;p&gt;Lord of the Rings applies at two levels. At the change level, Middle Earth went through &lt;a href="http://en.wikipedia.org/wiki/Middle-earth"&gt;three ages&lt;/a&gt;. While listening to Luiz talk, it seems so has Google: Batch (indexes calculated every month), Warehouse (the datacenter is the computer), and Instant (make it all real-time). At the &amp;quot;what was forgot&amp;quot; level, in the Instant Age section of the talk,  a common theme was the challenge of making low latency systems on top of commodity systems. These are issues very common in the real-time area and it struck me that these were the things that should not have been forgotten.&lt;/p&gt;
&lt;p&gt;What is completely new, however, is the combining of Warehouse + Instant, and that's where the opportunities and the future is to be found- the Fourth Age.&lt;/p&gt;
&lt;h2&gt;The First Age - The Age of Batch&lt;/h2&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/TeZhwg1pMhk" height="1" width="1"/&gt;</summary><author><name>Todd Hoff</name></author><source gr:stream-id="feed/http://highscalability.com/rss.xml"><id>tag:google.com,2005:reader/feed/http://highscalability.com/rss.xml</id><title type="html">High Scalability</title><link rel="alternate" href="http://highscalability.com/blog/" type="text/html" /></source><feedburner:origLink>http://highscalability.com/blog/2011/8/29/the-three-ages-of-google-batch-warehouse-instant.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1313292734009"><id gr:original-id="http://www.engadget.com/2011/08/13/visualized-the-apple-mothership/">tag:google.com,2005:reader/item/48de609317a3fc71</id><category term="Apple" /><category term="Apple Campus" /><category term="Apple Campus 2" /><category term="AppleCampus" /><category term="AppleCampus2" /><category term="architectural renderings" /><category term="ArchitecturalRenderings" /><category term="architecture" /><category term="building plans" /><category term="BuildingPlans" /><category term="Campus 2" /><category term="Campus2" /><category term="Cupertino" /><category term="gallery" /><category term="images" /><category term="pictures" /><category term="plans" /><category term="renderings" /><category term="visualized" /><title type="html">Visualized: the Apple mothership</title><published>2011-08-14T00:23:00Z</published><updated>2011-08-14T00:23:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/UGPVvqkfbhY/" type="text/html" /><summary xml:base="http://www.engadget.com/" type="html">&lt;div style="text-align:center"&gt;
	&lt;a href="http://www.engadget.com/2011/08/13/visualized-the-apple-mothership/"&gt;&lt;img alt="Visualized: the Apple mothership" src="http://www.blogcdn.com/www.engadget.com/media/2011/08/applecampus2rendering.jpg" style="border-width:0px;border-style:solid;margin:4px"&gt;&lt;/a&gt;&lt;/div&gt;
We've already caught a glimpse of Apple's proposed &lt;strike&gt;science fiction museum&lt;/strike&gt; &lt;a href="http://www.engadget.com/2011/06/08/steve-jobs-reveals-apples-new-spaceship-campus-calls-it-the-b/"&gt;new campus&lt;/a&gt; in Cupertino, but screen grabs just don't do this behemoth justice. A recently released set of renderings of Apple Campus 2, as it's known to the city of Cupertino, however, give it that proper otherworldly glow. According to the accompanying proposal, the building will take up a measly 2.8 million square feet, contain a 1,000-seat auditorium and research facilities totaling 300,000 square feet. Really? Is that all? If architectural renderings are your thing, hit the source link for some building-plan booty. &lt;div&gt;&lt;p&gt;&lt;strong&gt;Gallery: &lt;a href="http://www.engadget.com/photos/the-apple-mothership/"&gt;The Apple mothership&lt;/a&gt;&lt;/strong&gt;&lt;/p&gt;&lt;a href="http://www.engadget.com/photos/the-apple-mothership/#4363594"&gt;&lt;img src="http://www.blogcdn.com/www.engadget.com/media/2011/08/apple-campus2-04_thumbnail.jpg" alt="" title=""&gt;&lt;/a&gt;&lt;a href="http://www.engadget.com/photos/the-apple-mothership/#4363596"&gt;&lt;img src="http://www.blogcdn.com/www.engadget.com/media/2011/08/apple-campus2-06_thumbnail.jpg" alt="" title=""&gt;&lt;/a&gt;&lt;a href="http://www.engadget.com/photos/the-apple-mothership/#4363598"&gt;&lt;img src="http://www.blogcdn.com/www.engadget.com/media/2011/08/apple-campus2-09_thumbnail.jpg" alt="" title=""&gt;&lt;/a&gt;&lt;a href="http://www.engadget.com/photos/the-apple-mothership/#4363591"&gt;&lt;img src="http://www.blogcdn.com/www.engadget.com/media/2011/08/apple-campus2-01_thumbnail.jpg" alt="" title=""&gt;&lt;/a&gt;&lt;a href="http://www.engadget.com/photos/the-apple-mothership/#4363593"&gt;&lt;img src="http://www.blogcdn.com/www.engadget.com/media/2011/08/apple-campus2-03_thumbnail.jpg" alt="" title=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;p style="padding:5px;background:#ddd;border:1px solid #ccc;clear:both"&gt;&lt;a href="http://www.engadget.com/2011/08/13/visualized-the-apple-mothership/"&gt;Visualized: the Apple mothership&lt;/a&gt; originally appeared on &lt;a href="http://www.engadget.com"&gt;Engadget&lt;/a&gt; on Sat, 13 Aug 2011 20:23:00 EDT.  Please see our &lt;a href="http://www.weblogsinc.com/feed-terms/"&gt;terms for use of feeds&lt;/a&gt;.&lt;/p&gt;&lt;h6 style="clear:both;padding:8px 0 0 0;height:2px;font-size:1px;border:0;margin:0;padding:0"&gt;&lt;/h6&gt;&lt;a href="http://www.engadget.com/2011/08/13/visualized-the-apple-mothership/" rel="bookmark" title="Permanent link to this entry"&gt;Permalink&lt;/a&gt; &lt;img src="http://www.blogsmithmedia.com/www.engadget.com/media/post_label_VIA.gif" alt=""&gt;&lt;span&gt;&lt;a href="http://techcrunch.com/2011/08/13/apples-new-headquarters/"&gt;TechCrunch&lt;/a&gt;&lt;/span&gt;  |  &lt;img src="http://www.blogsmithmedia.com/www.engadget.com/media/post_label_source.gif" alt="source"&gt;&lt;span&gt;&lt;a href="http://www.cupertino.org/index.aspx?page=1107"&gt;Cupertino.org&lt;/a&gt;&lt;/span&gt;  | &lt;a href="http://www.engadget.com/forward/20017110/" title="Send this entry to a friend via email"&gt;Email this&lt;/a&gt; | &lt;a href="http://www.engadget.com/2011/08/13/visualized-the-apple-mothership/#comments" title="View reader comments on this entry"&gt;Comments&lt;/a&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/UGPVvqkfbhY" height="1" width="1"/&gt;</summary><author><name>Christopher Trout</name></author><source gr:stream-id="feed/http://www.engadget.com/rss.xml"><id>tag:google.com,2005:reader/feed/http://www.engadget.com/rss.xml</id><title type="html">Engadget</title><link rel="alternate" href="http://www.engadget.com" type="text/html" /></source><feedburner:origLink>http://www.engadget.com/2011/08/13/visualized-the-apple-mothership/</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1312452863691"><id gr:original-id="http://nosql.mypopescu.com/post/8436633131">tag:google.com,2005:reader/item/6c7cb98dae350f19</id><category term="Oozie" /><category term="Hadoop" /><category term="MapReduce" /><title type="html">A Detailed Guide to Oozie</title><published>2011-08-03T19:05:17Z</published><updated>2011-08-03T19:05:17Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/3xfrQrQ6Cz8/8436633131" type="text/html" /><summary xml:base="http://nosql.mypopescu.com/" type="html">&lt;p&gt;Boris Lublinsky and Michael Segel series of articles about Oozie, the Hadoop workflow framework, published on InfoQ:&lt;/p&gt;
&lt;ul&gt;&lt;li&gt;
&lt;p&gt;&lt;a href="http://www.infoq.com/articles/introductionOozie" rel="external nofollow"&gt;Introduction to Oozie&lt;/a&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Oozie workflow is a collection of actions (i.e. Hadoop Map/Reduce jobs, Pig jobs) arranged in a control dependency DAG (Direct Acyclic Graph), specifying a sequence of actions execution. This graph is specified in hPDL (a XML Process Definition Language).&lt;/p&gt;
&lt;/blockquote&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;a href="http://www.infoq.com/articles/oozieexample" rel="external nofollow"&gt;Oozie by Example&lt;/a&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;In this article we will describe a more complex Oozie example, which will allow us to discuss more Oozie features and demonstrate how to use them. The workflow which we are describing here implements vehicle GPS probe data ingestion. Probes data is delivered to a specific HDFS directory hourly in a form of file, containing all probes for this hour. Probes ingestion is done daily for all 24 files for this day. If the amount of files is 24, an ingestion process should start.  […]&lt;/p&gt;
&lt;/blockquote&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;a href="http://www.infoq.com/articles/ExtendingOozie" rel="external nofollow"&gt;Extending Oozie&lt;/a&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;In this article we will show how to leverage Oozie extensibility to implement custom orchestration language extensions.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;/li&gt;
&lt;/ul&gt;&lt;p&gt;These should be enough not only to give you on overview of Oozie but also a good start to using it when complex workflows are needed by your Hadoop MapReduce jobs.&lt;/p&gt;

&lt;p style="font-style:italic;font-size:0.9em"&gt;Original title and link: &lt;a href="http://nosql.mypopescu.com/post/8436633131" rel="permalink" style="color:red"&gt;A Detailed Guide to Oozie&lt;/a&gt; (&lt;a href="http://nosql.mypopescu.com"&gt;NoSQL database&lt;/a&gt;©myNoSQL)&lt;/p&gt;&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/nosql?a=xVYfk1878zE:RFvtUSofVX8:I9og5sOYxJI"&gt;&lt;img src="http://feeds.feedburner.com/~ff/nosql?d=I9og5sOYxJI" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/nosql?a=xVYfk1878zE:RFvtUSofVX8:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/nosql?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/nosql?a=xVYfk1878zE:RFvtUSofVX8:F7zBnMyn0Lo"&gt;&lt;img src="http://feeds.feedburner.com/~ff/nosql?i=xVYfk1878zE:RFvtUSofVX8:F7zBnMyn0Lo" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/nosql/~4/xVYfk1878zE" height="1" width="1"&gt;&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/nosql?a=AMtpeM1V6lU:xVYfk1878zE:I9og5sOYxJI"&gt;&lt;img src="http://feeds.feedburner.com/~ff/nosql?d=I9og5sOYxJI" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/nosql?a=AMtpeM1V6lU:xVYfk1878zE:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/nosql?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/nosql?a=AMtpeM1V6lU:xVYfk1878zE:F7zBnMyn0Lo"&gt;&lt;img src="http://feeds.feedburner.com/~ff/nosql?i=AMtpeM1V6lU:xVYfk1878zE:F7zBnMyn0Lo" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/nosql/~4/AMtpeM1V6lU" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/3xfrQrQ6Cz8" height="1" width="1"/&gt;</summary><author gr:unknown-author="true"><name>(author unknown)</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/nosql"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/nosql</id><title type="html">myNoSQL</title><link rel="alternate" href="http://nosql.mypopescu.com/" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/nosql/~3/AMtpeM1V6lU/8436633131</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1311966263590"><id gr:original-id="http://www.infoq.com/presentations/Testing-for-the-Unexpected">tag:google.com,2005:reader/item/857b21eb54d9c2b4</id><title type="html">Presentation:  Testing for the Unexpected</title><published>2011-07-29T15:00:00Z</published><updated>2011-07-29T15:00:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/K5yOn5ZPSoo/Testing-for-the-Unexpected" type="text/html" /><summary xml:base="http://www.infoq.com/" type="html">Ulf Wiger discusses the importance of automated testing along with some lessons learned at Ericsson, including using randomized and extensive testing, aiming to achieve system robustness. &lt;i&gt;By Ulf Wiger&lt;/i&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/K5yOn5ZPSoo" height="1" width="1"/&gt;</summary><author><name>Ulf Wiger</name></author><source gr:stream-id="feed/http://www.infoq.com/rss/rss.action?token=pnh3tDf0ZtgBsB2JJ70MoS0Ie5s6Ccgw"><id>tag:google.com,2005:reader/feed/http://www.infoq.com/rss/rss.action?token=pnh3tDf0ZtgBsB2JJ70MoS0Ie5s6Ccgw</id><title type="html">InfoQ Personalized Feed for Arnon Rotem-Gal-Oz</title><link rel="alternate" href="http://www.infoq.com" type="text/html" /></source><feedburner:origLink>http://www.infoq.com/presentations/Testing-for-the-Unexpected</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1311804308240"><id gr:original-id="e847c0e7-38d9-45c0-b593-56747303e088:18620">tag:google.com,2005:reader/item/3726630c3086e284</id><title type="html">What is Enterprise Search ?</title><published>2011-07-27T09:56:00Z</published><updated>2011-07-27T09:56:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/HTGYlTWZ5qY/what-is-enterprise-search.aspx" type="text/html" /><summary xml:base="http://consultingblogs.emc.com/default.aspx" type="html">&lt;p&gt;Searching for something of interest on the internet has become a norm for billions of&lt;br&gt;people around the world. Internet Search has revolutionized the way business&lt;br&gt;transformation happens. Similarly Enterprise Search has revolutionized the way data is&lt;br&gt;handled and analyzed in corporate and e-commerce world. The one single point that&lt;br&gt;differentiates Enterprise Search from internet Search is the importance of organizing and&lt;br&gt;categorization of data, which is most of the time over looked in internet search.&lt;/p&gt;&lt;p&gt;• Enterprise search is a process of organizing and categorizing information either&lt;br&gt;structured or unstructured inside a single corporate websites/networks to search&lt;br&gt;with utmost user friendliness and meeting to-the-point business objectives as&lt;br&gt;motivation.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Enterprise search is here to increase business value to the randomly distributed&lt;br&gt;data across the corporate website/ networks. It’s a foundation for new generation&lt;br&gt;business intelligence solution. It provides contextual and logical insight into all&lt;br&gt;enterprise data with high precision, increased scalability and friendly usability.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Cutting across structured and unstructured information, Enterprise search provides&lt;br&gt;relevant data to ordinary workers, research scholars to CEO's which increases the&lt;br&gt;productivity and quality of work accomplished using the result data set.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Traffic and revenue increase in significant proportions is the hall mark of enterprise&lt;br&gt;search. &lt;br&gt;&lt;/p&gt;&lt;p&gt;Every Enterprise Search Software (ESS) product would have to support following&lt;br&gt;functionality: &lt;/p&gt;&lt;p&gt;• Ability to crawl and fetch the Enterprise content and perform indexing,&lt;br&gt;summarization, etc on it for faster and effective access.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Ability to perform free text-based search on the indexed Enterprise content and&lt;br&gt;serve matching set of records to the Enterprise users.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Ability to ensure that user access to the Enterprise content records is based on&lt;br&gt;access rights granted to the Enterprise user on the Enterprise content.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Ability to report changes to the content records (additions, modifications,&lt;br&gt;deletions) on the data sources.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Ability to report changes to the access rights information in terms of grant and&lt;br&gt;revocation to users and security groups.&lt;/p&gt;&lt;p&gt;&lt;br&gt;• Ability to perform interactions with the connected data sources in a secure and&lt;br&gt;encrypted manner. &lt;br&gt;&lt;/p&gt;&lt;p&gt; &lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=18620" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/HTGYlTWZ5qY" height="1" width="1"/&gt;</summary><author><name>Ajay.Shivarathri</name></author><source gr:stream-id="feed/http://blogs.conchango.com/MainFeed.aspx"><id>tag:google.com,2005:reader/feed/http://blogs.conchango.com/MainFeed.aspx</id><title type="html">EMC Consulting Blogs</title><link rel="alternate" href="http://consultingblogs.emc.com/default.aspx" type="text/html" /></source><feedburner:origLink>http://consultingblogs.emc.com/ajayshivarathri/archive/2011/07/27/what-is-enterprise-search.aspx</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1310754608647"><id gr:original-id="tag:typepad.com,2003:post-6a00d835457b7453ef015433afa04f970c">tag:google.com,2005:reader/item/a8eb9001c15a45f8</id><category term="Cassandra" scheme="http://www.sixapart.com/ns/types#category" /><category term="Cloud" scheme="http://www.sixapart.com/ns/types#category" /><category term="Cloud Computing" scheme="http://www.sixapart.com/ns/types#category" /><category term="GigaSpaces" scheme="http://www.sixapart.com/ns/types#category" /><category term="Hbase" scheme="http://www.sixapart.com/ns/types#category" /><category term="latency" scheme="http://www.sixapart.com/ns/types#category" /><category term="NOSQL" scheme="http://www.sixapart.com/ns/types#category" /><category term="predictable analytics" scheme="http://www.sixapart.com/ns/types#category" /><category term="real-time" scheme="http://www.sixapart.com/ns/types#category" /><category term="scalability" scheme="http://www.sixapart.com/ns/types#category" /><title type="html">Real Time Analytics for Big Data: An Alternative Approach</title><published>2011-07-14T15:26:26Z</published><updated>2011-12-08T21:28:21Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/Ug-8Udd1wQY/real-time-analytics-for-big-data-an-alternative-approach.html" type="text/html" /><link rel="replies" href="http://natishalom.typepad.com/nati_shaloms_blog/2011/07/real-time-analytics-for-big-data-an-alternative-approach.html" type="text/html" /><content xml:base="http://natishalom.typepad.com/nati_shaloms_blog/" xml:lang="iw" type="html">&lt;div&gt;&lt;p&gt;Lately, we've been talking to various clients about realtime analytics, and with convenient timing Todd Hoff wrote up how Facebook's realtime analytics system was designed and implemented (See previous review on that regard &lt;a href="http://natishalom.typepad.com/nati_shaloms_blog/2011/07/real-time-analytics-for-big-data-an-alternative-approach-to-facebooks-new-realtime-analytics-system.html"&gt;here&lt;/a&gt;).&lt;/p&gt;&#xD;
&lt;p&gt;They had some assumptions in design that centered around the reliability of in-memory systems and database neutrality that affected what they did: for memory, that transactional memory was unreliable, and for the database, that HBase was the only targeted data store.&lt;/p&gt;&#xD;
&lt;p&gt;What if those assumptions are changed? We can see reliable transactional memory in the field, as a requirement for any in-memory data grid, and certainly there are more databases than HBase; given database and platform neutrality, and reliable transactional memory, how could you build a realtime analytics system?&lt;/p&gt;&#xD;
&lt;p&gt;Joseph Ottinger and I discussed this, and this is what we came up with.&lt;/p&gt;&#xD;
&lt;h1&gt;A Summary of History&lt;/h1&gt;&#xD;
&lt;p&gt;To understand what a new design might look like, it’s often useful to consider a previous design. This is a very short summary of Facebook’s realtime analytics system.&lt;/p&gt;&#xD;
&lt;p&gt;First, it’s based on a system of key/value pairs, where the key might be a URL and the value is a counter. Thus, there’s a requirement for atomic, transactional updates to a very simple piece of data. The difficulties come from scale, not from the focus of the system.&lt;/p&gt;&#xD;
&lt;p&gt;The process flow is fairly simple:&lt;/p&gt;&#xD;
&lt;ul&gt;&#xD;
&lt;li&gt;A user creates an event by performing some action on the website. This generates an AJAX request, sent to a service. &lt;/li&gt;&#xD;
&lt;li&gt;Scribe is used to write the events into logs, stored on HDFS. &lt;/li&gt;&#xD;
&lt;li&gt;PTail is used to consolidate the HDFS logs. &lt;/li&gt;&#xD;
&lt;li&gt;Puma takes the consolidated logs from PTail and stores them into HBase in groupings that represent roughly 1.5 seconds’ worth of events. &lt;/li&gt;&#xD;
&lt;li&gt;HBase serves as the long-term repository for analytics data. &lt;/li&gt;&#xD;
&lt;/ul&gt;&#xD;
&lt;p&gt;There are some questions around how PTail and Puma serve as scaling agents, and some of the notes around their use are still limited in scale – for example, one of the concerns is that an in-memory hash table will fill up, which sounds like fairly serious limitation to have to keep in mind.&lt;/p&gt;&#xD;
&lt;h1&gt;A Potential for Improvement&lt;/h1&gt;&#xD;
&lt;p&gt;There are lots of areas in which you can see potential improvements, if the assumptions are changed. As a contrast to Facebook's working system:&lt;/p&gt;&#xD;
&lt;ul&gt;&#xD;
&lt;li&gt;We can simplify the design. If memory can be seen as transactional - and it can - we can use them without transforming them as they proceed along our analytics workflow. This makes our design and implementation much simpler to implement and test, and performance improves as well.&lt;/li&gt;&#xD;
&lt;li&gt;We can strengthen the design. With a polling semantic, such systems are brittle, relying on systems that pull data in order to generate realtime analytics data. We should be able to reduce the fragility of the system, even while making it faster.&lt;/li&gt;&#xD;
&lt;li&gt;We can strengthen the implementation. With batching subsystems, there are limits shouldn’t exist. For example, one concern in Facebook's implementation is the use of an in-memory hash table that stores intermediate data; the in-memory aspect isn’t a concern until you realize that the batch sizes are chosen partially to make sure that this hash table doesn’t overflow available space.&lt;/li&gt;&#xD;
&lt;li&gt;We can allow deployments to change databases based on their requirements. There's nothing wrong with HBase, but it's got specific characteristics that aren't appropriate for all enterprises. We can design a system which you’d be able to deploy on various and flexible platforms, and we can migrate the underlying long-term data store to a different database if needed.&lt;/li&gt;&#xD;
&lt;li&gt;We can consolidate the analytics system so that management is easier and unified. While there are system management standards like SNMP that allow management events to be presented  in the same way no matter the source, having so many different pieces means that managing the system requires an encompassing understanding, which makes maintenance and scaling more difficult.&lt;/li&gt;&#xD;
&lt;/ul&gt;&#xD;
&lt;h1&gt;&lt;span style="font-weight:normal;font-size:small"&gt;What we want to do, then, is create a general model for an application that can accomplish the same goals as Facebook’s realtime analytics system, while leveraging the capabilities that in-memory data grids offer where available, potentially offering improvement in the areas of scalability, manageability, latency, platform neutrality, and simplicity, all while increasing ease of data access.&lt;/span&gt;&lt;/h1&gt;&#xD;
&lt;p&gt;That sounds like quite a tall order, but it’s doable.&lt;/p&gt;&#xD;
&lt;p&gt;The key is to remember that at heart, realtime analytics represent an events system. Facebook’s entire architecture is designed to funnel events through various channels, such that they can safely and sequentially manage event updates.&lt;/p&gt;&#xD;
&lt;p&gt;Therefore, they receive a massive set of events that “look like” marbles, which they line up in single file; they then sort the marbles by color, you might say, and for each color they create a bundle of sticks; the sticks are lit on fire, and when the heat goes up past a certain temperature, steam is generated, which turns a turbine.&lt;/p&gt;&#xD;
&lt;p&gt;It’s a real-life Rube Goldberg machine, which is admirable in that it works, but much of it is still unnecessary if the assumptions about memory ("unreliable") and database ("HBase is the only target that counts") are changed. Looking at the analogy from the previous paragraph, there’s no need to change a marble into anything. The marble is enough.&lt;/p&gt;&#xD;
&lt;h1&gt;A Plan for Implementation&lt;/h1&gt;&#xD;
&lt;p&gt;Our design for implementation is built around putting data and messaging together. A data grid is a perfect mechanism for this, as long as it provides some basic features: transactional operations, push and pull semantics, and data partitioning.&lt;/p&gt;&#xD;
&lt;p&gt;A data grid &lt;em&gt;does&lt;/em&gt; provide those basic features, or else it's not really much of a data grid; it'd be more of a cache otherwise.&lt;/p&gt;&#xD;
&lt;p&gt;With a data grid, then, the events come in as individual messages. When the user chooses an operation on the web site, an asynchronous operation would write the event, just as Facebook does today. However, instead of filtering and batching the events into various forms, the events are dispatched to waiting processes that perform many transactional updates in parallel.&lt;/p&gt;&#xD;
&lt;p&gt;There’s a danger that those updates might be slower than the generated events, if each event is processed sequentially. That said, this isn’t as much a problem as one might think; if data partitioning is used, then event handlers can receive partitioned events, which localizes updates and speeds them up dramatically.&lt;/p&gt;&#xD;
&lt;p&gt;In fact, you can still use batching to process events as a group; since the events would be partitioned coming in, the batch process would still be updating local data very quickly, which would be faster than individual event processing, even while retaining simplicity.&lt;/p&gt;&#xD;
&lt;p&gt;With this design, there is no overflow condition, because a system that’s designed to scale in and out as most data grids are will repartition to maintain even usage. If a data grid can’t provide this feature intrinsically, of course some management will be necessary, but finding data grids with this feature isn’t very difficult.&lt;/p&gt;&#xD;
&lt;p&gt;One other advantage of data grids is in write-through support. With write-through, updates to the data grid are written asynchronously to a backend data store – which could be HBase (as used by Facebook), Cassandra, a relational database such as MySQL, or any other data medium you choose for long-term storage, should you need that.&lt;/p&gt;&#xD;
&lt;p&gt;&lt;a href="http://natishalom.typepad.com/.a/6a00d835457b7453ef014e89d7445a970d-pi" style="display:inline"&gt;&lt;img alt="RealTimeAnalytics_big_data" border="0" src="http://natishalom.typepad.com/.a/6a00d835457b7453ef014e89d7445a970d-800wi" title="RealTimeAnalytics_big_data"&gt;&lt;/a&gt; &lt;br&gt;&lt;br&gt;&lt;/p&gt;&#xD;
&lt;p&gt;The memory system and the database - the external data store - work together. The in-memory solution is ideal for the realtime aspects, the events that affect &lt;em&gt;now&lt;/em&gt;. The external data storage solution is designed to handle long-term data, for which speed is not as much of an issue.&lt;/p&gt;&#xD;
&lt;h1&gt;A Discussion of Strengths&lt;/h1&gt;&#xD;
&lt;p&gt;The key concept here is that event handling is the lever that can move the realtime analytics mountain. By providing a simple, scalable publisher/subscriber model, you simplify design; by using a platform that supports data partitioning, transactional updates, and write through capabilities, you gain scalability.&lt;/p&gt;&#xD;
&lt;p&gt;The data grid’s flexible query API means that events can literally react when data is available.&lt;/p&gt;&#xD;
&lt;p&gt;For a call center, for example, you want to immediately identify signals that show that the caller should be handled differently; imagine an ecommerce site that was able to determine immediately if a user was losing interest, and thus could respond appropriately, before the customer moves on.&lt;/p&gt;&#xD;
&lt;p&gt;With external processes and a long funnel for data, immediate-response capabilities are very difficult to implement, not just because of latency but because the data transformations tend to homogenize the data, instead of allowing rich expressions and flexible event types.&lt;/p&gt;&#xD;
&lt;p&gt;The data grid also has much richer support in terms of client applications. Instead of applications going through an API that focuses on a specific phase of the data’s life (for example, an API focused on HBase), you can focus on a generic API that can capture events at any point in their lifecycle, and from anywhere. An external monitoring process, then, can have the same immediate, partition-aware access to data that the integrated message-handling system does; adding features and analysis is just a matter of connecting a client to the data grid.&lt;/p&gt;&#xD;
&lt;p&gt;Here we have a quick demo that shows much of this in motion. We have a market analysis application, deployed into GigaSpaces XAP via our new Cloud deployment too, Cloudify; it uses an event-driven system to display realtime data, with a write-through to Cassandra on the back-end. The design is very simple, and demonstrates the principles we've discussed here - and can scale up and down depending on demand.&lt;/p&gt;&#xD;
&lt;div style="margin:0px;display:inline;float:none;padding:0px"&gt;&#xD;
&lt;div style="margin:0px;padding:0px;display:inline"&gt;&#xD;
&lt;div&gt;&#xD;
&#xD;
&lt;iframe src="http://reader.googleusercontent.com/reader/embediframe?src=http://www.youtube.com/v/rt7-UnmliTE?hl%3Den%26hd%3D1&amp;amp;width=550&amp;amp;height=330" width="550" height="330"&gt;&lt;/iframe&gt;&#xD;
&#xD;
&lt;/div&gt;&#xD;
&lt;/div&gt;&#xD;
&lt;/div&gt;&#xD;
&lt;h2&gt;Final words&lt;/h2&gt;&#xD;
&lt;p&gt;As real-time-analytics &lt;a href="http://gigaom.com/cloud/big-data-in-real-time-is-no-fantasy/"&gt;gets into mainstream application design&lt;/a&gt;, it becomes important to draw a blueprint on how to build this sort of system without re-inventing the wheel.&lt;/p&gt;&#xD;
&lt;p&gt;&lt;a href="http://highscalability.com/blog/2011/3/22/facebooks-new-realtime-analytics-system-hbase-to-process-20.html"&gt;Todd Hoff&lt;/a&gt; (HighScalability) and &lt;a href="http://www.facebook.com/video/video.php?v=707216889765&amp;amp;oid=9445547199&amp;amp;comments"&gt;Alex Himel&lt;/a&gt; (Facebook) provided a fairly detailed description on their solution and even more importantly they even shared the rationales that made them do things in certain ways.&lt;/p&gt;&#xD;
&lt;p&gt;One main difference in assumptions that lead to the different implementation strategies are in reliable memory for event processing, and in the use of passive data storage.&lt;/p&gt;&#xD;
&lt;p&gt;Another difference is that we had to to think of the solution as an easily cloneable solution and therefore a lot of attention was put on the simplicity of the runtime, packaging and management of the solution.&lt;/p&gt;&#xD;
&lt;p&gt;Yet another difference is that we couldn’t decide on a specific database as there isn’t a "one size fits all" solution – for certain customers, SQL would still be preferred choice and the fact that we can buffer the write to the database gives them more headroom while still allowing them to scale on writes.&lt;/p&gt;&#xD;
&lt;p&gt;I hope that this would lead to constructive dialogue on the various tradeoffs which will serve the entire industry...&lt;/p&gt;&#xD;
&lt;p&gt;&lt;strong&gt;References&lt;/strong&gt;&lt;/p&gt;&#xD;
&lt;ul&gt;&#xD;
&lt;li&gt;&lt;strong&gt;&lt;a href="http://mrkn.co/forums/java/general/562.html#"&gt;Video: Realtime Analytics for Big Data: A Facebook Case Study&lt;/a&gt;&lt;/strong&gt;&lt;/li&gt;&#xD;
&lt;/ul&gt;&lt;/div&gt;&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/NatiShalom?a=eA1CZK6Hgbw:_fbtjZkcxyY:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/NatiShalom?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/NatiShalom?a=eA1CZK6Hgbw:_fbtjZkcxyY:qj6IDK7rITs"&gt;&lt;img src="http://feeds.feedburner.com/~ff/NatiShalom?d=qj6IDK7rITs" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/NatiShalom/~4/eA1CZK6Hgbw" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/Ug-8Udd1wQY" height="1" width="1"/&gt;</content><author><name>Nati Shalom</name></author><source gr:stream-id="feed/http://natishalom.typepad.com/nati_shaloms_blog/atom.xml"><id>tag:google.com,2005:reader/feed/http://natishalom.typepad.com/nati_shaloms_blog/atom.xml</id><title type="html">Nati Shalom&amp;#39;s Blog</title><link rel="alternate" href="http://natishalom.typepad.com/nati_shaloms_blog/" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/NatiShalom/~3/eA1CZK6Hgbw/real-time-analytics-for-big-data-an-alternative-approach.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1310744972489"><id gr:original-id="">tag:google.com,2005:reader/item/c61b6be4544d32f6</id><title type="html">Martin Fowler: Bliki: CQRS</title><published>2011-07-14T13:33:00Z</published><updated>2011-07-14T13:33:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/8rtjV06s3BA/CQRS.html" type="text/html" /><summary xml:base="http://www.thoughtworks.com/blogs/current" type="html">&lt;p&gt;CQRS stands for &lt;b&gt;Command Query Responsibility Segregation&lt;/b&gt;. It's a
  pattern that I first heard described by &lt;a href="http://codebetter.com/gregyoung/"&gt;Greg Young&lt;/a&gt;. At its heart is
  a simple notion that you can use a different model to update
  information than the model you use to read information. This simple
  notion leads to some profound consequences for the design of
  information systems.&lt;/p&gt;

&lt;p&gt;The mainstream approach people use for interacting with an
  information system is to treat it as a CRUD datastore. By this I
  mean that we have mental model of some record structure where we can
  &lt;b&gt;c&lt;/b&gt;reate new records, &lt;b&gt;r&lt;/b&gt;ead records, &lt;b&gt;u&lt;/b&gt;pdate
  existing records, and &lt;b&gt;d&lt;/b&gt;elete records when we're done with
  them. In the simplest case, our interactions are all about storing
  and retrieving these records.&lt;/p&gt;

&lt;p&gt;As our needs become more sophisticated we steadily move away from
  that model. We may want to look at the information in a different
  way to the record store, perhaps collapsing multiple records
  into one, or forming virtual records by combining information for
  different places. On the update side we may find validation rules
  that only allow certain combinations of data to be stored, or may
  even infer data to be stored that's different from that we
  provide.&lt;/p&gt;
&lt;img src="http://martinfowler.com/bliki/images/cqrs/single-model.png"&gt;
&lt;p&gt;As this occurs we begin to see multiple representations of
  information. When users interact with the information they use
  various presentations of this information, each of which is a
  different representation. Developers typically build their own
  conceptual model which they use to manipulate the core elements of
  the model. If you're using a Domain Model, then this is usually the
  conceptual representation of the domain. You typically also make the
  persistent storage as close to the conceptual model as you can.&lt;/p&gt;

&lt;p&gt;This structure of multiple layers of representation can get quite
  complicated, but when people do this they still resolve it down to a
  single conceptual representation which acts as a conceptual
  integration point between all the presentations.&lt;/p&gt;

&lt;p&gt;The change that CQRS introduces is to split that conceptual model
  into separate models for update and display, which it refers to as
  Command and Query respectively following the vocabulary of
  &lt;a href="http://martinfowler.com/bliki/CommandQuerySeparation.html"&gt;CommandQuerySeparation&lt;/a&gt;. The rationale is that for many
  problems, particularly in more complicated domains, having the same
  conceptual model for commands and queries leads to a more complex model that
  does neither well.&lt;/p&gt;
&lt;img src="http://martinfowler.com/bliki/images/cqrs/cqrs.png"&gt;
&lt;p&gt;By separate models we most commonly mean different object models,
  probably running in different logical processes, perhaps on separate
  hardware. A web example would see a user looking at a web page
  that's rendered using the query model. If they initiate a change
  that change is routed to the separate command model for processing, the
  resulting change is communicated to the query model to render the
  updated state.&lt;/p&gt;

&lt;p&gt;There's room for considerable variation here. The in-memory
  models may share the same database, in which case the database acts
  as the communication between the two models. However they may also
  use separate databases, effectively making the query-side's database
  by a real-time &lt;a href="http://martinfowler.com/bliki/ReportingDatabase.html"&gt;ReportingDatabase&lt;/a&gt;. In this case there
  needs to be some communication mechanism between the two models or
  their databases.&lt;/p&gt;

&lt;p&gt;The two models might not be separate object models, it could be
  that the same objects have different interfaces for their command
  side and their query side, rather like views in relational
  databases. But usually when I hear of CQRS, they are clearly
  separate models. &lt;/p&gt;

&lt;p&gt;CQRS naturally fits with some other architectural
  patterns. &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;As we move away from a single representation that we interact
    with via CRUD, we can easily move to a task-based UI.&lt;/li&gt;

&lt;li&gt;Interacting with the command-model naturally falls into
    commands or events, which meshes well with &lt;a href="http://martinfowler.com/bliki/../eaaDev/EventSourcing.html"&gt;Event Sourcing&lt;/a&gt;.&lt;/li&gt;

&lt;li&gt;Having separate models raises questions about how hard to keep
    those models consistent, which raises the likelihood of using
    &lt;a href="http://www.allthingsdistributed.com/2008/12/eventually_consistent.html"&gt;eventual consistency&lt;/a&gt;.&lt;/li&gt;

&lt;li&gt;For many domains, much of the logic is needed when you're
    updating, so it may make sense to use
    &lt;a href="http://martinfowler.com/bliki/EagerReadDerivation.html"&gt;EagerReadDerivation&lt;/a&gt; to simplify your query-side models.&lt;/li&gt;

&lt;li&gt;CQRS is suited to complex domains, the kind that also benefit
    from &lt;a href="http://www.amazon.com/gp/product/0321125215?ie=UTF8&amp;amp;tag=martinfowlerc-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=9325&amp;amp;creativeASIN=0321125215"&gt;Domain-Driven Design&lt;/a&gt;&lt;img alt="" border="0" height="1" src="http://www.assoc-amazon.com/e/ir?t=martinfowlerc-20&amp;amp;l=as2&amp;amp;o=1&amp;amp;a=0321601912" style="border:none!important;margin:0px!important" width="1"&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;hr&gt;
&lt;a name="WhenToUseIt"&gt;&lt;/a&gt;

&lt;h2&gt;When to use it&lt;/h2&gt;

&lt;p&gt;Like any pattern, CQRS is useful in some places, but not in
  others. Many systems do fit a CRUD mental model, and so should be
  done in that style. CQRS is a significant mental leap for all
  concerned, so shouldn't be tackled unless the benefit is worth the
  jump.&lt;/p&gt;

&lt;p&gt;In particular CQRS should only be used on specific portions of a
  system (a &lt;a href="http://domaindrivendesign.org/node/91"&gt;Bounded
  Context&lt;/a&gt; in DDD lingo) and not the the system as a whole. In this
  way of thinking, each Bounded Context needs its own decisions on how
  it should be modeled.&lt;/p&gt;

&lt;p&gt;So far I see benefits in two directions. Firstly is handling
  complexity - a complex domain may be easier to tackle by using
  CQRS. I do have to hedge this, usually there's enough overlap
  between the command and query sides that sharing a model is
  easier. Each domain has different characteristics.&lt;/p&gt;

&lt;p&gt;The other main benefit is in handling high performance
  applications. CQRS allows you to separate the load from reads and
  writes allowing you to scale each independently. If your application
  sees a big disparity between reads and writes this is very
  handy. Even without that, you can apply different optimization
  strategies to the two sides. An example of this is using different
  database access techniques for read and update.&lt;/p&gt;

&lt;p&gt;If your domain isn't suited to CQRS, but you have demanding
  queries that add complexity or performance problems, remember that
  you can still use a &lt;a href="http://martinfowler.com/bliki/ReportingDatabase.html"&gt;ReportingDatabase&lt;/a&gt;. CQRS uses a
  separate model for all queries. With a reporting database you still
  use your main system for most queries, but offload the more
  demanding ones to the reporting database.&lt;/p&gt;

&lt;p&gt;It's also true that we haven't seen enough uses of CQRS in the
  field yet to be confident that we understand its pros and cons. So
  while CQRS is a pattern I'd certainly want in my toolbox, I wouldn't
  keep it at the top.&lt;/p&gt;
&lt;hr&gt;
&lt;a name="FurtherReading"&gt;&lt;/a&gt;

&lt;h2&gt;Further Reading&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://codebetter.com/gregyoung/"&gt;Greg Young&lt;/a&gt; was the first person I heard talking about this
      approach - this is &lt;a href="http://codebetter.com/gregyoung/2010/02/16/cqrs-task-based-uis-event-sourcing-agh/"&gt;the summary from him&lt;/a&gt; that I like best.&lt;/li&gt;

&lt;li&gt;Udi Dahan is another advocate of CQRS, he has a &lt;a href="http://www.udidahan.com/2009/12/09/clarified-cqrs/"&gt;detailed
      description &lt;/a&gt;of the technique.&lt;/li&gt;

&lt;li&gt;There is a &lt;a href="http://cqrsinfo.com"&gt;CQRS info&lt;/a&gt;
      site that Greg set up. Its &lt;a href="http://cqrsinfo.com/documents/"&gt;documents section&lt;/a&gt; contains some
      interesting material. &lt;/li&gt;

&lt;li&gt;There is an &lt;a href="http://groups.google.com/group/dddcqrs"&gt;active mailing list&lt;/a&gt; to
      discuss the approach.&lt;/li&gt;

&lt;li&gt;Greg Young is working on a book on CQRS.&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/8rtjV06s3BA" height="1" width="1"/&gt;</summary><author gr:unknown-author="true"><name>(author unknown)</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/PlanetTw"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/PlanetTw</id><title type="html">www.thoughtworks.com aggregator</title><link rel="alternate" href="http://www.thoughtworks.com/blogs/current" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/PlanetTw/~3/2UM574Pho34/CQRS.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1310584639164"><id gr:original-id="">tag:google.com,2005:reader/item/705933bce60c62ce</id><title type="html">Martin Fowler: The LMAX Architecture</title><published>2011-07-12T13:43:00Z</published><updated>2011-07-12T13:43:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/O4pIgZGMNV0/lmax.html" type="text/html" /><summary xml:base="http://www.thoughtworks.com/blogs/current" type="html">&lt;p&gt;When I was at QCon London last year, there was much buzz around a talk about a new retail trading system. The thing that got people’s attention was its approach to achieving its high performance needs - reaching 6 million TPS. It does this by running all its business logic on a single JVM thread, getting high speed without all the complications of concurrent programming. This article describes the architecture they use to pull this off.&lt;/p&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/O4pIgZGMNV0" height="1" width="1"/&gt;</summary><author gr:unknown-author="true"><name>(author unknown)</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/PlanetTw"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/PlanetTw</id><title type="html">www.thoughtworks.com aggregator</title><link rel="alternate" href="http://www.thoughtworks.com/blogs/current" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/PlanetTw/~3/ii59keILbng/lmax.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1308046679602"><id gr:original-id="c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7828736">tag:google.com,2005:reader/item/9a8cbf9a3dd68ddb</id><category term="WCF" scheme="http://weblogs.asp.net/cibrax/archive/tags/WCF/default.aspx" /><category term=".NET" scheme="http://weblogs.asp.net/cibrax/archive/tags/.NET/default.aspx" /><title type="html">Interop Bindings for WCF released in codeplex</title><published>2011-06-14T01:06:40Z</published><updated>2011-06-14T01:06:40Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/tM3e50ld29Q/interop-bindings-for-wcf-released-in-codeplex.aspx" type="text/html" /><summary xml:base="http://weblogs.asp.net/cibrax/default.aspx" type="html">&lt;p&gt;I am happy to announce that one of the projects in which Microsoft and Tellago have been collaborating together during the last few months was released as part of &lt;a href="http://wcf.codeplex.com/wikipage?title=WCF%20Express%20Interop%20Bindings"&gt;wcf.codeplex.com&lt;/a&gt;. The primary aim of this “WCF Interop Bindings” project is to simplify the work needed for making WCF services interoperable with other service stacks like Oracle WebLogic, IBM Websphere, Metro or Apache Axis.  &lt;/p&gt;  &lt;p&gt;The main goal behind web services has always been to enable communication between heterogeneous systems. However, we all know that archiving such level of interoperability in the context of web services and WS-* is really complicated and requires good knowledge of the different message stacks to generate compatible messages at the wire level.&lt;/p&gt;  &lt;p&gt;For that reason, the WCF team came up with this interesting idea of providing a set of pre-defined bindings with a limited set of settings that you can use out of the box for supporting the most common interop scenarios with the mentioned stacks using protocols like WS-Security, WS-SecureConversation or WS-ReliableMessaging.&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;Bindings provided out of the box in the current bits&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;The current bits provides a set of custom binding implementations for Oracle WebLogic, IBM Websphere, Metro and Apache Axis. The name of those bindings basically matches the message stack you want to use. For example, the following configuration illustrates how a service can be configured to be compatible at wire level with Oracle WebLogic using Username over certificates as the security scenario.&lt;/p&gt;  &lt;div&gt;   &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;     &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;&lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;configuration&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;  &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;system.serviceModel&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;services&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;service&lt;/span&gt; &lt;span style="color:#ff0000"&gt;name&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;Microsoft.ServiceModel.Interop.Samples.HelloWorldService&amp;quot;&lt;/span&gt; &lt;span style="color:#ff0000"&gt;behaviorConfiguration&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;helloWorld&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;endpoint&lt;/span&gt; &lt;span style="color:#ff0000"&gt;address&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;Username_WebLogic&amp;quot;&lt;/span&gt; &lt;span style="color:#ff0000"&gt;binding&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;webLogicBinding&amp;quot;&lt;/span&gt; &lt;span style="color:#ff0000"&gt;bindingConfiguration&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;helloWorld_UsernameOverCertificate&amp;quot;&lt;/span&gt; &lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;&lt;span style="color:#ff0000"&gt;contract&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;Microsoft.ServiceModel.Interop.Samples.IHelloWorld&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;endpoint&lt;/span&gt; &lt;span style="color:#ff0000"&gt;address&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;Mex&amp;quot;&lt;/span&gt; &lt;span style="color:#ff0000"&gt;binding&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;mexHttpBinding&amp;quot;&lt;/span&gt; &lt;span style="color:#ff0000"&gt;contract&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;IMetadataExchange&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt; &lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;service&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;services&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;bindings&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;webLogicBinding&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;binding&lt;/span&gt; &lt;span style="color:#ff0000"&gt;name&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;helloWorld_UsernameOverCertificate&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;          &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;security&lt;/span&gt; &lt;span style="color:#ff0000"&gt;mode&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;UserNameOverCertificate&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;binding&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;webLogicBinding&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;bindings&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;behaviors&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceBehaviors&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;behavior&lt;/span&gt; &lt;span style="color:#ff0000"&gt;name&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;helloWorld&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;          &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceMetadata&lt;/span&gt; &lt;span style="color:#ff0000"&gt;httpGetEnabled&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;true&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;          &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceDebug&lt;/span&gt; &lt;span style="color:#ff0000"&gt;httpHelpPageEnabled&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;true&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;          &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceCredentials&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;            &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceCertificate&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;              &lt;span style="color:#ff0000"&gt;storeLocation&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;LocalMachine&amp;quot;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;              &lt;span style="color:#ff0000"&gt;storeName&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;TrustedPeople&amp;quot;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;              &lt;span style="color:#ff0000"&gt;x509FindType&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;FindBySubjectDistinguishedName&amp;quot;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;              &lt;span style="color:#ff0000"&gt;findValue&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;CN=HelloWorldService&amp;quot;&lt;/span&gt;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;          &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceCredentials&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;behavior&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;serviceBehaviors&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;behaviors&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;extensions&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;bindingExtensions&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;        &lt;span style="color:#0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color:#800000"&gt;add&lt;/span&gt; &lt;span style="color:#ff0000"&gt;name&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;webLogicBinding&amp;quot;&lt;/span&gt; &lt;span style="color:#ff0000"&gt;type&lt;/span&gt;&lt;span style="color:#0000ff"&gt;=&amp;quot;Microsoft.ServiceModel.Interop.WebLogic.Configuration.WebLogicBindingCollectionElement,&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt; Microsoft.ServiceModel.Interop, Version=1.0.0.0, Culture=neutral, PublicKeyToken=4fc38efee625237e&amp;quot;&lt;span style="color:#0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;      &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;bindingExtensions&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;    &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;extensions&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;  &lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;system.serviceModel&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;,courier,monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px"&gt;&lt;span style="color:#0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color:#800000"&gt;configuration&lt;/span&gt;&lt;span style="color:#0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Visual Studio 2010 Integration&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The binding implementations are not the only thing you get out of the box with the current bits. The WCF team also wanted to provide developers with a rich experience for configuring and creating the services with one of the pre-defined interop scenarios. Having that in mind, this project also integrates in Visual Studio 2010 by providing a set of project templates for creating WCF services for an specific scenario and a configuration wizard for generating the binding configuration.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/cibrax/ProjectTemplates_7BB28048.png"&gt;&lt;img style="background-image:none;border-right-width:0px;padding-left:0px;padding-right:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;padding-top:0px" title="ProjectTemplates" border="0" alt="ProjectTemplates" src="http://weblogs.asp.net/blogs/cibrax/ProjectTemplates_thumb_40127188.png" width="644" height="449"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;As you can see in the image above, two new project templates are automatically registered under the &amp;quot;WCF&amp;quot; category that you can use to create a new service configured with one of the provided interop bindings. You can use the &amp;quot;WCF Interoperable Service Library&amp;quot; template for creating a new WCF service as part of the service library, or &amp;quot;WCF Interoperable Service Application&amp;quot; for creating a new WCF service as part of a Web Application. The templates will automatically launch a configuration wizard for selecting the desired interop scenario as it is shown in the images bellow.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/cibrax/Wizard1_43D01658.png"&gt;&lt;img style="background-image:none;border-right-width:0px;padding-left:0px;padding-right:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;padding-top:0px" title="Wizard1" border="0" alt="Wizard1" src="http://weblogs.asp.net/blogs/cibrax/Wizard1_thumb_5AAEE7D4.png" width="644" height="434"&gt;&lt;/a&gt; 

  &lt;br&gt;&lt;a href="http://weblogs.asp.net/blogs/cibrax/Wizard2_6D173889.png"&gt;&lt;img style="background-image:none;border-right-width:0px;padding-left:0px;padding-right:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;padding-top:0px" title="Wizard2" border="0" alt="Wizard2" src="http://weblogs.asp.net/blogs/cibrax/Wizard2_thumb_1CF1DA4B.png" width="644" height="444"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the wizard you can pick one of the existing interop scenarios, and specific settings for those scenarios like Security or Reliable Messaging to give an example. At the end of wizard, the configuration file associated to the WCF project will be automatically updated with the chosen binding and settings.&lt;/p&gt;

&lt;p&gt;Enjoy!!&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7828736" width="1" height="1"&gt;&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/cibrax?a=td5mMKofpLU:5dN8R5ZzPmM:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/cibrax?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/cibrax?a=td5mMKofpLU:5dN8R5ZzPmM:F7zBnMyn0Lo"&gt;&lt;img src="http://feeds.feedburner.com/~ff/cibrax?i=td5mMKofpLU:5dN8R5ZzPmM:F7zBnMyn0Lo" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/cibrax?a=td5mMKofpLU:5dN8R5ZzPmM:qj6IDK7rITs"&gt;&lt;img src="http://feeds.feedburner.com/~ff/cibrax?d=qj6IDK7rITs" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/cibrax/~4/td5mMKofpLU" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/tM3e50ld29Q" height="1" width="1"/&gt;</summary><author><name>cibrax</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/cibrax"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/cibrax</id><title type="html">Pablo M. Cibraro (aka Cibrax)</title><link rel="alternate" href="http://weblogs.asp.net/cibrax/default.aspx" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/cibrax/~3/td5mMKofpLU/interop-bindings-for-wcf-released-in-codeplex.aspx</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1307710570802"><id gr:original-id="http://www.stucharlton.com/blog/archives/2011/06/the-trouble-with-apis.html">tag:google.com,2005:reader/item/364cf624f3cda2ee</id><category term="Tech" /><title type="html">The trouble with APIs</title><published>2011-06-09T13:45:20Z</published><updated>2011-06-09T13:45:20Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/Fv7OBhHNdoo/the-trouble-with-apis.html" type="text/html" /><summary xml:base="http://www.stucharlton.com/blog/" type="html">&lt;p&gt;I posted a couple of thoughts on Twitter and a few comments elsewhere recently as a results of a discussion &lt;a href="http://broadcast.oreilly.com/2011/06/the-good-the-bad-the-ugly-of-rest-apis.html"&gt;on George Reese's blog&lt;/a&gt; and &lt;a href="http://stage.vambenepe.com/archives/1777"&gt;William's followup&lt;/a&gt;.   I thought I'd repost these thoughts here with annotation as it seems to be evolving an interesting discussion.&lt;/p&gt;

&lt;p&gt;&lt;b&gt;1. REST APIs are a case of good intentions run amok. The point of REST was to *eliminate* specific APIs. Not cause their proliferation.  &lt;/b&gt;&lt;/p&gt;

&lt;p&gt;2. When someone says you shouldn't document a REST API, they're saying you shouldn't have an API. Not that you shouldn't document.&lt;br&gt;
&lt;/p&gt;

&lt;p&gt;I mean by this, Network APIs.   I also mean APIs that aren't re-implementable across sites.    The point is that the uniform interface isn't just HTTP - it's a small number of evolving media types, and the goal is to enable &lt;i&gt;sharing of information&lt;/i&gt; at a global scale.  Your pet JSON format may not be the way to do this.&lt;/p&gt;

&lt;p&gt;&lt;b&gt;3.   That said, RESTians saying you shouldn't have an API are somewhat vacuous because they offer no good alternative. Custom media types ain't.&lt;/b&gt;&lt;/p&gt;

&lt;p&gt;4.  Thus, IMO, until we have a workable generic media type or two for the 80% case of "REST APIs", we're just growing a frustrating mess.&lt;/p&gt;

&lt;p&gt; In other words, I completely recognize that crafting a media type is a bit heady, and even still a custom media type for generic use is quite hard.    With a REST API at least you get the benefits of HTTP GET (to some degree).    It does the job, if all you want is a trendy vaguely hopeful way of building something for the long term without getting too bogged down in philosophy.   I get it.&lt;/p&gt;

&lt;p&gt;What I would like to see is a generic media type (above &amp;amp; beyond a &amp;quot;format&amp;quot; like JSON) to cover the 80/20 cases.   This is seemingly contrary to where many RESTheads are at - they prefer often prefer opinionated media types, media types that &amp;quot;say something&amp;quot;.    &lt;/p&gt;

&lt;p&gt;I'm actually asking for that too, I think -- say something about the &lt;b&gt;programming model&lt;/b&gt; that breaks people&amp;#39;s habits away from RPCs.   Find a programming model that doesn&amp;#39;t orient all &amp;quot;write-side&amp;quot; communication in terms of a flat list of actions, and into something that can be extended &amp;amp; shared across the web via hyperlinks and URIs.  Hierarchical statecharts is my stab at this.   There may be others.&lt;/p&gt;

&lt;p&gt;&lt;b&gt;5.   From William's blog (with a couple tweaks)....&lt;/b&gt;&lt;/p&gt;

&lt;p&gt;I've sort of half given up on REST advocacy because it's pretty impossible these days. People want to ship APIs that will be valid for the next next 6 months, not build systems that will evolve over a decade or more.&lt;/p&gt;

&lt;p&gt;Jan Algermissen's comment about how when you've documented an API, you're not really doing REST, is actually spot on, fundamentally, but is met with ridicule. I can completely understand how vacuous the comment sounds if you just want to ship an API nownownow, are being short-term practically minded, or are just playing buzzword bingo with architectural styles. But if we actually want to leverage the benefits of the style, we'd work on the core issue of having a generic media type or two for these sorts of use cases.&lt;/p&gt;

&lt;p&gt;If one is thinking of "how to methods map to my URI structures", we've basically lost the plot as to why we have HTTP, URIs and media types in the first place. The goal is to *eliminate* the API as we normally think of it.   (It's not about a library of calls over a network).&lt;/p&gt;

&lt;p&gt;Five points. The consequences of REST changes some rules:&lt;/p&gt;

&lt;p&gt;1. The assumption can't be that the end user of your information service is going to be a programmer. Building an API bakes that assumption in how you expose your information or controls to manipulate it. The assumption rather should be that "this can be any agent of any sort". If your goal really is "I want a programmer to learn my API and program against this", then there's really no reason to use REST other than that it's trendy (and HTTP GET).&lt;/p&gt;

&lt;p&gt;2. The assumption can't be that you will be the only site implementing your interface. The whole point of the Web is sharing information - publishing an API bakes in the assumption that YOU, the publisher, are in control. It is the consumer, on the other hand - the agent itself, that's in control of how/what the information is consumed or manipulated.&lt;/p&gt;

&lt;p&gt;3. The semantics of the interface that need to be documented are the media type that you use to describe your data and links. The structure of your URIs really shouldn't be a part of said semantics.&lt;/p&gt;

&lt;p&gt;4. But doing this in a custom media type implies #2, that you're the only person implementing your interface. Of course, every media type has to start somewhere, but it really doesn't help matters unless you understand that others may be *implementing* your interface, not just *talking* to it. Facebook's Open Graph, for example, is an example of a custom overlay media type that takes great pains to be generic in either direction.&lt;/p&gt;

&lt;p&gt;5. All of the above is really heady stuff that is above most developer's pay grades, so it won't ever happen. The best we can hope for is some person/organization to step up with a generic media type or two + guidelines that help describe and document a Web of Data interface for accessibility by programmers. Call it a description language, if you'd like. Some RESTians don't like the idea of a description language. I think it's an essential 80/20 piece if developers are going to actually *use* the architecture the way it was meant to be used.&lt;/p&gt;

&lt;p&gt;Currently (as I mentioned in my WS-REST keynote) I think some kind of hierarchical lifecycle/state machine might be the right abstraction for such an interface. I'd like to demonstrate this if I ever got past my day job sucking up most of my time.   (But I may have an opportunity to work on this there soon.)&lt;/p&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/Fv7OBhHNdoo" height="1" width="1"/&gt;</summary><author><name>stu</name></author><source gr:stream-id="feed/http://www.stucharlton.com/blog/index.rdf"><id>tag:google.com,2005:reader/feed/http://www.stucharlton.com/blog/index.rdf</id><title type="html">Stu says stuff</title><link rel="alternate" href="http://www.stucharlton.com/blog/" type="text/html" /></source><feedburner:origLink>http://www.stucharlton.com/blog/archives/2011/06/the-trouble-with-apis.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1307475220671"><id gr:original-id="tag:blogger.com,1999:blog-19660677.post-4843754730060659254">tag:google.com,2005:reader/item/79145010a2529da9</id><title type="html">SATURN Conference 2011 Presentations are Available</title><published>2011-06-07T15:19:00Z</published><updated>2011-06-07T15:19:54Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/OJTqV1Mow2w/saturn-conference-2011-presentations.html" type="text/html" /><link rel="replies" href="http://realworldsa.blogspot.com/feeds/4843754730060659254/comments/default" title="Post Comments" type="application/atom+xml" /><link rel="replies" href="https://www.blogger.com/comment.g?blogID=19660677&amp;postID=4843754730060659254&amp;isPopup=true" title="0 Comments" type="text/html" /><content xml:base="http://realworldsa.blogspot.com/" type="html">The SATURN Conference 2011 presentations are available for download.&lt;br&gt;&lt;br&gt;Links to the downloads and descriptions of the presentations are available &lt;a href="http://www.sei.cmu.edu/saturn/2011/"&gt;here&lt;/a&gt;.&lt;div&gt;&lt;img width="1" height="1" src="https://blogger.googleusercontent.com/tracker/19660677-4843754730060659254?l=realworldsa.blogspot.com" alt=""&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/OJTqV1Mow2w" height="1" width="1"/&gt;</content><author><name>tadanderson</name></author><source gr:stream-id="feed/http://realworldsa.blogspot.com/atom.xml"><id>tag:google.com,2005:reader/feed/http://realworldsa.blogspot.com/atom.xml</id><title type="html">Real World Software Architecture</title><link rel="alternate" href="http://realworldsa.blogspot.com/" type="text/html" /></source><feedburner:origLink>http://realworldsa.blogspot.com/2011/06/saturn-conference-2011-presentations.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1306744495574"><id gr:original-id="http://www.julianbrowne.com/article/viewer/secret-sauce">tag:google.com,2005:reader/item/812ba34fa261d70e</id><category term="general" /><title type="html">The Secret Sauce</title><published>2011-05-29T18:50:00Z</published><updated>2011-05-29T18:50:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/cbXcSFkWmVg/secret-sauce" type="text/html" /><summary xml:base="http://www.julianbrowne.com/" type="html">&lt;p&gt;Last time, I was talking about what I consider to be the general &lt;a href="http://www.julianbrowne.com/article/viewer/crisis-over"&gt;lack of a crisis&lt;/a&gt; in software development. And it got me thinking - if there is no crisis in software development, no inherent flaws in our tools or our methods, then there must somehow be a way to convey the appropriate use of these tools and methods in order that everybody could get it right every time.&lt;/p&gt;

&lt;div&gt;&lt;/div&gt;

&lt;p&gt;Ah ha, I thought. A book. A book entitled "The Secret Sauce". A book that will make ... &lt;a href="http://www.julianbrowne.com/article/viewer/secret-sauce" title="The Secret Sauce"&gt;[more -&amp;gt;]&lt;/a&gt;&lt;/p&gt;&lt;img src="http://feeds.feedburner.com/~r/julianbrownerecent/~4/p4HoQ4zZHh0" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/cbXcSFkWmVg" height="1" width="1"/&gt;</summary><author gr:unknown-author="true"><name>(author unknown)</name></author><source gr:stream-id="feed/http://feeds2.feedburner.com/julianbrownerecent"><id>tag:google.com,2005:reader/feed/http://feeds2.feedburner.com/julianbrownerecent</id><title type="html">Julian Browne</title><link rel="alternate" href="http://www.julianbrowne.com/" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/julianbrownerecent/~3/p4HoQ4zZHh0/secret-sauce</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1306116394307"><id gr:original-id="426227:4867632:11497452">tag:google.com,2005:reader/item/a0fe7dc2077f4aee</id><category term="Strategy" /><title type="html">Zynga's Z Cloud - Scale Fast or Fail Fast by Merging Private and Public Clouds</title><published>2011-05-19T16:06:44Z</published><updated>2011-05-19T16:06:44Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/41hlQGw9GQc/zyngas-z-cloud-scale-fast-or-fail-fast-by-merging-private-an.html" type="text/html" /><summary xml:base="http://highscalability.com/blog/" type="html">&lt;p&gt;&lt;img src="http://farm5.static.flickr.com/4049/4335031559_fa690c1f81_m.jpg" alt="" width="175" height="175" align="right"&gt;&lt;/p&gt;
&lt;p&gt;Release early and often. A/B testing. Creating a landing page and buying ads on AdSense. All are ways of providing quick feedback in order to validate an idea. If you are like Zynga, with 250 million active users a month, how do you cost effectively prove out a game that could flop or get 90 million users (like CityVille) in an instant?&lt;/p&gt;
&lt;p&gt;Zynga handles this problem inlle an innovative way, by inverting the typical cloud burst scenario that has excess traffic flowing from a datacenter to a cloud, to having a game start in the cloud and then moving to the datacenter once the game has proved popular enough to keep.&lt;/p&gt;
&lt;p&gt;This process is nicely described by Charles Babcock in &lt;a href="http://www.informationweek.com/news/global-cio/interviews/229402805"&gt;Lessons From FarmVille: How Zynga Uses The Cloud&lt;/a&gt;, in an interview with Allan Leinwand, CTO of infrastructure engineering at Zynga.&lt;/p&gt;
&lt;p&gt;When paired down to its essence, Zynga's strategy goes something like this:&lt;/p&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/41hlQGw9GQc" height="1" width="1"/&gt;</summary><author><name>Todd Hoff</name></author><source gr:stream-id="feed/http://highscalability.com/rss.xml"><id>tag:google.com,2005:reader/feed/http://highscalability.com/rss.xml</id><title type="html">High Scalability</title><link rel="alternate" href="http://highscalability.com/blog/" type="text/html" /></source><feedburner:origLink>http://highscalability.com/blog/2011/5/19/zyngas-z-cloud-scale-fast-or-fail-fast-by-merging-private-an.html</feedburner:origLink></entry><entry><title type="text">Links for 2009-12-16 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/BCAmASHabHU/arnonrgo" /><updated>2009-12-17T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-12-16</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://natishalom.typepad.com/nati_shaloms_blog/2009/12/the-common-principles-behind-the-nosql-alternatives.html?utm_source=feedburner&amp;utm_medium=feed&amp;utm_campaign=Feed%3A+NatiShalom+%28Nati+Shalom%27s+Blog%29"&gt;The Common Principles Behind the NOSQL Alternatives&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/BCAmASHabHU" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-12-16</feedburner:origLink></entry><entry><title type="text">Links for 2009-12-13 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/4xkbne8iinA/arnonrgo" /><updated>2009-12-14T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-12-13</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://feedproxy.google.com/~r/SamGentile/~3/1g7V561jwXQ/"&gt;AppFabric a.ka. &amp;quot;Dublin&amp;quot; Links&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.bizcoder.com/index.php/2009/12/09/http-content-instead-of-streams/"&gt;HttpContent instead of streams&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/4xkbne8iinA" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-12-13</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1304785471672"><id gr:original-id="http://convective.wordpress.com/2009/12/08/diagnostics-in-windows-azure">tag:google.com,2005:reader/item/8a51a13b768b8de8</id><category term="Diagnostics" /><category term="Windows Azure" /><category term="Windows Azure Diagnostics" /><title type="html">Diagnostics in Windows Azure</title><published>2009-12-08T13:11:38Z</published><updated>2009-12-08T13:11:38Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/BofxS6ZArtY/diagnostics-in-windows-azure" type="text/html" /><content xml:base="http://convective.wordpress.com/" type="html">&lt;div&gt;
&lt;p&gt;Microsoft introduced a set of classes supporting diagnostics monitoring in the November 2009 Azure Services SDK. The classes are composed into two namespaces:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.aspx"&gt;Microsoft.WindowsAzure.Diagnostics&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.management.aspx"&gt;Microsoft.WindowsAzure.Diagnostics.Management&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The &lt;em&gt;Diagnostics&lt;/em&gt; namespace comprises classes for the configuration and collection of diagnostic information. The &lt;em&gt;Diagnostics.Management&lt;/em&gt; namespace comprises classes supporting local and remote management of the collection of diagnostics information and its transfer to persistent storage in Azure Tables and Blobs. This post is focused on the &lt;em&gt;Diagnostics&lt;/em&gt; namespace and a subsequent post will consider the &lt;em&gt;Diagnostics.Management&lt;/em&gt; namespace.&lt;/p&gt;
&lt;p&gt;MSDN has a good section on &lt;a href="http://msdn.microsoft.com/en-us/library/ee758705.aspx"&gt;Implementing Windows Azure Diagnostics for Hosted Services&lt;/a&gt; that includes the following sections:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/ee843890.aspx"&gt;Initializing and Configuring Diagnostics Data Sources&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/ee830425.aspx"&gt;Transferring Diagnostic Data to Windows Azure Storage&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/ee830424.aspx"&gt;Managing Windows Azure Diagnostics Remotely&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Matthew Kerner gave an excellent presentation on &lt;a href="http://microsoftpdc.com/Sessions/SVC15"&gt;Windows Azure Monitoring, Logging, and Management APIs&lt;/a&gt; at PDC 2009 – he has posted his samples &lt;a href="http://code.msdn.microsoft.com/WADiagnostics"&gt;here&lt;/a&gt;. The November 2009 Update of the &lt;a href="http://www.microsoft.com/downloads/details.aspx?FamilyID=413E88F8-5966-4A83-B309-53B7B77EDF78&amp;amp;displaylang=en"&gt;Windows Azure Platform Training Kit&lt;/a&gt; has a good hands-on-lab &lt;em&gt;Windows Azure: Deploying and Monitoring Applications in Windows Azure&lt;/em&gt; with Example 3 being &lt;em&gt;Monitoring Applications in Windows Azure.&lt;/em&gt; Sumit Mehrotra, from the Azure team, has a couple of posts – &lt;a href="http://blogs.msdn.com/sumitm/archive/2009/11/18/introducing-windows-azure-diagnostics.aspx"&gt;here&lt;/a&gt; and &lt;a href="http://blogs.msdn.com/sumitm/archive/2009/11/25/windows-azure-walkthrough-simple-logging.aspx"&gt;here&lt;/a&gt; – looking at Azure Diagnostics.&lt;/p&gt;
&lt;p&gt;UPDATE 12/1/2010: This &lt;a href="http://convective.wordpress.com/"&gt;post &lt;/a&gt;describes some configuration changes to Azure Diagnostics implemented in the &lt;a href="http://www.microsoft.com/downloads/en/details.aspx?FamilyID=7a1089b6-4050-4307-86c4-9dadaa5ed018"&gt;Azure SDK v1.3 &lt;/a&gt;release.&lt;/p&gt;
&lt;p&gt;UPDATE 5/6/2011. I uploaded a Windows Azure Diagnostics &lt;a href="http://code.msdn.microsoft.com/Windows-Azure-Diagnostics-e321eed9"&gt;sample&lt;/a&gt; to the MSDN &lt;a href="http://code.msdn.microsoft.com/"&gt;Code Samples Gallery&lt;/a&gt; that demonstrates the features described in this post.&lt;/p&gt;
&lt;h3&gt;Diagnostics Information&lt;/h3&gt;
&lt;p&gt;Azure Diagnostics captures the following information:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Directories – file-based data buffers (including IIS Logs, failed request logs and crash dumps)&lt;/li&gt;
&lt;li&gt;Diagnostic infrastructure logs – logs the diagnostics infrastructure itself&lt;/li&gt;
&lt;li&gt;Logs – Windows Azure logs&lt;/li&gt;
&lt;li&gt;Performance counters – Windows Performance Counters&lt;/li&gt;
&lt;li&gt;Windows Event Logs&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Note that developers can create and configure their own user-defined file-based data buffers.&lt;/p&gt;
&lt;p&gt;The diagnostic information is captured in data buffers in the local storage of each instance. Diagnostic infrastructure logs, IIS Logs, (Windows Azure) Logs are stored by default – the others must be initiated programmatically. Once captured, diagnostic information can be transferred either by schedule or on-demand to persistent Azure Storage.  Directories (file-based data buffers) are stored in Blobs and all other diagnostics information is is stored in Tables.&lt;/p&gt;
&lt;p&gt;The data buffers containing the diagnostics information are configured through several data-buffer configuration classes. Diagnostics monitoring is configured through the &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.aspx"&gt;DiagnosticMonitor&lt;/a&gt; and &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.aspx"&gt;DiagnosticMonitorConfiguration&lt;/a&gt; classes.&lt;/p&gt;
&lt;h3&gt;Data Buffer Configuration&lt;/h3&gt;
&lt;p&gt;The data buffers are configured through a simple set of classes which persist the configuration in an Azure blob named &lt;em&gt;wad-control-container&lt;/em&gt;. The configuration for each instance of each role is persisted in an individual blob in the container named with a combination of the deployment Id, role name and instance Id of the current role instance. For example:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;deployment(301)/WebRole1/deployment(301).NovemberStorageClient.WebRole1.0&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;The diagnostics configuration classes can be invoked either from the running instance of the Azure Service or through, for example,  a remote desktop application interacting with the configuration through the diagnostics management and diagnostics configuration classes. Every Azure instance hosts a &lt;em&gt;MonAgentHost.exe&lt;/em&gt; executable to manage the Azure diagnostics configuration and management process.&lt;/p&gt;
&lt;h4&gt;DiagnosticDataBufferConfiguration&lt;/h4&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticdatabufferconfiguration.aspx"&gt;DiagnosticDataBufferConfiguration&lt;/a&gt; is an abstract base class for the various diagnostics configuration classes representing data buffers. It is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public abstract class DiagnosticDataBufferConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    protected DiagnosticDataBufferConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public Int32 BufferQuotaInMB { get; set; }&lt;br&gt;
    public TimeSpan ScheduledTransferPeriod { get; set; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;The &lt;em&gt;DiagnosticsDataBufferConfiguration&lt;/em&gt; properties are exposed through its derived classes each of which represents a data buffer containing a specific type of diagnostics information. These derived classes are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.basiclogsbufferconfiguration.aspx"&gt;BasicLogsBufferConfiguration&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoriesbufferconfiguration.aspx"&gt;DirectoriesBufferConfiguration&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.performancecountersbufferconfiguration.aspx"&gt;PerformanceCountersBufferConfiguration&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.windowseventlogsbufferconfiguration.aspx"&gt;WindowsEventLogsBufferConfiguration&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticdatabufferconfiguration.bufferquotainmb.aspx"&gt;BufferQuotaInMB&lt;/a&gt; specifies the maximum quota for an data buffer. The maximum overall quota is specified by &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.overallquotainmb.aspx"&gt;DiagnosticMonitorConfiguration.OverallQuotaInMB&lt;/a&gt;. By default the overall quota is 4GB and there is no maximum quota specified for the individual buffers. (When an individual quota is reached I believe the policy is to delete the oldest records.) &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticdatabufferconfiguration.scheduledtransferperiod.aspx"&gt;ScheduledTransferPeriod&lt;/a&gt; is the &lt;a href="http://msdn.microsoft.com/en-us/library/system.timespan.aspx"&gt;TimeSpan&lt;/a&gt; in minutes between scheduled transfers of the data buffer to Azure Storage.&lt;/p&gt;
&lt;h4&gt;BasicLogsBufferConfiguration&lt;/h4&gt;
&lt;p&gt;The &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.basiclogsbufferconfiguration.aspx"&gt;BasicLogsBufferConfiguration&lt;/a&gt; class is derived from &lt;em&gt;DiagnosticDataBufferConfiguration&lt;/em&gt; and supports configuration of (basic windows) logs. It is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class BasicLogsBufferConfiguration : DiagnosticDataBufferConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public BasicLogsBufferConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public LogLevel ScheduledTransferLogLevelFilter { get; set; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;The &lt;em&gt;BasicLogsBufferConfiguration&lt;/em&gt; adds a &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.basiclogsbufferconfiguration.scheduledtransferloglevelfilter.aspx"&gt;ScheduledTransferLogLevelFilter&lt;/a&gt; to the &lt;em&gt;BufferQuotaInMB&lt;/em&gt; and &lt;em&gt;ScheduledTransferPeriod&lt;/em&gt; of the base &lt;em&gt;DiagnosticDataBufferConfiguration&lt;/em&gt; class. &lt;em&gt;ScheduledTransferLogLevelFilter&lt;/em&gt; specifies a filter level to limit the log information persisted to Azure Tables. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.loglevel.aspx"&gt;LogLevel&lt;/a&gt; is the following enumeration:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public enum LogLevel {&lt;br&gt;
    Undefined,&lt;br&gt;
    Critical,&lt;br&gt;
    Error,&lt;br&gt;
    Warning,&lt;br&gt;
    Information,&lt;br&gt;
    Verbose&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;Note that when a filter level, here or another data buffer class, is set to a value from this enumeration it implicitly includes any levels earlier in the enumeration. &lt;em&gt;Undefined&lt;/em&gt; has the same effect as &lt;em&gt;Verbose&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;The Logs are persisted in an Azure Table named:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;WadLogsTable&lt;/li&gt;
&lt;/ul&gt;
&lt;h4&gt;DirectoriesBufferConfiguration&lt;/h4&gt;
&lt;p&gt;The &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoriesbufferconfiguration.aspx"&gt;DirectoriesBufferConfiguration&lt;/a&gt; class is derived from &lt;em&gt;DiagnosticsDataBufferConfiguration&lt;/em&gt; and supports configuration of file-based data buffers such as IIS Logs, failed request logs, crash dumps, and user-defined diagnostics. &lt;em&gt;DirectoriesBufferConfiguration&lt;/em&gt; is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class DirectoriesBufferConfiguration : DiagnosticDataBufferConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public DirectoriesBufferConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public IList&amp;lt;DirectoryConfiguration&amp;gt; DataSources { get; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;The &lt;em&gt;DirectoriesBufferConfiguration&lt;/em&gt; adds a list of &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoriesbufferconfiguration.datasources.aspx"&gt;DataSources&lt;/a&gt; to the &lt;em&gt;BufferQuotaInMB&lt;/em&gt; and &lt;em&gt;ScheduledTransferPeriod&lt;/em&gt; of the base &lt;em&gt;DiagnosticDataBufferConfiguration&lt;/em&gt; class. The &lt;em&gt;DataSources&lt;/em&gt; are instances of the &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoryconfiguration.aspx"&gt;DirectoryConfiguration&lt;/a&gt; class declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class DirectoryConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public DirectoryConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public String Container { get; set; }&lt;br&gt;
    public Int32 DirectoryQuotaInMB { get; set; }&lt;br&gt;
    public String Path { get; set; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;Each directory has its own quota, &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoryconfiguration.directoryquotainmb.aspx"&gt;DirectoryQuotaInMB&lt;/a&gt;, which is 1GB by default. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoryconfiguration.path.aspx"&gt;Path&lt;/a&gt; specifies the absolute path of the directory containing the file-based data buffer such as the Crash Dumps (and eventually the IIS Logs). that contains the log &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.directoryconfiguration.container.aspx"&gt;Container&lt;/a&gt; names the Azure Blob container into which the diagnostic log will be transferred for persistence. The Azure provided file-based data buffers are transferred into the following containers by default:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;wad-iis-failedreqlogfiles&lt;/li&gt;
&lt;li&gt;wad-iis-logfiles&lt;/li&gt;
&lt;li&gt;wad-crash-dumps&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Note that the IIS Failed Request Logs require that IIS be configured to capture the information. The feature is not turned on by default for performance reasons. The additional configuration comprises an additional section in the web.config file and is documented &lt;a href="http://msdn.microsoft.com/en-us/library/ee843890.aspx"&gt;here&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Note that although this section implies that IIS Logs are configured like other Directories this does not appear to be true. Currently, the scheduled transfer of IIS Logs is configured through &lt;em&gt;BasicLogsBufferConfiguration&lt;/em&gt; rather than &lt;em&gt;DirectoriesBufferConfiguration&lt;/em&gt;. Although not confirming this, Matthew Kerner’s presentation states:&lt;em&gt; Coming Soon: IIS Logs generated in role’s local data directory&lt;/em&gt;. I suspect that once this change happens IIS Logs will be configured through &lt;em&gt;DirectoriesBufferConfiguration&lt;/em&gt; rather than &lt;em&gt;BasicLogsBufferConfiguration. &lt;/em&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;UPDATE 3/25/2010: &lt;/em&gt;IIS Logs are now configured through &lt;em&gt;DirectoriesBufferConfiguration&lt;/em&gt;.&lt;/p&gt;
&lt;h4&gt;PerformanceCountersBufferConfiguration&lt;/h4&gt;
&lt;p&gt;The &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.performancecountersbufferconfiguration.aspx"&gt;PerformanceCountersBufferConfiguration&lt;/a&gt; class is derived from &lt;em&gt;DiagnosticsDataBufferConfiguration&lt;/em&gt; and supports configuration of performance counters data buffers. &lt;em&gt;PerformanceCountersBufferConfiguration&lt;/em&gt; is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class PerformanceCountersBufferConfiguration : DiagnosticDataBufferConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public PerformanceCountersBufferConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public IList&amp;lt;PerformanceCounterConfiguration&amp;gt; DataSources { get; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;The &lt;em&gt;PerformanceCountersBufferConfiguration&lt;/em&gt; adds a list of &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.performancecountersbufferconfiguration.datasources.aspx"&gt;DataSources&lt;/a&gt; to the &lt;em&gt;BufferQuotaInMB&lt;/em&gt; and &lt;em&gt;ScheduledTransferPeriod&lt;/em&gt; of the base &lt;em&gt;DiagnosticDataBufferConfiguration&lt;/em&gt; class. The &lt;em&gt;DataSources&lt;/em&gt; are instances of the &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.performancecounterconfiguration.aspx"&gt;PerformanceCounterConfiguration&lt;/a&gt; class declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class PerformanceCounterConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public PerformanceCounterConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public String CounterSpecifier { get; set; }&lt;br&gt;
    public TimeSpan SampleRate { get; set; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.performancecounterconfiguration.counterspecifier.aspx"&gt;CounterSpecifier&lt;/a&gt; specifies a Windows &lt;a href="http://msdn.microsoft.com/en-us/library/aa373083(VS.85).aspx"&gt;Performance Counter&lt;/a&gt; to be captured. This specification is in special &lt;a href="http://msdn.microsoft.com/en-us/library/aa373193(VS.85).aspx"&gt;syntax&lt;/a&gt; defined for Windows Performance Counters. An example of this syntax is:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;@”Processor(*)% Processor Time”&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;This captures the % of processor time for all processors. Note that the names of performance counters on a development machine can be found by typing the following at a command prompt:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;typeperf.exe /q&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.performancecounterconfiguration.samplerate.aspx"&gt;SampleRate&lt;/a&gt; is a TimeSpan specifying when the performance counter is measured. The &lt;em&gt;SampleRate&lt;/em&gt; is rounded to the nearest second.&lt;/p&gt;
&lt;p&gt;The Windows Performance Counters are persisted in an Azure Table named:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;WadPerformanceCountersTable&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Note that each measurement of a performance counter is stored as one entity in the table.&lt;/p&gt;
&lt;h4&gt;WindowsEventLogsBufferConfiguration&lt;/h4&gt;
&lt;p&gt;The &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.windowseventlogsbufferconfiguration.aspx"&gt;WindowsEventLogsBufferConfiguration&lt;/a&gt; class is derived from &lt;em&gt;DiagnosticsDataBufferConfiguration&lt;/em&gt; and supports configuration of &lt;a href="http://msdn.microsoft.com/en-us/library/aa385780(VS.85).aspx"&gt;Windows Event Log&lt;/a&gt; data buffers. &lt;em&gt;WindowsEventLogsBufferConfiguration&lt;/em&gt; is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class WindowsEventLogsBufferConfiguration : DiagnosticDataBufferConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public WindowsEventLogsBufferConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public IList&amp;lt;String&amp;gt; DataSources { get; }&lt;br&gt;
    public LogLevel ScheduledTransferLogLevelFilter { get; set; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;The &lt;em&gt;WindowsEventLogsBufferConfiguration&lt;/em&gt; adds a list of &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.windowseventlogsbufferconfiguration.datasources.aspx"&gt;DataSources&lt;/a&gt; and a &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.windowseventlogsbufferconfiguration.scheduledtransferloglevelfilter.aspx"&gt;ScheduledTransferLogLevelFilter&lt;/a&gt; to the &lt;em&gt;BufferQuotaInMB&lt;/em&gt; and &lt;em&gt;ScheduledTransferPeriod&lt;/em&gt; of the base &lt;em&gt;DiagnosticDataBufferConfiguration&lt;/em&gt; class. &lt;em&gt;ScheduledTransferLogLevelFilter&lt;/em&gt; specifies a filter level taken to limit the log information persisted to Azure Tables. The filter level comes from the &lt;em&gt;LogLevel&lt;/em&gt; enumeration. The &lt;em&gt;DataSources&lt;/em&gt; are Strings in a special syntax defined for specifying how to &lt;a href="http://msdn.microsoft.com/en-us/library/dd996910(VS.85).aspx"&gt;consume events&lt;/a&gt; from Windows Event Logs. This syntax allows all events in an Event Log to be retrieved or only a filtered list of events.&lt;/p&gt;
&lt;p&gt;The Windows Event Logs are persisted in an Azure Table named:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;WadWindowsEventLogsTable&lt;/li&gt;
&lt;/ul&gt;
&lt;h4&gt;Crash Dumps&lt;/h4&gt;
&lt;p&gt;There is one type of diagnostics data that is not configured through the normal data buffer configuration technique described here – crash dumps. These are initiated through the &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.crashdumps.aspx"&gt;CrashDumps&lt;/a&gt; class declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public static class CrashDumps {&lt;br&gt;
    // Methods&lt;br&gt;
    public static void EnableCollection(Boolean enableFullDumps);&lt;br&gt;
    public static void EnableCollectionToDirectory(String directory, Boolean enableFullDumps);&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.crashdumps.enablecollection.aspx"&gt;EnableCollection()&lt;/a&gt; enables either full or mini crash dumps. This data is placed in the &lt;em&gt;CrashDumps&lt;/em&gt; directory in the same location as the other file-based Directories. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.crashdumps.enablecollectiontodirectory.aspx"&gt;EnableCollectionToDirectory()&lt;/a&gt; allows the specification of an alternative directory in local storage.&lt;/p&gt;
&lt;p&gt;Note that ASP.Net handles almost all exceptions so that it is almost impossible to create a crash dump in a web role.&lt;/p&gt;
&lt;h3&gt;Diagnostics Monitoring&lt;/h3&gt;
&lt;p&gt;Diagnostics monitoring is supported by two classes: &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.aspx"&gt;DiagnosticMonitor&lt;/a&gt; which controls the diagnostics monitoring process; and &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.aspx"&gt;DiagnosticMonitorConfiguration&lt;/a&gt; which associates the data buffer configuration with the diagnostics monitoring process.&lt;/p&gt;
&lt;h4&gt;DiagnosticMonitorConfiguration&lt;/h4&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.aspx"&gt;DiagnosticMonitorConfiguration&lt;/a&gt; associates the data buffer configuration with the diagnostics monitoring process. &lt;em&gt;DiagnosticMonitorConfiguration&lt;/em&gt; is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class DiagnosticMonitorConfiguration {&lt;br&gt;
    // Constructors&lt;br&gt;
    public DiagnosticMonitorConfiguration();&lt;/p&gt;
&lt;p&gt;// Properties&lt;br&gt;
    public TimeSpan ConfigurationChangePollInterval { get; set; }&lt;br&gt;
    public BasicLogsBufferConfiguration DiagnosticInfrastructureLogs { get; set; }&lt;br&gt;
    public DirectoriesBufferConfiguration Directories { get; set; }&lt;br&gt;
    public BasicLogsBufferConfiguration Logs { get; set; }&lt;br&gt;
    public Int32 OverallQuotaInMB { get; set; }&lt;br&gt;
    public PerformanceCountersBufferConfiguration PerformanceCounters { get; set; }&lt;br&gt;
    public WindowsEventLogsBufferConfiguration WindowsEventLog { get; set; }&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.diagnosticinfrastructurelogs.aspx"&gt;DiagnosticInfrastructureLogs&lt;/a&gt;, &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.directories.aspx"&gt;Directories&lt;/a&gt;, &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.logs.aspx"&gt;Logs&lt;/a&gt;, &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.performancecounters.aspx"&gt;PerformanceCounters&lt;/a&gt; and &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.windowseventlog.aspx"&gt;WindowsEventLog&lt;/a&gt; provide access to an instance of each of the five Azure Diagnostics data buffers. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.configurationchangepollinterval.aspx"&gt;ConfigurationChangePollInterval&lt;/a&gt; specifies the TimeSpan dictating when the diagnostics monitor polls for configuration changes. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitorconfiguration.overallquotainmb.aspx"&gt;OverallQuotaInMB&lt;/a&gt; specifies the total amount of local storage allocated to all Azure Diagnostics data buffers.&lt;/p&gt;
&lt;h4&gt;DiagnosticMonitor&lt;/h4&gt;
&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.aspx"&gt;DiagnosticMonitor&lt;/a&gt; controls the Azure Diagnostics process by providing methods to start and stop diagnostics monitoring and to transfer the diagnostics logs to persistent Azure Storage. DiagnosticMonitor is declared:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;public class DiagnosticMonitor {&lt;br&gt;
    // Properties&lt;br&gt;
    public static Boolean AllowInsecureRemoteConnections { get; set; }&lt;br&gt;
    public String LocalDataDirectory { get; }&lt;/p&gt;
&lt;p&gt;// Methods&lt;br&gt;
    public static DiagnosticMonitorConfiguration GetDefaultInitialConfiguration();&lt;br&gt;
    public void Shutdown();&lt;br&gt;
    public static DiagnosticMonitor Start(String diagnosticsStorageAccountConfigurationSettingName,&lt;br&gt;
       DiagnosticMonitorConfiguration initialConfiguration);&lt;br&gt;
    public static DiagnosticMonitor Start(CloudStorageAccount storageAccount,&lt;br&gt;
       DiagnosticMonitorConfiguration initialConfiguration);&lt;br&gt;
    public static DiagnosticMonitor Start(String diagnosticsStorageAccountConfigurationSettingName);&lt;br&gt;
    public void UpdateStorageAccount(CloudStorageAccount storageAccount);&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;A &lt;em&gt;DiagnosticMonitor&lt;/em&gt; object is created using one of the static &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.start.aspx"&gt;Start()&lt;/a&gt; methods parameterized by various combinations of &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.cloudstorageaccount.aspx"&gt;CloudStorageAccount&lt;/a&gt;, &lt;em&gt;DiagnosticMonitorConfiguration&lt;/em&gt; and storage account configuration setting name. The &lt;em&gt;Start()&lt;/em&gt; methods actually starts the Monitoring Agent Host, &lt;em&gt;MonAgentHost.exe&lt;/em&gt;, which provides for out-of-service diagnostics monitoring and management. Either a &lt;em&gt;diagnosticsStorageAccountConfigurationSettingName&lt;/em&gt; String or a &lt;em&gt;CloudStorageAccount&lt;/em&gt; must be supplied to provide the authentication required to access Azure Storage both to save the diagnostics configuration information and to persist the Azure Diagnostics data buffers. The &lt;em&gt;Start()&lt;/em&gt; methods can be invoked either with a supplied initial &lt;em&gt;DiagnosticMonitorConfiguration&lt;/em&gt; or using a default initial &lt;em&gt;DiagnosticMonitorConfiguration&lt;/em&gt;. A common pattern is to retrieve a copy of the default initial configuration using the static &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.getdefaultinitialconfiguration.aspx"&gt;GetDefaultInitialConfiguration()&lt;/a&gt; method, modify this configuration, and then use the modified configuration when &lt;em&gt;Start()&lt;/em&gt; is invoked.&lt;/p&gt;
&lt;p&gt;The basic example is:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;DiagnosticMonitor diagnosticMonitor = DiagnosticMonitor.Start(“DiagnosticsConnectionString”);&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;This starts the Azure Diagnostics monitoring agent host and uses the Azure Storage configuration information identified by the name, &lt;em&gt;DiagnosticsConnectionString,&lt;/em&gt; in the Azure Service configuration file. This name is merely a convention and is not mandatory.&lt;/p&gt;
&lt;p&gt;A more sophisticated example is:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;protected void StartDiagnosticMonitor()&lt;br&gt;
{&lt;br&gt;
    DiagnosticMonitorConfiguration diagnosticMonitorConfiguration =&lt;br&gt;
       DiagnosticMonitor.GetDefaultInitialConfiguration();&lt;br&gt;
    diagnosticMonitorConfiguration.Directories.ScheduledTransferPeriod = TimeSpan.FromMinutes(5.0);&lt;br&gt;
    diagnosticMonitorConfiguration.Logs.ScheduledTransferPeriod = TimeSpan.FromMinutes(1.0);&lt;br&gt;
    diagnosticMonitorConfiguration.WindowsEventLog.ScheduledTransferPeriod = TimeSpan.FromMinutes(5.0);&lt;br&gt;
    diagnosticMonitorConfiguration.PerformanceCounters.ScheduledTransferPeriod = TimeSpan.FromMinutes(1.0);&lt;/p&gt;
&lt;p&gt;diagnosticMonitorConfiguration.WindowsEventLog.DataSources.Add(“Application!*”);&lt;br&gt;
    diagnosticMonitorConfiguration.WindowsEventLog.DataSources.Add(“System!*”);&lt;/p&gt;
&lt;p&gt;PerformanceCounterConfiguration performanceCounterConfiguration = new PerformanceCounterConfiguration();&lt;br&gt;
    performanceCounterConfiguration.CounterSpecifier = @”Processor(*)% Processor Time”;&lt;br&gt;
    performanceCounterConfiguration.SampleRate = System.TimeSpan.FromSeconds(1.0);&lt;br&gt;
    diagnosticMonitorConfiguration.PerformanceCounters.DataSources.Add(performanceCounterConfiguration);&lt;/p&gt;
&lt;p&gt;CloudStorageAccount cloudStorageAccount = CloudStorageAccount.DevelopmentStorageAccount;&lt;br&gt;
    DiagnosticMonitor diagnosticMonitor = DiagnosticMonitor.Start(&lt;br&gt;
       cloudStorageAccount, diagnosticMonitorConfiguration);&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;This example retrieves the &lt;em&gt;DiagnosticMonitor&lt;/em&gt; default initial configuration. It then specifies in this configuration various transfer periods to persistent Azure Storage for Directories, Logs, Windows Event Logs. and Windows Performance Counters. It adds Event Log data sources for the Windows Application and System Event Logs to the configuration. Then it configures the collection of a Windows Performance Counter for the %processor time for all processors with data collection taking place every second. Finally, it retrieves the built-in &lt;em&gt;DevelopmentStorageAccount&lt;/em&gt; and starts the Monitoring Agent Host by invoking the &lt;em&gt;DiagnosticMonitor&lt;/em&gt; Start() method.&lt;/p&gt;
&lt;p&gt;Note. I got an error in the Start() method when I tried to use a CloudStorageAccount created as follows:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;CloudStorageAccount cloudStorageAccount = CloudStorageAccount.FromConfigurationSetting(“DiagnosticsConnectionString”);&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;This happened even though the Azure Service configuration file had the following:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;&amp;lt;Setting name=”DiagnosticsConnectionString” value=”UseDevelopmentStorage=true” /&amp;gt;&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;and &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.cloudstorageaccount.setconfigurationsettingpublisher.aspx"&gt;CloudStorageAccount.SetConfigurationSettingPublisher()&lt;/a&gt; had been invoked.&lt;/p&gt;
&lt;p&gt;This problem could easily be due to user error.&lt;/p&gt;
&lt;p&gt;The &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.allowinsecureremoteconnections.aspx"&gt;AllowInsecureRemoteConnections&lt;/a&gt; property specifies whether or not the Monitoring Agent Host can communicate with Azure Storage using http instead of https. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.localdatadirectory.aspx"&gt;LocalDataDirectory&lt;/a&gt;  gets the full path in local storage where the Azure Diagnostics data files and configuration are stored.&lt;/p&gt;
&lt;p&gt;The &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.shutdown.aspx"&gt;Shutdown()&lt;/a&gt; method stops the Monitoring Agent Host and stops the collection of diagnostics data. &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitor.updatestorageaccount.aspx"&gt;UpdateStorageAccount()&lt;/a&gt; allows new &lt;em&gt;CloudStorageAccount&lt;/em&gt; information to be supplied to the Monitoring Agent Host.&lt;/p&gt;
&lt;h3&gt;Tracing to the Log&lt;/h3&gt;
&lt;p&gt;Azure has a special trace listener, &lt;a href="http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.diagnostics.diagnosticmonitortracelistener.aspx"&gt;DiagnosticMonitorTraceListener&lt;/a&gt;, that writes Trace information to the Azure log files. An Azure role is configured to use the &lt;em&gt;DiagnosticMonitorTraceListener&lt;/em&gt; by &lt;a href="http://msdn.microsoft.com/en-us/library/ee843890.aspx"&gt;placing&lt;/a&gt; the following in the web.config or app.config file as appropriate:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;&amp;lt;system.diagnostics&amp;gt;&lt;br&gt;
    &amp;lt;trace&amp;gt;&lt;br&gt;
        &amp;lt;listeners&amp;gt;&lt;br&gt;
            &amp;lt;add type=”Microsoft.WindowsAzure.Diagnostics.DiagnosticMonitorTraceListener,&lt;br&gt;
                 Microsoft.WindowsAzure.Diagnostics, Version=1.0.0.0, Culture=neutral,&lt;br&gt;
                 PublicKeyToken=31bf3856ad364e35″ name=”AzureDiagnostics”&amp;gt;&lt;br&gt;
                &amp;lt;filter type=”&amp;quot; /&amp;gt;&lt;br&gt;
            &amp;lt;/add&amp;gt;&lt;br&gt;
        &amp;lt;/listeners&amp;gt;&lt;br&gt;
    &amp;lt;/trace&amp;gt;&lt;br&gt;
&amp;lt;/system.diagnostics&amp;gt;&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;Tracing is then performed by using static methods in the &lt;a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.trace.aspx"&gt;System.Diagnostics.Trace&lt;/a&gt; class. For example, &lt;a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.trace.traceinformation.aspx"&gt;TraceInformation()&lt;/a&gt; writes an informational trace to the Azure logs while &lt;a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.trace.tracewarning.aspx"&gt;TraceWarning()&lt;/a&gt; writes a warning trace to the event logs. These log levels can later be used to filter messages during analysis of the trace output. The Trace class also provides basic &lt;a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.trace.write.aspx"&gt;Write()&lt;/a&gt; and &lt;a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.trace.writeif.aspx"&gt;WriteIf()&lt;/a&gt; methods, the latter writing a trace depending on the Boolean value of a parameter. For example, the following writes the instance Id of the current instance as an informational trace to the Azure logs:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;protected void WriteTraceInformation()&lt;br&gt;
{&lt;br&gt;
    String roleInstance = RoleEnvironment.CurrentRoleInstance.Id;&lt;br&gt;
    System.Diagnostics.Trace.TraceInformation(“Role instance: ” + roleInstance);&lt;br&gt;
}&lt;/p&gt;&lt;/blockquote&gt;
&lt;p&gt;UPDATE 10/13/2010 – A &lt;a href="http://www.dotnetsolutions.co.uk/blog/archive/2010/02/22/windows-azure-diagnostics-%E2%80%93-why-the-trace-writeline-method-only-sends-verbose-messages/"&gt;post&lt;/a&gt; on the Dot Net Solutions blog warns that &lt;a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.trace.writeline.aspx"&gt;Trace.WriteLine()&lt;/a&gt; issues only Verbose messages.&lt;/p&gt;
&lt;h3&gt;Accessing Logs&lt;/h3&gt;
&lt;p&gt;The Azure Diagnostics logs are accessible once they have been persisted to Azure Storage. They can then be viewed using an application like &lt;a href="http://azurestorageexplorer.codeplex.com/"&gt;Azure Storage Explorer&lt;/a&gt; or &lt;a href="http://www.cerebrata.com/Products/CloudStorageStudio/"&gt;Cloud Storage Studio&lt;/a&gt;. They can also be downloaded from Azure Storage to a local system for further analysis.&lt;/p&gt;
&lt;p&gt;UPDATE 3/25/2010&lt;/p&gt;
&lt;p&gt;Confirmed that IIS Logs are now configured through &lt;em&gt;DirectoriesBufferConfiguration&lt;/em&gt;.&lt;/p&gt;
&lt;div style="display:inline;float:none;margin:0;padding:0"&gt;Technorati Tags: &lt;a href="http://technorati.com/tags/Azure" rel="tag"&gt;Azure&lt;/a&gt;,&lt;a href="http://technorati.com/tags/Azure+Diagnostics" rel="tag"&gt;Azure Diagnostics&lt;/a&gt;,&lt;a href="http://technorati.com/tags/Azure+Storage" rel="tag"&gt;Azure Storage&lt;/a&gt;&lt;/div&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/BofxS6ZArtY" height="1" width="1"/&gt;</content><author><name>Neil Mackenzie</name></author><source gr:stream-id="feed/http://convective.wordpress.com/feed/"><id>tag:google.com,2005:reader/feed/http://convective.wordpress.com/feed/</id><title type="html">Convective</title><link rel="alternate" href="http://convective.wordpress.com" type="text/html" /></source><feedburner:origLink>http://convective.wordpress.com/2009/12/08/diagnostics-in-windows-azure</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1304569969389"><id gr:original-id="tag:typepad.com,2003:post-6a00d8341d3df553ef01538e4b5a04970b">tag:google.com,2005:reader/item/edee72358040add9</id><title type="html">Time Has Changed</title><published>2011-05-04T21:02:43Z</published><updated>2011-05-04T21:14:39Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/JrXCC7bVKYg/the-e-and-the-f.html" type="text/html" /><link rel="replies" href="http://geekandpoke.typepad.com/geekandpoke/2011/05/the-e-and-the-f.html" type="text/html" /><content xml:base="http://geekandpoke.typepad.com/geekandpoke/" xml:lang="en-US" type="html">&lt;div&gt;&lt;p&gt;&lt;a style="display:inline" href="http://geekandpoke.typepad.com/.a/6a00d8341d3df553ef01538e4b535e970b-pi"&gt;&lt;img title="E-and-f" src="http://geekandpoke.typepad.com/.a/6a00d8341d3df553ef01538e4b535e970b-800wi" border="0" alt="E-and-f"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
See &lt;a href="http://techcrunch.com/2011/05/04/facebook-one-third-online-ads/"&gt;TechCrunch: "comScore: Facebook Now Serves One Third Of Online Ads In U.S."&lt;/a&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;a href="http://twitter.com/share"&gt;Tweet&lt;/a&gt;&lt;/div&gt;
&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=cH28NcFlqtI:oOR95DbgTqs:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=cH28NcFlqtI:oOR95DbgTqs:V_sGLiPBpWU"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?i=cH28NcFlqtI:oOR95DbgTqs:V_sGLiPBpWU" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=cH28NcFlqtI:oOR95DbgTqs:qj6IDK7rITs"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?d=qj6IDK7rITs" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=cH28NcFlqtI:oOR95DbgTqs:7Q72WNTAKBA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?d=7Q72WNTAKBA" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/GeekAndPoke/~4/cH28NcFlqtI" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/JrXCC7bVKYg" height="1" width="1"/&gt;</content><author><name>Oliver Widder</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/GeekAndPoke"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/GeekAndPoke</id><title type="html">Geek And Poke</title><link rel="alternate" href="http://geekandpoke.typepad.com/geekandpoke/" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/GeekAndPoke/~3/cH28NcFlqtI/the-e-and-the-f.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1304282077541"><id gr:original-id="tag:typepad.com,2003:post-6a00d8341d3df553ef0154320f6e7a970c">tag:google.com,2005:reader/item/98d8109d2ef6883b</id><title type="html">Captcha On mensa.org</title><published>2011-05-01T20:03:50Z</published><updated>2011-05-01T20:03:50Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/-5V0jbOeXW0/captcha-on-mensaorg.html" type="text/html" /><link rel="replies" href="http://geekandpoke.typepad.com/geekandpoke/2011/05/captcha-on-mensaorg.html" type="text/html" /><content xml:base="http://geekandpoke.typepad.com/geekandpoke/" xml:lang="en-US" type="html">&lt;div&gt;&lt;p&gt;&lt;a style="display:inline" href="http://geekandpoke.typepad.com/.a/6a00d8341d3df553ef014e8830119b970d-pi"&gt;&lt;img title="Mensa" src="http://geekandpoke.typepad.com/.a/6a00d8341d3df553ef014e8830119b970d-800wi" border="0" alt="Mensa"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;a href="http://twitter.com/share"&gt;Tweet&lt;/a&gt;&lt;/div&gt;
&lt;div&gt;
&lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=RIQycdtupN0:lvmhnUMMQ-4:yIl2AUoC8zA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?d=yIl2AUoC8zA" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=RIQycdtupN0:lvmhnUMMQ-4:V_sGLiPBpWU"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?i=RIQycdtupN0:lvmhnUMMQ-4:V_sGLiPBpWU" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=RIQycdtupN0:lvmhnUMMQ-4:qj6IDK7rITs"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?d=qj6IDK7rITs" border="0"&gt;&lt;/a&gt; &lt;a href="http://feeds.feedburner.com/~ff/GeekAndPoke?a=RIQycdtupN0:lvmhnUMMQ-4:7Q72WNTAKBA"&gt;&lt;img src="http://feeds.feedburner.com/~ff/GeekAndPoke?d=7Q72WNTAKBA" border="0"&gt;&lt;/a&gt;
&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/GeekAndPoke/~4/RIQycdtupN0" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/-5V0jbOeXW0" height="1" width="1"/&gt;</content><author><name>Oliver Widder</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/GeekAndPoke"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/GeekAndPoke</id><title type="html">Geek And Poke</title><link rel="alternate" href="http://geekandpoke.typepad.com/geekandpoke/" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/GeekAndPoke/~3/RIQycdtupN0/captcha-on-mensaorg.html</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1304274829568"><id gr:original-id="http://www.leastprivilege.com/PermaLink.aspx?guid=3b250501-92dd-4318-a991-52dce93952b4">tag:google.com,2005:reader/item/2e803058b7779a84</id><category term="IdentityModel" /><title type="html">What I don’t like about WIF’s Claims-based Authorization</title><published>2011-04-30T06:45:09Z</published><updated>2011-04-30T06:45:09Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/sAQaZWRtisg/WhatIDonrsquotLikeAboutWIFrsquosClaimsbasedAuthorization.aspx" type="text/html" /><summary xml:base="http://www.leastprivilege.com/" type="html">&lt;p&gt;
In my last post I wrote about what I like about WIF’s proposed approach to authorization
– I also said that I definitely would build upon that infrastructure for my own systems.
But implementing such a system is a little harder as it could be. Here’s why (and
that’s purely my perspective):
&lt;/p&gt;
&lt;p&gt;
First of all WIF’s authorization comes in two “modes”
&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
Per-request authorization.&lt;br&gt;
When an ASP.NET/WCF request comes in, the registered authorization manager gets called.
For SOAP the SOAP action gets passed in. For HTTP requests (ASP.NET, WCF REST) the
URL and verb.&lt;/li&gt;
&lt;li&gt;
Imperative authorization&lt;br&gt;
This happens when you explicitly call the claims authorization API from within your
code. There you have full control over the values for action and resource.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;
In ASP.NET per-request authorization is optional (depends on if you have added the &lt;em&gt;ClaimsAuthorizationHttpModule&lt;/em&gt;).
In WCF you always get the per-request checks as soon as you register the authorization
manager in configuration. 
&lt;/p&gt;
&lt;p&gt;
I personally prefer the imperative authorization because first of all I don’t believe
in URL based authorization. Especially in the times of MVC and routing tables, URLs
can be easily changed – but then you also have to adjust your authorization logic
every time. Also – you typically need more knowledge than a simple “if user x is allowed
to invoke operation x”.
&lt;/p&gt;
&lt;p&gt;
One problem I have is, both the per-request calls as well as the standard WIF imperative
authorization APIs wrap actions and resources in the same claim type. This makes it
hard to distinguish between the two authorization modes in your authorization manager.
But you typically need that feature to structure your authorization policy evaluation
in a clean way.
&lt;/p&gt;
&lt;p&gt;
The second problem (which is somehow related to the first one) is the standard API
for interacting with the claims authorization manager. The API comes as an attribute
(&lt;em&gt;ClaimsPrincipalPermissionAttribute&lt;/em&gt;) as well as a class to use programmatically
(&lt;em&gt;ClaimsPrincipalPermission&lt;/em&gt;). Both only allow to pass in simple strings (which
results in the wrapping with standard claim types mentioned earlier). Both throw a &lt;em&gt;SecurityException&lt;/em&gt; when
the check fails.
&lt;/p&gt;
&lt;p&gt;
The attribute is a code access permission attribute (like &lt;em&gt;PrincipalPermission&lt;/em&gt;).
That means it will always be invoked regardless how you call the code. This may be
exactly what you want, or not. In a unit testing situation (like an MVC controller)
you typically want to test the logic in the function – not the security check.
&lt;/p&gt;
&lt;p&gt;
The good news is, the WIF API is flexible enough that you can build your own infrastructure
around their core. For my own projects I implemented the following extensions:
&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
A way to invoke the registered claims authorization manager with more overloads, e.g.
with different claim types or a complete &lt;em&gt;AuthorizationContext&lt;/em&gt;.&lt;/li&gt;
&lt;li&gt;
A new CAS attribute (with the same calling semantics as the built-in one) with custom
claim types.&lt;/li&gt;
&lt;li&gt;
A MVC authorization attribute with custom claim types.&lt;/li&gt;
&lt;li&gt;
A way to use branching – as opposed to catching a &lt;em&gt;SecurityException&lt;/em&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;
I will post the code for these various extensions here – so stay tuned.
&lt;/p&gt;
&lt;img width="0" height="0" src="http://www.leastprivilege.com/aggbug.ashx?id=3b250501-92dd-4318-a991-52dce93952b4"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/sAQaZWRtisg" height="1" width="1"/&gt;</summary><author><name>Your DisplayName here!</name></author><source gr:stream-id="feed/http://www.leastprivilege.com/SyndicationService.asmx/GetRss"><id>tag:google.com,2005:reader/feed/http://www.leastprivilege.com/SyndicationService.asmx/GetRss</id><title type="html">www.leastprivilege.com</title><link rel="alternate" href="http://www.leastprivilege.com/" type="text/html" /></source><feedburner:origLink>http://www.leastprivilege.com/WhatIDonrsquotLikeAboutWIFrsquosClaimsbasedAuthorization.aspx</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1303907644877"><id gr:original-id="">tag:google.com,2005:reader/item/68b97bab5bf67e5a</id><title type="html">Use More VMs On Your Laptop</title><published>2011-04-15T17:14:00Z</published><updated>2011-04-15T17:14:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/QfU48qOGLBg/229402296" type="text/html" /><summary xml:base="http://drdobbs.com/" type="html">Developers grossly underutilize virtualization on their development platforms&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/QfU48qOGLBg" height="1" width="1"/&gt;</summary><author gr:unknown-author="true"><name>(author unknown)</name></author><source gr:stream-id="feed/http://www.ddj.com/rss/architect_feature.xml"><id>tag:google.com,2005:reader/feed/http://www.ddj.com/rss/architect_feature.xml</id><title type="html">Dr. Dobb&amp;#39;s Articles</title><link rel="alternate" href="http://drdobbs.com/" type="text/html" /></source><feedburner:origLink>http://drdobbs.com/articles/229402296</feedburner:origLink></entry><entry gr:crawl-timestamp-msec="1303902130614"><id gr:original-id="http://www.readwriteweb.com/cloud/2011/04/almost-as-galling-as-the.php">tag:google.com,2005:reader/item/b718f2a5d3a5cc4a</id><category term="Cloud Providers" /><title type="html">Stop Blaming the Customers - the Fault is on Amazon Web Services</title><published>2011-04-25T23:00:00Z</published><updated>2011-04-25T23:00:00Z</updated><link rel="alternate" href="http://feedproxy.google.com/~r/ARGOReadings/~3/Rozy6W2T57A/almost-as-galling-as-the.php" type="text/html" /><summary xml:base="http://www.readwriteweb.com/cloud/" type="html">&lt;p&gt;&lt;img alt="Blame" src="http://www.readwriteweb.com/cloud/images/blame_image_0411.jpg" width="150" height="150"&gt; Almost as galling as the Amazon Web Services outage itself is a the litany of blog posts, such as &lt;a href="http://cloudability.com/single-points-of-failure"&gt;this one&lt;/a&gt; and &lt;a href="http://www.lockergnome.com/it/2011/04/23/the-aws-outage-how-to-avoid-downtime-in-the-cloud/"&gt;this one&lt;/a&gt;, that place the blame not on AWS for having a long failure and not communicating with its customers about it, but on AWS customers for not being better prepared for an outage. It's a tendency that displays a "blame the customer" mentality I've been seeing a lot lately. To understand why it's wrong one has to understand what actually happened and what claims AWS made about it services.&lt;/p&gt;

&lt;p&gt;We covered the differences between availability zones and availability regions, and AWS' lack of communication, in our &lt;a href="http://www.readwriteweb.com/cloud/2011/04/timeline-the-aws-outage-and-wh.php"&gt;previous coverage&lt;/a&gt;. Now that the dust has settled, it's worth looking back at what happened. &lt;a href="http://www.randomhacks.net/articles/2011/04/25/aws-outage-timeline-and-recovery-strategy-downtimes"&gt;This timeline&lt;/a&gt; by Eric Kidd explains the series of events, and the various options different customers had. &lt;a href="http://blog.rightscale.com/2011/04/25/amazon-ec2-outage-summary-and-lessons-learned/"&gt;RightScale&lt;/a&gt; provides another good summary. What can we learn?&lt;/p&gt;
&lt;p align="right"&gt;&lt;em&gt;Sponsor&lt;/em&gt;&lt;br&gt;&lt;a href="http://d1.openx.org/ck.php?n=26221&amp;amp;cb=26221"&gt;&lt;img src="http://d1.openx.org/avw.php?zoneid=11205&amp;amp;cb=26221&amp;amp;n=26221" border="0" alt="" align="right"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;What Amazon Claims&lt;/h2&gt;

&lt;p&gt;Here's what AWS claims about Availability Zones:&lt;/p&gt;

&lt;blockquote&gt;Each availability zone runs on its own physically distinct, independent infrastructure, and is engineered to be highly reliable. Common points of failures like generators and cooling equipment are not shared across Availability Zones. Additionally, they are physically separate, such that even extremely uncommon disasters such as fires, tornados or flooding would only affect a single Availability Zone.&lt;/blockquote&gt;

&lt;p&gt;In other words, AWS claimed that by putting your data in different availability zones, within one region, &lt;em&gt;was&lt;/em&gt; redundant. As far as AWS' customers were concerned, they didn't have a single point of failure.&lt;/p&gt;

&lt;p&gt;Amazon Relational Database Service customers have the option of &lt;a href="http://aws.amazon.com/rds/#pricing"&gt;paying double&lt;/a&gt; the regular cost of the service for a multi-zone service: "When you run your DB Instance as a Multi-AZ deployment for enhanced data durability and availability, Amazon RDS provisions and maintains a standby in a different Availability Zone for automatic failover in the event of a scheduled or unplanned outage."&lt;/p&gt;

&lt;h2&gt;What Happened vs. What Was Supposed to Happen&lt;/h2&gt;

&lt;p&gt;The mass outage was due to Elastic Block Storage (EBS) service problems in a single Availability Zone. EBS instances can only live in one Availability Zone, but users should have been able to use their snapshots to create a new EBS instance in another availability zone. RDS depends on EBS, but RDS customers paying for multi-zone service should have had their databases failed-over to another zone automatically.&lt;/p&gt;

&lt;p&gt;However, the "control plane" for creating new EBS instances suffered congestion, preventing any ability to failover either manually or automatically. The current assumption is that it was overloaded by customers who's initial EBS instance failed. Kidd calls this a "bank run."&lt;/p&gt;

&lt;p&gt;The important thing here is that there actually was, unbeknownst to AWS customers, a single point of failure across zones: the control plane. This made AWS unable to fulfill its own failover promises. In fact, RDS customers ended up in worse shape than many others - it took over 14 hours to get many of their databases moved over, longer than those that were able to failover manually.&lt;/p&gt;

&lt;h2&gt;Multi-Region Multi-Vendor Deployments&lt;/h2&gt;

&lt;p&gt;So why not place applications in multiple regions, just to be safe? It's not that simple. First, AWS charges more for transfers between regions. But more importantly, it's technologically more complex. Amazon Machine Instances (AMIs) can't just been moved from one region to another. &lt;a href="http://justinsb.posterous.com/aws-down-why-the-sky-is-falling"&gt;Justin Santa Barbara writes&lt;/a&gt; "The different regions have different features available, different AMI ids, I think reserved instances can't be moved between datacenters - in reality failover between regions is not realistic."&lt;/p&gt;

&lt;p&gt;Barbara writes that it may actually be easier to failover to an entirely separate cloud than to use regions as failover. I'm not sure that's the case, but regional failover is certainly complicated. And based on the claims made about Availability Zones, would have seemed unnecessary before last week. After all, if each data center in the availability region is a discrete entity insulated from the failures of each other data center, then why would it be necessary add yet another data center in another region? Especially if doing so adds great expense?&lt;/p&gt;

&lt;p&gt;&lt;a href="http://www.thestoragearchitect.com/2011/04/22/so-your-aws-based-application-is-down-dont-blame-amazon/"&gt;Chris M Evans recommends&lt;/a&gt; using multiple cloud providers. To his credit, he recommended this even before the AWS outage (one of the things that bothers me about the blame the customer crowd is that their wisdom about what customers should have done comes entirely after the fact). Again, however, this adds additional complexity - and with that additional complexity, additional costs and additional risks. To many customers it seemed natural to just live with having multiple Availability Zones instead of multiple providers.&lt;/p&gt;

&lt;p&gt;Even &lt;a href="http://www.bigdoor.com/"&gt;BigDoor&lt;/a&gt; CEO Keith Smith, concluded his &lt;a href="http://www.readwriteweb.com/cloud/www.geekwire.com/2011/amazoncoms-real-problem-outage-communication"&gt;widely cited piece&lt;/a&gt; on Amazon's failure to communicate with customers by writing:&lt;/p&gt;

&lt;blockquote&gt;We can spend cycles designing and building technical belts and suspenders that will help us avoid a massive failure like this in the future, or we can continue to rely on a single huge partner and also continue our break-neck pace of iteration and product development.

&lt;p&gt;I can't tell you today which option we will choose. But I'm sure it will be the question on the mind of many startups across the country.&lt;/p&gt;&lt;/blockquote&gt;

&lt;p&gt;George Reese of enStratus wrote for &lt;a href="http://broadcast.oreilly.com/2011/04/the-aws-outage-the-clouds-shining-moment.html"&gt;O'Reilly Media&lt;/a&gt;: "In short, if your systems failed in the Amazon cloud this week, it wasn't Amazon's fault. You either deemed an outage of this nature an acceptable risk or you failed to design for Amazon's cloud computing model."&lt;/p&gt;

&lt;p&gt;That misses the point. Accepting a certain amount of downtime is one thing, accepting 14 hours of downtime when you've already paid extra for redundancy is another. &lt;/p&gt;

&lt;p&gt;Yes, customers accept a certain amount of risk, but that doesn't make it their fault when Amazon screws up.&lt;/p&gt;

&lt;h2&gt;Why Didn't Some Sites, Like SmugMug and Twilio, Go Down?&lt;/h2&gt;

&lt;p&gt;What about the companies that had the good fortune to avoid outages? Aren't they evidence that it's the customers' fault for not setting things up right? Not really. Both &lt;a href="http://www.twilio.com/engineering/2011/04/22/why-twilio-wasnt-affected-by-todays-aws-issues/"&gt;Twilio&lt;/a&gt; and &lt;a href="http://don.blogs.smugmug.com/2011/04/24/how-smugmug-survived-the-amazonpocalypse/"&gt;SmugMug&lt;/a&gt; boast about their "design for failure" but the important thing is that neither company relied on EBS. Had these companies been dependent on EBS, they likely would have suffered a similar fate.&lt;/p&gt;

&lt;h2&gt;What About Netflix?&lt;/h2&gt;

&lt;p&gt;What about Netflix? Netflix, as documented by &lt;a href="http://perfcap.blogspot.com/2011/03/understanding-and-using-amazon-ebs.html"&gt;Adrian Cockcroft&lt;/a&gt;, does use EBS.&lt;/p&gt;

&lt;p&gt;Kidd writes about Netflix:&lt;/p&gt;

&lt;blockquote&gt;Run in 3 AZs, at no more than 60% capacity in each. This is the approach taken by Netflix, which sailed through this outage without no known downtime. If a single AZ fails, then the remaining two zones will be at 90% capacity. And because the extra capacity is running at all times, Netflix doesn't need to launch new instances in the middle of a "bank run."&lt;/blockquote&gt;

&lt;p&gt;It's not clear how much Netflix uses EBS, but Cockcroft gave a presentation saying &lt;a href="http://www.slideshare.net/adrianco/performance-architecture-for-cloud-connect"&gt;Netflix avoids it&lt;/a&gt;. &lt;a href="http://twitter.com/#!/adrianco/status/61327037327097856"&gt;This tweet&lt;/a&gt; indicates that Netflix is more reliant on S3, SimpleDB and Apache Cassandra than on EBS, but Cockcroft did &lt;a href="http://twitter.com/#!/adrianco/status/61307174260977664"&gt;note&lt;/a&gt; that the company was having EBS trouble during the outage.&lt;/p&gt;

&lt;p&gt;It's also worth noting that Cockcroft &lt;a href="http://twitter.com/#!/adrianco/status/61459359229681666"&gt;tweeted&lt;/a&gt; that Netflix only runs out of one region.&lt;/p&gt;

&lt;h2&gt;It's The Customers' Fault Because They Shouldn't Have Been Using EBS in the First Place&lt;/h2&gt;

&lt;p&gt;I love this argument - that it's customers' fault for using EBS in the first place. Mashery co-founder &lt;a href="http://claylo.com/post/4844798650/failure-is-not-an-option"&gt;Clay Loveless&lt;/a&gt; makes this case.&lt;/p&gt;

&lt;p&gt;AWS has been offering the EBS service since 2008. It's not considered a "beta" product.  Why shouldn't customers be able to rely on it? True it's had issues over the years, leading some companies to decide not to use it. But AWS has happily taken money from customers for years now. If it's a product that isn't ready for product, AWS should have said so. (Unfortunately for customers, the EBS outage &lt;a href="http://www.zdnet.com/blog/saas/seven-lessons-to-learn-from-amazons-outage/1296"&gt;won't count towards their SLAs&lt;/a&gt;.)&lt;/p&gt;

&lt;p&gt;What the "they shouldn't have used EBS" argument comes down to is: customers are stupid for trusting AWS to provide the service promised. It's saying that customers that paid for multi-zone RDS replication should have expected 14+ hours of downtime. If AWS itself were to tell its customers "You should have known better than to trust our service," we would be up in arms - wouldn't we?&lt;/p&gt;

&lt;p&gt;I keep seeing similar arguments. "We shouldn't blame Dropbox for lying about its encryption, we should blame customers for trusting Dropbox." "We shouldn't blame Apple for not giving users control over their location logs, we should blame customers for expecting privacy." I'm sick of it.&lt;/p&gt;

&lt;p&gt;It might in fact be true that we can't expect vendors to provide customers' what they promise. But that is squarely on the shoulders of vendors, not the customers. And I'm sick of "savvy" pundits putting down customers and excusing failure and bad behavior on the part of companies.&lt;/p&gt;

&lt;p&gt;Yes, things happen. AWS is run by humans, and humans make mistakes. AWS deserves some forgiveness . But let's not forget who messed up.&lt;/p&gt;

&lt;h2&gt;How to Fix the Problem&lt;/h2&gt;

&lt;p&gt;In the short term, I suspect many customers will move away from using EBS and RDS. In the medium term, infrastructure-as-a-service providers need to come up with a standard system for sharing instances across clouds, whether that's OpenStack, Cloud Foundry, Eucalyptus or something else. Customers shouldn't have to choose between trusting only one provider or committing to a complex and potentially unreliable multi-vendor solution. The days of vendor lock-in must come to end. &lt;/p&gt;

&lt;p&gt;Meanwhile, bloggers, analysts, journalists and other opinion-makers need to put the blame back where it belongs: on service providers that don't live-up to their promises.&lt;/p&gt;

&lt;p&gt;(&lt;em&gt;Lead image by &lt;a href="http://www.flickr.com/photos/iandesign/1205496024/"&gt;Ian&lt;/a&gt;&lt;/em&gt;)&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Disclosure: Mashery is a ReadWriteWeb sponsor&lt;/em&gt;.&lt;/p&gt;
&lt;strong&gt;&lt;a href="http://www.readwriteweb.com/cloud/2011/04/almost-as-galling-as-the.php#comments-open"&gt;Discuss&lt;/a&gt;&lt;/strong&gt;&lt;img src="http://feeds.feedburner.com/~r/readwritecloud/~4/cf3kaVk4n0k" height="1" width="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/Rozy6W2T57A" height="1" width="1"/&gt;</summary><author><name>Klint Finley</name></author><source gr:stream-id="feed/http://feeds.feedburner.com/readwritecloud"><id>tag:google.com,2005:reader/feed/http://feeds.feedburner.com/readwritecloud</id><title type="html">ReadWriteCloud</title><link rel="alternate" href="http://www.readwriteweb.com/cloud/" type="text/html" /></source><feedburner:origLink>http://feedproxy.google.com/~r/readwritecloud/~3/cf3kaVk4n0k/almost-as-galling-as-the.php</feedburner:origLink></entry><entry><title type="text">Links for 2009-11-28 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/-BXe4M6eR0g/arnonrgo" /><updated>2009-11-29T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-11-28</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.specflow.org/specflow/workflow.aspx"&gt;SpecFlow - workflow&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/-BXe4M6eR0g" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-11-28</feedburner:origLink></entry><entry><title type="text">Links for 2009-11-27 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/D19GFhnVf4U/arnonrgo" /><updated>2009-11-28T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-11-27</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://go.microsoft.com/?linkid=9698711"&gt;Media Foundation Team Blog&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://tav.espians.com/ciao-python-hola-go.html"&gt;Ciao Python, Hola Go!&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/D19GFhnVf4U" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-11-27</feedburner:origLink></entry><entry><title type="text">Links for 2009-11-26 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/PEDXpJ8Ozig/arnonrgo" /><updated>2009-11-27T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-11-26</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.leastprivilege.com/ThinktectureIdentityModelV06.aspx"&gt;Thinktecture.IdentityModel v0.6&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/PEDXpJ8Ozig" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-11-26</feedburner:origLink></entry><entry><title type="text">Links for 2009-11-12 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/_yEMspEfExU/arnonrgo" /><updated>2009-11-13T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-11-12</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://blogs.msdn.com/shawnfa/archive/2009/11/11/transparency-models-a-tale-of-two-levels.aspx"&gt;Transparency Models: A Tale of Two Levels&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/_yEMspEfExU" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-11-12</feedburner:origLink></entry><entry><title type="text">Links for 2009-11-08 [del.icio.us]</title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/ARGOReadings/~3/fXDAP89wSFg/arnonrgo" /><updated>2009-11-09T00:00:00-08:00</updated><id>http://del.icio.us/arnonrgo#2009-11-08</id><content type="html">&lt;ul&gt;
&lt;li&gt;&lt;a href="http://research.microsoft.com/en-us/news/features/nagappan-100609.aspx"&gt;Exploding Software-Engineering Myths - Microsoft Research&lt;/a&gt;&lt;br/&gt;
More Isnt Always Better, Write Test Code First, Proving the Utility of Assertions, Organizational Structure Does Mattera Lot. Geographical Distance Doesnt Matter Much.&lt;/li&gt;
&lt;/ul&gt;&lt;img src="http://feeds.feedburner.com/~r/ARGOReadings/~4/fXDAP89wSFg" height="1" width="1"/&gt;</content><feedburner:origLink>http://del.icio.us/arnonrgo#2009-11-08</feedburner:origLink></entry></feed>

