Register Login

 

Welcome to the Coach Factor blog. Here you will find all of our ideas on software development. Subscribe at  http://blog.nventive.net.

# Monday, October 26, 2009

Les tweets de la semaine

http://twitter.com/PauloMorgado/statuses/5345415268: Pouvoir démarrer un serveur Cassini (le serveur utilisé par Visual Studio) à partir de n’importe quel répertoire, la solution pour ASP.NET 3.5 /4.

http://twitter.com/sensenet une alternative open source à Sharepoint

http://twitter.com/rogerjenn/statuses/5340211244 .NET Services va connaître une mise à jour majeure le 5 novembre, deux semaines avant l’annonce officielle de l’offre commerciale.

La question Stackoverflow

http://stackoverflow.com/questions/885955/whats-the-compelling-reason-to-upgrade-to-visual-studio-2010-from-vs2008

Pour continuer sur la sortie la semaine dernière de Visual Studio 2010 beta 2, voici une liste de fonctionnalités et améliorations pour vous déculpabiliser d'avoir installer une version beta sur votre poste de développeur (alors que votre patron vous l’a expressément interdit bien sûr).

Actualités Microsoft

Où est passé Dublin ? Le serveur d’application présenté pendant la PDC 2008 n’a pas fait beaucoup parler de lui depuis. Un planning a été annoncé : beta 1 fermée en fin d’année et RTM au printemps 2010 mais à part les présentations colorées on en a pas vu beaucoup plus sur l’assemblage de WCF et WF autour de IIS. En attendant on devra se contenter de retours sur certaines présentations. Le PDC répondra peut-être à certaines interrogations, mais WF4 et WCF4 sont déjà deux Frameworks pouvant nous occuper jusqu’au printemps…

Actualités Alt.NET

Si vous n’avez pas la chance d’habiter dans une ville dotée d’un groupe Alt.NET, vous pouvez assister aux réunions virtuelles : virtual ALT.NET (la section “recording” contient des archives). Par exemple, l’épisode “Separated Presentation” avec Jeremy Miller présente les différents patterns de présentation.

De l’autre côté

Amazon a ajouté un nouveau membre à la famille déjà bien nombreuse de ses services "cloud": RDS pour "Relationnal Databse Service”. Basé sur MySql ce service offre un stockage relationnel avec sauvegarde programmable. Azure SQL n’est donc plus seul face aux offres non relationnelles comme les très à la mode système “clé–valeur” qu’offre aussi Amazon (SimpleDB), Microsoft (Azure), Google (GAE et Big Table). Les détails de cette annonce en suivant ce lien. On trouvera une comparaison des offres d’Amazon et de Microsoft ici.

Un projet

PSake est un système pour construire (compiler, packager, déployer) des projets .NET. Le monde .NET n’a pas encore son Maven qui repose sur le principe “convention over configuration”. Il y a Nant, MSBuild mais aucun outil ne nous libère de la dure tâche d’écrire des scripts. PSake ne fait pas exception mais essaie de simplifier le travail. Basé sur Powershell, il expose le concept de tâche avec dépendances.

On commence par déclarer une liste de propriétés :

properties {
  $currentdir= resolve-path .
  $basedir= resolve-path .\..\..\
  $releasedir= 'C:\Release\'
  $releasewebsitedir = $releasedir+"_PublishedWebsites\Projet.Web.Web\"
  $solutionfile= "$basedir\Projet.Web\Projet.Web.Web.csproj"
  $configuration= 'staging'
}

Puis on définit une tâche par défaut :

task default -depends tacheDependante

Et on peut appeler ensuite des outils externes comme msbuild de façon simplifiée :

task Compile -depends Init { 
  exec msbuild "/p:OutDir=""$releasedir "" $sln_file"
} 

Le support pour des serveurs d’intégration continue (Cruise Control .NET, Team City, TFS ) fait encore défaut mais pour des projets de complexité moyenne, PSake est simple et rapide à mettre en place (et puis cela permet de se familiariser avec Powershell, ce qu’en tant que développeur on a toujours voulu faire sans jamais avoir eu le temps).

Monday, October 26, 2009 3:11:49 PM (Eastern Standard Time, UTC-05:00)  #    Comments [0] -
.net
# Tuesday, October 20, 2009

Voici notre première revue du web sur l’actualité du monde .NET. Elle ne se veut pas exhaustive, nous essayons de mettre en avant des choses intéressantes, peu connues parfois mais toujours pertinentes. L’objectif est d’offrir une vue synthétique des nouvelles du développement sur notre plateforme préférée.

Vous trouverez 7 petites rubriques : les deux premières sont des extraits de sites qu’on ne présente plus maintenant (Twitter et Stackoverflow). Ensuite des actualités du monde Microsoft et de la communauté Alt.NET. Nous mettrons aussi en avant un projet ou une application .NET et jetterons un coup œil ailleurs (Java, Ruby, PHP) . Enfin on retiendra un évènement pour la semaine à venir.

N’hésitez pas à réagir dans la section “commentaires” !

Les tweets de la semaine

http://twitter.com/SharedProphet/statuses/4925873898
Une introduction à la nouvelle invention du père de Linq : Rx, Reactive framework

http://twitter.com/EdgarSanchez/statuses/4905530109 
ServiceStack : un stack alternatif à WCF pour faire de l’appel distant depuis Linux, Windows et une version pour MonoTouch

http://twitter.com/oising/statuses/4867514391
On a tous de belles machines en 64bit et on est tous un peu ennuyés par ce message du débogueur de Visual Studio : "Change to 64-bit applications are not allowed" voici une solution.

La question stackoverflow.com

http://stackoverflow.com/questions/9033/hidden-features-of-c

« hidden features of c# » c'est la question la plus "active". Il y a sans doute des choses que vous connaissez déjà dans cette liste, d'autres dont vous ne vous servirez peut-être jamais mais la parcourir de temps à autre, avec son café du matin, c'est toujours instructif.

Actualités Microsoft

Le site de MSDN a connu un lifting de son interface, ici le portail consacré à C# http://msdn.microsoft.com/en-us/vcsharp/default.aspx et le site de référence de l’API a aussi une nouvelle version légère.

Un site peu connu avec pleins de projets petits ou grands : http://msdn.microsoft.com/en-us/devlabs/dd125421.aspx

Dans un mois c'est la PDC 09 dont les grands moments seront sans doute : le lancement commercial de Azure, .NET Framework 4 et VS 2010.  http://microsoftpdc.com /    

Le support de MS pour jQuery continue encore plus avec la version 6 de la Preview des contrôles ASP.NET Ajax qui s’exposent aussi comme plugins jQuery : http://weblogs.asp.net/scottgu/archive/2009/10/15/announcing-microsoft-ajax-library-preview-6-and-the-microsoft-ajax-minifier.aspx

Actualités Alt.Net

Ce n'est pas de l'actualité chaude mais Karl Seguin (http://codebetter.com/blogs/karlseguin/ ), développeur canadien et membre de la communauté codebetter.com a publié un e-book de près de 80 pages sur les bonnes pratiques de développement : « Foundations of Programming ». Le sommaire est alléchant et une application accompagne le texte : http://codebetter.com/blogs/karlseguin/archive/2009/05/25/revisiting-codebetter-canvas.aspx

Ailleurs

Jetbrains, l'éditeur connu dans le monde .NET pour Resharper (le plugin pour Visual Studio) vient de rendre disponible une version gratuite de son produit phare IntelliJIDEA (un IDE Java) ainsi que le code source de la plateforme. La version dite communauté ne contient pas beaucoup de fonctionnalités au-delà de la programmation JAVA SE mais comme Eclipse un écosystème de plugin va sans doute apparaître.

Avec Eclipse, Netbeans et maintenant IntelliJIDEA, le monde des IDE Java semble plus dynamique que celui de .NET. MonoDevelop et SharpDevelop n'ont pas vu leur adoption croître beaucoup. Et les tentatives infructueuses comme celle de Together .NET de Borland ne sont pas là pour nous rendre optimistes.

On peut juste espérer que Visual Studio 2010 simplifie vraiment l’intégration de plugins.

http://www.jetbrains.com/idea/nextversion/editions_comparison_matrix.html?utm_source=IDEA_BLOG&utm_media=Anouncement&utm_campaign=IDEA9_CE

http://blogs.jetbrains.com/idea/

Un projet

http://www.sparkviewengine.com

Spark View Engine est un moteur de vue pour le Framework ASP.NET MVC (et Castle MonoRail) créé par Louis Dejardin (qui depuis a été embauché par Microsoft) pour un projet interne à son ancien employeur. Il simplifie la construction des pages en évitant les spaghettis de tags que représentent pour certains le moteur de vue par défaut de ASP.NET MVC.

Un des cas les plus courants courants les boucles.

  1: <viewdata Posts="IList[[MyApp.Models.Post]"/>
  2: <for each="var post in Posts">
  3:   <p>${post.Title}</p>
  4: </for>

ou encore plus simple :

  1: <var classes="new [] {'even','odd'}">
  2: <tr each="var user in users" class="${classes[userIndex%2]}">
  3: <td>${userIndex}) ${user.Name}</td>
  4: <td>${user.UserType}</td>
  5: </tr>
  6: </var>

L’intellisense est un peu dur à mettre en place mais avec Fluent HTML du projet  MVC Contrib on arrive à une productivité agréable :

  1: <content name="MainContent">
  2: <viewdata model="IList[[Story]]"/>
  3: !{this.Html.Grid(Model).Columns(column =>
  4: {
  5: column.For(x => x.Id).Named("ID");
  6: column.For(x => x.Title);
  7: column.For(x => x.DateSubmitted).Format("{0:d}");
  8: column.For(x => Html.ActionLink<StoryController>(c => c.Single(x.Ref), "View Details"))
.DoNotEncode();
  9: })}
 10: 
 11: </content>
 12: 
 13: 

Qui a dit « IntelliSense pour XAML ! » ?

ASP.NET MVC devient un des domaines où la communauté est des plus actives.

La semaine prochaine

La conférence Monospace sur 4 jours avec bien sûr la vedette du moment MonoTouch, l’environnement de développement .NET pour l’iPhone : http://monospace.us/

Tuesday, October 20, 2009 8:37:28 AM (Eastern Standard Time, UTC-05:00)  #    Comments [0] -
.net
# Wednesday, September 30, 2009

logo altnet

Le 22 octobre prochain Matthieu animera une présentation organisée par le groupe ALT.NET de Montréal. Pour ceux qui ne connaissent pas ALT.NET, le groupe montréalais est tout jeune mais il fait parti d’un mouvement plus large . Bien que peu formalisée cette communauté est vivante : elle organise des conférences réelles ou virtuelles, une liste de discussion technique et bien sûr des évènements locaux autour des bonnes pratiques logiciels.

Le sujet de cette présentation sera Umbrella :

vue sur hanselman.com et ayende.com

Umbrella n’est pas un nième framework, il n’y a pas de setup, juste une assemblie de 56k avec plein de goodies !

Voici un petit avant-goût de ce que vous allez voir, Umbrella est une bonne façon d’apprendre : en connaissant ses limites, on découvre d’autres choses sur le framework .NET.

IEnumerable & Dictionnaire : les méthodes qu’on a toujours voulues avoir sans jamais avoir oser les demander !

  1: maCollection.ForEach(item => Console.WriteLine(item + 1));
  2: maCollection.Remove(item => item == "1");
  3: var maybe = monDictionnaire.GetValueOrDefault("AD");

Exécuter une action à la fin d’un bloc using :

  1: public static void DummyMethod()
  2: {
  3: 	using (TimeMethod())
  4: 	{
  5: 		Console.WriteLine("I'm in the method...");
  6: 		// Do something...
  7: 	}
  8: 	//The approximate time spent in the using block has been displayed at the end 
  9: }
 10: public static IDisposable TimeMethod()
 11: {
 12: 	var w = Stopwatch.StartNew();
 13: 	Action stopTimer = () => {
 14: 	   Console.WriteLine(w.Elapsed);
 15: 	};
 16: 	return stopTimer.ToDisposable();
 17: }
 18: 

Ou avoir le Cast facile :

  1: public static IEnumerable<Type> EnumPlugins(Assembly assembly)
  2: {
  3:     return from pluginType in assembly.GetTypes()
  4: 	   where pluginType.Is<IPlugin>()
  5:        select pluginType;
  6: }
  7: 

Mais il y a encore plein d’autres choses à voir.

Vous trouverez les détails sur le site de Alt.NET Montréal et n’oubliez de vous inscrire !

Wednesday, September 30, 2009 6:57:12 AM (Eastern Standard Time, UTC-05:00)  #    Comments [0] -

# Sunday, April 26, 2009

More fun with dictionaries on the way. We’ve seen how to read from a dictionary with the GetValueOrDefault() extension method but that’s not enough.

We usually need a way to add items to a dictionary if they aren’t already there. Here’s a simple example of a caching mechanism that relies on in-memory dictionaries:

Given:

public interface IOrderRepository

{

    Order GetOrderById(int id);

}

 

public class Order

{

    public int Id { get; set; }

}

 

A simple caching mechanism can be obtained using the Decorator pattern:

public class CacheOrderRepository : IOrderRepository

{

    private Dictionary<int, Order> orders = new Dictionary<int, Order>();

 

    public CacheOrderRepository(IOrderRepository repository)

    {

        Repository = repository;

    }

 

    public IOrderRepository Repository

    {

        get;

        private set;

    }

 

    #region IOrderRepository Members

 

    public Order GetOrderById(int id)

    {

        Order order;

 

        if (!orders.TryGetValue(id, out order))

        {

            order = Repository.GetOrderById(id);

            orders.Add(id, order);

        }

 

        return order;

    }

 

    #endregion

}

 

What basically happens here is that we’ll first try to find the value from the local dictionary (hence the cache) and if not present, go to the real repository to fetch the value and then create an entry in the local cache with the result. So what the code really wants to say is:

public Order GetOrderById(int id)

{

    return orders.FindOrCreate(id, () => Repository.GetOrderById(id));

}

 

A simple refactoring of the previous implementation into an extension method would lead to something like:

 

public static class DictionaryExtensions

{

    public static TValue FindOrCreate<TKey, TValue>(

        this IDictionary<TKey, TValue> items, TKey key,

        Func<TValue> factory)

    {

        TValue value;

 

        if (!items.TryGetValue(key, out value))

        {

            value = factory();

            items.Add(key, value);

        }

 

        return value;

    }

}

 

Note again that we’re extending the minimal interface, IDictionary<T>, and leveraging an existing delegate type, Func<T>.

() => “Francois”

Sunday, April 26, 2009 6:28:29 PM (Eastern Standard Time, UTC-05:00)  #    Comments [2] -
.net - Extension Methods | Umbrella
# Friday, April 24, 2009

So far, we’ve seen useful tricks to extend basic collection types like IEnumerable<T> and ICollection<T> but more complex collections deserve attention too!

 

Let’s look at IDictionary<T>. Here’s some code I stumbled upon recently; it is a partial implementation of IDataErrorInfo:

 

public class Order : IDataErrorInfo

{

    private IDictionary<string, string> errors =

        new Dictionary<string, string>();

 

    private decimal amount;

 

    public decimal Amount

    {

        get { return amount; }

        set

        {

            amount = value;

 

            if (amount <= 0)

            {

                errors["Amount"] = "Amount has to be larger than 0";

            }

            else

            {

                errors.Remove("Amount");

            }

        }

    }

 

    #region IDataErrorInfo Members

 

    public string Error

    {

        get { return null; }

    }

 

    public string this[string columnName]

    {

        get

        {

            if (errors.ContainsKey(columnName))

            {

                return errors[columnName];

            }

            else

            {

                return null;

            }

        }

    }

 

    #endregion

}

 

The interesting part is:

if (errors.ContainsKey(columnName))

{

    return errors[columnName];

}

else

{

    return null;

}

 

What’s the intent of this code? Pretty obvious isn’t it? It checks whether the dictionary has a value for a given key, then returns the value. If the key isn’t found, it returns the default value. This is similar to how the Nullable<T> type works:

int? index = null;

 

int indexValue = index.GetValueOrDefault();

 

Here, for obvious reasons, indexValue’s value will equal 0. But what’s interesting is the GetValueOrDefault() method. It clearly expresses the intent as opposed to:

int indexValue = index == null ? 0 : index.Value;

 

The same thing could apply to dictionaries but hasn’t been provided as part of the Base Class Library:

public string this[string columnName]

{

    get { return errors.GetValueOrDefault(columnName); }

}

 

Here’s Umbrella’s implementation:

public static class DictionaryExtensions

{

    public static TValue GetValueOrDefault<TKey, TValue>(

        this IDictionary<TKey, TValue> dictionary,

        TKey key)

    {

        return GetValueOrDefault(dictionary, key, default(TValue));

    }

 

    public static TValue GetValueOrDefault<TKey, TValue>(

        this IDictionary<TKey, TValue> dictionary,

        TKey key,

        TValue defaultValue)

    {

        return GetValueOrDefault(dictionary, key, () => defaultValue);

    }

 

    public static TValue GetValueOrDefault<TKey, TValue>(

        this IDictionary<TKey, TValue> dictionary,

        TKey key,

        Func<TValue> defaultValueProvider)

    {

        TValue value;

 

        if (!dictionary.TryGetValue(key, out value))

        {

            value = defaultValueProvider();

        }

 

        return value;

    }

}

 

The first method is an overload that will return default(T) if a default value is required.

The second method takes the defaultValue as a parameter

The third method contains the actual implementation and relies on a delegate to obtain the value since the defaultValue could either take some time to process or cannot be known in advance.

Again, these extension methods are small helpers to reduce the friction of th BCL. They are not meant to completely change the programming paradigm. They aren’t intrusive either. They should increase predictability of the source code with a side effect of decreasing the total lines of code count.

() => “Francois”

Friday, April 24, 2009 7:23:50 AM (Eastern Standard Time, UTC-05:00)  #    Comments [1] -
.net - Extension Methods | Umbrella
# Thursday, April 23, 2009

There is code what we type over and over again without realizing how many mistakes can be made in a few lines. Let’s take the example where we want to remove items from a collection. Intuitively, the code should be something like:

var orders = new List<Order> {

    new Order { Total = 100 },

    new Order { Total = 150 },

    new Order { Total = 200 }};

 

foreach (var order in orders)

{

    if (order.Total > 100)

    {

        orders.Remove(order);

    }

}

 

However, this will fail miserably with an “InvalidOperationException: Collection was modified; enumeration operation may not execute.”

In fact, it doesn’t fail on the Remove() call, it fails on the MoveNext() as we can’t enumerate a modified collection or can’t modify a collection while enumerating. In order to work correctly, we learned that we need to first keep track of the items to remove and then enumerate through those and remove them from the collection:

var orders = new List<Order> {

    new Order { Total = 100 },

    new Order { Total = 150 },

    new Order { Total = 200 }};

 

var ordersToRemove = new List<Order>();

 

foreach (var order in orders)

{

    if (order.Total > 100)

    {

        ordersToRemove.Add(order);

    }

}

 

foreach (var order in ordersToRemove)

{

    orders.Remove(order);

}

 

Wow! That is a huge amount of code. At least it can be refactored in a generic extension method:

public static class CollectionExtensions

{

    public static void Remove<T>(

        this ICollection<T> collection,

        Func<T, bool> predicate)

    {

        var itemsToRemove = new List<T>();

 

        foreach (var item in collection)

        {

            if (predicate(item))

            {

                itemsToRemove.Add(item);

            }

        }

 

        foreach (var item in itemsToRemove)

        {

            collection.Remove(item);

        }

    }

}

 

And then be used as:

orders.Remove(o => o.Total > 100);

 

In Umbrella, we go the extra mile and “simplify” the implementation of the Remove() extension method and dog food our own extensions:

public static void Remove<T>(

    this ICollection<T> collection,

    Func<T, bool> predicate)

{

    collection

        .Where(predicate)

        .ToList()

        .ForEach(item => collection.Remove(item));

}

 

What basically happens here is that we:

  1. Filter the original collection to keep only the items to remove (Sounds familiar?)
  2. Copy those items to a temporary list (Remember?)
  3. For each of those items, call Remove() on the original collection (Rings a bell?)

() => “Francois”

Thursday, April 23, 2009 9:03:24 AM (Eastern Standard Time, UTC-05:00)  #    Comments [1] -
.net - Extension Methods | Umbrella
Search
Archive
<October 2009>
SunMonTueWedThuFriSat
27282930123
45678910
11121314151617
18192021222324
25262728293031
1234567
Statistics
Total Posts: 98
This Year: 28
This Month: 1
This Week: 1
Comments: 17
Sign In