<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>Andrei Rinea's technical blog</title>
	
	<link>http://blog.andrei.rinea.ro</link>
	<description>.NET and SQL Server</description>
	<lastBuildDate>Tue, 08 May 2012 10:52:30 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/Andrei-Rinea" /><feedburner:info uri="andrei-rinea" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>How to deal with unwanted LinkedIn invites</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/hCMertvHfIo/</link>
		<comments>http://blog.andrei.rinea.ro/2012/05/07/how-to-deal-with-unwanted-linkedin-invites/#comments</comments>
		<pubDate>Mon, 07 May 2012 15:22:24 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[Recruitment]]></category>
		<category><![CDATA[hr]]></category>
		<category><![CDATA[it]]></category>
		<category><![CDATA[LinkedIn]]></category>
		<category><![CDATA[recruitment]]></category>
		<category><![CDATA[report]]></category>
		<category><![CDATA[spam]]></category>
		<category><![CDATA[strategy]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=109</guid>
		<description><![CDATA[How many of haven&#8217;t received unwanted LinkedIn invites from people that claim to know you, been colleagues and you haven&#8217;t even heard of? Like&#8230; so : or like so : Don&#8217;t be fooled, they&#8217;re just trying to get their recruitment &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2012/05/07/how-to-deal-with-unwanted-linkedin-invites/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>
How many of haven&#8217;t received unwanted LinkedIn invites from people that claim to know you, been colleagues and you haven&#8217;t even heard of?</p>
<p>Like&#8230; so :
</p>
<p>
<img src="http://blog.andrei.rinea.ro/wp-content/uploads/2012/05/linkedinspam1.png" alt="" title="linkedinspam1" width="539" height="240" class="size-full wp-image-110" />
</p>
<p>
or like so :
</p>
<p>
<img src="http://blog.andrei.rinea.ro/wp-content/uploads/2012/05/linkedinspam2.png" alt="" title="linkedinspam1" class="size-full wp-image-110" />
</p>
<p>
Don&#8217;t be fooled, they&#8217;re just trying to get their recruitment bonus. The right choice? The &#8220;REPORT SPAM&#8221; button up above. Press it. They deserve it. The correct way would have been a private message but it&#8217;s more useful for the recruiters to add a new contact since they may need to contact him/her again.</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/hCMertvHfIo" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2012/05/07/how-to-deal-with-unwanted-linkedin-invites/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2012/05/07/how-to-deal-with-unwanted-linkedin-invites/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=how-to-deal-with-unwanted-linkedin-invites</feedburner:origLink></item>
		<item>
		<title>Back to basics – object equality</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/rlXghKYXNvA/</link>
		<comments>http://blog.andrei.rinea.ro/2012/04/05/back-to-basics-object-equality/#comments</comments>
		<pubDate>Thu, 05 Apr 2012 12:31:44 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[Basics]]></category>
		<category><![CDATA[boxing]]></category>
		<category><![CDATA[c#]]></category>
		<category><![CDATA[equals]]></category>
		<category><![CDATA[referenceequals]]></category>
		<category><![CDATA[ReSharper]]></category>
		<category><![CDATA[unboxing]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=103</guid>
		<description><![CDATA[What do you think this piece of code will output? I won&#8217;t be like others and ask you not to run the code. Run the code if you feel like it. I&#8217;ll wait here. &#8230; Back already? Surprised? I surely &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2012/04/05/back-to-basics-object-equality/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>What do you think this piece of code will output?</p>
<pre class="brush: csharp; title: ; notranslate">
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine(GetValue() == (object)true);
            Console.WriteLine(object.Equals(GetValue(), true));
        }

        static object GetValue()
        {
            return true;
        }
    }
</pre>
<p>I won&#8217;t be like others and ask you not to run the code. Run the code if you feel like it. I&#8217;ll wait here.</p>
<p>&#8230;</p>
<p>Back already? Surprised?<br />
I surely have been.. I&#8217;ve found a piece of code similar to this as I was cleaning up code in our repository. You have a method that is required to return object (as in <a href="http://msdn.microsoft.com/en-us/library/system.object.aspx">System.Object</a>) and you want to check if, <a href="http://msdn.microsoft.com/en-us/library/yz2be5wk.aspx">unboxed</a>, it holds the value of true (or not).</p>
<p>Why exactly does </p>
<pre class="brush: csharp; title: ; notranslate">
    GetValue() == (object)true
</pre>
<p>return false considering that GetValue() returns always a true value? Well&#8230; because you are comparing two instances of a <a href="http://msdn.microsoft.com/en-us/library/system.object.aspx">System.Object</a> and the &#8216;==&#8217; operator is coded in a way that uses the <a href="http://msdn.microsoft.com/en-us/library/system.object.referenceequals.aspx">ReferenceEquals</a> (and not <a href="http://msdn.microsoft.com/en-us/library/bsc2ak47.aspx">Equals</a>) method on <a href="http://msdn.microsoft.com/en-us/library/system.object.aspx">System.Object</a>.</p>
<p>The author could have unboxed it to a local variable and do the check after but the speed of coding is so much important for some of us.. Thank you <a href="http://www.jetbrains.com/resharper/">ReSharper</a> for pointing this to us and fixing a potentially subtle bug.</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/rlXghKYXNvA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2012/04/05/back-to-basics-object-equality/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2012/04/05/back-to-basics-object-equality/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=back-to-basics-object-equality</feedburner:origLink></item>
		<item>
		<title>How not to build an online flight booking site</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/F3liBa3YSVs/</link>
		<comments>http://blog.andrei.rinea.ro/2012/04/03/how-not-to-build-an-online-flight-booking-site/#comments</comments>
		<pubDate>Tue, 03 Apr 2012 15:45:23 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[Architecture]]></category>
		<category><![CDATA[absolute-expiration]]></category>
		<category><![CDATA[architecture]]></category>
		<category><![CDATA[banking]]></category>
		<category><![CDATA[fail]]></category>
		<category><![CDATA[session]]></category>
		<category><![CDATA[TAROM]]></category>
		<category><![CDATA[wtf]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=92</guid>
		<description><![CDATA[I had a rough experience a few days ago while trying to book a flight for my upcoming holiday. I &#8230; no, we, chose TAROM (site link here). What happened, in short, I started to book the flight, filled-in all &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2012/04/03/how-not-to-build-an-online-flight-booking-site/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>I had a rough experience a few days ago while trying to book a flight for my upcoming holiday. I &#8230; no, we, chose <a href="http://en.wikipedia.org/wiki/Tarom">TAROM</a> (site link <a href="http://www.tarom.ro/en/">here</a>).</p>
<p>What happened, in short, I started to book the flight, filled-in all the flight details, got to the point where I need to provide the billing details (card number etc.), pressed next and then&#8230; &#8220;session expired, please start over again&#8221;. For a moment I checked my bank account. Sure enough they took the money and offered me just an error. No email, no nothing.</p>
<p>After 1 hour and something, I finally got to customer service representative who manually issued the tickets which couldn&#8217;t have been issued by the site. (Meanwhile I found out how hard is to cancel a payment from your bank to a rogue vendor).</p>
<p>In the end things got fixed but a bitter taste persists towards this TAROM operator. Anyway I tried to understand what went wrong in the process, IT-wise and this is what happened, I think :</p>
<ol>
<li>The site gathered all the flight details from the <del datetime="2012-04-03T13:45:42+00:00">sucker</del> customer (me)</li>
<li>The site then asked for the billing info</li>
<li>Tried to bill me and succeeded</li>
<li>Tried to book the flight and failed (the session expired in the meanwhile)</li>
</ol>
<p>From this short analysis a few WTFs have emerged :</p>
<ul>
<li>Why did they chose to have an absolute-date expiration policy for the session? (i.e. the session expires precisely 10 minutes after you start the booking process, no matter how many or how frequent you do further requests</li>
<li>Why didn&#8217;t they leave the billing step as the final step?</li>
</ul>
<p>Having had to put up with Romanian services for the last three decades I&#8217;ve learnt that the most probable reason for these WTFs is this : </p>
<p><img src="http://blog.andrei.rinea.ro/wp-content/uploads/2012/04/why-because-fuck-you-that-s-why.jpg" alt="Why? Because FUCK YOU! that's why.." title="Why? Because FUCK YOU! that's why.." width="453" height="604" /></p>
<p>Leaving the funny thing aside I suppose the &#8216;architects&#8217; that built TAROM&#8217;s site (hope the plane doesn&#8217;t crash like the site) thought that it&#8217;s better to have the money in the bag and then see if all else went ok&#8230; or maybe they thought of a situation where many people would try to book few tickets? Or who knows&#8230;</p>
<p><strong><em>What do you think dear reader?</em></strong></p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/F3liBa3YSVs" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2012/04/03/how-not-to-build-an-online-flight-booking-site/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2012/04/03/how-not-to-build-an-online-flight-booking-site/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=how-not-to-build-an-online-flight-booking-site</feedburner:origLink></item>
		<item>
		<title>Benchmark code blocks easy</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/hQZD1Ac22Z4/</link>
		<comments>http://blog.andrei.rinea.ro/2012/03/15/benchmark-code-blocks-easy/#comments</comments>
		<pubDate>Thu, 15 Mar 2012 16:20:17 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[benchmark]]></category>
		<category><![CDATA[Benchmark.NET]]></category>
		<category><![CDATA[Codeplex]]></category>
		<category><![CDATA[open-source]]></category>
		<category><![CDATA[performance]]></category>
		<category><![CDATA[Stopwatch]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=79</guid>
		<description><![CDATA[Have you been testing code speed like this? Or maybe you&#8217;ve found the Stopwatch class and been happy with its superior time precision? Better, I&#8217;d say, but I&#8217;ve quite had it. Plus I needed to benchmark a local website and &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2012/03/15/benchmark-code-blocks-easy/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>Have you been testing code speed like this?</p>
<pre class="brush: csharp; title: ; notranslate">

var start = DateTime.Now;
int i;
for(i = 0; i &lt; 1000; i++)
{
    DoSomething();
}
var stop = DateTime.Now;
var total = stop - start;
var timePerIteration = total.Ticks / i;
</pre>
<p>Or maybe you&#8217;ve found <a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.stopwatch.aspx">the Stopwatch class</a> and been happy with its superior time precision?</p>
<p>Better, I&#8217;d say, but I&#8217;ve quite had it. Plus I needed to benchmark a local website and needed to test parallel requests (something similar to <a href="http://en.wikipedia.org/wiki/ApacheBench">ab &#8211; ApacheBench</a>)</p>
<p>What does a programmer in such a case? Writes his own tools! <img src='http://blog.andrei.rinea.ro/wp-includes/images/smilies/icon_razz.gif' alt=':P' class='wp-smiley' />  That&#8217;s how <a href="http://benchmarknet.codeplex.com">BenchmarkNET</a> appeared. Using BenchmarkNET you can write the same thing as above only much shorter and with a better timing precision :</p>
<pre class="brush: csharp; title: ; notranslate">
var result = Benchmark.Sequentially(() =&gt; DoSomething(), 1000);
</pre>
<p>Neat? That&#8217;s not all. The result can easily printed out to a console or inspected with a debugger :</p>
<p><a href="http://blog.andrei.rinea.ro/wp-content/uploads/2012/03/benchmark.png"><img class="alignleft size-full wp-image-82" title="benchmark" src="http://blog.andrei.rinea.ro/wp-content/uploads/2012/03/benchmark.png" alt="" width="678" height="69" /></a></p>
<p>Benchmarking an HTTP operation over 10 parallel threads, 100 times for each thread?</p>
<pre class="brush: csharp; title: ; notranslate">
var dl2 = Benchmark.Parallel(new BenchmarkParams&lt;WebClient&gt;(c =&gt; c.DownloadString(&quot;http://localhost/&quot;), 100), 10, () =&gt; new WebClient());
</pre>
<p>The project has been published as open source (LGPL license) on <a href="http://benchmarknet.codeplex.com/">CodePlex</a>. You can <a href="http://benchmarknet.codeplex.com/discussions">discuss it</a>, <a href="http://benchmarknet.codeplex.com/workitem/list/basic">file bugs</a>, or even <a href="http://benchmarknet.codeplex.com/team/view">contribute to it</a>.</p>
<p>Have fun and if you test it out, please leave some feedback!</p>
<p><strong>Later edit</strong> : It seems <a href="http://alexpeta.ro/article/y-u-no-test-speed-code-with-benchmarknet/">some people already dig it</a> <img src='http://blog.andrei.rinea.ro/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> </p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/hQZD1Ac22Z4" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2012/03/15/benchmark-code-blocks-easy/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2012/03/15/benchmark-code-blocks-easy/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=benchmark-code-blocks-easy</feedburner:origLink></item>
		<item>
		<title>Random performance findings</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/B3onYkTOi24/</link>
		<comments>http://blog.andrei.rinea.ro/2011/12/13/random-performance-findings/#comments</comments>
		<pubDate>Tue, 13 Dec 2011 20:10:16 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[ASP.NET]]></category>
		<category><![CDATA[WCF]]></category>
		<category><![CDATA[ashx]]></category>
		<category><![CDATA[asp.net]]></category>
		<category><![CDATA[basicHttpBinding]]></category>
		<category><![CDATA[benchmark]]></category>
		<category><![CDATA[debug]]></category>
		<category><![CDATA[handler]]></category>
		<category><![CDATA[iis]]></category>
		<category><![CDATA[iis-express]]></category>
		<category><![CDATA[performance]]></category>
		<category><![CDATA[release]]></category>
		<category><![CDATA[sql server]]></category>
		<category><![CDATA[StackOverflow]]></category>
		<category><![CDATA[wcf]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=61</guid>
		<description><![CDATA[TL;DR version : Upon a curiosity of mine I found out that WCF with basicHttpBinding can be easily beaten (performance-wise) by plain-old ASP.NET even if stripped down of transactions, reliability, security etc. (1500 req/sec vs  800 req/sec) Also SQL Server &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2011/12/13/random-performance-findings/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p><strong>TL;DR version :</strong></p>
<p>Upon a curiosity of mine I found out that WCF with basicHttpBinding can be easily beaten (performance-wise) by plain-old ASP.NET even if stripped down of transactions, reliability, security etc. (1500 req/sec vs  800 req/sec)</p>
<p>Also SQL Server Express can handle 1300 inserts per second easily and up to 4300 queries per second just as well. This on a 6+ million rows table and stored on the hard disk not in RAM.</p>
<p><strong>Long version :</strong></p>
<p>A few days ago I was thinking how I implemented a certain web service a few years ago, a few employers ago. Although it was quite fast and efficient it wasn&#8217;t scalable. I, then, thought how I should have implemented it.</p>
<p>The web service had to receive an incoming (public) HTTP request, check for a visitor cookie. If there was a visitor-identifying cookie it would check against a data store (in-memory dictionary at that time) to see if that visitor answered.</p>
<p>It was about inviting visitors of certain sites to an on-line survey. A new visitor would be presented with a pop-up box having a &#8220;yes&#8221;, a &#8220;no&#8221; and &#8220;X&#8221; (close) button.</p>
<p>The business rules stated that if the visitor answered yes, the answer would be stored, the pop-up would close and then a new tab/window would appear with the survey. If the visitor answered no, then the same things would happen except opening the survey. If the visitor closed the pop-up, the next time the pop-up would appear again. If the visitor closed three times the pop-up then (s)he wouldn&#8217;t be bothered anymore with the invitation.</p>
<p><span id="more-61"></span></p>
<p>Quite simple I&#8217;d say. The tough thing was we only had one machine available (a quad-core Xeon 3.5 GHz 4GB RAM) and the expected traffic was 300-400 req/sec during normal load and maybe a peak load of 800-1000 req/sec. In that situation I decided to use a simple in-memory dictionary as data-store that I&#8217;d backup to disk a few times per hour. Things went smooth (at least till I left the company but also after I left, as an ex-colleague of mine told me).</p>
<p>You can easily see that this architecture, although efficient, is not scalable. At least not if you <a href="http://en.wikipedia.org/wiki/Scalability#Scale_horizontally_.28scale_out.29">scale out</a> I personally find efficiency and the ability to scale out completely independent.</p>
<p>So how would I reimplement this (if I would) in a scalable manner? Balancing and scaling the front-facing web servers would be straight-forward : a simple hardware NLB (network</p>
<p>load balancer) in front of n web servers and that&#8217;s that. In the back there would be m storage servers that would just store the visitors&#8217; responses and server query responses</p>
<p>to the web servers. Having naturally partitionable data such as this (especially because it is not inter-related) makes the &#8220;<a href="http://en.wikipedia.org/wiki/Sharding">sharding</a>&#8221; easy.</p>
<p>My questions that arise are :</p>
<ol>
<li><em><strong>What type of communication should I employ between the web servers and the storage servers?</strong></em></li>
<li><em><strong>What type of storage should I use on the storage servers?</strong></em></li>
</ol>
<p>For communication I tested and benchmarked WCF (with basicHttpBinding) hosted in IIS and a simple ASP.NET Generic handler (.ashx thingie) in an empty web application. As for the storage I only tested SQL Server 2008 R2 Express with a database stored on the hard disk (I fancied using MySql with an in-memory storage engine or SQL Server with a database stored on a ram disk, and a periodic backup on a hard disk). However the test results on a standard DB on SQL Server satisfied me and I didn&#8217;t need to go any further.</p>
<p>A few words on the machine I used for testing : my el-cheapo laptop : a two-year old, AMD dual core with 3GB of RAM with Windows 7 Ultimate 64 bit. (<a href="http://www.techsmart.co.za/hardware/notebook_and_tablet_pcs/Compaq_615_techspecs.html">complete specs here</a>)</p>
<p>I started testing communication options. I set up a WCF service hosted in IIS Express, with minimal features, intended to max out performance (no security, singleton service instance, multiple concurrent calls, 1000 max concurrent connections and so on). I then made a small console app that would set up 10 threads that each of them would sequentially make 1,000 calls to the service and measure the whole time.</p>
<p style="padding-left: 30px;">10 x 1,000 calls completed in <strong>60 seconds [170 req/sec]</strong>. Like lame, dude..</p>
<p>Then I thrown up a small, empty web application with just one generic handler which could be queried a bit like so : http://localhost:1234/GetData.ashx?id=39283&amp;opId=1 and it would only send out a single byte that would be the user state.</p>
<p style="padding-left: 30px;">10 x 1,000 calls completed in <strong>15 seconds [670 req/sec]</strong>.</p>
<p>Wow, quite a different set of results&#8230; I then went out to turn to the community to find out how to improve the WCF service and <a href="http://stackoverflow.com/q/8460013/1796">I asked this on stackoverflow</a>. Not much help there (at least at the time of this writing). I then set both web apps on IIS (full not express) 7.5 and turned compilation to release in all projects (wcf web app, asp.net web app and the test harness project). Things changed &#8220;a bit&#8221; :</p>
<p style="padding-left: 30px;">ASP.NET Generic handler : <strong>6.7 sec [1492 req/sec]</strong><br />
WCF service : <strong>13.7 sec [730 req/sec]</strong></p>
<p>Good enough I said to myself, since, in the end, you could easily scale them out. Then I went to see how the DB would stand up to this beating. At first I was quite pesimist about an RDBMS with the backing store on the HDD (no RAID 0, no nothing) &#8211; a 7200 rpm laptop hard-drive.</p>
<p>Starting from an empty table (Id &#8211; bigint &#8211; 64 bit, Response &#8211; tinyint &#8211; 8 bit) I started to insert sequentially (over the same connection, unclosed) 6 million rows. At first the table had a clustered index on the Id column slowing down the inserts. From 0 to the first 100,000th record it inserted at an approximate rate of 1500 rows/sec and then went down and down asymptotically until I got bored and stopped it (at around 3.5 million rows).</p>
<p>Then I truncated the table, removed the clustered index and I was able to insert consistently (again, sequentially on a single connection) at <strong>1250 rows/sec</strong>. For kicks I truncated the table again (use TRUNCATE rather than DELETE TABLE because it&#8217;s way faster and cleaner) and used BULK INSERT just as in <a href="http://blog.sqlauthority.com/2008/02/06/sql-server-import-csv-file-into-sql-server-using-bulk-insert-load-comma-delimited-file-into-sql-server/">Dave&#8217;s article</a> and got something like <strong>58,000 rows/second</strong>!!!</p>
<p>Being satisfied with the findings I got to test the query performance. I used a 6 million rows content for the table and tested with a clustered index and got around <strong>4.291 queries per second</strong>!!! while without an index the table scan ruined the performance to <strong>1 (one) query per second</strong>. Adding back the index to the indexless table took <strong>21 seconds</strong>. Decent, I&#8217;d say.</p>
<p>In the end I had one more &#8220;What if&#8221; question on the top of my head : What if instead of a bigint (Int64, long , however you call it) I would have a normal int (32 bits)? For 6 million generated visitorIds how many collisions I&#8217;d get? And by collision I mean something simillar to <a href="http://en.wikipedia.org/wiki/Hash_collision">hash collisions</a>. I got <strong>11,000</strong> for 6,000,000 (<strong>0.1%</strong>). Acceptable for the business case. Generating long (64 bit) Ids would not generate any collision.</p>
<p>&nbsp;</p>
<p><span style="text-decoration: underline;"><strong>Conclusion :</strong></span> You can safely use WCF with SQL Server and still get decent performance. If you really need and want to tweak the performance you can use other solutions (generic handlers, in-memory dictionaries or memory-backed DBMS&#8217;es or even NoSQL solutions) but they will be harder to design, implement, deploy and maintain. So start simple and then find your way.</p>
<p>http://en.wikipedia.org/wiki/Hash_collision</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/B3onYkTOi24" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2011/12/13/random-performance-findings/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2011/12/13/random-performance-findings/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=random-performance-findings</feedburner:origLink></item>
		<item>
		<title>WCF Streaming – slides and code</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/cO50QSFCyjQ/</link>
		<comments>http://blog.andrei.rinea.ro/2011/11/26/wcf-streaming-slides-and-code/#comments</comments>
		<pubDate>Sat, 26 Nov 2011 15:53:15 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[Presentations]]></category>
		<category><![CDATA[WCF]]></category>
		<category><![CDATA[cassini]]></category>
		<category><![CDATA[iis-express]]></category>
		<category><![CDATA[messagebodymember]]></category>
		<category><![CDATA[MessageContract]]></category>
		<category><![CDATA[messageheader]]></category>
		<category><![CDATA[operationcontract]]></category>
		<category><![CDATA[servicecontract]]></category>
		<category><![CDATA[streaming]]></category>
		<category><![CDATA[wcf]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/2011/11/26/wcf-streaming/</guid>
		<description><![CDATA[I held a presentation about WCF Streaming last Saturday, November 26th, at Microsoft HQ Bucharest. I illustrated WCF Streaming in a small client/server application which was supposed to (and in the end implemented it all) : Show all files available &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2011/11/26/wcf-streaming-slides-and-code/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p><a href="http://blog.andrei.rinea.ro/2011/11/15/it-community-meeting-codecamp-itspark/">I held a presentation about WCF Streaming last Saturday, November 26th, at Microsoft HQ Bucharest</a>. I illustrated WCF Streaming in a small client/server application which was supposed to (and in the end implemented it all) :</p>
<ul>
<li>Show all files available on the server in the client application</li>
<li>Allow the end user to upload a file (up to 2GB) to the server</li>
<li>Allow the user to download a file from the server</li>
<li>Display a progress bar that would update in real-time showing the progress of the current transfer (upload or download)</li>
<li>Allow the user to press the &#8220;Stop&#8221; button to stop the current transfer (upload or download)</li>
</ul>
<p>The code to achieve this in a simple (non-robust, not production quality etc.) manner is quite small : around 50 lines of code for the server and around 200 lines for the client. <strong>The WCF runtime takes care of the rest</strong>.</p>
<p>Points of interest (things for which I suffered and hopefully you won&#8217;t) :</p>
<ul>
<li>Cassini (ASP.NET Web development) server <a href="http://blog.andrei.rinea.ro/2011/11/07/cassini-and-wcf-streaming/">does not support streaming</a>, reports a cryptic (400 Bad request) error and <strong><em>it&#8217;s not documented at Microsoft</em></strong>!</li>
<li>It&#8217;s not enough at the server level to set the maxReceivedMessageSize at the binding element, you must also set it in the maxRequestLength attribute on the system.web/httpRuntime element if you host the service in a site.</li>
<li>Don&#8217;t try to define an operation with mixed types, that is, complex types that are decorated with MessageContract and any other types (including System.String). If one is MessageContract then all have to be. Found out the hard way, at runtime (not compile time)</li>
<li>In order to get the folder path for a WCF application you must use <a href="http://blog.andrei.rinea.ro/2011/11/08/wcf-service-local-path/">HostingEnvironment.GetApplicationPhysicalPath</a>.</li>
<li>In .NET 4 there is a CopyTo method on the Stream class which simplifies copying data from a stream to another.</li>
<li>Opt in for asynchronous method generation for the client-side WCF proxies</li>
</ul>
<p>You can find below the PowerPoint slides and the code archive attached to this post.</p>
<p><a href="http://blog.andrei.rinea.ro/wp-content/uploads/2011/11/WCF-Streaming.pptx">WCF Streaming &#8211; slides</a></p>
<p><a href="http://blog.andrei.rinea.ro/wp-content/uploads/2011/11/WCF-Streaming1.zip">WCF Streaming &#8211; the code</a></p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/cO50QSFCyjQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2011/11/26/wcf-streaming-slides-and-code/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2011/11/26/wcf-streaming-slides-and-code/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=wcf-streaming-slides-and-code</feedburner:origLink></item>
		<item>
		<title>IT community meeting (CodeCamp &amp; ITSpark)</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/N3xbtwj7rho/</link>
		<comments>http://blog.andrei.rinea.ro/2011/11/15/it-community-meeting-codecamp-itspark/#comments</comments>
		<pubDate>Tue, 15 Nov 2011 20:41:45 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[Presentations]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[azure]]></category>
		<category><![CDATA[bucharest]]></category>
		<category><![CDATA[cristea]]></category>
		<category><![CDATA[dionisie]]></category>
		<category><![CDATA[ef]]></category>
		<category><![CDATA[hyper-v]]></category>
		<category><![CDATA[ignat]]></category>
		<category><![CDATA[lefter]]></category>
		<category><![CDATA[lync]]></category>
		<category><![CDATA[microsoft]]></category>
		<category><![CDATA[mvc]]></category>
		<category><![CDATA[nadas]]></category>
		<category><![CDATA[office-365]]></category>
		<category><![CDATA[roman]]></category>
		<category><![CDATA[rusu]]></category>
		<category><![CDATA[scvmm]]></category>
		<category><![CDATA[show]]></category>
		<category><![CDATA[sql]]></category>
		<category><![CDATA[wcf]]></category>
		<category><![CDATA[windows8]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=47</guid>
		<description><![CDATA[Saturday, November 26th, there will be a session of presentations at Microsoft&#8217;s Bucharest Headquarters. Free entrance, drinks and lunch on the house. The event agenda : 09:30 &#8211; 10:00 Arrival 10:00 &#8211; 11:00 MVC / EF (Andrei Ignat) 11:00 &#8211; &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2011/11/15/it-community-meeting-codecamp-itspark/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>Saturday, November 26th, there will be a session of presentations at Microsoft&#8217;s Bucharest Headquarters.</p>
<p>Free entrance, drinks and lunch on the house.</p>
<p>The event agenda :</p>
<ul>
<li>09:30 &#8211; 10:00 Arrival</li>
<li>10:00 &#8211; 11:00 MVC / EF (Andrei Ignat)</li>
<li><strong>11:00 &#8211; 12:00 WCF Streaming (Andrei Rinea)</strong></li>
<li>12:00 &#8211; 13:00 SQL Server Denali (Cristian Lefter)</li>
<li>13:00 &#8211; 13:30 LUNCH</li>
<li>13:30 &#8211; 14:00 A lap around Windows 8 (Mihai Nadăș)</li>
<li>14:00 &#8211; 15:15 Hyper-V 3.0 și SCVMM 2012 (Valentin Cristea &amp; Răzvan Rusu)</li>
<li>15:15 &#8211; 16:30 Office 365 și Lync Online &amp; On-Premise (Alexandru Dionisie &amp; Paul Roman)</li>
</ul>
<p>I will be presenting WCF Streaming at 11:00. But I assure you the other presentations will be just as interesting as this!</p>
<p>Come and join us and you won&#8217;t regret it! But first <a href="http://itcamp-bucuresti.eventbrite.com/">register at the event site first</a>! Only 22 seats available at the time of the writing.</p>
<p>Hope to see you there!.</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/N3xbtwj7rho" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2011/11/15/it-community-meeting-codecamp-itspark/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2011/11/15/it-community-meeting-codecamp-itspark/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=it-community-meeting-codecamp-itspark</feedburner:origLink></item>
		<item>
		<title>WCF service local path</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/zC07sY2_c_U/</link>
		<comments>http://blog.andrei.rinea.ro/2011/11/08/wcf-service-local-path/#comments</comments>
		<pubDate>Tue, 08 Nov 2011 08:55:01 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[WCF]]></category>
		<category><![CDATA[ApplicationPhysicalPath]]></category>
		<category><![CDATA[App_Data]]></category>
		<category><![CDATA[basicHttpBinding]]></category>
		<category><![CDATA[HostingEnvironment]]></category>
		<category><![CDATA[HttpContext]]></category>
		<category><![CDATA[null]]></category>
		<category><![CDATA[StackOverflow]]></category>
		<category><![CDATA[wcf service]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=26</guid>
		<description><![CDATA[Developing that small WCF presentation that I was talking about earlier, I got stumped on trying to get the local path. The server needs to access the App_Data folder to handle uploads and downloads but it needs the base path &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2011/11/08/wcf-service-local-path/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>Developing that small WCF presentation that <a href="http://blog.andrei.rinea.ro/2011/11/07/cassini-and-wcf-streaming/">I was talking about earlier</a>, I got stumped on trying to get the local path. The server needs to access the App_Data folder to handle uploads and downloads but it needs the base path for that.</p>
<p>No, you don&#8217;t get <a href="http://msdn.microsoft.com/en-us/library/system.web.httpcontext.aspx">HttpContext</a> (HttpContext.Current is null) although the service is bound over basicHttpBinding.</p>
<p>Luckily <a href="http://stackoverflow.com/q/480504/1796">I&#8217;ve found</a><a href="http://stackoverflow.com/q/480504/1796"> via StackOverflow</a> that there is <a href="http://msdn.microsoft.com/en-us/library/system.web.hosting.hostingenvironment.applicationphysicalpath.aspx">HostingEnvironment.ApplicationPhysicalPath</a> which will help you.</p>
<p>Therefore a simple</p>
<pre class="brush: csharp; title: ; notranslate">
public class Service : IService
{
    private readonly string _dataFolder;

    public Service()
    {
       _dataFolder = Path.Combine(HostingEnvironment.ApplicationPhysicalPath, &quot;App_Data&quot;);
    }
}
</pre>
<p>.. will suffice.</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/zC07sY2_c_U" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2011/11/08/wcf-service-local-path/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2011/11/08/wcf-service-local-path/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=wcf-service-local-path</feedburner:origLink></item>
		<item>
		<title>Cassini and WCF streaming</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/SQjykQRgt0A/</link>
		<comments>http://blog.andrei.rinea.ro/2011/11/07/cassini-and-wcf-streaming/#comments</comments>
		<pubDate>Mon, 07 Nov 2011 10:49:33 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[WCF]]></category>
		<category><![CDATA[.net3.5]]></category>
		<category><![CDATA[.net4.0]]></category>
		<category><![CDATA[cassini]]></category>
		<category><![CDATA[iis]]></category>
		<category><![CDATA[iis-express]]></category>
		<category><![CDATA[MessageContract]]></category>
		<category><![CDATA[Stream]]></category>
		<category><![CDATA[streamedrequest]]></category>
		<category><![CDATA[streamedresponse]]></category>
		<category><![CDATA[streaming]]></category>
		<category><![CDATA[transferMode]]></category>
		<category><![CDATA[wcf]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=22</guid>
		<description><![CDATA[I am preparing a small talk &#38; demo on WCF streaming and I&#8217;ve tried a lot of things to get it started and working (the practical demo). I was trying to showcase uploading and downloading large files, in an async &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2011/11/07/cassini-and-wcf-streaming/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>I am preparing a small talk &amp; demo on WCF streaming and I&#8217;ve tried a lot of things to get it started and working (the practical demo).</p>
<p>I was trying to showcase uploading and downloading large files, in an async manner with progress report and so on.</p>
<p>Turns out I get an exception, with HTTP code 400 Bad request no matter what I&#8217;ve tried :</p>
<ul>
<li>transferMode : StreamedRequest, StreamedResponse or Streamed (Buffered works but it&#8217;s not streaming so&#8230;)</li>
<li>Tried using MessageContracts or plain Stream&#8217;s</li>
<li>.NET Framework 3.5 or 4.0</li>
<li>.. and many other things.</li>
</ul>
<p>What was the issue? Well the damn development server (code named Cassini) !!! It seems <a href="http://stackoverflow.com/q/1532078/1796">another guy had the same issue, reported on StackOverflow</a> and I was lucky to find it in the large WCF pile.</p>
<p><img class="alignnone" title="Cassini tray icon" src="http://cgeers.files.wordpress.com/2011/04/cassini.jpg" alt="" width="467" height="103" /></p>
<p>Running the same server project on the new <a title="Introducing IIS Express" href="http://weblogs.asp.net/scottgu/archive/2010/06/28/introducing-iis-express.aspx">IIS Express</a> or plain old IIS makes it work.</p>
<p>Hope this will help someone too.. At all costs avoid Cassini (&#8220;ASP.NET Development Server&#8221;). This is not the first issue that this damn server introduces and surely not the last. I hope Visual Studi vNext will NOT include it anymore and will ship with IIS Express only.</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/SQjykQRgt0A" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2011/11/07/cassini-and-wcf-streaming/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2011/11/07/cassini-and-wcf-streaming/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=cassini-and-wcf-streaming</feedburner:origLink></item>
		<item>
		<title>IEnumerable.All() gotcha</title>
		<link>http://feedproxy.google.com/~r/Andrei-Rinea/~3/RDUpS3Pe7RI/</link>
		<comments>http://blog.andrei.rinea.ro/2011/11/04/ienumerable-all-gotcha/#comments</comments>
		<pubDate>Fri, 04 Nov 2011 12:06:14 +0000</pubDate>
		<dc:creator>Andrei Rinea</dc:creator>
				<category><![CDATA[LINQ]]></category>
		<category><![CDATA[All]]></category>
		<category><![CDATA[Any]]></category>
		<category><![CDATA[IEnumerable]]></category>
		<category><![CDATA[linq]]></category>

		<guid isPermaLink="false">http://blog.andrei.rinea.ro/?p=8</guid>
		<description><![CDATA[Today as I was inspecting why some condition was evaluated to true instead of false I found out a strange thing. The code is something like : I was expecting that in case of an empty collection the All method &#8230;<p class="read-more"><a href="http://blog.andrei.rinea.ro/2011/11/04/ienumerable-all-gotcha/">Read more &#187;</a></p>]]></description>
			<content:encoded><![CDATA[<p>Today as I was inspecting why some condition was evaluated to true instead of false I found out a strange thing. The code is something like :</p>
<pre class="brush: csharp; title: ; notranslate">
var someList = new List&lt;Person&gt;();
if (someList.All(v =&gt; v.Age &gt; 18))
{
    Console.WriteLine(&quot;All are 18 or older.&quot;);
}
else
{
    Console.WriteLine(&quot;At least one is less than 18.&quot;);
}
</pre>
<p>I was expecting that in case of an empty collection the <strong>All</strong> method would return false. But it doesn&#8217;t. The &#8220;All are 18 or older.&#8221; string would be printed.</p>
<p>In my case one more simple condition solved this issue :</p>
<pre class="brush: csharp; title: ; notranslate">
    if (someList.Any() &amp;&amp; someList.All(v =&gt; v.Age &gt; 18))
</pre>
<p>After this I read the manual (<a href="http://en.wikipedia.org/wiki/RTFM">RTFM</a>) and <a href="http://msdn.microsoft.com/en-us/library/bb548541.aspx">according to MSDN (in a community comment however)</a> :</p>
<blockquote><p>It&#8217;s important to note that Enumerable.All() returns true for empty sequences</p></blockquote>
<p>So it&#8217;s a &#8220;doh&#8221; moment for me.</p>
<p>Watch out for this in your code.</p>
<img src="http://feeds.feedburner.com/~r/Andrei-Rinea/~4/RDUpS3Pe7RI" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.andrei.rinea.ro/2011/11/04/ienumerable-all-gotcha/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://blog.andrei.rinea.ro/2011/11/04/ienumerable-all-gotcha/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=ienumerable-all-gotcha</feedburner:origLink></item>
	</channel>
</rss>

