<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://consultingblogs.emc.com/utility/FeedStylesheets/atom.xsl" media="screen"?><feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en"><title type="html">SSIS Junkie</title><subtitle type="html">Once upon a time this blog was a hive of activity. Now however its pretty lifeless as you can probably tell so if are pining for more of the same you can find me over at &lt;a href=http://sqlblog.com/blogs/jamie_thomson&gt;http://sqlblog.com/blogs/jamie_thomson&lt;/a&gt;. I look forward to seeing you there!</subtitle><id>http://consultingblogs.emc.com/jamiethomson/atom.aspx</id><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/default.aspx" /><link rel="self" type="application/atom+xml" href="http://consultingblogs.emc.com/jamiethomson/atom.aspx" /><generator uri="http://communityserver.org" version="2.1.20423.1">Community Server</generator><updated>2009-06-09T21:42:54Z</updated><entry><title>The curtain falls</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/08/29/the-curtain-falls.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/08/29/the-curtain-falls.aspx</id><published>2009-08-29T22:27:25Z</published><updated>2009-08-29T22:27:25Z</updated><content type="html">&lt;p&gt;In October 2004 I was in Orlando airport returning home from the annual SQL PASS summit and I happened to pick up a copy of MIT’s Technology Review magazine in which the cover story was an interview with Tim Berners-Lee called “Internet 2.0”.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://www.technologyreview.com/magazine/21/"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;margin-left:0px;border-left-width:0px;margin-right:0px;" title="MIT Technology Review October 2004 cover" border="0" alt="MIT Technology Review October 2004 cover" align="left" src="http://blogs.conchango.com/blogs/jamiethomson/image_7D718C76.png" width="175" height="215" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;One subject covered in the interview was the emerging phenomenon of blogging and it was then that I decided I wanted to get my own blog to talk about the stuff I was interested which, at the time, was the early beta of SQL Server Yukon (later renamed to SQL Server 2005).&lt;/p&gt;  &lt;p&gt;Soon after returning to the UK it was announced internally that Conchango were soon to support their own blog site at &lt;a href="http://blogs.conchango.com"&gt;http://blogs.conchango.com&lt;/a&gt; and would anyone be interested in contributing. Inspired by the Berners-Lee article I threw my hat in and on 3rd November 2004 I wrote my first blog entry &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2004/11/03/Intro.aspx"&gt;Intro&lt;/a&gt; where I said:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;em&gt;So...I've got a blog. Now the inevitable question...what on earth to put in it?&lt;/em&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Well I guess I found something to write about because since that original post I’ve written another 674 of the things!:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/Bloggers.aspx?GroupID=6"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="Conchango blogger statistics" border="0" alt="Conchango blogger statistics" src="http://blogs.conchango.com/blogs/jamiethomson/image_13E42AFE.png" width="690" height="100" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Why am I telling you this? Well, this blog post is going to be both the 676th and the last at &lt;a href="http://blogs.conchango.com/jamiethomson"&gt;http://blogs.conchango.com/jamiethomson&lt;/a&gt; for in a few weeks I shall be leaving &lt;strike&gt;Conchango&lt;/strike&gt; EMC Consulting after five and a half very very happy years. Its been a painstaking decision to do this for I’ll be leaving behind a bunch of brilliantly talented colleagues and fun people whom it has been a genuine pleasure to be around but I feel the time is right to branch out on my own.&lt;/p&gt;  &lt;p&gt;My blogging activity will not die, I shall be continuing over at &lt;a title="http://sqlblog.com/blogs/jamie_thomson" href="http://sqlblog.com/blogs/jamie_thomson"&gt;http://sqlblog.com/blogs/jamie_thomson&lt;/a&gt; and I would encourage you to point your RSS readers at &lt;a title="http://feeds.feedburner.com/jamiet" href="http://feeds.feedburner.com/jamiet"&gt;http://feeds.feedburner.com/jamiet&lt;/a&gt; if you want to continue to read my inane wafflings.&lt;/p&gt;  &lt;p&gt;Thanks for reading here for at least some of the past five years, see you on the other side!&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;hr /&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Given my interest in all things BI I thought I’d provide some stats to summarise my activity here over the past 5 years (also because I’m not going to have access to some of this data for much later):&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;# of posts: 676 &lt;/li&gt;    &lt;li&gt;# of comments: 4109 &lt;/li&gt;    &lt;li&gt;# of hits: 6.99million &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Distribution of blog posts per month (unsurprisingly my output declined once I’d run out of stuff to talk about in regard to SSIS 2005)&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_2F1C83FF.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="blog posts per month on http://blogs.conchango.com/jamiethomson" border="0" alt="blog posts per month on http://blogs.conchango.com/jamiethomson" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_4DF2F7DD.png" width="883" height="383" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;Number of people subscribed to my blog on Google Reader since March 2008&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_180E02C3.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="google reader subscribers to http://blogs.conchango.com/jamiethomson" border="0" alt="google reader subscribers to http://blogs.conchango.com/jamiethomson" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_6C5D38C6.png" width="514" height="295" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Top posts in terms of hits&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;a href="http://blogs.conchango.com/jamiethomson/archive/2006/01/05/SSIS_3A00_-Suggested-Best-Practices-and-naming-conventions.aspx"&gt;Suggested Best Practices and naming conventions&lt;/a&gt; (102448 hits) &lt;/li&gt;    &lt;li&gt;&lt;a href="http://blogs.conchango.com/jamiethomson/archive/2006/09/12/SSIS_3A00_-Checking-if-a-row-exists-and-if-it-does_2C00_-has-it-changed.aspx"&gt;Checking if a row exists and if it does, has it changed?&lt;/a&gt; (67851 hits) &lt;/li&gt; &lt;/ul&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=16154" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author></entry><entry><title>Reporting Services FixedColumnHeaders property bug [Note to self]</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/08/24/reporting-services-fixedcolumnheaders-property-bug-note-to-self.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/08/24/reporting-services-fixedcolumnheaders-property-bug-note-to-self.aspx</id><published>2009-08-24T08:31:00Z</published><updated>2009-08-24T08:31:00Z</updated><content type="html">&lt;P&gt;[Every time I come across this problem&amp;nbsp;I seem to spend a good five minutes scanning the interwebs trying to find the answer - maybe if I write it here it'll be easier to find in the future!]&lt;/P&gt;
&lt;P&gt;SQL Server Reporting Services 2008 has a bug concerning the FixedColumnHeaders property of a tablix.&lt;/P&gt;
&lt;P&gt;The property's description is given as :&lt;/P&gt;
&lt;BLOCKQUOTE&gt;
&lt;P&gt;"Indicates whether the column headers remain displayed on the page when the user scrolls the tablix data region off the page."&lt;/P&gt;&lt;/BLOCKQUOTE&gt;
&lt;P&gt;Well that's not actually true because setting that property to, well,&amp;nbsp;&lt;EM&gt;anything &lt;/EM&gt;has no discernible effect. Microsoft have acknowledge the bug (without actually calling it a bug) and provided a workaround in a knowledge base article:&lt;/P&gt;
&lt;BLOCKQUOTE&gt;
&lt;P&gt;&lt;A class="" href="http://support.microsoft.com/kb/955822" target=_blank&gt;You cannot keep the column headers or the row headers visible when you scroll through a report in SQL Server 2008 Reporting Services&lt;/A&gt;&lt;/P&gt;&lt;/BLOCKQUOTE&gt;
&lt;P&gt;&amp;nbsp;I haven't yet checked whether this is fixed in the recent CTP2 release build of SQL Server 2008 R2. If I find out I'll try and remember to come back and update this post.&lt;/P&gt;
&lt;P&gt;&lt;A class="" href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/A&gt;&lt;/P&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=16102" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="SQL Server" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server/default.aspx" /><category term="sqL server 2008" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/sqL+server+2008/default.aspx" /><category term="reporting services" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/reporting+services/default.aspx" /><category term="sqL server reporting services" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/sqL+server+reporting+services/default.aspx" /><category term="ssrs" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/ssrs/default.aspx" /></entry><entry><title>Editing Configuration files : SSIS Nugget</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/08/04/editing-configuration-files-ssis-nugget.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/08/04/editing-configuration-files-ssis-nugget.aspx</id><published>2009-08-04T15:51:41Z</published><updated>2009-08-04T15:51:41Z</updated><content type="html">&lt;p&gt;Its been a long-g-g-g-g time since I did a SSIS-related post so here’s a little ditty that I picked up while reviewing some internal stuff today.&lt;/p&gt;  &lt;p&gt;Editing SSIS configuration (i.e. .dtsConfig) files isn’t particularly easy. Most people I see who try to do this use a traditional text editor like Notepad but that isn’t a great experience because the contents don’t look particularly friendly when you open them up. Observe:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_2B1D2348.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_1AE13582.png" width="871" height="160" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Instead you may wish to use Visual Studio which, if you’re messing about with SSIS configuration files, you should already have installed. The steps are pretty simple, firstly hit CTRL-O to open your config file. It may look something like this:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_669CE66E.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_72522DA0.png" width="834" height="93" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;Well, that’s not much better but with a little wave of Visual Studio’s magic wand (otherwise known as CTRL-K, CTRL-D) then it will get turned into this:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_378A84CA.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_1DF2D1D0.png" width="878" height="229" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;which, I’m sure you’ll agree, is a whole lot friendlier. You can save that and it will continue to work just fine, SSIS will of course ignore the whitespace (why BIDS doesn’t create configuration files like this in the first place I do not know).&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15990" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="SQL Server Integration Services" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server+Integration+Services/default.aspx" /><category term="SQL Server" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server/default.aspx" /><category term="SSIS" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SSIS/default.aspx" /><category term="configurations" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/configurations/default.aspx" /><category term="Nugget" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/Nugget/default.aspx" /></entry><entry><title>Peering into the SQL Azure documentation</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/08/04/peering-into-the-sql-azure-documentation.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/08/04/peering-into-the-sql-azure-documentation.aspx</id><published>2009-08-04T09:54:25Z</published><updated>2009-08-04T09:54:25Z</updated><content type="html">&lt;p&gt;Some documentation for SQL Azure has been released on MSDN at &lt;a title="http://msdn.microsoft.com/en-us/library/ee336279.aspx" href="http://msdn.microsoft.com/en-us/library/ee336279.aspx"&gt;http://msdn.microsoft.com/en-us/library/ee336279.aspx&lt;/a&gt; and upon reading there are some interesting nuggets of information that are worth calling out.&lt;/p&gt;  &lt;p&gt;Under a section headed “Key benefits of the service” the following statement appears:&lt;/p&gt;  &lt;blockquote&gt;   &lt;h5&gt;&lt;em&gt;Scalability&lt;/em&gt;&lt;/h5&gt;    &lt;p&gt;&lt;em&gt;A key advantage of SQL Azure is the ease with which you can scale your solution. After partitioning your data, the service scales as your data grows.&lt;/em&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;Hmmm…there’s two seemingly contradictory statements in there, “ease” and “partitioning your data”. Last time I looked there was nothing particularly easy about partitioning data, certainly not when it is going to be partitioned across multiple databases. I wonder if the captain of the Titanic proudly declared “Sailing to New York will be easy once we’re past all those meddlesome icebergs”!&lt;/p&gt;  &lt;p&gt;Another name for this partitioning technique is sharding for which Dare Obasanjo has a great discussion up at &lt;a href="http://www.25hoursaday.com/weblog/2009/01/16/BuildingScalableDatabasesProsAndConsOfVariousDatabaseShardingSchemes.aspx"&gt;Building Scalable Databases: Pros and Cons of Various Database Sharding Schemes&lt;/a&gt;. Dare says database sharding is:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;em&gt;the process of splitting up a database across multiple machines to improve the scalability of an application&lt;/em&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;which is exactly what SQL Azure proposes except that they use the word “partitioning” rather than “splitting” and its across multiple virtual instances rather than multiple machines.&lt;/p&gt;  &lt;p&gt;Dare talks about numerous disadvantages of sharding but the key one is that you lose the benefit of referential integrity (RI) which is, to my mind, THE main reason for using a relational database in the first place. Let’s take a look at a simple example. Suppose (incredibly hypothetically) that Amazon adopted SQL Azure and chose to shard its product catalogue across multiple instances; they then face the very real situation where it is not possible to have full RI between their products, customers and the orders that link them together. An order would most likely contain products from different shards therefore which shard should the order live on? Maybe Amazon could shard the order line items according by product but how do they enforce RI back to the order header and, onward, to the customer? Clearly Amazon can’t enforce RI across shards so they have to use some different data storage mechanism in which case why bother using SQL Azure at all?&lt;/p&gt;  &lt;p&gt;This is an extreme case but its one that you have to consider when using SQL Azure and the problem is exacerbated when you consider that the maximum size of a database in SQL Azure is 10GB. “Oh, you want to store your new product in my database? You say it’ll only use up 5KB of storage? No can do, you’re maxed out! Sorry!” (Although arguably the 10GB limit is an advantage because at least your shard’s maximum limit is absolute rather than theoretical.)&lt;/p&gt;  &lt;p&gt;There are of course solutions to these problems and they generally involve writing your application to workaround these limitations. Doing that is, however, an expensive and time-consuming undertaking which is something anyone adopting SQL Azure needs to be aware of and you won’t find it written down anywhere in the SQL Azure documentation.&lt;/p&gt;  &lt;p&gt;Be aware, that’s all I’m saying! If your database is not going to grow anywhere near 10GB then SQL Azure might well be a good fit for you.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15982" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/azure/default.aspx" /><category term="sharding" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/sharding/default.aspx" /><category term="SQL Azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Azure/default.aspx" /></entry><entry><title>.Net Service bus demo by EasyJet at UK Azure Net user group meeting</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/30/net-service-bus-demo-by-easyjet-at-uk-azure-net-user-group-meeting.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/30/net-service-bus-demo-by-easyjet-at-uk-azure-net-user-group-meeting.aspx</id><published>2009-07-30T14:38:00Z</published><updated>2009-07-30T14:38:00Z</updated><content type="html">&lt;p&gt;Yesterday evening I attended the second meeting of the UK Azure Net user group in London Victoria. Normally this wouldn’t in itself be blog worthy but one of the presentations given really piqued my interest and I wanted to draw some attention to it.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://cid-61ea3f98c8957a87.profile.live.com/"&gt;Bert Craven&lt;/a&gt; from &lt;a href="http://easyjet.com/"&gt;EasyJet&lt;/a&gt; gave a demo of an application that EasyJet are going to be trialling in the near future, one that allows their employees to use handheld devices to check-in passengers rather than have those passengers queue up at check-in desks. The really compelling part of the demo though was the underlying technology; Bert’s team are using the Azure .Net Service Bus to expose service endpoints from their &lt;em&gt;existing &lt;/em&gt;firewalled systems in order to make them consumable from the handheld devices. It was (as I fed back to Bert last night) by some distance the best Azure demo I’ve seen yet&lt;/p&gt;  &lt;p&gt;Bert claimed that they had to do little more than change a configuration file in order to expose their services in this way and that’s when I had the “AHA” moment that had thus far escaped me and I began to understand why people like &lt;a href="http://blogs.conchango.com/simonevans/"&gt;Simon Evans&lt;/a&gt; and &lt;a href="http://blogs.msdn.com/simondavies/default.aspx"&gt;Simon Davies&lt;/a&gt; have been speaking so enthusiastically about the .Net Service Bus. I realised the power inherent in this thing - it allows you to deliver features that previously would have taken reams and reams of code using little more than a configuration change.&lt;/p&gt;  &lt;p&gt;Bert’s presentation included a demo where a service and a client were able to communicate via a service bus relay in under a second – this involved two round trips to a datacentre on the west coast of the US no less. He also showed data being synchronised between two handheld devices (running on emulators) via the service bus and again in sub-second intervals. To say this was impressive is an understatement.&lt;/p&gt;  &lt;p&gt;Bert has blogged about his talk at &lt;a href="http://bertcraven.spaces.live.com/blog/cns!61EA3F98C8957A87!480.entry"&gt;Azure Service Bus Presentation and Demo Code&lt;/a&gt; and as the title suggests he has made demo code available there. I’m going away now to try it for myself.&lt;/p&gt;  &lt;p&gt;That’s all really. The .Net Service Bus is the ace in the pack of Microsoft’s Azure offering and if you work in B2B scenarios or with distributed systems it could be well worth spending some time understanding it.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;UPDATE: A video of Bert’s session is now available:&lt;/p&gt;  &lt;div id="xrPlayerEmbededDiv68f8580ab54342349617c9c83a0e1353"&gt;&lt;object id="xrPlayerEmbeded68f8580ab54342349617c9c83a0e1353" classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000" codebase="http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=9,0,124,0" width="640" height="360"&gt;&lt;param name="movie" value="http://exposureroom.com/flash/XRVideoPlayer2.swf?domain=exposureroom.com/&amp;amp;assetId=68f8580ab54342349617c9c83a0e1353&amp;amp;size=md&amp;amp;titleColor=#ffffff" /&gt;&lt;param name="allowNetworking" value="all" /&gt;&lt;param name="quality" value="best" /&gt;&lt;param name="wmode" value="transparent" /&gt;&lt;param name="allowScriptAccess" value="always" /&gt;&lt;param name="allowFullScreen" value="True" /&gt;&lt;embed name="xrPlayerEmbeded68f8580ab54342349617c9c83a0e1353" type="application/x-shockwave-flash" pluginspage="http://www.macromedia.com/go/getflashplayer" src="http://exposureroom.com/flash/XRVideoPlayer2.swf?domain=exposureroom.com/&amp;amp;assetId=68f8580ab54342349617c9c83a0e1353&amp;amp;size=md&amp;amp;titleColor=#ffffff" quality="best" width="640" height="360" allowScriptAccess="always" allowFullScreen="True"&gt;&lt;/embed&gt;&lt;/object&gt;    &lt;div&gt;&lt;a title="UK Azure User Group Meeting#2 Talk #2: EasyJet and Azure (Bert Craven) by UK AzureUserGroup:View it on ExposureRoom" href="http://exposureroom.com/68f8580ab54342349617c9c83a0e1353"&gt;View on ExposureRoom&lt;/a&gt;&lt;/div&gt; &lt;/div&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15957" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/azure/default.aspx" /><category term="Service Bus" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/Service+Bus/default.aspx" /><category term="Easyjet" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/Easyjet/default.aspx" /></entry><entry><title>Sync is the word</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/22/sync-is-the-word.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/22/sync-is-the-word.aspx</id><published>2009-07-22T16:56:22Z</published><updated>2009-07-22T16:56:22Z</updated><content type="html">&lt;p&gt;I &lt;a href="http://twitter.com/jamiet/status/2780989286"&gt;recently tweeted&lt;/a&gt; the following rather silly little ditty…&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;em&gt;Sync is the word       &lt;br /&gt;Its in Groove, its in GMail        &lt;br /&gt;Sync works any time, any place, in motion        &lt;br /&gt;Sync is the way we'll be storing&lt;/em&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;Ahem, yes. Well… silly but with a relevant point. Sync is becoming an integral aspect of how we build and consume apps and I expect that trend to increase in the years to come. Let’s look at the evidence. Big tech companies are tripping up over themselves with their efforts to build synchronisation capabilities into their products:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;strong&gt;Google&lt;/strong&gt; use &lt;a href="http://gears.google.com/"&gt;Google Gears&lt;/a&gt; to enable you to &lt;a href="http://gmailblog.blogspot.com/2009/01/new-in-labs-offline-gmail.html"&gt;read your GMail offline&lt;/a&gt; as well as &lt;a href="http://www.google.com/help/reader/offline.html"&gt;your Google Reader subscriptions&lt;/a&gt;. They also have &lt;a href="http://www.google.com/apps/intl/en/business/outlook_sync.html#utm_medium=et&amp;amp;utm_source=us-en-ogb&amp;amp;utm_campaign=en"&gt;Google Apps Sync for Microsoft Outlook&lt;/a&gt; which enables you to synchronise Microsoft Outlook with GMail, Google Calendar and Google Contacts.&lt;/li&gt;    &lt;li&gt;&lt;strong&gt;Apple&lt;/strong&gt; pioneered syncing capabilities with &lt;a href="http://www.apple.com/itunes/download/"&gt;iTunes&lt;/a&gt; and iPod and are now pushing further into the sync space with &lt;a href="http://www.me.com/"&gt;MobileMe&lt;/a&gt;&lt;/li&gt;    &lt;li&gt;&lt;strong&gt;Twitter &lt;/strong&gt;has a plethora of apps available for syncing your Twitter feed to an offline store including &lt;a href="http://tweetdeck.com/"&gt;Tweetdeck&lt;/a&gt; and &lt;a href="http://www.thirteen23.com/experiences/desktop/blu/"&gt;Blu&lt;/a&gt; to name but two&lt;/li&gt;    &lt;li&gt;&lt;strong&gt;Microsoft&lt;/strong&gt; have been in the sync game for a fair while, most prominently through the ability to synchronise email between Exchange &amp;amp; Outlook and between Exchange &amp;amp; mobile phone (via &lt;a href="http://msdn.microsoft.com/en-us/library/ms879772.aspx"&gt;ActiveSync&lt;/a&gt;) – capabilities that are now available to consumers via &lt;a href="http://mail.live.com/"&gt;Hotmail&lt;/a&gt; and &lt;a href="http://download.live.com/wlmail"&gt;Windows Live Mail&lt;/a&gt;. They are also investing heavily in synchronisation platforms such as the &lt;a href="http://code.msdn.microsoft.com/sync"&gt;Sync Framework&lt;/a&gt; and &lt;a href="http://www.mesh.com"&gt;Live Mesh&lt;/a&gt;.&lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;I often hear that we are living in an increasingly connected world but in some ways the opposite is true, we are actually living in an increasingly &lt;em&gt;dis&lt;/em&gt;connected world due to the increasing number of devices in our pocket that are online either some or none of the time. Until online connectivity is ubiquitous sync is an essential part of any smartphone platform.&lt;/p&gt;  &lt;p&gt;Indeed, almost five years ago &lt;a href="http://www.russellbeattie.com/blog/about"&gt;Russell Beattie&lt;/a&gt; said:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;em&gt;“Syncing is *THE* most important piece of technology in the future of mobility. Voice is and will be the number one service, but after that it's syncing. Syncing! SYNCING!”&lt;/em&gt;      &lt;br /&gt;&lt;em&gt;from &lt;/em&gt;&lt;a href="http://www.russellbeattie.com/notebook/1008086.html"&gt;&lt;em&gt;Syncing. Syncing! Syncing! Syncing! SYNCING!!!&lt;/em&gt;&lt;/a&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;I quite agree! More about sync to follow…&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitpic.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15900" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="sync" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/sync/default.aspx" /></entry><entry><title>String Aggregation in T-SQL &amp; PL-SQL : SQL Nugget</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/16/string-aggregation-in-t-sql-amp-pl-sql.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/16/string-aggregation-in-t-sql-amp-pl-sql.aspx</id><published>2009-07-16T12:32:00Z</published><updated>2009-07-16T12:32:00Z</updated><content type="html">&lt;P&gt;In my current day job I’m doing a lot of work against an Oracle back-end and I’ve just come across a situation where I need to do some string aggregation. Effectively I needed to turn this:&lt;/P&gt;
&lt;TABLE border=1 cellSpacing=0 cellPadding=2 width=400&gt;
&lt;TBODY&gt;
&lt;TR&gt;
&lt;TD&gt;
&lt;H5&gt;Parent&lt;/H5&gt;&lt;/TD&gt;
&lt;TD&gt;
&lt;H5&gt;Child&lt;/H5&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Charles&lt;/TD&gt;
&lt;TD&gt;William&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Charles&lt;/TD&gt;
&lt;TD&gt;Harry&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Anne&lt;/TD&gt;
&lt;TD&gt;Peter&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Anne&lt;/TD&gt;
&lt;TD&gt;Zara&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Andrew&lt;/TD&gt;
&lt;TD&gt;Beatrice&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Andrew&lt;/TD&gt;
&lt;TD&gt;Eugenie&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;
&lt;P&gt;into this:&lt;/P&gt;
&lt;TABLE border=1 cellSpacing=0 cellPadding=2 width=400&gt;
&lt;TBODY&gt;
&lt;TR&gt;
&lt;TD&gt;
&lt;H5&gt;Parent&lt;/H5&gt;&lt;/TD&gt;
&lt;TD&gt;
&lt;H5&gt;Children&lt;/H5&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Charles&lt;/TD&gt;
&lt;TD&gt;William,Harry&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Anne&lt;/TD&gt;
&lt;TD&gt;Peter,Zara&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD&gt;Andrew&lt;/TD&gt;
&lt;TD&gt;Eugenie,Beatrice&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;
&lt;P&gt;In other words I wanted to take a list of children per parent and produce a comma-delimited list of each of their children.&lt;/P&gt;
&lt;P&gt;I know how to do this in T-SQL, you use the FOR XML PATH(‘’) construct like so:&lt;/P&gt;
&lt;DIV id=codeSnippetWrapper&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;" id=codeSnippet&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;with&lt;/SPAN&gt; t  &lt;SPAN style="COLOR:#0000ff;"&gt;as&lt;/SPAN&gt;(&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Charles'&lt;/SPAN&gt; parent, &lt;SPAN style="COLOR:#ff0000;"&gt;'William'&lt;/SPAN&gt; child &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Charles'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Harry'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Anne'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Peter'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Anne'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Zara'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Andrew'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Beatrice'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Andrew'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Eugenie'&lt;/SPAN&gt; &lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt;)&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;SELECT&lt;/SPAN&gt; parent, STUFF( ( &lt;SPAN style="COLOR:#0000ff;"&gt;SELECT&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;','&lt;/SPAN&gt;+ child &lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt;                        &lt;SPAN style="COLOR:#0000ff;"&gt;FROM&lt;/SPAN&gt; t a &lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt;                        &lt;SPAN style="COLOR:#0000ff;"&gt;WHERE&lt;/SPAN&gt; b.parent = a.parent &lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt;                        &lt;SPAN style="COLOR:#0000ff;"&gt;FOR&lt;/SPAN&gt; XML &lt;SPAN style="COLOR:#0000ff;"&gt;PATH&lt;/SPAN&gt;(&lt;SPAN style="COLOR:#ff0000;"&gt;''&lt;/SPAN&gt;)),1 ,1, &lt;SPAN style="COLOR:#ff0000;"&gt;''&lt;/SPAN&gt;)  children&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;FROM&lt;/SPAN&gt; t b &lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;GROUP&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;BY&lt;/SPAN&gt; parent&lt;/FONT&gt;&lt;/FONT&gt;&lt;/PRE&gt;&lt;/DIV&gt;&lt;/DIV&gt;
&lt;P&gt;which, yes, turned this:&lt;/P&gt;
&lt;P&gt;&lt;A href="http://blogs.conchango.com/blogs/jamiethomson/image_1D376E50.png"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH:0px;DISPLAY:inline;BORDER-TOP-WIDTH:0px;BORDER-BOTTOM-WIDTH:0px;BORDER-LEFT-WIDTH:0px;" title=image border=0 alt=image src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_6E71B5AD.png" width=187 height=165&gt;&lt;/A&gt; &lt;/P&gt;
&lt;P&gt;into this:&lt;/P&gt;
&lt;P&gt;&lt;A href="http://blogs.conchango.com/blogs/jamiethomson/image_46CB3983.png"&gt;&lt;IMG style="BORDER-RIGHT-WIDTH:0px;DISPLAY:inline;BORDER-TOP-WIDTH:0px;BORDER-BOTTOM-WIDTH:0px;BORDER-LEFT-WIDTH:0px;" title=image border=0 alt=image src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_3B357C44.png" width=244 height=141&gt;&lt;/A&gt; &lt;/P&gt;
&lt;P&gt;Unfortunately I didn’t know how to accomplish it in Oracle however after a bit of searching around I found the answer:&lt;/P&gt;
&lt;DIV id=codeSnippetWrapper&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;" id=codeSnippet&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;with&lt;/SPAN&gt; t  &lt;SPAN style="COLOR:#0000ff;"&gt;as&lt;/SPAN&gt;(&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Charles'&lt;/SPAN&gt; parent, &lt;SPAN style="COLOR:#ff0000;"&gt;'William'&lt;/SPAN&gt; child &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; dual &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Charles'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Harry'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; dual &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Anne'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Peter'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; dual &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Anne'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Zara'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; dual &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Andrew'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Beatrice'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; dual &lt;SPAN style="COLOR:#0000ff;"&gt;union&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; &lt;SPAN style="COLOR:#ff0000;"&gt;'Andrew'&lt;/SPAN&gt;, &lt;SPAN style="COLOR:#ff0000;"&gt;'Eugenie'&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; dual&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt;)&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;select&lt;/SPAN&gt; parent, rtrim(xmlagg(xmlelement(e,child || &lt;SPAN style="COLOR:#ff0000;"&gt;','&lt;/SPAN&gt;))&lt;/FONT&gt;&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4 face="Lucida Console"&gt;                .&lt;SPAN style="COLOR:#0000ff;"&gt;extract&lt;/SPAN&gt;(&lt;SPAN style="COLOR:#ff0000;"&gt;'//text()'&lt;/SPAN&gt;),&lt;SPAN style="COLOR:#ff0000;"&gt;','&lt;/SPAN&gt;) childs &lt;SPAN style="COLOR:#0000ff;"&gt;from&lt;/SPAN&gt; t&lt;/FONT&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:'Courier New', courier, monospace;DIRECTION:ltr;BORDER-TOP-STYLE:none;COLOR:black;FONT-SIZE:8pt;BORDER-LEFT-STYLE:none;OVERFLOW:visible;PADDING-TOP:0px;"&gt;&lt;FONT size=4&gt;&lt;FONT face="Lucida Console"&gt;&lt;SPAN style="COLOR:#0000ff;"&gt;group&lt;/SPAN&gt; &lt;SPAN style="COLOR:#0000ff;"&gt;by&lt;/SPAN&gt; parent&lt;/FONT&gt;&lt;/FONT&gt;&lt;/PRE&gt;&lt;/DIV&gt;&lt;/DIV&gt;
&lt;P&gt;So, now you know. And so will I if I ever need to find this again!&lt;/P&gt;
&lt;P&gt;&lt;A href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/A&gt;&lt;/P&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15863" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="SQL Server" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server/default.aspx" /><category term="Oracle" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/Oracle/default.aspx" /><category term="T-SQL" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/T-SQL/default.aspx" /><category term="Nugget" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/Nugget/default.aspx" /><category term="pl-sql" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/pl-sql/default.aspx" /></entry><entry><title>The Longest Tweet</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/10/the-longest-tweet.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/10/the-longest-tweet.aspx</id><published>2009-07-10T10:59:45Z</published><updated>2009-07-10T10:59:45Z</updated><content type="html">&lt;p&gt;I read an article today called &lt;a href="http://www.forbes.com/2009/07/09/longest-tweet-ever-technology-internet-forbes.html"&gt;The Longest Tweet In History&lt;/a&gt; which explained how it is now possible to send Tweets via Twitter that are longer than the supposed 140 character limit.&lt;/p&gt;  &lt;p&gt;As it happens I’ve written a noddy app called &lt;a href="http://tweetpoll.cloudapp.net/"&gt;Tweetpoll&lt;/a&gt; onto Windows Azure that periodically polls Twitter’s public timeline to determine the distribution of Tweet length and displays that distribution at &lt;a title="http://tweetpoll.cloudapp.net/" href="http://tweetpoll.cloudapp.net/"&gt;http://tweetpoll.cloudapp.net/&lt;/a&gt;. Here’s a screenshot of the latest distribution:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_5216863A.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_3CB8D0D2.png" width="713" height="243" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;This is based on a sample set of 2940150 tweets (so far). Unsurprisingly its a fairly smooth curve (I can’t explain the peaks though – probably a bug in my code) although before I started I expected the frequency of tweet lengths to increase exponentially and clearly that’s not the case because we have a sustained increase around 30-50 characters before dropping off again.&lt;/p&gt;  &lt;p&gt;Anyway, I digress. Its been running a couple of months now and I became puzzled when, soon after launching it, I began getting results that were greater than 140 characters (as you can see on the graph above). I didn’t have an explanation for those numbers so I set about uncovering why. Three days ago I deployed an update to the app so that it now explicitly captures all tweets greater than 140 characters and stores them somewhere. Thanks to &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2009/07/06/linqpad-and-azure.aspx"&gt;my new best friend&lt;/a&gt; LINQPad and the following query:&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var results = svc.LongTweetsTable.ToList().Select(r =&amp;gt; &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; { r.RowKey, Length = r.RowKey.Length})&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;                    .OrderByDescending(r =&amp;gt; r.Length );&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;I can now find out what’s going on in those tweets:&lt;/p&gt;
&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_2350CD98.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_28BF3E3C.png" width="701" height="346" /&gt;&lt;/a&gt; 

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;Notice anything about those tweets? They all contain either “&amp;amp;lt;” or “&amp;amp;gt;” which are the escape characters for less-than/greater-than symbols in markup and hence the mystery is explained; the markup for tweets might well be longer than the actual tweet itself. Pretty logical if you think about it although it didn’t occur to me without actually examining the data. That’s an important lesson learned – make sure you know your data intimately.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://twitgoo.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15811" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="twitter" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/twitter/default.aspx" /><category term="windows azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/windows+azure/default.aspx" /><category term="azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/azure/default.aspx" /><category term="tweetpoll" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/tweetpoll/default.aspx" /><category term="LINQPad" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/LINQPad/default.aspx" /><category term="LINQ" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/LINQ/default.aspx" /></entry><entry><title>Kapow – ETL for HTML</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/08/kapow-etl-for-html.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/08/kapow-etl-for-html.aspx</id><published>2009-07-08T21:29:21Z</published><updated>2009-07-08T21:29:21Z</updated><content type="html">&lt;p&gt;A couple of weeks ago &lt;a href="http://cid-7b84b0f2c239489a.profile.live.com/"&gt;Chris Webb&lt;/a&gt; sent me an IM telling me about a new technology he’d just seen a demo of called Kapow. Chris has since blogged about it at &lt;a href="http://cwebbbi.spaces.live.com/blog/cns!7B84B0F2C239489A!4586.entry"&gt;Kapow Technologies&lt;/a&gt; and in that blog post he described Kapow as:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;em&gt;“a cross between a screenscraper and an ETL tool”&lt;/em&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;That’s a very apt description, for what Kapow enables you to do is build what are effectively ETL packages (although they call them Robots) that extract data from HTML pages and either (a) load it into a database for you or (more interestingly) (b) make that data available as a RESTful web service. A robot pulls out the data embedded in the markup and presents it as strongly-typed data entities.&lt;/p&gt;  &lt;p&gt;I never really thought about a web page as being structured data but actually nothing could be further from the truth; HTML is after all nothing more than a hierarchical dataset with the added luxury of metadata - otherwise known as the Document Object Model (DOM). Kapow takes that structured data and its rich metadata, parses it for us, and presents it to us in ways that are easily consumable.&lt;/p&gt;  &lt;p&gt;I was given a tour of Kapow by their UK rep Dominic Dunkley. Dominic had a great demo where he built, from scratch, a Kapow robot that:&lt;/p&gt;  &lt;ol&gt;   &lt;li&gt;visited a search engine before…&lt;/li&gt;    &lt;li&gt;…entering a search term (in this case “EMC”)&lt;/li&gt;    &lt;li&gt;iterated over each page of results within which it…&lt;/li&gt;    &lt;li&gt;…iterated over each search result….&lt;/li&gt;    &lt;li&gt;…and extracted the title, URL and description before…&lt;/li&gt;    &lt;li&gt;…making all the search results available in a strongly-typed dataset&lt;/li&gt; &lt;/ol&gt;  &lt;p&gt;It all took about 15 minutes and that was with him pausing to explain it step-by-step. That demo really grabbed my attention because I realised that not only does Kapow have the ability to parse the DOM but it also has notions of &lt;em&gt;workflow &lt;/em&gt;and &lt;em&gt;data composition&lt;/em&gt; which are of course two vital features of any ETL tool.&lt;/p&gt;  &lt;p&gt;I’m reminded of 3scale Networks that I mentioned in my blog post &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2009/06/23/enterprise-mashups.aspx"&gt;Enterprise Mashups&lt;/a&gt; a couple of weeks back (it was actually after reading that blog post that Chris got in touch with me); in that I describe how 3scale have taken information made freely available by the United Nations at &lt;a title="http://data.un.org/" href="http://data.un.org/"&gt;http://data.un.org/&lt;/a&gt; and made it available as an easily consumable data service. In essence this same service could be built using Kapow without being monotonously handcrafted which is how I suspect 3scale did it.&lt;/p&gt;  &lt;p&gt;I’m hoping I have some reason to use Kapow in the future because I think there are some very interesting scenarios that come into play here. Chiefly, as Chris pointed out in his blog post, we can pull data from any web site and use it for BI purposes. For example, suppose you work for an airline and you want to easily compare your advertised prices with those of your competitors – Kapow is a one-stop shop for enabling that.&lt;/p&gt;  &lt;p&gt;Impressive stuff. If you’re interested go and check out Kapow for yourself at &lt;a title="http://kapowtech.com/index.php/solutions/web-and-business-intelligence" href="http://kapowtech.com/index.php/solutions/web-and-business-intelligence"&gt;http://kapowtech.com/index.php/solutions/web-and-business-intelligence&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15795" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="Kapow" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/Kapow/default.aspx" /><category term="etl" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/etl/default.aspx" /></entry><entry><title>LINQPad and Azure</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/06/linqpad-and-azure.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/06/linqpad-and-azure.aspx</id><published>2009-07-06T15:51:19Z</published><updated>2009-07-06T15:51:19Z</updated><content type="html">&lt;p&gt;Since I started dealing with Azure tables I’ve become frustrated that there is no ad-hoc query tool, nothing equivalent to SQL Server Management Studio. Then I heard about &lt;a href="http://www.linqpad.net/"&gt;LINQPad&lt;/a&gt; and figured there must be a way to use it to query Azure tables using LINQ and indeed there is as I’ll explain here (this post assumes that you have a working knowledge of LINQPad and Azure storage).&lt;/p&gt;  &lt;p&gt;Firstly you need to reference the correct assemblies. I’ve been using the StorageClient that is provided with the Azure Samples in the Azure SDK (&lt;a href="http://www.microsoft.com/downloads/details.aspx?familyid=B44C10E8-425C-417F-AF10-3D2839A5A362&amp;amp;displaylang=en"&gt;March 2009 CTP of the SDK linked here&lt;/a&gt;) which in turn uses ADO.Net Services client library hence you’ll need to reference the following assemblies:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;StorageClient.dll &lt;/li&gt;    &lt;li&gt;System.Data.Services.Client.dll &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;You’ll also need to reference your &lt;font color="#008080"&gt;DataServiceContext&lt;/font&gt; implementation. For demo purposes I am pulling data from my &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2009/05/06/tweetpoll-my-first-windows-azure-application-is-live.aspx"&gt;Tweetpoll&lt;/a&gt; application so I’m referencing the assembly containing my &lt;font color="#008080"&gt;TweetPollDataServiceContext&lt;/font&gt; class - TweetPoll.dll:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_2E1549B7.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_4ABE98FF.png" width="658" height="280" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;We also need to import the namespaces into LINQPad. You’ll need the following:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Microsoft.Samples.ServiceHosting.StorageClient &lt;/li&gt;    &lt;li&gt;System.Data.Services.Client &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;plus whichever namespace holds your &lt;font color="#008080"&gt;DataServiceContext&lt;/font&gt; implementation:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_3ACF543B.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_571C965B.png" width="658" height="280" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Thereafter you just need to write some code. You need to supply the following:&lt;/p&gt;  &lt;ol&gt;   &lt;li&gt;Your Azure storage account name &lt;/li&gt;    &lt;li&gt;Your Azure storage shared key &lt;/li&gt;    &lt;li&gt;The name of your DataServiceContext implementation &lt;/li&gt;    &lt;li&gt;A LINQ query &lt;/li&gt; &lt;/ol&gt;  &lt;p&gt;Here’s my code:&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var accountName = &lt;span style="color:#006080;"&gt;&amp;quot;jamiekt&amp;quot;&lt;/span&gt;;  &lt;span style="color:#008000;"&gt;// 1) Enter your storage account name&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var sharedKey = &lt;span style="color:#006080;"&gt;&amp;quot;smXblLn+UgXR6ysbIhoeTfE3dyOZhAaONXOP/SUawRSLzCWwDXrhkpRG45A5aeAP5IEjSBEN2mEmPM8O5HnWGQ==&amp;quot;&lt;/span&gt;; &lt;span style="color:#008000;"&gt;// 2) SharedKey&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var uri = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; System.Uri(&lt;span style="color:#006080;"&gt;&amp;quot;http://table.core.windows.net/&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var tableAccountInfo = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; StorageAccountInfo(uri, &lt;span style="color:#0000ff;"&gt;null&lt;/span&gt;, accountName, sharedKey);&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var svc = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; TweetPollDataServiceContext(tableAccountInfo); &lt;span style="color:#008000;"&gt;// 3) Specify your DataServiceContext&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&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:'Courier New', 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:#008000;"&gt;// 4) Supply your query&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var query = from row &lt;span style="color:#0000ff;"&gt;in&lt;/span&gt; svc.Table &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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;                       select row;&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;query.Dump();&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;br /&gt;And here are the results in LINQPad:&lt;/div&gt;

&lt;div&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image12_363511FF.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image12_thumb_05525A94.png" width="708" height="749" /&gt;&lt;/a&gt; &lt;/div&gt;

&lt;div&gt;Hope that helps!!!&lt;/div&gt;

&lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15756" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="windows azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/windows+azure/default.aspx" /><category term="azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/azure/default.aspx" /><category term="LINQPad" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/LINQPad/default.aspx" /><category term="LINQ" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/LINQ/default.aspx" /></entry><entry><title>SSIS Connect digest 2009-07-05</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/05/ssis-connect-digest-2009-07-05.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/05/ssis-connect-digest-2009-07-05.aspx</id><published>2009-07-05T08:31:58Z</published><updated>2009-07-05T08:31:58Z</updated><content type="html">&lt;p&gt;Here is the latest collection of submissions to &lt;a href="http://connect.microsoft.com/sqlserver/feedback"&gt;http://connect.microsoft.com/sqlserver/feedback&lt;/a&gt; that pertain to SQL Server Integration Services (SSIS) and which I think are worthy of your attention. &lt;/p&gt;  &lt;p&gt;Take a read of the items below and if you agree with the aim of the submission, please click through and vote for it – it only takes a few seconds. If you want to leave a comment supporting your vote, that would be even better.&lt;/p&gt;  &lt;p&gt;Don’t feel obliged to vote on everything carte blanche, only vote for those that you would like the SSIS product team to concentrate on. Most of these are already closed but that doesn’t mean they can’t be opened again. And remember, voting really does make a difference; if you don’t believe me take a read of Doug Laudenschlager’s blog post &lt;a href="http://dougbert.com/blogs/dougbert/archive/2008/11/14/your-vote-on-microsoft-connect-influenced-sql-server-2008-service-pack-1.aspx"&gt;Your vote on Microsoft Connect influenced SQL Server 2008 Service Pack 1&lt;/a&gt;.&lt;/p&gt;  &lt;hr /&gt;  &lt;h3&gt;Ability to create an empty raw file with required metadata&lt;/h3&gt;  &lt;p&gt;In the raw file destination adapter, have the option to create the an empty raw file with the appropriate metadata when (for example) you close the raw file destination adapter editor.    &lt;br /&gt;Or perhaps just have a button in raw file destination adapter editor called &amp;quot;Go create an empty raw file&amp;quot;&lt;/p&gt;  &lt;p&gt;#225974 : Create an empty raw file with required metadata   &lt;br /&gt;(&lt;a title="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=225974" href="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=225974"&gt;https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=225974&lt;/a&gt;)&lt;/p&gt;  &lt;hr /&gt;  &lt;h3&gt;A better performing distinct component&lt;/h3&gt;  &lt;p&gt;SORT component is an asynchronous, fully blocking component. This makes sense of course but it seemed to me that if 'Remove rows with duplicate sort values' check box is checked then it could be made into a partially blocking component instead. &lt;/p&gt;  &lt;p&gt;Let me explain. We know that the component is only going to output one row for duplicates. That doesn't mean though that the output necessarily is required to be sorted does it? Hence, why not just give us a new component that puts every new combination of values into the pipeline as soon as it is encountered. Sure, it still has to do a SORT internally in order to determine whether a combination of values is new or not, but if the output doesn't need to be sorted, why bother waiting until we have all the values before we start processing them downstream?&lt;/p&gt;  &lt;p&gt;#244313 : SSIS: Improve performance of DISTINCT sort component   &lt;br /&gt;(&lt;a title="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=244313" href="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=244313"&gt;https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=244313&lt;/a&gt;)&lt;/p&gt;  &lt;hr /&gt;  &lt;h3&gt;Keep Raw files sorted&lt;/h3&gt;  &lt;p&gt;I have an input into a raw file destination that has IsSorted=TRUE. Any output from a raw file source that uses that raw file will have IsSorted=FALSE.&lt;/p&gt;  &lt;p&gt;Proposed solution: Store IsSorted property of the input and SortKey property of the columns in a raw file&lt;/p&gt;  &lt;p&gt;#242351 : Should IsSorted metadata be stored in raw files?   &lt;br /&gt;(&lt;a title="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=242351" href="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=242351"&gt;https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=242351&lt;/a&gt;)&lt;/p&gt;  &lt;hr /&gt;  &lt;h3&gt;Improve DtExecUI by adding a package browser&lt;/h3&gt;  &lt;p&gt;There is no ability be able to browse the package and select a value to be set via the /SET option of dtexec. Add the ability to browse the package. Simply use the browser that is used in the configuration wizard.&lt;/p&gt;  &lt;p&gt;#124577 : Put package browser on Set Values tab of dtexecui.exe   &lt;br /&gt;(&lt;a title="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=124577" href="https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=124577"&gt;https://connect.microsoft.com/SQLServer/feedback/ViewFeedback.aspx?FeedbackID=124577&lt;/a&gt;)&lt;/p&gt;  &lt;p&gt;   &lt;hr /&gt; &lt;/p&gt;  &lt;p&gt;To read more in this series of SSIS Connect digests go to &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/connect/digest/SSIS/default.aspx"&gt;SSIS Connect Digest&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15746" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="SQL Server Integration Services" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server+Integration+Services/default.aspx" /><category term="SQL Server" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server/default.aspx" /><category term="SSIS" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SSIS/default.aspx" /><category term="connect" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/connect/default.aspx" /><category term="feedback" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/feedback/default.aspx" /><category term="digest" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/digest/default.aspx" /></entry><entry><title>DRY SQL</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/07/02/dry-sql.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/07/02/dry-sql.aspx</id><published>2009-07-02T21:05:00Z</published><updated>2009-07-02T21:05:00Z</updated><content type="html">&lt;p&gt;I recently inherited some SQL that someone else had written and had the job of “tidying it up” before it gets pushed out to production. Here’s a slightly simplified (yes, simplified) version of that SQL:&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum1"&gt;   1:&lt;/span&gt; &lt;font color="#008000"&gt;--options&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum2"&gt;   2:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum3"&gt;   3:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum4"&gt;   4:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum5"&gt;   5:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum6"&gt;   6:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum7"&gt;   7:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;&lt;font color="#ff00ff"&gt;sum&lt;/font&gt;&lt;/span&gt;(volume) &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; total_volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum8"&gt;   8:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t1&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum9"&gt;   9:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'options'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum10"&gt;  10:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;group&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;by&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum11"&gt;  11:&lt;/span&gt;         asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum12"&gt;  12:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum13"&gt;  13:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum14"&gt;  14:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum15"&gt;  15:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum16"&gt;  16:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;union&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;&lt;font color="#808080"&gt;all&lt;/font&gt;&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum17"&gt;  17:&lt;/span&gt; &lt;font color="#008000"&gt;--swaps&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum18"&gt;  18:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum19"&gt;  19:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum20"&gt;  20:&lt;/span&gt;                     &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum21"&gt;  21:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum22"&gt;  22:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum23"&gt;  23:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum24"&gt;  24:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;&lt;font color="#ff00ff"&gt;sum&lt;/font&gt;&lt;/span&gt;(volume) &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; total_volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum25"&gt;  25:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t2&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum26"&gt;  26:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'swaps'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum27"&gt;  27:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;group&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;by&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum28"&gt;  28:&lt;/span&gt;         asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum29"&gt;  29:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum30"&gt;  30:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum31"&gt;  31:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum32"&gt;  32:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;The SQL basically takes data from two tables (t1 &amp;amp; t2), aggregates each, carries out some inline expressions (for &lt;font face="Lucida Console"&gt;profit_or_loss&lt;/font&gt;) and finally unions it all together. On the surface it looks fine but there are a few problems here, namely that there is a lot of repeated code; it violates the principle of &lt;a href="http://en.wikipedia.org/wiki/Don%27t_repeat_yourself"&gt;don’t repeat yourself&lt;/a&gt; (DRY) which preaches “single point of maintenance” and “deduplication” of code. If you take the time to check it out you’ll see that identical aggregations are carried out on the two datasets (lines 7 &amp;amp; 24) as are the same conversions for &lt;font face="Lucida Console"&gt;profit_or_loss &lt;/font&gt;(lines 3-5 &amp;amp; 19-22). Not only that but we have expressions appearing in both the SELECT clause and GROUP BY of both halves of the query (lines 12-14 &amp;amp; 29-31), another violation of DRY.&lt;/p&gt;

&lt;p&gt;A bit of refactoring is called for. First job, eliminate those expressions for &lt;font face="Lucida Console"&gt;profit_or_loss &lt;/font&gt;which appear in the GROUP BY clauses:&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum1"&gt;   1:&lt;/span&gt; &lt;font color="#008000"&gt;--options&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum2"&gt;   2:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum3"&gt;   3:&lt;/span&gt; ,        profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum4"&gt;   4:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum5"&gt;   5:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;&lt;font color="#ff00ff"&gt;sum&lt;/font&gt;&lt;/span&gt;(volume) &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; total_volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum6"&gt;   6:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    (&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum7"&gt;   7:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum8"&gt;   8:&lt;/span&gt;         ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum9"&gt;   9:&lt;/span&gt;         ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum10"&gt;  10:&lt;/span&gt;                         &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum11"&gt;  11:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum12"&gt;  12:&lt;/span&gt;         ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum13"&gt;  13:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t1&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum14"&gt;  14:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'options'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum15"&gt;  15:&lt;/span&gt;         )t1&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum16"&gt;  16:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;group&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;by&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum17"&gt;  17:&lt;/span&gt;         asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum18"&gt;  18:&lt;/span&gt; ,        profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum19"&gt;  19:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum20"&gt;  20:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;union&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;&lt;font color="#808080"&gt;all&lt;/font&gt;&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum21"&gt;  21:&lt;/span&gt; &lt;font color="#008000"&gt;--swaps&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum22"&gt;  22:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum23"&gt;  23:&lt;/span&gt; ,        profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum24"&gt;  24:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum25"&gt;  25:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;&lt;font color="#ff00ff"&gt;sum&lt;/font&gt;&lt;/span&gt;(volume) &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; total_volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum26"&gt;  26:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    (&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum27"&gt;  27:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum28"&gt;  28:&lt;/span&gt;         ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum29"&gt;  29:&lt;/span&gt;         ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum30"&gt;  30:&lt;/span&gt;                         &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum31"&gt;  31:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum32"&gt;  32:&lt;/span&gt;         ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum33"&gt;  33:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t2&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum34"&gt;  34:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'swaps'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum35"&gt;  35:&lt;/span&gt;         )t2&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum36"&gt;  36:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;group&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;by&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum37"&gt;  37:&lt;/span&gt;         asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum38"&gt;  38:&lt;/span&gt; ,        profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum39"&gt;  39:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Ok cool, we’ve moved the expression for &lt;font face="Lucida Console"&gt;profit_or_loss&lt;/font&gt; into a subquery (aka derived table) and hence expressions have gone from our GROUP BY clauses … but we’ve still got DRY violations. The aggregation (lines 5 &amp;amp; 25) and expression for &lt;font face="Lucida Console"&gt;profit_or_loss &lt;/font&gt;(lines 9-11 &amp;amp; 29-31) still appear in two places. More refactoring….&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum1"&gt;   1:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum2"&gt;   2:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum3"&gt;   3:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;&lt;font color="#ff00ff"&gt;sum&lt;/font&gt;&lt;/span&gt;(volume) &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; total_volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum4"&gt;   4:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    (&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum5"&gt;   5:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum6"&gt;   6:&lt;/span&gt;         ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum7"&gt;   7:&lt;/span&gt;                         &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum8"&gt;   8:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum9"&gt;   9:&lt;/span&gt;         ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum10"&gt;  10:&lt;/span&gt;         ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum11"&gt;  11:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    (&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum12"&gt;  12:&lt;/span&gt;                 &lt;font color="#008000"&gt;--options&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum13"&gt;  13:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum14"&gt;  14:&lt;/span&gt;                 ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum15"&gt;  15:&lt;/span&gt;                 ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum16"&gt;  16:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t1&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum17"&gt;  17:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'options'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum18"&gt;  18:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;union&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;&lt;font color="#808080"&gt;all&lt;/font&gt;&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum19"&gt;  19:&lt;/span&gt;                 &lt;font color="#008000"&gt;--swaps&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum20"&gt;  20:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum21"&gt;  21:&lt;/span&gt;                 ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum22"&gt;  22:&lt;/span&gt;                 ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum23"&gt;  23:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t2&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum24"&gt;  24:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'swaps'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum25"&gt;  25:&lt;/span&gt;                 )t&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum26"&gt;  26:&lt;/span&gt;         )q&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum27"&gt;  27:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;group&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;by&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum28"&gt;  28:&lt;/span&gt;         asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum29"&gt;  29:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;There, much better; the aggregation only occurs once as does the expression for &lt;font face="Lucida Console"&gt;profit_or_loss&lt;/font&gt; (which in the code that I inherited occurred &lt;em&gt;four &lt;/em&gt;different times). Our SQL is DRY and its going to be a lot easier to maintain for whomever picks the code up from me.&lt;/p&gt;

&lt;p&gt;You’ll notice we’ve got 2 levels of nested subqueries (aka derived tables). I make no apologies for that - derived tables are a great mechanism for eliminating repeated code and if you take but one bit of advice away from this blog post it would be this: &lt;em&gt;&lt;strong&gt;derived tables are your friend&lt;/strong&gt;&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;Would you have refactored this the same way? Maybe you might have moved the derived tables into a dedicated view. Perhaps you might even have put the derived tables into a WITH clause like so:&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum1"&gt;   1:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;with&lt;/span&gt;    t &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; (&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum2"&gt;   2:&lt;/span&gt;         &lt;font color="#008000"&gt;--options&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum3"&gt;   3:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum4"&gt;   4:&lt;/span&gt;         ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum5"&gt;   5:&lt;/span&gt;         ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum6"&gt;   6:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t1&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum7"&gt;   7:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'options'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum8"&gt;   8:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;union&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;&lt;font color="#808080"&gt;all&lt;/font&gt;&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum9"&gt;   9:&lt;/span&gt;         &lt;font color="#008000"&gt;--swaps&lt;/font&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum10"&gt;  10:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum11"&gt;  11:&lt;/span&gt;         ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum12"&gt;  12:&lt;/span&gt;         ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum13"&gt;  13:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t2&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum14"&gt;  14:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;where&lt;/span&gt;    asset_class = &lt;span style="color:#ff0000;"&gt;'swaps'&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum15"&gt;  15:&lt;/span&gt; ),&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum16"&gt;  16:&lt;/span&gt; q &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt;    (&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum17"&gt;  17:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum18"&gt;  18:&lt;/span&gt;         ,        &lt;span style="color:#0000ff;"&gt;case&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;when&lt;/span&gt; volume &amp;gt; 0 &lt;span style="color:#0000ff;"&gt;then&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'profit'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum19"&gt;  19:&lt;/span&gt;                         &lt;span style="color:#0000ff;"&gt;else&lt;/span&gt; &lt;span style="color:#ff0000;"&gt;'loss'&lt;/span&gt; &lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum20"&gt;  20:&lt;/span&gt;                 &lt;span style="color:#0000ff;"&gt;end&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; profit_or_loss&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum21"&gt;  21:&lt;/span&gt;         ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum22"&gt;  22:&lt;/span&gt;         ,        volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum23"&gt;  23:&lt;/span&gt;         &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    t&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum24"&gt;  24:&lt;/span&gt; )&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum25"&gt;  25:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;select&lt;/span&gt;    asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum26"&gt;  26:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum27"&gt;  27:&lt;/span&gt; ,        &lt;span style="color:#0000ff;"&gt;&lt;font color="#ff00ff"&gt;sum&lt;/font&gt;&lt;/span&gt;(volume) &lt;span style="color:#0000ff;"&gt;as&lt;/span&gt; total_volume&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum28"&gt;  28:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;from&lt;/span&gt;    q&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum29"&gt;  29:&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;group&lt;/span&gt;    &lt;span style="color:#0000ff;"&gt;by&lt;/span&gt;&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum30"&gt;  30:&lt;/span&gt;         asset_class&lt;/font&gt;&lt;/font&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:'Courier New', courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;font size="4"&gt;&lt;font face="Lucida Console"&gt;&lt;span style="color:#606060;" id="lnum31"&gt;  31:&lt;/span&gt; ,        customer&lt;/font&gt;&lt;/font&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Let me know in the comments!&lt;/p&gt;

&lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@Jamiet&lt;/a&gt;&lt;/p&gt;

&lt;hr /&gt;

&lt;p&gt;Further reading:&lt;/p&gt;

&lt;p&gt;&lt;a href="http://www.nearinfinity.com/blogs/seth_schroeder/views_keep_your_sql_queries.html"&gt;Views keep your SQL queries DRY&lt;/a&gt; - Seth Schroeder&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15667" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="SQL Server" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server/default.aspx" /><category term="SQL" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL/default.aspx" /><category term="T-SQL" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/T-SQL/default.aspx" /><category term="DRY" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/DRY/default.aspx" /></entry><entry><title>Azure worker role development tips</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/06/29/azure-worker-role-development-tips.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/06/29/azure-worker-role-development-tips.aspx</id><published>2009-06-29T13:29:41Z</published><updated>2009-06-29T13:29:41Z</updated><content type="html">&lt;p&gt;Just lately I’ve been doing a lot of messing around with Windows Azure the main focus of which has been exploring Azure storage (tables, queues, blobs) and how those things can be manipulated from Azure worker roles. One output from that “messing around” has been my &lt;a href="http://tweetpoll.cloudapp.net/"&gt;Tweetpoll&lt;/a&gt; application (read more: &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2009/05/06/tweetpoll-my-first-windows-azure-application-is-live.aspx"&gt;Tweetpoll my first Windows Azure application is live&lt;/a&gt;).&lt;/p&gt;  &lt;p&gt;Since then I’ve found some blog resources that would have been useful during development had I found them earlier so I’m linking to them from here mainly so that I can easily find them again but also so that other people might be made aware of them because there’s some really good content here.&lt;/p&gt;  &lt;p&gt;Firstly, &lt;a href="http://blogs.msdn.com/domgreen"&gt;Dom Green&lt;/a&gt; has developed a library that provides rich application tracing capabilities on top of Azure’s bog standard logging mechanisms. Read more at &lt;a href="http://blogs.msdn.com/domgreen/archive/2009/06/29/azuretrace-managing-all-your-azure-logging-needs.aspx"&gt;AzureTrace … managing all your Azure Logging Needs&lt;/a&gt;. I’ve put together something slightly similar myself recently but its not as feature rich as Dominic’s and, as anyone at &lt;strike&gt;Conchango&lt;/strike&gt; &lt;a href="http://www.emc.com/services/index.htm"&gt;EMC Consulting&lt;/a&gt; will tell you, I’m no .Net expert by any stretch of the imagination so I’ll be working to put Dom’s library into my own stuff forthwith.&lt;/p&gt;  &lt;p&gt;Secondly, Dom &lt;a href="http://blogs.msdn.com/domgreen/archive/2009/02/08/building-reliable-azure-processes.aspx"&gt;linked&lt;/a&gt; to a great series of articles from &lt;a href="http://blogs.msdn.com/neilkidd/default.aspx"&gt;Neil Kidd&lt;/a&gt; which cover how we could (and should) build reliable Azure worker roles. Those links:&lt;/p&gt;  &lt;ul&gt;   &lt;ul&gt;     &lt;li&gt;&lt;a href="http://blogs.msdn.com/neilkidd/archive/2008/12/08/building-a-reliable-windows-azure-process-part-1.aspx"&gt;Part 1 – Building a Reliable Windows Azure Process&lt;/a&gt; &lt;/li&gt;      &lt;li&gt;&lt;a href="http://blogs.msdn.com/neilkidd/archive/2008/12/08/reliable-azure-processes-part-2-was-part-1-thread-safe.aspx"&gt;Part 2 – Was Part 1 Thread Safe?&lt;/a&gt; &lt;/li&gt;      &lt;li&gt;&lt;a href="http://blogs.msdn.com/neilkidd/archive/2008/12/10/reliable-azure-processes-part-3-dealing-with-errors.aspx"&gt;Part 3 – Dealing With Errors&lt;/a&gt; &lt;/li&gt;      &lt;li&gt;&lt;a href="http://blogs.msdn.com/neilkidd/archive/2008/12/15/reliable-azure-processes-part-4-scaling-down.aspx"&gt;Part 4 – Scaling Down&lt;/a&gt; &lt;/li&gt;   &lt;/ul&gt; &lt;/ul&gt;  &lt;p&gt;Thank you Dom. Thank you Neil. There’s some really useful material here that I’ll be devouring constantly over the coming weeks and months.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://twitter.com/jamiet"&gt;@JamieT&lt;/a&gt;&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15635" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="windows azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/windows+azure/default.aspx" /><category term="azure" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/azure/default.aspx" /></entry><entry><title>Enterprise Mashups</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/06/23/enterprise-mashups.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/06/23/enterprise-mashups.aspx</id><published>2009-06-23T22:16:00Z</published><updated>2009-06-23T22:16:00Z</updated><content type="html">&lt;p&gt;Of late one may have noticed that I have become very interested in high-brow, generally vaporous, disciplines such as &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/RESTful/default.aspx"&gt;RESTful data services&lt;/a&gt;, &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/data+interoperability/default.aspx"&gt;data interoperability&lt;/a&gt; and &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/cloud+computing/default.aspx"&gt;cloud computing&lt;/a&gt; whilst coincident with that has been the inexorable rise of the term “&lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/mashups/default.aspx"&gt;mashup&lt;/a&gt;” in the information technology lexicon.&lt;/p&gt;  &lt;p&gt;“Mashup” means different things to different people but to me its simply the practice of combining data from multiple places with the aim of discovering or passing on knowledge that wasn’t known before. Well hey, that sounds a lot like what I do in my day job; the main difference being that I don’t generally hear the term “mashup” being bandied about the London meeting rooms that I frequent to the same extent that it does in the funky web 2.0 and swanky startup world; the term I hear (and use) is the considerably less cool “data integration”. Fundamentally though I don’t think there’s that much difference between the two so maybe enterprise data integration people like myself have something to learn from these so-called mashup players.&lt;/p&gt;  &lt;p align="left"&gt;One of my favourite mashup tools out there is one &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/yahoo+pipes/default.aspx"&gt;I’ve spoken about before&lt;/a&gt; – &lt;a href="http://pipes.yahoo.com"&gt;Yahoo Pipes&lt;/a&gt;. If you haven’t had a look at this it really is worth taking a glance. Yahoo Pipes enables you to extract data from multiple web-based data sources, transform it using a series of operations like sorting, joining, unioning and filtering before finally outputting that transformed data in one of a number of different formats; its a data pipeline for web-based data (A pipeline? Oh, there’s something else I’ve &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/pipeline/default.aspx"&gt;talked about before&lt;/a&gt; – noticing a pattern here?). Here is an example of a Yahoo Pipe: &lt;a href="http://pipes.yahoo.com/pipes/pipe.info?_id=ZKJobpaj3BGZOew9G8evXg"&gt;Yahoo Finance Stock Quote Watch List Feed w/Chart&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Extracting. Transforming. Sorting. Unioning. Filtering. Outputting. This Yahoo Pipes thing is starting to sound awfully like ETL tools such as &lt;a href="http://blogs.conchango.com/jamiethomson/archive/tags/SQL+Server+Integration+Services/default.aspx"&gt;SQL Server Integration Services (SSIS)&lt;/a&gt; wouldn’t you say? They even look a little bit like each other with their boxes joined up with lines between them:&lt;/p&gt;  &lt;p align="left"&gt;&lt;img src="http://blogs.conchango.com/blogs/jamiethomson/image_191E6589.png"&gt; &lt;/p&gt;  &lt;p align="left"&gt;&lt;img src="http://blogs.conchango.com/blogs/jamiethomson/WindowsLiveWriter/SSISNuggetConditionallyemailafilecontain_C5A5/image_4.png"&gt; &lt;/p&gt;  &lt;p align="left"&gt;&amp;nbsp;&lt;/p&gt;  &lt;p align="left"&gt;&lt;i&gt;I’m now reminded of what my good friend &lt;/i&gt;&lt;a href="http://twitter.com/andybritcliffe"&gt;&lt;i&gt;Andy Britcliffe&lt;/i&gt;&lt;/a&gt;&lt;i&gt; of &lt;a href="http://www.sharpcloud.com"&gt;Sharpcloud &lt;/a&gt;once said to me upon reading my blog post (and viewing the embedded video) &lt;/i&gt;&lt;a href="http://blogs.conchango.com/jamiethomson/archive/2007/06/19/SSIS_3A00_--Consuming-web-services-in-SSIS-2008.aspx"&gt;&lt;i&gt;Consuming web services in SSIS 2008&lt;/i&gt;&lt;/a&gt;&lt;i&gt; a full two years ago. I distinctly remember Andy’s words on that occasion: “SSIS is the ultimate mashup tool”! I didn’t disagree!&lt;/i&gt;&lt;/p&gt;  &lt;p align="left"&gt;Most mashup tools share one common characteristic in that they invariably require someone with some technical nous to set them up in advance so that they can be used by the less tech-savvy amongst us and the same applies in enterprises as well; data is distributed &lt;i&gt;by &lt;/i&gt;the IT guys &lt;i&gt;to &lt;/i&gt;the information workers and this distribution of data typically takes months whereas the consumers of that data want it available in hours. In both arenas I sense a shift occurring; now the consumers of the data are being &lt;i&gt;empowered&lt;/i&gt; to find and interrogate data for themselves and in the enterprise this is happening through the adoption of tools such as &lt;a href="http://www.qlikview.com/"&gt;Qlikview&lt;/a&gt;, &lt;a href="http://www.visokio.com/omniscope"&gt;Omniscope&lt;/a&gt; and (in the near future) Microsoft’s Gemini. I find this to be a fascinating development not because it means there may be less work for me to do (admittedly that would be nice) but because information workers now have the opportunity to be much more productive in their daily jobs and I expect those who invest in learning these new technologies to be the cream that rises to the top of enterprises in the near future.&lt;/p&gt;  &lt;p align="left"&gt;Up until recently I hadn’t been all that interested in Microsoft’s Gemini project, indeed I was very sceptical of it, but as I started to formulate some of the thoughts that I’m writing about here I began to realise how important it will be when it gets released sometime (hopefully) in early 2010. I earlier described mashups as being “the practice of combining data from multiple places with the aim of discovering or passing on knowledge that wasn’t known before” and that description fits very well with Gemini. If you don’t know what Gemini is take a look at this video:&lt;/p&gt;  &lt;p align="left"&gt;&lt;object width="425" height="344"&gt;&lt;param name="movie" value="http://www.youtube.com/v/N3l1VDOASUU&amp;amp;hl=en&amp;amp;fs=1&amp;amp;"&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;embed src="http://www.youtube.com/v/N3l1VDOASUU&amp;amp;hl=en&amp;amp;fs=1&amp;amp;" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"&gt;&lt;/object&gt;&lt;/p&gt;  &lt;p&gt;That demo glosses over the main point I’m making which is that here we see data that is originally pulled from multiple sources and combined in a familiar place (Excel) where the end user can consume it. The person speaking in the video is Donald Farmer and he has a blog entry with many other links to Gemini resources at &lt;a href="http://www.beyeblogs.com/donaldfarmer/"&gt;Microsoft Project Gemini links&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;At the top of this email I also talked about how I’m interested in data services, that is data available over the web that we can consume via an API and use for our own knowledge discovery and I was introduced to such a data service just yesterday when listening to Jon Udell’s “&lt;a href="http://itc.conversationsnetwork.org/series/innovators.html"&gt;Interviews with Innovators&lt;/a&gt;” podcast. In the &lt;a href="http://itc.conversationsnetwork.org/shows/detail4149.html"&gt;most recent episode&lt;/a&gt; Jon interviewed Stephen Willmott whose company &lt;a href="http://www.3scale.net/"&gt;3scale Networks&lt;/a&gt; has taken it upon themselves to make data held by the United Nations freely available via a data service to anyone that would like to consume it [UPDATE: Read Jon's own writeup of the interview at &lt;a href="http://blog.jonudell.net/2009/07/06/influencing-the-production-of-public-data/" rel="bookmark" title="Permanent Link: Influencing the production of public&amp;nbsp;data"&gt;Influencing the production of public&amp;nbsp;data&lt;/a&gt;]. For example, if you want to know the United Kingdom population’s annual growth rate since 1991, that data is available, for free, at &lt;a href="http://undata-api.appspot.com/data/query/Population%20annual%20growth%20rate%20%28percent%29/United%20Kingdom?user_key=XXXX"&gt;http://undata-api.appspot.com/data/query/Population%20annual%20growth%20rate%20(percent)/United%20Kingdom?user_key=XXXX&lt;/a&gt;&amp;nbsp; (you need to &lt;a href="http://www.undata-api.org/plans"&gt;sign-up&lt;/a&gt; for a free user-key and substitute it for XXXX in order for this query to work) and is returned like so:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_01C0236B.png"&gt;&lt;img src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_2FE9F958.png" style="border-width:0px;display:inline;margin-left:0px;margin-right:0px;" title="image" alt="image" width="683" align="left" border="0" height="358"&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;&amp;nbsp;&lt;/p&gt;  &lt;p&gt;“Wouldn’t it be cool” I thought, “if I could consume that data inside of Excel using Gemini”, perhaps in this example to combine it with birth rates over the same period to discover if there is a correlation between the two. At the time though I didn’t know if Gemini made it possible to consume data directly from data sources so I went straight to ask the man who would know, the aforementioned Donald Farmer. I contacted Donald over Twitter and here is the conversation that ensued:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Me: @&lt;a href="http://twitter.com/donalddotfarmer"&gt;donalddotfarmer&lt;/a&gt; Is there a list of data sources types from which #Gemini can get data? Interested in data from web APIs e.g. undata-api.org (&lt;a href="http://twitter.com/jamiet/status/2292293763"&gt;link&lt;/a&gt;) &lt;/li&gt;    &lt;li&gt;Donald: @&lt;a href="http://twitter.com/jamiet"&gt;jamiet&lt;/a&gt; I'll need to check out that site in particular, but we do support Atom feeds. (&lt;a href="http://twitter.com/donalddotfarmer/status/2296286323"&gt;link&lt;/a&gt;) &lt;/li&gt;    &lt;li&gt;Me: @&lt;a href="http://twitter.com/donalddotfarmer"&gt;donalddotfarmer&lt;/a&gt; Ahh that's good news. How about POX/RSS? Does Gemini allow us to parse it or use XQuery? (&lt;a href="http://twitter.com/jamiet/status/2296349687"&gt;link&lt;/a&gt;) &lt;/li&gt;    &lt;li&gt;Donald: @&lt;a href="http://twitter.com/jamiet"&gt;jamiet&lt;/a&gt; No we don't support XQuery - we just consume Atom feeds as they come - the users can then filter and sort in Gemini (&lt;a href="http://twitter.com/donalddotfarmer/status/2296520167"&gt;link&lt;/a&gt;) &lt;/li&gt;    &lt;li&gt;Me: @&lt;a href="http://twitter.com/donalddotfarmer"&gt;donalddotfarmer&lt;/a&gt; OK, so Atom only right now. Looking forward to getting hands dirty, think I know what 1st feature request will be :) (&lt;a href="http://twitter.com/jamiet/status/2296665400"&gt;link&lt;/a&gt;) &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Lots of techy abbreviations in there so let me summarise. Gemini will be able to consume data from web services that deliver it in the popular &lt;a href="http://tools.ietf.org/html/rfc4287"&gt;Atom XML dialect&lt;/a&gt; (&lt;a href="http://en.wikipedia.org/wiki/Atom_%28standard%29"&gt;more on Wikipedia&lt;/a&gt;) which is great news and no great surprise given that &lt;a href="http://dev.live.com/blogs/devlive/archive/2008/02/27/213.aspx"&gt;Microsoft announced in February 2008&lt;/a&gt; that Atom would be their XML syndication format of choice going forward (see my blog post &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2008/02/28/windows-live-dev-announcements.aspx"&gt;Windows Live Dev announcements&lt;/a&gt; for a more complete commentary). I happen to know that the United Nations data provided by Stephen Willmott is not currently delivered in Atom format but no matter, at least things are moving in the right direction and as I alluded during my last tweet to Donald I’ll be asking for support for other syndication formats in the future.&lt;/p&gt;  &lt;p&gt;This has turned into a rather rambling blog post so I’ll call a halt here. As always though I’d be interested to know other people’s thoughts on data services, usage of that data in enterprises or anything else I’ve mentioned herein so if you have any thoughts please leave comments in &lt;a href="http://blogs.conchango.com/jamiethomson/archive/2009/06/23/enterprise-mashups.aspx#comments"&gt;the space below&lt;/a&gt;!&lt;/p&gt;  &lt;p&gt;-Jamie&lt;/p&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15591" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="SQL Server Integration Services" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server+Integration+Services/default.aspx" /><category term="SQL Server" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SQL+Server/default.aspx" /><category term="SSIS" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/SSIS/default.aspx" /><category term="yahoo pipes" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/yahoo+pipes/default.aspx" /><category term="mashups" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/mashups/default.aspx" /><category term="cloud computing" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/cloud+computing/default.aspx" /><category term="RESTful" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/RESTful/default.aspx" /><category term="data interoperability" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/data+interoperability/default.aspx" /><category term="gemini" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/gemini/default.aspx" /><category term="data services" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/data+services/default.aspx" /><category term="omniscope" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/omniscope/default.aspx" /><category term="qlikview" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/qlikview/default.aspx" /></entry><entry><title>Powershell over Bing = geek coolness</title><link rel="alternate" type="text/html" href="http://consultingblogs.emc.com/jamiethomson/archive/2009/06/09/powershell-over-bing-geek-coolness.aspx" /><id>http://consultingblogs.emc.com/jamiethomson/archive/2009/06/09/powershell-over-bing-geek-coolness.aspx</id><published>2009-06-09T20:42:54Z</published><updated>2009-06-09T20:42:54Z</updated><content type="html">&lt;p&gt;I like to think that most of the stuff I blog about on here is in some way useful but sometimes I just want to put something out there that i think is simply damn cool, this is one of the latter cases.&lt;/p&gt;  &lt;p&gt;Today I stumbled upon Joe Pruitt’s &lt;a href="http://devcentral.f5.com/weblogs/Joe/archive/2009/06/03/introducing-poshbing-ndash-the-powershell-library-for-microsoftrsquos-bing-search.aspx"&gt;PoshBing – a Powershell library for Microsoft’s new Bing search engine&lt;/a&gt;. Its a wrapper around the Bing API and enables you to call the Bing search engine and consume the results inside the Powershell pipeline. A picture speaks a thousand words so here are some example of what you can do with it:&lt;/p&gt;  &lt;p&gt;Spellchecking&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/clip_image002_12A18E93.jpg"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="clip_image002" border="0" alt="clip_image002" src="http://blogs.conchango.com/blogs/jamiethomson/clip_image002_thumb_35EE8338.jpg" width="1001" height="188" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;Translations&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_5BE4338E.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_3AF0C0E7.png" width="1001" height="188" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_3365517A.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_7909DB98.png" width="1001" height="212" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Basic web search&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_6654E1E1.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_2C659EF5.png" width="1001" height="140" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;News articles&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blogs.conchango.com/blogs/jamiethomson/image_76ECDCCF.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://blogs.conchango.com/blogs/jamiethomson/image_thumb_3CFD99E3.png" width="1001" height="140" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;Not sure how useful it is but its all very cool stuff I’m sure you’ll agree (if you’re a fan of Powershell)! Download the Powershell script file containing this good stuff from &lt;a title="http://poshbing.codeplex.com/" href="http://poshbing.codeplex.com/"&gt;http://poshbing.codeplex.com/&lt;/a&gt; and happy querying!&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;As an aside, Joe has also built a Twitter wrapper around his Powershell Bing wrapper which means you can now use Twitter to use Powershell to query Bing; simply head for &lt;a href="http://twitter.com/askbing"&gt;@askbing&lt;/a&gt; and ask it whatever you want. Probably not all that useful but nonetheless very very cool.&lt;/p&gt;  &lt;p&gt;-Jamie&lt;/p&gt;  &lt;hr /&gt;  &lt;p&gt;Please check out more of my Powershell related blog posts: &lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;a href="http://blogs.conchango.com/jamiethomson/archive/2008/12/09/talking-pipelines-ssis-and-powershell.aspx"&gt;Talking Pipelines : SSIS and Powershell&lt;/a&gt; &lt;/li&gt;    &lt;li&gt;&lt;a href="http://blogs.conchango.com/jamiethomson/archive/2009/01/14/the-perils-of-staticly-typed-languages-and-schema-less-data-stores.aspx"&gt;The perils of staticly-typed languages and schema-less data stores&lt;/a&gt;&lt;/li&gt; &lt;/ul&gt;&lt;img src="http://consultingblogs.emc.com/aggbug.aspx?PostID=15487" width="1" height="1"&gt;</content><author><name>jamie.thomson</name><uri>http://consultingblogs.emc.com/members/jamie.thomson.aspx</uri></author><category term="powershell" scheme="http://consultingblogs.emc.com/jamiethomson/archive/tags/powershell/default.aspx" /></entry></feed>