<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:pingback="http://madskills.com/public/xml/rss/module/pingback/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" version="2.0">
  <channel>
    <title>Round The Campfire</title>
    <link>http://blog.roundthecampfire.net/</link>
    <description>Ghost stories from the microsoft campfire</description>
    <language>en-us</language>
    <copyright>Chris Ballard</copyright>
    <lastBuildDate>Mon, 08 Feb 2010 22:32:02 GMT</lastBuildDate>
    <generator>newtelligence dasBlog 2.3.9074.18820</generator>
    <managingEditor>worldoflard@googlemail.com</managingEditor>
    <webMaster>worldoflard@googlemail.com</webMaster>
    <item>
      <trackback:ping>http://blog.roundthecampfire.net/Trackback.aspx?guid=80b71cfa-ca82-4975-bd24-89bbce180ee7</trackback:ping>
      <pingback:server>http://blog.roundthecampfire.net/pingback.aspx</pingback:server>
      <pingback:target>http://blog.roundthecampfire.net/PermaLink,guid,80b71cfa-ca82-4975-bd24-89bbce180ee7.aspx</pingback:target>
      <dc:creator>Chris Ballard</dc:creator>
      <wfw:comment>http://blog.roundthecampfire.net/CommentView,guid,80b71cfa-ca82-4975-bd24-89bbce180ee7.aspx</wfw:comment>
      <wfw:commentRss>http://blog.roundthecampfire.net/SyndicationService.asmx/GetEntryCommentsRss?guid=80b71cfa-ca82-4975-bd24-89bbce180ee7</wfw:commentRss>
      <body xmlns="http://www.w3.org/1999/xhtml">
        <p>
Continuing on from my <a href="http://blog.roundthecampfire.net/2010/02/06/A+Quick+Play+With+Reactive+Extensions+Rx.aspx">first
play with the Rx framework</a> yesterday, I thought it would be good to come up with
a real world example. I thought about rss feeds and stock tickers, but in the end
decided on an app with consumes the <a href="http://apiwiki.twitter.com/Twitter-API-Documentation">Twitter
REST API</a>.
</p>
        <p>
I will build up an application which can subscribe to a couple of twitter news feeds,
polling for new messages on a particular schedule, and merging the results into a
single output stream to which we subscribe.
</p>
        <h5>Accessing the Twitter API
</h5>
        <p>
I am going to keep this very simple, just access the <font size="2" face="Courier New">user_timeline</font> service
for a given user, and get the results in XML format, which make it easy for us to
project into a <font size="2" face="Courier New">Tweet</font> class which we define.
I create a class called <font size="2" face="Courier New">TwitterAccess</font> with
one key <font size="2" face="Courier New">static</font> method:
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">public static Tweet[] GetNewTweets(string username, long lastTweetId)
{
    if(lastTweetId &lt; 1)
        throw new ArgumentOutOfRangeException("lastTweetId", "id must be greater than 0");

    string url = String.Format("http://twitter.com/statuses/user_timeline/{0}.xml?since_id={1}",
                               username.Replace("@", ""), lastTweetId);
    var doc = XDocument.Load(url);

    var items = from s in doc.Descendants("status")
                orderby long.Parse(s.Element("id").Value)
                select new Tweet { Id = long.Parse(s.Element("id").Value),
                                   Time = ParseTwitterDate(s.Element("created_at").Value),
                                   Username = s.Element("user").Element("screen_name").Value,
                                   Status = s.Element("text").Value };
     
    return items.ToArray();
}</pre>
        <p>
This method gets all tweets on the given users timeline whose ID is greater than <font size="2" face="Courier New">lastTweetId</font> (although
the default limit in twitter is 20 tweets, you will need to specify the <font size="2" face="Courier New">count</font> parameter
in the rest url if you need more, but this suits our purpose).
</p>
        <p>
The <font size="2" face="Courier New">Tweet</font> class just wraps the properties
you can see above, and the <font size="2" face="Courier New">ParseTwitterDate</font> method
just does a <font size="2" face="Courier New">DateTime.ParseExact</font> for the specific
date format used in twitter.
</p>
        <h5>Wrapping Twitter in an IObservable&lt;T&gt;
</h5>
        <p>
Now that we have a means to access twitter, we should create a class which handles
the polling of this service and pushes all new tweets out through an <font size="2" face="Courier New">IObservable&lt;Tweet&gt;</font> as
follows:
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">public class TweetStream
{
    private long lastTweet = 1;
    private object updateLock = new object();
    private IObservable&lt;Tweet&gt; stream;

    public IObservable&lt;Tweet&gt; Stream
    {
        get { return stream; }
    }

    public TweetStream(string username, int interval)
    {
        var xs = Observable.Interval(TimeSpan.FromSeconds(interval));
        stream = xs.SelectMany(count =&gt;
            {
                Tweet[] items;
                lock (updateLock)
                {
                    items = TwitterAccess.GetNewTweets(username, lastTweet);
                    lastTweet = items.Length &gt; 0 ? items.Last().Id : lastTweet;
                }
                return items.ToObservable();
            });
    }
}</pre>
        <p>
The <font size="2" face="Courier New">SelectMany </font>call allows us to define a
function which is called each time the interval fires and which itself returns an <font size="2" face="Courier New">IObservable</font>.
Note that we must use <font size="2" face="Courier New">SelectMany </font>instead
of <font size="2" face="Courier New">Select </font>as <font size="2" face="Courier New">SelectMany </font>will
automatically flatten all the items in the returned stream into its own stream of <font size="2" face="Courier New">Tweets </font>whereas <font size="2" face="Courier New">Select </font>would
leave you with a stream of <font size="2" face="Courier New">IObservables</font>,
which will then be difficult to handle.
</p>
        <h5>Getting some output from this stream
</h5>
        <p>
I can now update the console app we looked at yesterday in order to create an instance
of <font size="2" face="Courier New">TweetStream</font> and subscribe to its output,
writing this in turn out to the console.
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">TweetStream bbc = new TweetStream("bbcnews", 120);

var sub = bbc.Stream.Subscribe(i =&gt; Console.WriteLine("{0}: {1}: {2}",
                                i.Time.ToString("dd hh:mm"), i.Username, i.Status));</pre>
        <p>
Running this up we get the following output:
</p>
        <table border="1">
          <tbody>
            <tr>
              <td>
                <font size="2">
                  <pre>07 08:10: bbcnews: A man who was injured during a Premier League football match at Stoke City dies in hospital.  http://
bit.ly/bDjtDM
07 09:00: bbcnews: Worst snow storms to hit eastern US for decades  http://bit.ly/93Jpn9
07 09:00: bbcnews: Iran's leader asks the country's nuclear chief to begin enriching uranium to 20%, in a new challenge
to Western.. http://bit.ly/9AUplq
...
07 02:20: bbcnews: A Scottish pensioner becomes only the seventh person in history to achieve judo's highest rank. http:
//bit.ly/8XRsxv
07 02:40: bbcnews: Scotland take on France at Murrayfield in the third of the opening round of Six Nations fixtures. htt
p://bit.ly/98KHLc</pre>
                </font>
              </td>
            </tr>
          </tbody>
        </table>
        <p>
This is very cool – without much code we now have a live twitter feed from a single
source, which will automatically bring in new tweets (if available) every two minutes.
As a final exercise I will attempt to merge two twitter news feeds into one single
stream.
</p>
        <h5>Merging Twitter Feeds
</h5>
        <p>
It is a simple matter now to update the above code to create two input feeds and then
merge them:
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">TweetStream bbc = new TweetStream("bbcnews", 120);
TweetStream cnn = new TweetStream("cnn", 120);

var news = bbc.Stream.Merge(cnn.Stream);

var sub = news.Subscribe(i =&gt; Console.WriteLine("{0}: {1}: {2}",
                                i.Time.ToString("dd hh:mm"), i.Username, i.Status));</pre>
        <p>
Just by calling the <font size="2" face="Courier New">Merge </font>method, the output
from the two streams gets combined into a single stream. Note that the tweets from
a given stream remain in order, but the relative ordering between the two streams
depends on how they are scheduled to execute, the merge doesn’t work based on the
feed dates or Ids – this is left as an exercise for the reader.
</p>
        <table border="1">
          <tbody>
            <tr>
              <td>
                <font size="2">
                  <pre>07 12:00: bbcnews: England and Wales are drawn in the same qualifying group for Euro 2012 in Poland and the Ukraine. htt
p://bit.ly/cCEza2
07 12:00: bbcnews: Home Secretary Alan Johnson rejects the idea that MPs facing expenses charges might avoid trial by ci
ting Parli.. http://bit.ly/9tk3X9
...
07 03:20: bbcnews: A court in Libya dismisses a case against a Swiss businessman who was accused of illegal business act
ivities. http://bit.ly/da0kFc
07 03:20: bbcnews: Police have launched an inquiry after a man's body was found on a main road in rural Stirlingshire. h
ttp://bit.ly/9xHMGp
06 01:06: CNN: Toyota: Apology but no new recall. http://on.cnn.com/cxQQrj
06 01:31: CNN: All military health facilities get Plan B pill. http://on.cnn.com/dbrZox
...
06 11:26: CNN: Tonight 9 ET: Watch the Tea Party Convention's keynote address by Sarah Palin live on CNN, CNN.com and CN
N's iPhone App.
07 11:29: CNN: Residents shovel out from heavy snow as blizzard conditions sweep across the eastern U.S.: http://bit.ly/
cFmAiU
07 11:30: CNN: Steps turn into slopes:  http://bit.ly/cyVbMM</pre>
                </font>
              </td>
            </tr>
          </tbody>
        </table>
        <img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=80b71cfa-ca82-4975-bd24-89bbce180ee7" />
      </body>
      <title>A concrete example of a reactive application</title>
      <guid isPermaLink="false">http://blog.roundthecampfire.net/PermaLink,guid,80b71cfa-ca82-4975-bd24-89bbce180ee7.aspx</guid>
      <link>http://blog.roundthecampfire.net/2010/02/08/A+Concrete+Example+Of+A+Reactive+Application.aspx</link>
      <pubDate>Mon, 08 Feb 2010 22:32:02 GMT</pubDate>
      <description>&lt;p&gt;
Continuing on from my &lt;a href="http://blog.roundthecampfire.net/2010/02/06/A+Quick+Play+With+Reactive+Extensions+Rx.aspx"&gt;first
play with the Rx framework&lt;/a&gt; yesterday, I thought it would be good to come up with
a real world example. I thought about rss feeds and stock tickers, but in the end
decided on an app with consumes the &lt;a href="http://apiwiki.twitter.com/Twitter-API-Documentation"&gt;Twitter
REST API&lt;/a&gt;.
&lt;/p&gt;
&lt;p&gt;
I will build up an application which can subscribe to a couple of twitter news feeds,
polling for new messages on a particular schedule, and merging the results into a
single output stream to which we subscribe.
&lt;/p&gt;
&lt;h5&gt;Accessing the Twitter API
&lt;/h5&gt;
&lt;p&gt;
I am going to keep this very simple, just access the &lt;font size="2" face="Courier New"&gt;user_timeline&lt;/font&gt; service
for a given user, and get the results in XML format, which make it easy for us to
project into a &lt;font size="2" face="Courier New"&gt;Tweet&lt;/font&gt; class which we define.
I create a class called &lt;font size="2" face="Courier New"&gt;TwitterAccess&lt;/font&gt; with
one key &lt;font size="2" face="Courier New"&gt;static&lt;/font&gt; method:
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;public static Tweet[] GetNewTweets(string username, long lastTweetId)
{
    if(lastTweetId &amp;lt; 1)
        throw new ArgumentOutOfRangeException(&amp;quot;lastTweetId&amp;quot;, &amp;quot;id must be greater than 0&amp;quot;);

    string url = String.Format(&amp;quot;http://twitter.com/statuses/user_timeline/{0}.xml?since_id={1}&amp;quot;,
                               username.Replace(&amp;quot;@&amp;quot;, &amp;quot;&amp;quot;), lastTweetId);
    var doc = XDocument.Load(url);

    var items = from s in doc.Descendants(&amp;quot;status&amp;quot;)
                orderby long.Parse(s.Element(&amp;quot;id&amp;quot;).Value)
                select new Tweet { Id = long.Parse(s.Element(&amp;quot;id&amp;quot;).Value),
                                   Time = ParseTwitterDate(s.Element(&amp;quot;created_at&amp;quot;).Value),
                                   Username = s.Element(&amp;quot;user&amp;quot;).Element(&amp;quot;screen_name&amp;quot;).Value,
                                   Status = s.Element(&amp;quot;text&amp;quot;).Value };
     
    return items.ToArray();
}&lt;/pre&gt;
&lt;p&gt;
This method gets all tweets on the given users timeline whose ID is greater than &lt;font size="2" face="Courier New"&gt;lastTweetId&lt;/font&gt; (although
the default limit in twitter is 20 tweets, you will need to specify the &lt;font size="2" face="Courier New"&gt;count&lt;/font&gt; parameter
in the rest url if you need more, but this suits our purpose).
&lt;/p&gt;
&lt;p&gt;
The &lt;font size="2" face="Courier New"&gt;Tweet&lt;/font&gt; class just wraps the properties
you can see above, and the &lt;font size="2" face="Courier New"&gt;ParseTwitterDate&lt;/font&gt; method
just does a &lt;font size="2" face="Courier New"&gt;DateTime.ParseExact&lt;/font&gt; for the specific
date format used in twitter.
&lt;/p&gt;
&lt;h5&gt;Wrapping Twitter in an IObservable&amp;lt;T&amp;gt;
&lt;/h5&gt;
&lt;p&gt;
Now that we have a means to access twitter, we should create a class which handles
the polling of this service and pushes all new tweets out through an &lt;font size="2" face="Courier New"&gt;IObservable&amp;lt;Tweet&amp;gt;&lt;/font&gt; as
follows:
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;public class TweetStream
{
    private long lastTweet = 1;
    private object updateLock = new object();
    private IObservable&amp;lt;Tweet&amp;gt; stream;

    public IObservable&amp;lt;Tweet&amp;gt; Stream
    {
        get { return stream; }
    }

    public TweetStream(string username, int interval)
    {
        var xs = Observable.Interval(TimeSpan.FromSeconds(interval));
        stream = xs.SelectMany(count =&amp;gt;
            {
                Tweet[] items;
                lock (updateLock)
                {
                    items = TwitterAccess.GetNewTweets(username, lastTweet);
                    lastTweet = items.Length &amp;gt; 0 ? items.Last().Id : lastTweet;
                }
                return items.ToObservable();
            });
    }
}&lt;/pre&gt;
&lt;p&gt;
The &lt;font size="2" face="Courier New"&gt;SelectMany &lt;/font&gt;call allows us to define a
function which is called each time the interval fires and which itself returns an &lt;font size="2" face="Courier New"&gt;IObservable&lt;/font&gt;.
Note that we must use &lt;font size="2" face="Courier New"&gt;SelectMany &lt;/font&gt;instead
of &lt;font size="2" face="Courier New"&gt;Select &lt;/font&gt;as &lt;font size="2" face="Courier New"&gt;SelectMany &lt;/font&gt;will
automatically flatten all the items in the returned stream into its own stream of &lt;font size="2" face="Courier New"&gt;Tweets &lt;/font&gt;whereas &lt;font size="2" face="Courier New"&gt;Select &lt;/font&gt;would
leave you with a stream of &lt;font size="2" face="Courier New"&gt;IObservables&lt;/font&gt;,
which will then be difficult to handle.
&lt;/p&gt;
&lt;h5&gt;Getting some output from this stream
&lt;/h5&gt;
&lt;p&gt;
I can now update the console app we looked at yesterday in order to create an instance
of &lt;font size="2" face="Courier New"&gt;TweetStream&lt;/font&gt; and subscribe to its output,
writing this in turn out to the console.
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;TweetStream bbc = new TweetStream(&amp;quot;bbcnews&amp;quot;, 120);

var sub = bbc.Stream.Subscribe(i =&amp;gt; Console.WriteLine(&amp;quot;{0}: {1}: {2}&amp;quot;,
                                i.Time.ToString(&amp;quot;dd hh:mm&amp;quot;), i.Username, i.Status));&lt;/pre&gt;
&lt;p&gt;
Running this up we get the following output:
&lt;/p&gt;
&lt;table border="1"&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;font size="2"&gt; &lt;pre&gt;07 08:10: bbcnews: A man who was injured during a Premier League football match at Stoke City dies in hospital.  http://
bit.ly/bDjtDM
07 09:00: bbcnews: Worst snow storms to hit eastern US for decades  http://bit.ly/93Jpn9
07 09:00: bbcnews: Iran's leader asks the country's nuclear chief to begin enriching uranium to 20%, in a new challenge
to Western.. http://bit.ly/9AUplq
...
07 02:20: bbcnews: A Scottish pensioner becomes only the seventh person in history to achieve judo's highest rank. http:
//bit.ly/8XRsxv
07 02:40: bbcnews: Scotland take on France at Murrayfield in the third of the opening round of Six Nations fixtures. htt
p://bit.ly/98KHLc&lt;/pre&gt;
&lt;/font&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;
This is very cool – without much code we now have a live twitter feed from a single
source, which will automatically bring in new tweets (if available) every two minutes.
As a final exercise I will attempt to merge two twitter news feeds into one single
stream.
&lt;/p&gt;
&lt;h5&gt;Merging Twitter Feeds
&lt;/h5&gt;
&lt;p&gt;
It is a simple matter now to update the above code to create two input feeds and then
merge them:
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;TweetStream bbc = new TweetStream(&amp;quot;bbcnews&amp;quot;, 120);
TweetStream cnn = new TweetStream(&amp;quot;cnn&amp;quot;, 120);

var news = bbc.Stream.Merge(cnn.Stream);

var sub = news.Subscribe(i =&amp;gt; Console.WriteLine(&amp;quot;{0}: {1}: {2}&amp;quot;,
                                i.Time.ToString(&amp;quot;dd hh:mm&amp;quot;), i.Username, i.Status));&lt;/pre&gt;
&lt;p&gt;
Just by calling the &lt;font size="2" face="Courier New"&gt;Merge &lt;/font&gt;method, the output
from the two streams gets combined into a single stream. Note that the tweets from
a given stream remain in order, but the relative ordering between the two streams
depends on how they are scheduled to execute, the merge doesn’t work based on the
feed dates or Ids – this is left as an exercise for the reader.
&lt;/p&gt;
&lt;table border="1"&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;font size="2"&gt; &lt;pre&gt;07 12:00: bbcnews: England and Wales are drawn in the same qualifying group for Euro 2012 in Poland and the Ukraine. htt
p://bit.ly/cCEza2
07 12:00: bbcnews: Home Secretary Alan Johnson rejects the idea that MPs facing expenses charges might avoid trial by ci
ting Parli.. http://bit.ly/9tk3X9
...
07 03:20: bbcnews: A court in Libya dismisses a case against a Swiss businessman who was accused of illegal business act
ivities. http://bit.ly/da0kFc
07 03:20: bbcnews: Police have launched an inquiry after a man's body was found on a main road in rural Stirlingshire. h
ttp://bit.ly/9xHMGp
06 01:06: CNN: Toyota: Apology but no new recall. http://on.cnn.com/cxQQrj
06 01:31: CNN: All military health facilities get Plan B pill. http://on.cnn.com/dbrZox
...
06 11:26: CNN: Tonight 9 ET: Watch the Tea Party Convention's keynote address by Sarah Palin live on CNN, CNN.com and CN
N's iPhone App.
07 11:29: CNN: Residents shovel out from heavy snow as blizzard conditions sweep across the eastern U.S.: http://bit.ly/
cFmAiU
07 11:30: CNN: Steps turn into slopes:  http://bit.ly/cyVbMM&lt;/pre&gt;
&lt;/font&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=80b71cfa-ca82-4975-bd24-89bbce180ee7" /&gt;</description>
      <comments>http://blog.roundthecampfire.net/CommentView,guid,80b71cfa-ca82-4975-bd24-89bbce180ee7.aspx</comments>
      <category>Rx</category>
    </item>
    <item>
      <trackback:ping>http://blog.roundthecampfire.net/Trackback.aspx?guid=079cef0f-3e4b-4516-952d-bc307bbca158</trackback:ping>
      <pingback:server>http://blog.roundthecampfire.net/pingback.aspx</pingback:server>
      <pingback:target>http://blog.roundthecampfire.net/PermaLink,guid,079cef0f-3e4b-4516-952d-bc307bbca158.aspx</pingback:target>
      <dc:creator>Chris Ballard</dc:creator>
      <wfw:comment>http://blog.roundthecampfire.net/CommentView,guid,079cef0f-3e4b-4516-952d-bc307bbca158.aspx</wfw:comment>
      <wfw:commentRss>http://blog.roundthecampfire.net/SyndicationService.asmx/GetEntryCommentsRss?guid=079cef0f-3e4b-4516-952d-bc307bbca158</wfw:commentRss>
      <body xmlns="http://www.w3.org/1999/xhtml">
        <p>
I have finally got around to taking a look at this <a href="http://msdn.microsoft.com/en-us/devlabs/ee794896.aspx">very
interesting framework</a> by DevLabs at Microsoft. What it promises to do is amazing,
namely to revolutionize certain types of event driven (i.e. asynchronous) applications
by allowing to developer to use the familiar LINQ paradigm to manage multiple streams
of incoming asynchronous events.
</p>
        <p>
There are already a fair number of videos about Rx available on Channel 9. In my opinion, <a href="http://channel9.msdn.com/posts/Charles/Erik-Meijer-Rx-in-15-Minutes/">this
Introduction by Erik Meijer</a> is the best starting point, followed by <a href="http://channel9.msdn.com/posts/J.Van.Gogh/Writing-your-first-Rx-Application/">Wes
Dyer’s Hello World equivalent</a>. Following these there are a number of In Depth
videos, which are indexed on the <a href="http://blogs.msdn.com/rxteam/archive/2009/12/16/reactive-extensions-api-in-depth-retry.aspx">Team
Blog</a>. I cannot hope to describe Rx and its API anywhere near as well as those
guys, so for the rest of this post will assume you have at least skimmed through those
intros.
</p>
        <h4>Getting Started
</h4>
        <p>
For this quick test, I downloaded the <a href="http://download.microsoft.com/download/6/2/A/62A3E195-254C-445A-8109-6AE77A28AB63/Rx_Net35_SP1.exe">.NET
Framework 3.5 SP1 variant</a> and installed it. The install goes to <font size="2" face="Courier New">Program
Files\Microsoft Reactive Extensions\Redist\DesktopV2</font> and includes four assemblies
and matching help files.
</p>
        <p>
I crack open Visual Studio 2008 SP1 and create a new windows console application (oh
yeah, we are pushing the boat out with this demonstration). Add references to the
Rx framework assemblies:
</p>
        <h5>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Assemblies_2.png">
            <img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="Assemblies" border="0" alt="Assemblies" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Assemblies_thumb.png" width="192" height="92" />
          </a>Hello
World
</h5>
        <p>
Lets just get straight in there and create a real hello world application using the
Rx framework:
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">static void Main(string[] args)
{
    var xs = Observable.Return("Hello world");
    var sb = xs.Subscribe(msg =&gt; Console.WriteLine(msg));

    Console.WriteLine("Press any key to exit");
    Console.ReadKey();

    sb.Dispose();
}</pre>
        <p>
In this trivial snippet, we call <font size="2" face="Courier New">Observable.Return</font> which
creates an <font size="2" face="Courier New">IObservable<String></String></font> whose sole purpose is to push out a single string value and then
terminate. In itself this would achieve nothing unless we create something which can
subscribe to this stream, so we call <font size="2" face="Courier New">Subscribe</font> on
this <font size="2" face="Courier New">IObservable</font> and pass in a lambda which
takes the message content (a string) and writes it to the console. So we get:
</p>
        <p>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/HelloWorld-output_2.png">
            <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="HelloWorld-output" border="0" alt="HelloWorld-output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/HelloWorld-output_thumb.png" width="493" height="55" />
          </a>
        </p>
        <p>
This is a start, but is not exactly stretching the capabilities of Rx so far. Over
the next few demos, hopefully we can start to see some of the real possibilities.
</p>
        <h5>Counting
</h5>
        <p>
The above demo did one thing and then stopped. For real excitement, lets now create
an <font size="2" face="Courier New">IObservable</font> which just keeps pushing out
events forever:
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var sb = xs.Subscribe(i =&gt; Console.WriteLine("{0}: {1}", 
                               DateTime.Now.ToString("mm:ss"), i));</pre>
        <p>
The call to <font size="2" face="Courier New">Observable.Interval</font> gives us
an <font size="2" face="Courier New">IObservable</font> which will sit there pushing
events continuously. It starts with an integer value of 0, and after each of the defined
intervals it increments this and pushes it out again.
</p>
        <p>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementOne-Output_2.png">
            <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="IncrementOne-Output" border="0" alt="IncrementOne-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementOne-Output_thumb.png" width="494" height="106" />
          </a>
        </p>
        <p>
By itself this appears to be a relatively useless feature, but we will see later that
in conjunction with some of the more advanced facilities offered by Rx, this can be
quite powerful as a means to quantize some other stream of events.
</p>
        <h5>Advanced Counting
</h5>
        <p>
For this section, lets first start by creating two separate streams of events with <font size="2" face="Courier New">Observable.Interval</font>.
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var ys = Observable.Interval(TimeSpan.FromMilliseconds(200));

var sb1 = xs.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (xs)",
                                DateTime.Now.ToString("mm:ss"), i));
var sb2 = ys.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (ys)",
                                DateTime.Now.ToString("mm:ss"), i));</pre>
        <p>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementTwo-Output_2.png">
            <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="IncrementTwo-Output" border="0" alt="IncrementTwo-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementTwo-Output_thumb.png" width="494" height="183" />
          </a>
        </p>
        <p>
As expected, we have two streams outputting results, one ticking five times faster
than the other. If we want to synchronize these, we have two options, either throttle
each stream so that we output a single event only when both streams have a new event
available, or alternatively each time one of the streams pushes a new event we combine
that with the most recent event of the other stream. These features are provided by
the <font size="2" face="Courier New">Zip</font> and the <font size="2" face="Courier New">CombineLatest</font> methods
respectively.
</p>
        <h5>Zipping Up
</h5>
        <p>
One of the nice touches in the videos linked above is the concept of marble diagrams.
These do a very good job of visualizing some potentially mind-melting concurrency
scenarios, and also do a good job in showing what each of the Rx operators achieve.
The simple (no failures) scenario for <font size="2" face="Courier New">Zip</font> is
as follows:
</p>
        <p>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Marble_2.png">
            <img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="Zip-Marble" border="0" alt="Zip-Marble" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Marble_thumb.png" width="569" height="221" />
          </a> Each
blob represents some event occurring with <font size="2" face="Courier New">xs</font> and <font size="2" face="Courier New">ys</font> being
the input streams in this case. Stream <font size="2" face="Courier New">zs</font> is
created by zipping <font size="2" face="Courier New">xs</font> with <font size="2" face="Courier New">ys</font> and
combining the two events using the function ‘<font size="2" face="Courier New">f</font>’.
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var ys = Observable.Interval(TimeSpan.FromMilliseconds(200));
var zs = xs.Zip(ys, (x, y) =&gt; String.Format("({0},{1})", x, y));

var sb = zs.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (zs)",
                               DateTime.Now.ToString("mm:ss"), i));</pre>
        <p>
In this method we introduce the call to <font size="2" face="Courier New">Zip</font>,
which combines events from the input streams, and created new events using the lambda.
In this case we simply return a string representation of the tuple.
</p>
        <p>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Output_2.png">
            <img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="Zip-Output" border="0" alt="Zip-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Output_thumb.png" width="494" height="116" />
          </a>
        </p>
        <p>
As we can see here, the 200ms stream is effectively throttled back to the speed of
the slowest stream. In many cases this may be the desired result, but consider if
the two streams were different types of financial market data, one remains up to date
whilst the other gets more and more stale, after one hour of this, one of the streams
would be feeding data 48 minutes old.
</p>
        <h5>CombineLatest
</h5>
        <p>
So to solve this problem, another operator, CombineLatest, steps in. The marble diagram
below shows that the same type of function is performed to pair the events, but the
means for achieving this is quite different:
</p>
        <p align="center">
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Marble_2.png">
            <img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="CombineLatest-Marble" border="0" alt="CombineLatest-Marble" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Marble_thumb.png" width="569" height="221" />
          </a>
        </p>
        <p align="left">
In this case, whenever we get an event on either stream, we combine that with the
most recent event (or wait until there is one) on the other stream. So once we have
data on both streams, the combined event stream pushes events as fast as the fastest
of the input streams.
</p>
        <pre class="brush: csharp; ruler: true; auto-links: false;">var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var ys = Observable.Interval(TimeSpan.FromMilliseconds(200));
var zs = xs.CombineLatest(ys, (x, y) =&gt; String.Format("({0},{1})", x, y));

var sb = zs.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (zs)",
                               DateTime.Now.ToString("mm:ss"), i));</pre>
        <p>
          <a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Output_2.png">
            <img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="CombineLatest-Output" border="0" alt="CombineLatest-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Output_thumb.png" width="494" height="191" />
          </a>
        </p>
        <h5>Summary
</h5>
        <p>
What I have briefly looked at is just the tip of the iceberg in terms of functionality.
There are numerous other methods in the framework for dealing with events, and many
ways in which they can be composed to achieve some very powerful results. Also, I
have only looked at success scenarios so far, and Rx has much to give in terms of
dealing with exceptions and retry policies on particular event streams.
</p>
        <img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=079cef0f-3e4b-4516-952d-bc307bbca158" />
      </body>
      <title>A quick play with Reactive Extensions (Rx)</title>
      <guid isPermaLink="false">http://blog.roundthecampfire.net/PermaLink,guid,079cef0f-3e4b-4516-952d-bc307bbca158.aspx</guid>
      <link>http://blog.roundthecampfire.net/2010/02/06/A+Quick+Play+With+Reactive+Extensions+Rx.aspx</link>
      <pubDate>Sat, 06 Feb 2010 13:35:55 GMT</pubDate>
      <description>&lt;p&gt;
I have finally got around to taking a look at this &lt;a href="http://msdn.microsoft.com/en-us/devlabs/ee794896.aspx"&gt;very
interesting framework&lt;/a&gt; by DevLabs at Microsoft. What it promises to do is amazing,
namely to revolutionize certain types of event driven (i.e. asynchronous) applications
by allowing to developer to use the familiar LINQ paradigm to manage multiple streams
of incoming asynchronous events.
&lt;/p&gt;
&lt;p&gt;
There are already a fair number of videos about Rx available on Channel 9. In my opinion, &lt;a href="http://channel9.msdn.com/posts/Charles/Erik-Meijer-Rx-in-15-Minutes/"&gt;this
Introduction by Erik Meijer&lt;/a&gt; is the best starting point, followed by &lt;a href="http://channel9.msdn.com/posts/J.Van.Gogh/Writing-your-first-Rx-Application/"&gt;Wes
Dyer’s Hello World equivalent&lt;/a&gt;. Following these there are a number of In Depth
videos, which are indexed on the &lt;a href="http://blogs.msdn.com/rxteam/archive/2009/12/16/reactive-extensions-api-in-depth-retry.aspx"&gt;Team
Blog&lt;/a&gt;. I cannot hope to describe Rx and its API anywhere near as well as those
guys, so for the rest of this post will assume you have at least skimmed through those
intros.
&lt;/p&gt;
&lt;h4&gt;Getting Started
&lt;/h4&gt;
&lt;p&gt;
For this quick test, I downloaded the &lt;a href="http://download.microsoft.com/download/6/2/A/62A3E195-254C-445A-8109-6AE77A28AB63/Rx_Net35_SP1.exe"&gt;.NET
Framework 3.5 SP1 variant&lt;/a&gt; and installed it. The install goes to &lt;font size="2" face="Courier New"&gt;Program
Files\Microsoft Reactive Extensions\Redist\DesktopV2&lt;/font&gt; and includes four assemblies
and matching help files.
&lt;/p&gt;
&lt;p&gt;
I crack open Visual Studio 2008 SP1 and create a new windows console application (oh
yeah, we are pushing the boat out with this demonstration). Add references to the
Rx framework assemblies:
&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Assemblies_2.png"&gt;&lt;img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="Assemblies" border="0" alt="Assemblies" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Assemblies_thumb.png" width="192" height="92" /&gt;&lt;/a&gt;Hello
World
&lt;/h5&gt;
&lt;p&gt;
Lets just get straight in there and create a real hello world application using the
Rx framework:
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;static void Main(string[] args)
{
    var xs = Observable.Return("Hello world");
    var sb = xs.Subscribe(msg =&gt; Console.WriteLine(msg));

    Console.WriteLine("Press any key to exit");
    Console.ReadKey();

    sb.Dispose();
}&lt;/pre&gt;
&lt;p&gt;
In this trivial snippet, we call &lt;font size="2" face="Courier New"&gt;Observable.Return&lt;/font&gt; which
creates an &lt;font size="2" face="Courier New"&gt;IObservable&lt;String&gt;
&lt;/font&gt; whose sole purpose is to push out a single string value and then terminate.
In itself this would achieve nothing unless we create something which can subscribe
to this stream, so we call &lt;font size="2" face="Courier New"&gt;Subscribe&lt;/font&gt; on this &lt;font size="2" face="Courier New"&gt;IObservable&lt;/font&gt; and
pass in a lambda which takes the message content (a string) and writes it to the console.
So we get:
&lt;/p&gt;
&lt;p&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/HelloWorld-output_2.png"&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="HelloWorld-output" border="0" alt="HelloWorld-output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/HelloWorld-output_thumb.png" width="493" height="55" /&gt;&lt;/a&gt; 
&lt;/p&gt;
&lt;p&gt;
This is a start, but is not exactly stretching the capabilities of Rx so far. Over
the next few demos, hopefully we can start to see some of the real possibilities.
&lt;/p&gt;
&lt;h5&gt;Counting
&lt;/h5&gt;
&lt;p&gt;
The above demo did one thing and then stopped. For real excitement, lets now create
an &lt;font size="2" face="Courier New"&gt;IObservable&lt;/font&gt; which just keeps pushing out
events forever:
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var sb = xs.Subscribe(i =&gt; Console.WriteLine("{0}: {1}", 
                               DateTime.Now.ToString("mm:ss"), i));&lt;/pre&gt;
&lt;p&gt;
The call to &lt;font size="2" face="Courier New"&gt;Observable.Interval&lt;/font&gt; gives us
an &lt;font size="2" face="Courier New"&gt;IObservable&lt;/font&gt; which will sit there pushing
events continuously. It starts with an integer value of 0, and after each of the defined
intervals it increments this and pushes it out again.
&lt;/p&gt;
&lt;p&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementOne-Output_2.png"&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="IncrementOne-Output" border="0" alt="IncrementOne-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementOne-Output_thumb.png" width="494" height="106" /&gt;&lt;/a&gt;
&lt;/p&gt;
&lt;p&gt;
By itself this appears to be a relatively useless feature, but we will see later that
in conjunction with some of the more advanced facilities offered by Rx, this can be
quite powerful as a means to quantize some other stream of events.
&lt;/p&gt;
&lt;h5&gt;Advanced Counting
&lt;/h5&gt;
&lt;p&gt;
For this section, lets first start by creating two separate streams of events with &lt;font size="2" face="Courier New"&gt;Observable.Interval&lt;/font&gt;.
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var ys = Observable.Interval(TimeSpan.FromMilliseconds(200));

var sb1 = xs.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (xs)",
                                DateTime.Now.ToString("mm:ss"), i));
var sb2 = ys.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (ys)",
                                DateTime.Now.ToString("mm:ss"), i));&lt;/pre&gt;
&lt;p&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementTwo-Output_2.png"&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="IncrementTwo-Output" border="0" alt="IncrementTwo-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/IncrementTwo-Output_thumb.png" width="494" height="183" /&gt;&lt;/a&gt; 
&lt;/p&gt;
&lt;p&gt;
As expected, we have two streams outputting results, one ticking five times faster
than the other. If we want to synchronize these, we have two options, either throttle
each stream so that we output a single event only when both streams have a new event
available, or alternatively each time one of the streams pushes a new event we combine
that with the most recent event of the other stream. These features are provided by
the &lt;font size="2" face="Courier New"&gt;Zip&lt;/font&gt; and the &lt;font size="2" face="Courier New"&gt;CombineLatest&lt;/font&gt; methods
respectively.
&lt;/p&gt;
&lt;h5&gt;Zipping Up
&lt;/h5&gt;
&lt;p&gt;
One of the nice touches in the videos linked above is the concept of marble diagrams.
These do a very good job of visualizing some potentially mind-melting concurrency
scenarios, and also do a good job in showing what each of the Rx operators achieve.
The simple (no failures) scenario for &lt;font size="2" face="Courier New"&gt;Zip&lt;/font&gt; is
as follows:
&lt;/p&gt;
&lt;p&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Marble_2.png"&gt;&lt;img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="Zip-Marble" border="0" alt="Zip-Marble" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Marble_thumb.png" width="569" height="221" /&gt;&lt;/a&gt; Each
blob represents some event occurring with &lt;font size="2" face="Courier New"&gt;xs&lt;/font&gt; and &lt;font size="2" face="Courier New"&gt;ys&lt;/font&gt; being
the input streams in this case. Stream &lt;font size="2" face="Courier New"&gt;zs&lt;/font&gt; is
created by zipping &lt;font size="2" face="Courier New"&gt;xs&lt;/font&gt; with &lt;font size="2" face="Courier New"&gt;ys&lt;/font&gt; and
combining the two events using the function ‘&lt;font size="2" face="Courier New"&gt;f&lt;/font&gt;’.
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var ys = Observable.Interval(TimeSpan.FromMilliseconds(200));
var zs = xs.Zip(ys, (x, y) =&gt; String.Format("({0},{1})", x, y));

var sb = zs.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (zs)",
                               DateTime.Now.ToString("mm:ss"), i));&lt;/pre&gt;
&lt;p&gt;
In this method we introduce the call to &lt;font size="2" face="Courier New"&gt;Zip&lt;/font&gt;,
which combines events from the input streams, and created new events using the lambda.
In this case we simply return a string representation of the tuple.
&lt;/p&gt;
&lt;p&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Output_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="Zip-Output" border="0" alt="Zip-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/Zip-Output_thumb.png" width="494" height="116" /&gt;&lt;/a&gt; 
&lt;/p&gt;
&lt;p&gt;
As we can see here, the 200ms stream is effectively throttled back to the speed of
the slowest stream. In many cases this may be the desired result, but consider if
the two streams were different types of financial market data, one remains up to date
whilst the other gets more and more stale, after one hour of this, one of the streams
would be feeding data 48 minutes old.
&lt;/p&gt;
&lt;h5&gt;CombineLatest
&lt;/h5&gt;
&lt;p&gt;
So to solve this problem, another operator, CombineLatest, steps in. The marble diagram
below shows that the same type of function is performed to pair the events, but the
means for achieving this is quite different:
&lt;/p&gt;
&lt;p align="center"&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Marble_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="CombineLatest-Marble" border="0" alt="CombineLatest-Marble" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Marble_thumb.png" width="569" height="221" /&gt;&lt;/a&gt; 
&lt;/p&gt;
&lt;p align="left"&gt;
In this case, whenever we get an event on either stream, we combine that with the
most recent event (or wait until there is one) on the other stream. So once we have
data on both streams, the combined event stream pushes events as fast as the fastest
of the input streams.
&lt;/p&gt;
&lt;pre class="brush: csharp; ruler: true; auto-links: false;"&gt;var xs = Observable.Interval(TimeSpan.FromSeconds(1));
var ys = Observable.Interval(TimeSpan.FromMilliseconds(200));
var zs = xs.CombineLatest(ys, (x, y) =&gt; String.Format("({0},{1})", x, y));

var sb = zs.Subscribe(i =&gt; Console.WriteLine("{0}: {1} (zs)",
                               DateTime.Now.ToString("mm:ss"), i));&lt;/pre&gt;
&lt;p&gt;
&lt;a href="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Output_2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="CombineLatest-Output" border="0" alt="CombineLatest-Output" src="http://blog.roundthecampfire.net/content/binary/WindowsLiveWriter/AquickplaywithReactiveExtensionsRx_F890/CombineLatest-Output_thumb.png" width="494" height="191" /&gt;&lt;/a&gt; 
&lt;/p&gt;
&lt;h5&gt;Summary
&lt;/h5&gt;
&lt;p&gt;
What I have briefly looked at is just the tip of the iceberg in terms of functionality.
There are numerous other methods in the framework for dealing with events, and many
ways in which they can be composed to achieve some very powerful results. Also, I
have only looked at success scenarios so far, and Rx has much to give in terms of
dealing with exceptions and retry policies on particular event streams.
&lt;/p&gt;
&lt;img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=079cef0f-3e4b-4516-952d-bc307bbca158" /&gt;</description>
      <comments>http://blog.roundthecampfire.net/CommentView,guid,079cef0f-3e4b-4516-952d-bc307bbca158.aspx</comments>
      <category>Rx</category>
    </item>
    <item>
      <trackback:ping>http://blog.roundthecampfire.net/Trackback.aspx?guid=ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608</trackback:ping>
      <pingback:server>http://blog.roundthecampfire.net/pingback.aspx</pingback:server>
      <pingback:target>http://blog.roundthecampfire.net/PermaLink,guid,ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608.aspx</pingback:target>
      <dc:creator>Chris Ballard</dc:creator>
      <wfw:comment>http://blog.roundthecampfire.net/CommentView,guid,ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608.aspx</wfw:comment>
      <wfw:commentRss>http://blog.roundthecampfire.net/SyndicationService.asmx/GetEntryCommentsRss?guid=ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608</wfw:commentRss>
      <body xmlns="http://www.w3.org/1999/xhtml">
        <p>
One of the key changes in Visual Studio 2010 is the start of a move to a fully managed
code implementation. Several aspects of the product are implemented in managed code
using the Managed Extensibility Framework (MEF) - see <a href="http://blogs.msdn.com/terryclancy/archive/2009/05/19/visual-studio-2010-new-features-extensibility-points-and-partner-opportunities.aspx">Visual
Studio 2010 New Features, Extensibility Points and Partner Opportunities</a> for
the full detail, and watch <a href="http://channel9.msdn.com/posts/VisualStudio/Paramesh-Vaidyanathan-and-Rico-Mariani-The-Future-of-Visual-Studio-Extensibility/">this
video</a> by Paramesh Vaidyanathan and Rico Mariani for an overview of the direction
Microsoft is taking here.
</p>
        <p>
I want to see how easy it is to create a simple extension for Visual Studio 2010,
in terms of development and deployment, and so I start by <a href="http://go.microsoft.com/fwlink/?LinkId=147422">downloading
the SDK</a>. This SDK includes all the bits needed for developing extensions to Visual
Studio, along with a number of project templates to get you started.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-new-project-templates.png" width="80%" />
        </p>
        <p>
Notice the description of the selected template - this isn't just a blank project,
it actually implements an editor adornment, which in this case highlights every character
'a' within the editor document by putting it within a box.
</p>
        <p>
What I would like to do as a first project is to implement a similar editor adornment,
but in this case look for block comments which contain the text "TODO:" as the first
non-whitespace text in the comment, and highlight the entire comment in a graduated
red box (similar to the blue selection box we have in VS 2010). This highlight will
extend to the first line which isn't a comment (or which is a comment, but only has
whitespace characters). So something like this:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-highlight-requirement.png" />
        </p>
        <p>
So I create a new <font face="Courier New">Editor Text Adornment</font> project, and
take a look at what comes out
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-solution-explorer.png" />
        </p>
        <p>
We get two C# files and a <font face="Courier New">.vsixmanifest</font> file - which
I guess we should take a look at first. Double clicking on this opens up a property
editor
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-vsixmanifest-designer.png" width="80%" />
        </p>
        <p>
I'm not going to dig into this in detail for the moment, but looks like this gives
us the ability to define what we want packaged up with our extension in terms of additional
files and referenced packages and assemblies. We can also name our extension and define
some icons which appear in the Extension Manager. Finally we can restrict supported
versions of Visual Studio and the framework if we so desire.
</p>
        <p>
OK, now lets look at the classes. AdornmentFactory.cs is responsible for two things
- firstly it defines a new layer onto which our class will draw its adornments.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-layer-defn.png" />
        </p>
        <p>
And secondly the class itself implements <font face="Courier New">IWpfTextViewCreationListener</font> which
allows it to hook into <font face="Courier New">IWpfTextView</font> events in the <font face="Courier New">TextViewCreated</font> method.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-view-created.png" />
        </p>
        <p align="left">
I don't like the way this is implemented - ie having the contructor "do stuff" with
a class which is never used, a very non-intuitive bit of code in my opinion, it would
look better with a static method which itself calls the constructor, eg <font face="Courier New">ScarletCharacter.RegisterView(textView)</font>.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-constructor.png" />
        </p>
        <p align="left">
The constructor of our adornment class itself simply caches the view, and the adornment
layer which we registered for this view, along with some graphics objects (<font face="Courier New">Brush</font>, <font face="Courier New">Pen</font> etc
not shown above) and registers a <font face="Courier New">LayoutChanged</font> handler
for this view.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-onlayoutchanged.png" />
        </p>
        <p>
This event handler gets details of each change made in the editor, and is called when
the editor is first opened also. The <font face="Courier New">CreateVisuals</font> implementation
by default deals with highlighting all 'a' characters in the file, but we want a different
implementation. So lets rename this adornment class to <font face="Courier New">TodoHighlighter</font> and
we should get away with changing <font face="Courier New">CreateVisuals</font> to
achieve our purpose.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-create-visuals.png" />
        </p>
        <p>
This is similar to the original implementation, except here we go through all lines
in the editor, looking for those which start a TODO block, and for each of these
determine the extent of the block and then create the highlight based on a <font face="Courier New">SnapshotSpan</font>.
TODO blocks are detected with these methods:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-util-methods.png" />
        </p>
        <p>
Finally we can add some sparkle to the default brush used to draw the highlight -
we wanted a gradient red, similar to the blue used for normal highlight in the WPF
based text editor. Lets modify the constructor code as follows:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-gradient-brush.png" />
        </p>
        <p>
We should be ready to rock. Lets <font face="Courier New">F5</font> this bad boy and
see what comes out. Well, as is so happens, <font face="Courier New">F5</font> spins
up a new visual studio instance running under the debugger and by default took ages.
I stopped the debugger, changed Options to disable Historical Debug, and tried again
- much better.
</p>
        <p>
So in this debug Visual Studio, I create a console app, and modify <font face="Courier New">Program.cs</font> with
a TODO comment, and tada:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-highlight-complete.png" />
        </p>
        <p>
Great stuff, maybe needs some tweeking but the concept is proven. Now what do we do
about installing this into Visual Studio? Lets examine what has actually been generated
for us.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-bin-debug-dir.png" />
        </p>
        <p>
This is the contents of bin |&gt; debug for this project. We have what we would expect,
but also this <font face="Courier New">TodoCustomHighlighter.vsix</font> file. This
is actually the zipped package file which Visual Studio now recognises for extensions.
If we go into the Extension Manager, we should be able to select this and install
it.
</p>
        <p>
Hmm, no options there for installing from a local drive. Lets just double click on
the vsix file. This seems to work fine:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-installer.png" />
        </p>
        <p>
So I click install, then restart Visual Studio as suggested. Nothing, no sign of my
extension in the Extension Manager, and no highlighting of my TODO comments.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-manager-none.png" width="80%" />
        </p>
        <p>
Perhaps it didn't hear me. I try installing from the vsix again. This time it fails
with the following error in the log:<br /><font face="Courier New"><br />
Install Error : Microsoft.VisualStudio.ExtensionManager.AlreadyInstalledException:
TodoCustomHighlighter is already installed.</font></p>
        <p>
This is weird - looks like Visual Studio recognises that the extension has been installed,
but for some reason is not running it, or even acknowledging its existence. Looking
at the options dialog, there are some extension manager options.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-options.png" />
        </p>
        <p>
This has the option <font face="Courier New">Load extensions from my local application
data folder</font>, but this is unchecked and also disabled. I am running the
Windows 7 RTM, so this may be a UAC issue. I shut down VS and restart in escalated
mode by holding down <font face="Courier New">Ctrl-Shift</font> whilst clicking the
Visual Studio taskbar icon. This allows me to check the Load extensions... option
- great.
</p>
        <p>
Except that even now, before or after restarting Visual Studio, I still don't get
my "installed" extension. Something strange is going on here. Time to check the event
log and the registry to see if we can find out what is happening.
</p>
        <p>
OK I find the extension in <font face="Courier New">HKCU\Software\Microsoft\VisualStudio\10.0Exp\ExtensionManager\EnabledExtensions</font> containing:
</p>
        <p>
Name: <font face="Courier New">TodoCustomHighlighter..fbe86c05-ea59-4bb6-b982-b1478430e535,1.0</font><br />
Value: <font face="Courier New">C:\Users\Chris\AppData\Local\Microsoft\VisualStudio\10.0Exp\Extensions\TodoCustomHighlighter\1.0\</font></p>
        <p>
Looking for that specified directory, all I have is <font face="Courier New">C:\Users\Chris\AppData\Local\Microsoft\VisualStudio\10.0Exp\Extensions
-</font> which is empty. Possible that something went wrong because I didn't
have <font face="Courier New">Load extensions from my local application data folder</font> enabled
when I first installed the extension. I will delete this registry value, and see if
that allows me to install again.
</p>
        <p>
Nope, same problem. Although I notice the <font face="Courier New">TodoCustomHighlighter\1.0</font> folder
has appeared in the root of the C drive for some reason. Moved this to the path specified
above, but still doesn't load.
</p>
        <p>
It's annoying, but I am going to have to leave it there for now. I will monitor some
of the VSX blogs for any solutions or workarounds to this problem and update this
post when I have more info, but for now it looks like I have a working extension which
just can't be installed. 
</p>
        <p>
          <em>EDIT: I found a workaround by re-reading </em>
          <a href="http://www.hanselman.com/blog/DemoDashboardAndIDEExtensionsWhirlwindTourAroundNET4AndVisualStudio2010Beta1.aspx">
            <em>Scott
Hanselman's post on the Demo Dashboard extension</em>
          </a>
          <em> - if you just drop the
DLL into <font face="Courier New">C:\Program Files\Microsoft Visual Studio 10.0\Common7\IDE\Components</font> and
restart Visual Studio, the extension is installed, although still isn't listed in
the Extension Manager. Perhaps this area isn't quite there in this beta 1 release
for home grown extensions?</em>
        </p>
        <p>
ADDITIONAL: Finally worked it out - I noticed that I could download and install .vsix
from the <a href="http://visualstudiogallery.msdn.microsoft.com/">Visual Studio Gallery</a> but
that these had an additional part to the filename beneath the <font face="Courier New">Extensions</font> area
in <font face="Courier New">AppData</font>. I also noted that I left the Author field
blank in the .vsixmanifest file - so I fill this in with "roundthecampfire", and replace
the name GUID with a new one so that this looks like a new component.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-change-vxismanifest.png" />
        </p>
        <p>
Now if I rebuild all and reinstall from the .vsix file, it shows success (as it did
previously), but if I start Visual Studio it's a different story:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-manager-sorted.png" width="80%" />
        </p>
        <p>
Finally - I have what I wanted all along, a standalone installer file for my extension,
and a good user experience for installing it, enabling/disabling it, and for uninstall.
The process was tougher than it needed to be for me, but this is beta software, and
I guess I should have taken more notice of the little red exclaimation mark next to
Author in the .vsixmanifest editor. Hopefully come the RTM this will cause a compilation
failure, or an install failure rather than feining success.
</p>
        <img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608" />
      </body>
      <title>Visual Studio 2010 Extensibility - First Look</title>
      <guid isPermaLink="false">http://blog.roundthecampfire.net/PermaLink,guid,ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608.aspx</guid>
      <link>http://blog.roundthecampfire.net/2009/05/30/Visual+Studio+2010+Extensibility+First+Look.aspx</link>
      <pubDate>Sat, 30 May 2009 14:45:55 GMT</pubDate>
      <description>&lt;p&gt;
One of the key changes in Visual Studio 2010 is the start of a move to a fully managed
code implementation. Several aspects of the product are implemented in managed code
using the Managed Extensibility Framework (MEF) - see &lt;a href="http://blogs.msdn.com/terryclancy/archive/2009/05/19/visual-studio-2010-new-features-extensibility-points-and-partner-opportunities.aspx"&gt;Visual
Studio 2010 New Features, Extensibility Points and Partner Opportunities&lt;/a&gt;&amp;nbsp;for
the full detail, and watch &lt;a href="http://channel9.msdn.com/posts/VisualStudio/Paramesh-Vaidyanathan-and-Rico-Mariani-The-Future-of-Visual-Studio-Extensibility/"&gt;this
video&lt;/a&gt; by Paramesh Vaidyanathan and Rico Mariani for an overview of the direction
Microsoft is taking here.
&lt;/p&gt;
&lt;p&gt;
I want to see how easy it is to create a simple extension for Visual Studio 2010,
in terms of development and deployment, and so I start by &lt;a href="http://go.microsoft.com/fwlink/?LinkId=147422"&gt;downloading
the SDK&lt;/a&gt;. This SDK includes all the bits needed for developing extensions to Visual
Studio, along with a number of project templates to get you started.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-new-project-templates.png" width="80%"&gt;
&lt;/p&gt;
&lt;p&gt;
Notice the description of the selected template - this isn't just a blank project,
it actually implements an editor adornment, which in this case highlights every character
'a' within the editor document by putting it within a box.
&lt;/p&gt;
&lt;p&gt;
What I would like to do as a first project is to implement a similar editor adornment,
but in this case look for block comments which contain the text "TODO:" as the first
non-whitespace text in the comment, and highlight the entire comment in a graduated
red box (similar to the blue selection box we have in VS 2010). This highlight will
extend to the first line which isn't a comment (or which is a comment, but only has
whitespace characters). So something like this:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-highlight-requirement.png"&gt;
&lt;/p&gt;
&lt;p&gt;
So I create a new &lt;font face="Courier New"&gt;Editor Text Adornment&lt;/font&gt; project, and
take a look at what comes out
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-solution-explorer.png"&gt;
&lt;/p&gt;
&lt;p&gt;
We get two C# files and a &lt;font face="Courier New"&gt;.vsixmanifest&lt;/font&gt; file - which
I guess we should take a look at first. Double clicking on this opens up a property
editor
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-vsixmanifest-designer.png" width="80%"&gt;
&lt;/p&gt;
&lt;p&gt;
I'm not going to dig into this in detail for the moment, but looks like this gives
us the ability to define what we want packaged up with our extension in terms of additional
files and referenced packages and assemblies. We can also name our extension and define
some icons which appear in the Extension Manager. Finally we can restrict supported
versions of Visual Studio and the framework if we so desire.
&lt;/p&gt;
&lt;p&gt;
OK, now lets look at the classes. AdornmentFactory.cs is responsible for two things
- firstly it defines a new layer onto which our class will draw its adornments.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-layer-defn.png"&gt;
&lt;/p&gt;
&lt;p&gt;
And secondly the class itself implements &lt;font face="Courier New"&gt;IWpfTextViewCreationListener&lt;/font&gt; which
allows it to hook into &lt;font face="Courier New"&gt;IWpfTextView&lt;/font&gt; events in the &lt;font face="Courier New"&gt;TextViewCreated&lt;/font&gt; method.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-view-created.png"&gt;
&lt;/p&gt;
&lt;p align=left&gt;
I don't like the way this is implemented - ie having the contructor "do stuff" with
a class which is never used, a very non-intuitive bit of code in my opinion, it would
look better with a static method which itself calls the constructor, eg &lt;font face="Courier New"&gt;ScarletCharacter.RegisterView(textView)&lt;/font&gt;.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-constructor.png"&gt;
&lt;/p&gt;
&lt;p align=left&gt;
The constructor of our adornment class itself simply caches the view, and the adornment
layer which we registered for this view, along with some graphics objects (&lt;font face="Courier New"&gt;Brush&lt;/font&gt;, &lt;font face="Courier New"&gt;Pen&lt;/font&gt; etc
not shown above) and registers a &lt;font face="Courier New"&gt;LayoutChanged&lt;/font&gt; handler
for this view.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-onlayoutchanged.png"&gt;
&lt;/p&gt;
&lt;p&gt;
This event handler gets details of each change made in the editor, and is called when
the editor is first opened also. The &lt;font face="Courier New"&gt;CreateVisuals&lt;/font&gt; implementation
by default deals with highlighting all 'a' characters in the file, but we want a different
implementation. So lets rename this adornment class to &lt;font face="Courier New"&gt;TodoHighlighter&lt;/font&gt; and
we should get away with changing &lt;font face="Courier New"&gt;CreateVisuals&lt;/font&gt; to
achieve our purpose.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-create-visuals.png"&gt;
&lt;/p&gt;
&lt;p&gt;
This is similar to the original implementation, except here we go through all lines
in the editor, looking for those which start&amp;nbsp;a TODO block, and for each of these
determine the extent of the block and then create the highlight based on a &lt;font face="Courier New"&gt;SnapshotSpan&lt;/font&gt;.
TODO blocks are detected with these methods:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-util-methods.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Finally we can add some sparkle to the default brush used to draw the highlight -
we wanted a gradient red, similar to the blue used for normal highlight in the WPF
based text editor. Lets modify the constructor code as follows:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-adornment-gradient-brush.png"&gt;
&lt;/p&gt;
&lt;p&gt;
We should be ready to rock. Lets &lt;font face="Courier New"&gt;F5&lt;/font&gt; this bad boy and
see what comes out. Well, as is so happens, &lt;font face="Courier New"&gt;F5&lt;/font&gt; spins
up a new visual studio instance running under the debugger and by default took ages.
I stopped the debugger, changed Options to disable Historical Debug, and tried again
- much better.
&lt;/p&gt;
&lt;p&gt;
So in this debug Visual Studio, I create a console app, and modify &lt;font face="Courier New"&gt;Program.cs&lt;/font&gt; with
a TODO comment, and tada:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-highlight-complete.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Great stuff, maybe needs some tweeking but the concept is proven. Now what do we do
about installing this into Visual Studio? Lets examine what has actually been generated
for us.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-TODO-bin-debug-dir.png"&gt;
&lt;/p&gt;
&lt;p&gt;
This is the contents of bin |&amp;gt; debug for this project. We have what we would expect,
but also this &lt;font face="Courier New"&gt;TodoCustomHighlighter.vsix&lt;/font&gt; file. This
is actually the zipped package file which Visual Studio now recognises for extensions.
If we go into the Extension Manager, we should be able to select this and install
it.
&lt;/p&gt;
&lt;p&gt;
Hmm, no options there for installing from a local drive. Lets just double click on
the vsix file. This seems to work fine:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-installer.png"&gt;
&lt;/p&gt;
&lt;p&gt;
So I click install, then restart Visual Studio as suggested. Nothing, no sign of my
extension in the Extension Manager, and no highlighting of my TODO comments.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-manager-none.png" width="80%"&gt;
&lt;/p&gt;
&lt;p&gt;
Perhaps it didn't hear me. I try installing from the vsix again. This time it fails
with the following error in the log:&lt;br&gt;
&lt;font face="Courier New"&gt;
&lt;br&gt;
Install Error : Microsoft.VisualStudio.ExtensionManager.AlreadyInstalledException:
TodoCustomHighlighter is already installed.&lt;/font&gt;
&lt;/p&gt;
&lt;p&gt;
This is weird - looks like Visual Studio recognises that the extension has been installed,
but for some reason is not running it, or even acknowledging its existence. Looking
at the options dialog, there are some extension manager options.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-options.png"&gt;
&lt;/p&gt;
&lt;p&gt;
This has the option &lt;font face="Courier New"&gt;Load extensions from my local application
data folder&lt;/font&gt;, but this is unchecked and also disabled. I am running&amp;nbsp;the
Windows 7 RTM, so this may be a UAC issue. I shut down VS and restart&amp;nbsp;in escalated
mode by holding down &lt;font face="Courier New"&gt;Ctrl-Shift&lt;/font&gt; whilst clicking the
Visual Studio taskbar icon. This allows me to check the Load extensions... option
- great.
&lt;/p&gt;
&lt;p&gt;
Except that even now, before or after restarting Visual Studio, I still don't get
my "installed" extension. Something strange is going on here. Time to check the event
log and the registry to see if we can find out what is happening.
&lt;/p&gt;
&lt;p&gt;
OK I find the extension in &lt;font face="Courier New"&gt;HKCU\Software\Microsoft\VisualStudio\10.0Exp\ExtensionManager\EnabledExtensions&lt;/font&gt; containing:
&lt;/p&gt;
&lt;p&gt;
Name: &lt;font face="Courier New"&gt;TodoCustomHighlighter..fbe86c05-ea59-4bb6-b982-b1478430e535,1.0&lt;/font&gt;
&lt;br&gt;
Value: &lt;font face="Courier New"&gt;C:\Users\Chris\AppData\Local\Microsoft\VisualStudio\10.0Exp\Extensions\TodoCustomHighlighter\1.0\&lt;/font&gt;
&lt;/p&gt;
&lt;p&gt;
Looking for that specified directory, all I have is &lt;font face="Courier New"&gt;C:\Users\Chris\AppData\Local\Microsoft\VisualStudio\10.0Exp\Extensions
-&lt;/font&gt;&amp;nbsp;which is empty. Possible that something went wrong because I didn't
have &lt;font face="Courier New"&gt;Load extensions from my local application data folder&lt;/font&gt; enabled
when I first installed the extension. I will delete this registry value, and see if
that allows me to install again.
&lt;/p&gt;
&lt;p&gt;
Nope, same problem. Although I notice the &lt;font face="Courier New"&gt;TodoCustomHighlighter\1.0&lt;/font&gt; folder
has appeared in the root of the C drive for some reason. Moved this to the path specified
above, but still doesn't load.
&lt;/p&gt;
&lt;p&gt;
It's annoying, but I am going to have to leave it there for now. I will monitor some
of the VSX blogs for any solutions or workarounds to this problem and update this
post when I have more info, but for now it looks like I have a working extension which
just can't be installed. 
&lt;/p&gt;
&lt;p&gt;
&lt;em&gt;EDIT: I found a workaround by re-reading &lt;/em&gt;&lt;a href="http://www.hanselman.com/blog/DemoDashboardAndIDEExtensionsWhirlwindTourAroundNET4AndVisualStudio2010Beta1.aspx"&gt;&lt;em&gt;Scott
Hanselman's post on the Demo Dashboard extension&lt;/em&gt;&lt;/a&gt;&lt;em&gt; - if you just drop the
DLL into &lt;font face="Courier New"&gt;C:\Program Files\Microsoft Visual Studio 10.0\Common7\IDE\Components&lt;/font&gt; and
restart Visual Studio, the extension is installed, although still isn't listed in
the Extension Manager. Perhaps this area isn't quite there in this beta 1 release
for home grown extensions?&lt;/em&gt;
&lt;/p&gt;
&lt;p&gt;
ADDITIONAL: Finally worked it out - I noticed that I could download and install .vsix
from the &lt;a href="http://visualstudiogallery.msdn.microsoft.com/"&gt;Visual Studio Gallery&lt;/a&gt; but
that these had an additional part to the filename beneath the &lt;font face="Courier New"&gt;Extensions&lt;/font&gt; area
in &lt;font face="Courier New"&gt;AppData&lt;/font&gt;. I also noted that I left the Author field
blank in the .vsixmanifest file - so I fill this in with "roundthecampfire", and replace
the name GUID with a new one so that this looks like a new component.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-change-vxismanifest.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Now if I rebuild all and reinstall from the .vsix file, it shows success (as it did
previously), but if I start Visual Studio it's a different story:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-VSX-extension-manager-sorted.png" width="80%"&gt;
&lt;/p&gt;
&lt;p&gt;
Finally - I have what I wanted all along, a standalone installer file for my extension,
and a good user experience for installing it, enabling/disabling it, and for uninstall.
The process was tougher than it needed to be for me, but this is beta software, and
I guess I should have taken more notice of the little red exclaimation mark next to
Author in the .vsixmanifest editor. Hopefully come the RTM this will cause a compilation
failure, or an install failure rather than feining success.
&lt;/p&gt;
&lt;img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608" /&gt;</description>
      <comments>http://blog.roundthecampfire.net/CommentView,guid,ef80bfbb-7b6d-4bfd-ab69-0d9a0f185608.aspx</comments>
      <category>MEF</category>
      <category>Visual Studio 2010</category>
    </item>
    <item>
      <trackback:ping>http://blog.roundthecampfire.net/Trackback.aspx?guid=ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6</trackback:ping>
      <pingback:server>http://blog.roundthecampfire.net/pingback.aspx</pingback:server>
      <pingback:target>http://blog.roundthecampfire.net/PermaLink,guid,ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6.aspx</pingback:target>
      <dc:creator>Chris Ballard</dc:creator>
      <wfw:comment>http://blog.roundthecampfire.net/CommentView,guid,ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6.aspx</wfw:comment>
      <wfw:commentRss>http://blog.roundthecampfire.net/SyndicationService.asmx/GetEntryCommentsRss?guid=ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6</wfw:commentRss>
      <body xmlns="http://www.w3.org/1999/xhtml">
        <p>
A number of enhancements have been made to the intellisense and refactoring features
build into Visual Studio 2010 which should greatly enhance support for real test driven
development. This post documents my investigation into how well this works in reality.
</p>
        <p>
First I need to recap what I mean by "real" test driven development. This is where
each test is written <em>before</em> the code itself, which assists the developer
in focussing on the requirements, and essentially defining these requirements through
the test alone. Once the test is written, classes and method stubs are added in order
to allow the project to compile, the test is executed (and fails), then the classes
&amp; methods are updated with the required functionality, and the test re-run to
ensure that it passes. See <a href="http://en.wikipedia.org/wiki/Test-driven_development">Test
Driven Development on wikipedia</a> and the book <a href="http://www.amazon.co.uk/Test-Driven-Development-Addison-Wesley-Signature/dp/0321146530">Test
Driven Development by Kent Beck</a> for further reading.
</p>
        <p>
So to use an example that has never been done before (not) lets implement a calculator
class, and create a class library (<font face="Courier New">CalcLib</font>) and
related test assembly (<font face="Courier New">CalcLib.Test</font>) in a new solution.
Add a reference from <font face="Courier New">CalcLib.Test</font> back to <font face="Courier New">CalcLib</font>.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-calculator-class.png" />
        </p>
        <p>
Lets start by adding a test for the constructor - we (arbitrarily) decide that the
constructor should initialise the running total to whatever we ask for, so add a new
test class <font face="Courier New">CalculatorTests.cs</font> to the test project,
and add the first test <font face="Courier New">ConstructorInitialisesTotal</font> to
this class.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-test-stubs.png" />
        </p>
        <p>
Now if we start typing the test, by created a new instance of the <font face="Courier New">Calculator</font> class,
something annoying happens with intellisense - the test class itself is the default
choice, so even if we type <font face="Courier New">Calculator</font> in full and
type the first parenthesis, it autocompletes as <font face="Courier New">CalculatorTest</font> instead,
and we have to <font face="Courier New">Ctrl-Z</font> to get what we wanted. Grrrr.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-default-intellisense.png" />
        </p>
        <p>
Notice that intellisense now has an initial item which says <font face="Courier New">&lt;Ctrl-Alt-Space&gt;</font> -
type that - I dare you! This switches intellisense into Consume First Completion Mode,
which is what we have been missing all along. Now if I type <font face="Courier New">=
new Calculator();</font> I am allowed to type this without interference, and I see
the blue smart tag underline beneath <font face="Courier New">Calculator</font>. A
swift <font face="Courier New">Ctrl-.</font> gives me the <font face="Courier New">Generate...</font> menu:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-class-menu.png" />
        </p>
        <p>
So click on <font face="Courier New">Generate class for Calculator</font> - right?
I must admit I already had misgivings before I clicked on this, and this proves to
be correct - click on this option and you get a nice fat <font face="Courier New">Calculator</font> class
in a <font face="Courier New">Calculator.cs</font> source file and, sadly, inside
your <font face="Courier New">CalcLib.Test</font> project, not inside the <font face="Courier New">CalcLib</font> project.
This is unfortunate, being as this functionality is in support of TDD, it would have
been good to see some intelligence here, ie noting that the current proj is a test
project, and has a single reference to another project in the same solution, and at
least give us a third option in the menu such as <font face="Courier New">Generate
class for Calculator in CalcLib project</font>.
</p>
        <p>
OK, not as good as it should have been. Click on <font face="Courier New">Generate
other...</font> instead - this is more long winded, but gives us the flexibility that
we are after:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-other-dialog.png" />
        </p>
        <p>
A quick flip of the project menu, press OK, and presto - we now have <font face="Courier New">Calculator.cs</font> in
our <font face="Courier New">CalcLib</font> project - is nice. The solution should
now build correctly.
</p>
        <p>
Still not much use, because we have an empty test testing an empty class, so lets
expand the test firstly by adding a double parameter to the call to the <font face="Courier New">Calculator</font> constructor,
thus:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-ctor-menu.png" />
        </p>
        <p>
Clicking this gives us a constructor taking a double value as a parameter (albeit
it generates a spurious backing property for this parameter, which we don't want in
this case - however if it had prompted for a name, we could have added the Total property
in one hit, never mind).
</p>
        <p>
Now lets add an assertion that the contructor sets the Total property, and in so doing
generate this property in the <font face="Courier New">Calculator</font> class.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-prop-field-menu[1].png" />
        </p>
        <p>
If we take the <font face="Courier New">Generate property stub...</font> option and
complete the assertion, we now have our test complete and the <font face="Courier New">Calculator</font> class
in a compileable state - so lets compile and run the tests. Oops, it doesn't build
- the property it generated for us is the wrong type, it can't really infer the type
from that overload of <font face="Courier New">Assert.AreEqual</font>, so it has a
guess.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-incorrect-prop.png" />
        </p>
        <p>
Lets try that again, but this time use the generic version of <font face="Courier New">AreEqual</font> so
that we know the concrete types for the parameters to this method - hopefully that
will allow <font face="Courier New">Generate property stub</font> to correctly guess
the type?
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-ctor-initialise-test.png" />
        </p>
        <p>
Which generates the property as follows:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-correct-prop.png" />
        </p>
        <p>
Much better, so now we CAN compile and run the tests with a <font face="Courier New">Ctrl-R,
A</font> and lets see what we get...
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-tests-failed.png" />
        </p>
        <p>
Well that sucks - it failed, why? Oh, maybe because we haven't actually implemented
the constructor yet - lets do that now.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-implement-ctor.png" />
        </p>
        <p>
Now we can build and run the tests one last time - 
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-tests-passed.png" />
        </p>
        <p>
Great, so we have implemented a test which defines our requirements, observed that
the test fails befored the requirement is implemented, and finally observed that once
implemented the test passes.
</p>
        <p>
Visual Studio 2010 goes some way towards supporting this method of development, although
we have seen a few shortcomings in this beta 1 version. Hopefully at least the issue
with generating code within the referenced assembly rather than the test assembly
itself can be addressed prior to RTM.
</p>
        <h4>Addendum
</h4>
        <p>
Got a great response from Karen Liu, Lead Program Manager on the C# and VB IDE team
regarding my questions above, and a quick search revealed some great channel 9 videos
she has produced in this same area, especially <a href="http://channel9.msdn.com/posts/VisualStudio/Test-Driven-Development-with-Visual-Studio-2010/">this
one</a> which has the exact same topic as this blog post, and I am embarrased
that I didn't spot this beforehand...
</p>
        <p>
Regarding the first issue - the fact that <font face="Courier New">Generate class</font> only
generates within the current assembly: the thinking here is that to iterate over referenced
assemblies might slow the presentation of the Generate menu, hence the decision was
made to only generate within the same class, and refactor later, or to use the <font face="Courier New">Generate
other</font> function, as I suggested above.
</p>
        <p>
Regarding the spuriously named property generated with the constructor - Karen had
a great suggestion - use a named parameter (C# 4.0 feature), which the <font face="Courier New">Generate
constructor</font> function picks up on as expected, so:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-ctor-named-param-menu.png" />
        </p>
        <p>
Gives us a Calculator class which is already exactly what we need - we don't need
to create the <font face="Courier New">Total</font> property in a later step as we
did before.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-calculator-class2.png" />
        </p>
        <p>
Thanks for the suggestions Karen - looking forward to seeing what we get in the next
release!
</p>
        <img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6" />
      </body>
      <title>An Investigation into Test Driven Development with Visual Studio 2010</title>
      <guid isPermaLink="false">http://blog.roundthecampfire.net/PermaLink,guid,ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6.aspx</guid>
      <link>http://blog.roundthecampfire.net/2009/05/28/An+Investigation+Into+Test+Driven+Development+With+Visual+Studio+2010.aspx</link>
      <pubDate>Thu, 28 May 2009 09:57:05 GMT</pubDate>
      <description>&lt;p&gt;
A number of enhancements have been made to the intellisense and refactoring features
build into Visual Studio 2010 which should greatly enhance support for real test driven
development. This post documents my investigation into how well this works in reality.
&lt;/p&gt;
&lt;p&gt;
First I need to recap what I mean by "real" test driven development. This is where
each test&amp;nbsp;is written &lt;em&gt;before&lt;/em&gt; the code itself, which assists the developer
in focussing on the requirements, and essentially defining these requirements through
the test alone. Once the test is written, classes and method stubs are added in order
to allow the project to compile, the test is executed (and fails), then the classes
&amp;amp; methods are updated with the required functionality, and the test re-run to
ensure that it passes. See &lt;a href="http://en.wikipedia.org/wiki/Test-driven_development"&gt;Test
Driven Development on wikipedia&lt;/a&gt; and the book &lt;a href="http://www.amazon.co.uk/Test-Driven-Development-Addison-Wesley-Signature/dp/0321146530"&gt;Test
Driven Development by Kent Beck&lt;/a&gt;&amp;nbsp;for further reading.
&lt;/p&gt;
&lt;p&gt;
So to use an example that has never been done before (not) lets implement a calculator
class, and create a class&amp;nbsp;library (&lt;font face="Courier New"&gt;CalcLib&lt;/font&gt;) and
related test assembly (&lt;font face="Courier New"&gt;CalcLib.Test&lt;/font&gt;) in a new solution.
Add a reference from &lt;font face="Courier New"&gt;CalcLib.Test&lt;/font&gt; back to &lt;font face="Courier New"&gt;CalcLib&lt;/font&gt;.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-calculator-class.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Lets start by adding a test for the constructor - we (arbitrarily) decide that the
constructor should initialise the running total to whatever we ask for, so add a new
test class &lt;font face="Courier New"&gt;CalculatorTests.cs&lt;/font&gt; to the test project,
and add the first test &lt;font face="Courier New"&gt;ConstructorInitialisesTotal&lt;/font&gt; to
this class.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-test-stubs.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Now if we start typing the test, by created a new instance of the &lt;font face="Courier New"&gt;Calculator&lt;/font&gt; class,
something annoying happens with intellisense - the test class itself is the default
choice, so even if we type &lt;font face="Courier New"&gt;Calculator&lt;/font&gt; in full and
type the first parenthesis, it autocompletes as &lt;font face="Courier New"&gt;CalculatorTest&lt;/font&gt; instead,
and we have to &lt;font face="Courier New"&gt;Ctrl-Z&lt;/font&gt; to get what we wanted. Grrrr.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-default-intellisense.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Notice that intellisense now has an initial item which says &lt;font face="Courier New"&gt;&amp;lt;Ctrl-Alt-Space&amp;gt;&lt;/font&gt; -
type that - I dare you! This switches intellisense into Consume First Completion Mode,
which is what we have been missing all along. Now if I type &lt;font face="Courier New"&gt;=
new Calculator();&lt;/font&gt; I am allowed to type this without interference, and I see
the blue smart tag underline beneath &lt;font face="Courier New"&gt;Calculator&lt;/font&gt;. A
swift &lt;font face="Courier New"&gt;Ctrl-.&lt;/font&gt; gives me the &lt;font face="Courier New"&gt;Generate...&lt;/font&gt; menu:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-class-menu.png"&gt;
&lt;/p&gt;
&lt;p&gt;
So click on &lt;font face="Courier New"&gt;Generate class for Calculator&lt;/font&gt; - right?
I must admit I already had misgivings before I clicked on this, and this proves to
be correct - click on this option&amp;nbsp;and you get a nice fat&amp;nbsp;&lt;font face="Courier New"&gt;Calculator&lt;/font&gt; class
in a &lt;font face="Courier New"&gt;Calculator.cs&lt;/font&gt; source file and, sadly, inside
your &lt;font face="Courier New"&gt;CalcLib.Test&lt;/font&gt; project, not inside the &lt;font face="Courier New"&gt;CalcLib&lt;/font&gt; project.
This is unfortunate, being as this functionality is in support of TDD, it would have
been good to see some intelligence here, ie noting that the current proj is a test
project, and has a single reference to another project in the same solution, and at
least give us a third option in the menu such as&amp;nbsp;&lt;font face="Courier New"&gt;Generate
class for Calculator in CalcLib project&lt;/font&gt;.
&lt;/p&gt;
&lt;p&gt;
OK, not as good as it should have been. Click on &lt;font face="Courier New"&gt;Generate
other...&lt;/font&gt; instead - this is more long winded, but gives us the flexibility that
we are after:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-other-dialog.png"&gt;
&lt;/p&gt;
&lt;p&gt;
A quick flip of the project menu, press OK, and presto - we now have &lt;font face="Courier New"&gt;Calculator.cs&lt;/font&gt; in
our &lt;font face="Courier New"&gt;CalcLib&lt;/font&gt; project - is nice. The solution should
now build correctly.
&lt;/p&gt;
&lt;p&gt;
Still not much use, because we have an empty test testing an empty class, so lets
expand the test firstly by adding a double parameter to the call to the &lt;font face="Courier New"&gt;Calculator&lt;/font&gt; constructor,
thus:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-ctor-menu.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Clicking this gives us a constructor taking a double value as a parameter (albeit
it generates a spurious backing property for this parameter, which we don't want in
this case - however if it had prompted for a name, we could have added the Total property
in one hit, never mind).
&lt;/p&gt;
&lt;p&gt;
Now lets add an assertion that the contructor sets the Total property, and in so doing
generate this property in the &lt;font face="Courier New"&gt;Calculator&lt;/font&gt; class.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-prop-field-menu[1].png"&gt;
&lt;/p&gt;
&lt;p&gt;
If we take the &lt;font face="Courier New"&gt;Generate property stub...&lt;/font&gt; option and
complete the assertion, we now have our test complete and the &lt;font face="Courier New"&gt;Calculator&lt;/font&gt; class
in a compileable state - so lets compile and run the tests. Oops, it doesn't build
- the property it generated for us is the wrong type, it can't really infer the type
from that overload of &lt;font face="Courier New"&gt;Assert.AreEqual&lt;/font&gt;, so it has a
guess.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-incorrect-prop.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Lets try that again, but this time use the generic version of &lt;font face="Courier New"&gt;AreEqual&lt;/font&gt; so
that we know the concrete types for the parameters to this method - hopefully that
will allow &lt;font face="Courier New"&gt;Generate property stub&lt;/font&gt; to correctly guess
the type?
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-ctor-initialise-test.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Which generates the property as follows:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-correct-prop.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Much better, so now we CAN compile and run the tests with a &lt;font face="Courier New"&gt;Ctrl-R,
A&lt;/font&gt; and lets see what we get...
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-tests-failed.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Well that sucks -&amp;nbsp;it failed, why? Oh, maybe because we haven't actually implemented
the constructor yet - lets do that now.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-implement-ctor.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Now we can build and run the tests one last time - 
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-tests-passed.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Great, so we have implemented a test which defines our requirements, observed that
the test fails befored the requirement is implemented, and finally observed that once
implemented the test passes.
&lt;/p&gt;
&lt;p&gt;
Visual Studio 2010 goes some way towards supporting this method of development, although
we have seen a few shortcomings in this beta 1 version. Hopefully at least the issue
with generating code within the referenced assembly rather than the test assembly
itself can be addressed prior to RTM.
&lt;/p&gt;
&lt;h4&gt;Addendum
&lt;/h4&gt;
&lt;p&gt;
Got a great response from Karen Liu, Lead Program Manager on the C# and VB IDE team
regarding my questions above, and a quick search revealed some great channel 9 videos
she has produced in this same area, especially &lt;a href="http://channel9.msdn.com/posts/VisualStudio/Test-Driven-Development-with-Visual-Studio-2010/"&gt;this
one&lt;/a&gt;&amp;nbsp;which has the exact same topic as this blog post, and I am embarrased
that I didn't spot this beforehand...
&lt;/p&gt;
&lt;p&gt;
Regarding the first issue - the fact that &lt;font face="Courier New"&gt;Generate class&lt;/font&gt; only
generates within the current assembly: the thinking here is that to iterate over referenced
assemblies might slow the presentation of the Generate menu, hence the decision was
made to only generate within the same class, and refactor later, or to use the &lt;font face="Courier New"&gt;Generate
other&lt;/font&gt; function, as I suggested above.
&lt;/p&gt;
&lt;p&gt;
Regarding the spuriously named property generated with the constructor - Karen had
a great suggestion - use a named parameter (C# 4.0 feature), which the &lt;font face="Courier New"&gt;Generate
constructor&lt;/font&gt; function picks up on as expected, so:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-gen-ctor-named-param-menu.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Gives us a Calculator class which is already exactly what we need - we don't need
to create the &lt;font face="Courier New"&gt;Total&lt;/font&gt; property in a later step as we
did before.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-tdd-calculator-class2.png"&gt;
&lt;/p&gt;
&lt;p&gt;
Thanks for the suggestions Karen - looking forward to seeing what we get in the next
release!
&lt;/p&gt;
&lt;img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6" /&gt;</description>
      <comments>http://blog.roundthecampfire.net/CommentView,guid,ec2585b4-7579-4b3a-85b1-e2fdc8ff31b6.aspx</comments>
      <category>Agile Development</category>
      <category>Visual Studio 2010</category>
    </item>
    <item>
      <trackback:ping>http://blog.roundthecampfire.net/Trackback.aspx?guid=c5066265-8323-47fc-b4f5-38612e2554ad</trackback:ping>
      <pingback:server>http://blog.roundthecampfire.net/pingback.aspx</pingback:server>
      <pingback:target>http://blog.roundthecampfire.net/PermaLink,guid,c5066265-8323-47fc-b4f5-38612e2554ad.aspx</pingback:target>
      <dc:creator>Chris Ballard</dc:creator>
      <wfw:comment>http://blog.roundthecampfire.net/CommentView,guid,c5066265-8323-47fc-b4f5-38612e2554ad.aspx</wfw:comment>
      <wfw:commentRss>http://blog.roundthecampfire.net/SyndicationService.asmx/GetEntryCommentsRss?guid=c5066265-8323-47fc-b4f5-38612e2554ad</wfw:commentRss>
      <body xmlns="http://www.w3.org/1999/xhtml">
        <p>
One of the major new features in VS2010 is Historical Debugging. This feature automatically
instruments applications running under the debugger, causing key events to be logged
into trace log files. These trace logs are integrated with the VS2010 debugger, and
enable the developer to step back through these events when looking for clues. It
is no longer necessary to set a breakpoint <em>before</em> the point at which the
bug occurs.
</p>
        <p>
There are two levels of logging supported by Historical Debugging, the first designed
to capture events at the OS / Framework level - such as registry access, file access,
exceptions etc. The second level supports instrumentation of methods and parameters
within your own code (and obviously has a significant impact on performance, although
we will dig into that a little later in this exercise). This is all set up within
Options |&gt; Historical Debugging |&gt; General:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-opts.png" />
        </p>
        <h3>Historical Debugger Operation
</h3>
        <p>
In order to test this feature, I have cobbled together a little console app which
does some file writes and reads as well as writing to the console. I have also introduced
a bug which should give us a FileNotFoundException somewhere in the code, but which
is immediately caught and swallowed - something which would previously have hindered
debugging. The main program is simply:
</p>
        <div align="center">
          <pre>
            <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet1.png" />
          </pre>
        </div>
        <p>
This makes use of two utility classes, one for creating a temporary file containing
the given text, and one for writing the contents of a specified file to the console:
</p>
        <div align="center">
          <pre>
            <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px">
              <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: blue; FONT-SIZE: 11px">
                <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet2.png" />
              </span>
            </span>
          </pre>
          <pre>
            <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px">
              <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: blue; FONT-SIZE: 11px">
                <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet3.png" />
              </span>
            </span>
          </pre>
        </div>
        <pre>
          <pre>
            <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px">
              <pre>
                <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px">
                </span>
              </pre>
            </span>
          </pre>So
now I can F5 this into the debugger, and immediately see something new:</pre>
        <p>
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-running.png" width="100%" />
        </p>
        <p>
The Debug History window gives us the ability to suspend a running application at
any time, and then look through the historical data captured so far. We can see some
failures occuring in that console output, so let's do that now. A list of eventds
is presented in this historical view, and scrolling up a little we can see some interesting
events prior to the console "Failed" output (note that Console output is not treated
as an event by default - I have enabled this in Options |&gt; Historical Debugging
|&gt; Diagnostic Events):
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-captured-events[1].png" />
        </p>
        <p>
We can see now that an exception has been thrown and caught, and the detail of this
exception actually gives us the reason - the filename has a spurious $ on the end.
We can also see this in the File: Access event above. However, assuming we didn't
get the detail we needed as this point, we can switch to Debug Tree view, at which
point we can take a look at our own call hierarchy - eg select the File: Access event,
then click on Show Tree View:
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-tree-view[1].png" />
        </p>
        <p>
Here we can see a lot of useful information - we can see the actual call to FileOutputter.WriteFile
and the parameter value supplied. Also, if we double click on this, we can see the
relevant line in the source file, and can even set watches for values which have been
logged (eg the filePath method parameter) - although anything which has not been logged
(such as local variables) will show "[Historical Data Has Not Been Collected]". 
</p>
        <p>
This is all clearly an invaluable resource for if not finding a big immediately based
on the historical data, then at least giving us a good idea as to where we should
set our initial breakpoint prior to a traditional debugging session.
</p>
        <p>
Clearly we don't get any of this for free, so lets now dig into some of the performance
aspects.
</p>
        <h3>Historical Debug Performance
</h3>
        <p>
In order to get some useful performance stats, I have modified the outputter class
to instead just keep a running total of the string lengths, and modified the main
routine as follows:
</p>
        <div align="center">
          <pre>
            <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px">
              <span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: blue; FONT-SIZE: 11px">
                <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet4.png" />
              </span>
            </span>
          </pre>
        </div>
        <p>
So we repeat the main loop 5,000 times, which should be enough to get some reasonable
numbers for overall execution time, and enough to get some relatively significant
trace log files. The test is repeated several times (results are averaged) for three
setups, all running under the debugger, but once with Historical Debug disabled, then
enabled in Events only mode, and finally in Full mode.
</p>
        <p align="center">
          <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-perf-stats.png" />
        </p>
        <p>
As expected, when running with Historical Debug enabled, the performance impact is
very significant (two orders of magnitude slower) albeit this is an extreme test with
logged events occuring continuously in a tight loop, so this should be nowhere near
as significant in typical client (eg WinForms) applications. However, this does signify
that in many cases this technology would not be appropriate for debugging server apps.
</p>
        <p>
One slight anomaly is that the full historical mode actually runs quicker than the
events only mode. It would be interesting to find out why this is, possibly due to
the full mode doing some sort of IL weaving which actually proves to be more efficient
in a simplistic piece of code like this.
</p>
        <p>
Anyway, performance issues asside, this looks like a very interesting bit of technology
which will prove highly useful in debugging intermittent or deeply buried issues in
client applications. Don't forget to disable it when debugging your server code though.
</p>
        <p>
For more detail check out <a href="http://channel9.msdn.com/posts/VisualStudio/Historical-Debugger-and-Test-Impact-Analysis-in-Visual-Studio-Team-System-2010/">this
video</a> on channel 9 which shows it all in action.
</p>
        <img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=c5066265-8323-47fc-b4f5-38612e2554ad" />
      </body>
      <title>Visual Studio 2010 - Historical Debugging</title>
      <guid isPermaLink="false">http://blog.roundthecampfire.net/PermaLink,guid,c5066265-8323-47fc-b4f5-38612e2554ad.aspx</guid>
      <link>http://blog.roundthecampfire.net/2009/05/27/Visual+Studio+2010+Historical+Debugging.aspx</link>
      <pubDate>Wed, 27 May 2009 10:55:37 GMT</pubDate>
      <description>&lt;p&gt;
One of the major new features in VS2010 is Historical Debugging. This feature automatically
instruments applications running under the debugger, causing key events to be logged
into trace log files. These trace logs are integrated with the VS2010 debugger, and
enable the developer to step back through these events when looking for clues. It
is no longer necessary to set a breakpoint &lt;em&gt;before&lt;/em&gt; the point at which the
bug occurs.
&lt;/p&gt;
&lt;p&gt;
There are two levels of logging supported by Historical Debugging, the first designed
to capture events at the OS / Framework level - such as registry access, file access,
exceptions etc. The second level supports instrumentation of methods and parameters
within your own code (and obviously has a significant impact on performance, although
we will dig into that a little later in this exercise). This is all set up within
Options |&amp;gt; Historical Debugging |&amp;gt; General:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-opts.png"&gt;
&lt;/p&gt;
&lt;h3&gt;Historical Debugger Operation
&lt;/h3&gt;
&lt;p&gt;
In order to test this feature, I have cobbled together a little console app which
does some file writes and reads as well as writing to the console. I have also introduced
a bug which should give us a FileNotFoundException somewhere in the code, but which
is immediately caught and swallowed - something which would previously have hindered
debugging. The main program is simply:
&lt;/p&gt;
&lt;div align=center&gt;&lt;pre&gt;&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet1.png"&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;p&gt;
This makes use of two utility classes, one for creating a temporary file containing
the given text, and one for writing the contents of a specified file to the console:
&lt;/p&gt;
&lt;div align=center&gt;&lt;pre&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px"&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: blue; FONT-SIZE: 11px"&gt;&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet2.png"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px"&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: blue; FONT-SIZE: 11px"&gt;&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet3.png"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;pre&gt;&lt;pre&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px"&gt;&lt;pre&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/span&gt;&lt;/pre&gt;So
now I can F5 this into the debugger, and immediately see something new:&lt;/pre&gt;
&lt;p&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-running.png" width="100%"&gt;
&lt;/p&gt;
&lt;p&gt;
The Debug History window gives us the ability to suspend a running application at
any time, and then look through the historical data captured so far. We can see some
failures occuring in that console output, so let's do that now. A list of eventds
is presented in this historical view, and scrolling up a little we can see some interesting
events prior to the console "Failed" output (note that Console output is not treated
as an event by default - I have enabled this in Options |&amp;gt; Historical Debugging
|&amp;gt; Diagnostic Events):
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-captured-events[1].png"&gt;
&lt;/p&gt;
&lt;p&gt;
We can see now that an exception has been thrown and caught, and the detail of this
exception actually gives us the reason - the filename has a spurious $ on the end.
We can also see this in the File: Access event above. However, assuming we didn't
get the detail we needed as this point, we can switch to Debug Tree view, at which
point we can take a look at our own call hierarchy - eg select the File: Access event,
then click on Show Tree View:
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-tree-view[1].png"&gt;
&lt;/p&gt;
&lt;p&gt;
Here we can see a lot of useful information - we can see the actual call to FileOutputter.WriteFile
and the parameter value supplied. Also, if we double click on this, we can see the
relevant line in the source file, and can even set watches for values which have been
logged (eg the filePath method parameter) - although anything which has not been logged
(such as local variables) will show "[Historical Data Has Not Been Collected]".&amp;nbsp;
&lt;/p&gt;
&lt;p&gt;
This is all clearly an invaluable resource for if not finding a big immediately based
on the historical data, then at least giving us a good idea as to where we should
set our initial breakpoint prior to a traditional debugging session.
&lt;/p&gt;
&lt;p&gt;
Clearly we don't get any of this for free, so lets now dig into some of the performance
aspects.
&lt;/p&gt;
&lt;h3&gt;Historical Debug Performance
&lt;/h3&gt;
&lt;p&gt;
In order to get some useful performance stats, I have modified the outputter class
to instead just keep a running total of the string lengths, and modified the main
routine as follows:
&lt;/p&gt;
&lt;div align=center&gt;&lt;pre&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: black; FONT-SIZE: 11px"&gt;&lt;span style="BACKGROUND-COLOR: transparent; FONT-FAMILY: Courier New; COLOR: blue; FONT-SIZE: 11px"&gt;&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-snippet4.png"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;
&lt;/div&gt;
&lt;p&gt;
So we repeat the main loop 5,000 times, which should be enough to get some reasonable
numbers for overall execution time, and enough to get some relatively significant
trace log files. The test is repeated several times (results are averaged)&amp;nbsp;for&amp;nbsp;three
setups, all running under the debugger, but once with Historical Debug disabled, then
enabled in Events only mode, and finally in Full mode.
&lt;/p&gt;
&lt;p align=center&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-histo-debug-perf-stats.png"&gt;
&lt;/p&gt;
&lt;p&gt;
As expected, when running with Historical Debug enabled, the performance impact is
very significant (two orders of magnitude slower) albeit this is an extreme test with
logged events occuring continuously in a tight loop, so this should be nowhere near
as significant in typical client (eg WinForms) applications. However, this does signify
that in many cases this technology would not be appropriate for debugging server apps.
&lt;/p&gt;
&lt;p&gt;
One slight anomaly is that the full historical mode actually runs quicker than the
events only mode. It would be interesting to find out why this is, possibly due to
the full mode doing some sort of IL weaving which actually proves to be more efficient
in a simplistic piece of code like this.
&lt;/p&gt;
&lt;p&gt;
Anyway, performance issues asside, this looks like a very interesting bit of technology
which will prove highly useful in debugging intermittent or deeply buried issues in
client applications. Don't forget to disable it when debugging your server code though.
&lt;/p&gt;
&lt;p&gt;
For more detail check out &lt;a href="http://channel9.msdn.com/posts/VisualStudio/Historical-Debugger-and-Test-Impact-Analysis-in-Visual-Studio-Team-System-2010/"&gt;this
video&lt;/a&gt;&amp;nbsp;on channel 9 which shows it all in action.
&lt;/p&gt;
&lt;img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=c5066265-8323-47fc-b4f5-38612e2554ad" /&gt;</description>
      <comments>http://blog.roundthecampfire.net/CommentView,guid,c5066265-8323-47fc-b4f5-38612e2554ad.aspx</comments>
      <category>Visual Studio 2010</category>
    </item>
    <item>
      <trackback:ping>http://blog.roundthecampfire.net/Trackback.aspx?guid=a8149bda-7e67-4926-bc8f-67adafae951f</trackback:ping>
      <pingback:server>http://blog.roundthecampfire.net/pingback.aspx</pingback:server>
      <pingback:target>http://blog.roundthecampfire.net/PermaLink,guid,a8149bda-7e67-4926-bc8f-67adafae951f.aspx</pingback:target>
      <dc:creator>Chris Ballard</dc:creator>
      <wfw:comment>http://blog.roundthecampfire.net/CommentView,guid,a8149bda-7e67-4926-bc8f-67adafae951f.aspx</wfw:comment>
      <wfw:commentRss>http://blog.roundthecampfire.net/SyndicationService.asmx/GetEntryCommentsRss?guid=a8149bda-7e67-4926-bc8f-67adafae951f</wfw:commentRss>
      <body xmlns="http://www.w3.org/1999/xhtml">
        <p>
Following my usual technique of learning a new technology by blogging about it, I
have decided to start a series covering new features in Visual Studio 2010 and .NET
Framework 4.0 / C# 4.0 (these posts will be based on <a href="http://go.microsoft.com/fwlink/?LinkId=147407">Visual
Studio 2010 Team System Edition, Beta 1</a>, which is available at that link for public
download).
</p>
        <img border="0" src="http://blog.roundthecampfire.net/content/binary/VS2010-home-page.png" width="100%" />
        <p>
I will start by looking at some of the basic new VS2010 features, and then go in depth
into some of the more extensive new features, such as the Architecture Browser, Data
Modelling and Code Metrics. Following this I will look into what's new in .NET 4.0
and C# 4.0, with a little help from my trusty Reflector. 
</p>
        <p>
Posts to follow soon, and will be indexed from this entry.
</p>
        <img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=a8149bda-7e67-4926-bc8f-67adafae951f" />
      </body>
      <title>Visual Studio 2010, C# 4.0 and .NET 4.0 series introduction</title>
      <guid isPermaLink="false">http://blog.roundthecampfire.net/PermaLink,guid,a8149bda-7e67-4926-bc8f-67adafae951f.aspx</guid>
      <link>http://blog.roundthecampfire.net/2009/05/26/Visual+Studio+2010+C+40+And+NET+40+Series+Introduction.aspx</link>
      <pubDate>Tue, 26 May 2009 12:47:57 GMT</pubDate>
      <description>&lt;p&gt;
Following my usual technique of learning a new technology by blogging about it, I
have decided to start a series covering new features in Visual Studio 2010 and .NET
Framework 4.0 / C# 4.0 (these posts will be based on &lt;a href="http://go.microsoft.com/fwlink/?LinkId=147407"&gt;Visual
Studio 2010 Team System Edition, Beta 1&lt;/a&gt;, which is available at that link for public
download).
&lt;/p&gt;
&lt;img border=0 src="http://blog.roundthecampfire.net/content/binary/VS2010-home-page.png" width="100%"&gt; 
&lt;p&gt;
I will start by looking at some of the basic new VS2010 features, and then go in depth
into some of the more extensive new features, such as the Architecture Browser, Data
Modelling and Code Metrics. Following this I will look into what's new in .NET 4.0
and C# 4.0, with a little help from my trusty Reflector. 
&lt;p&gt;
Posts to follow soon, and will be indexed from this entry.
&lt;/p&gt;
&lt;img width="0" height="0" src="http://blog.roundthecampfire.net/aggbug.ashx?id=a8149bda-7e67-4926-bc8f-67adafae951f" /&gt;</description>
      <comments>http://blog.roundthecampfire.net/CommentView,guid,a8149bda-7e67-4926-bc8f-67adafae951f.aspx</comments>
      <category>.NET 4.0</category>
      <category>C# 4.0</category>
      <category>Visual Studio 2010</category>
    </item>
  </channel>
</rss>