Click here to Skip to main content
13,447,249 members (37,312 online)
Click here to Skip to main content
Add your own
alternative version


5 bookmarked
Posted 26 Jun 2010

Strongly typed AppSettings with Genuilder.Extensibility

, 26 Jun 2010
Rate this:
Please Sign up or sign in to vote.
Practical use case of Genuilder.Extensibility: Strongly typed AppSettings.

Table of Contents


My last article on Genuilder.Extensibility did not have much success, a reader on my blog told me it was because there is no real use case shown in it. So here it is!

The goal is to create a code generator which allows you to use AppSettings in a safely typed manner. I already have done an article on that and integrated it to Genuilder. The problem is that to understand how I have done it, you have to understand how MSBuild works. So today, I'll show you how to implement this feature yourself with Genuilder.Extensibility.


I won't explain again how to install Genuilder, since it's fully described on CodePlex and in my last articles.

Create the plug-in

So let's create two projects: the first one is a console application with a config file and some appSettings inside. The second one is our feature project, a Class Library.

Do not forget, the feature project mus end with .Gen.

Let's create the plug-in StronglyTypedAppSettingsPlugin in the feature project.

In this code snippet, I subscribe to the CodeItemCreated event of the CodeRepository. This event is fired for every source code file + config file in the project.

Then I create a dependency between my config file and a target file, named StronglyTypedSettings.cs.

public class StronglyTypedAppSettingsPlugin : IPlugin
    #region IPlugin Members

    public void Initialize(ICodeRepository repository)
        repository.CodeItemCreated += 
           new CodeItemCreatedHandler(repository_CodeItemCreated);

    void repository_CodeItemCreated(ICodeRepository sender, CodeItem item)
            var dependency = item.SourceOf("StronglyTypedSettings.cs");
            dependency.ShouldUpdateTarget += 
                new CodeDependencyHandler(dependency_ShouldUpdateTarget);

dependency_ShouldUpdateTarget generates the code in StronglyTypedSettings.cs based on the config file.

void dependency_ShouldUpdateTarget(CodeDependency sender, CodeItem target)
    var configuration = 
        ConfigurationManager.OpenMappedExeConfiguration(new ExeConfigurationFileMap()
        ExeConfigFilename = ((FileCodeItem)sender.Source).File.FullName
    }, ConfigurationUserLevel.None);

    string generatedClass = "public static class AppConfigSettings{";

    foreach(KeyValueConfigurationElement setting in configuration.AppSettings.Settings)

        string getter = "public static System.String " + setting.Key + 
          " { get{ return System.Configuration.ConfigurationManager.AppSettings[\"" + 
          setting.Key + "\"]; } }";
        generatedClass += getter;
    generatedClass += "}";
    target.Content = generatedClass;

To show how to send warning and error notification to the build, let's send a warning each time StronglyTypedSettings.cs is updated.

target.Logger.Send("Settings generated !!", 


Here is the config file in the console application:

<?xml version="1.0"?>
        <add key="SomeKey" value="SomeValue"/>

Build ConsoleApplication1 and enjoy the show.

You can even see the warning message.

As you can see, when you rebuild, the warning does not appear because the source file (App.config) has not changed. If you modify your feature project, you must clean the project prior to build.

This plug-in works only in C#, how can I make it work in VB.NET too?

We will just modify dependency_ShouldUpdateTarget to use NRefactory extension. But before that, let's reference the NRefactory integration assembly in our project.

Here is the code of dependency_ShouldUpdateTarget using CompilationUnitExtension (NRefactory extension)... A bit more complicated, but works in both C# and VB.NET !!

void dependency_ShouldUpdateTarget(CodeDependency sender, CodeItem target)
    var configuration = 
        new ExeConfigurationFileMap()
        ExeConfigFilename = ((FileCodeItem)sender.Source).File.FullName
    }, ConfigurationUserLevel.None);

    var targetNRefactoryExtension = 

    var typeDeclaration = new TypeDeclaration(Modifiers.Public | Modifiers.Static, null)
        Name = "AppConfigSettings"

    foreach(KeyValueConfigurationElement setting in configuration.AppSettings.Settings)

        var propertyDeclaration = new PropertyDeclaration(
               Modifiers.Public | Modifiers.Static, null, setting.Key, null)
            TypeReference = new TypeReference(typeof(String).FullName)
        var indexer = new IndexerExpression(
            new MemberReferenceExpression(
                new TypeReferenceExpression(
                    new TypeReference(typeof(ConfigurationManager).FullName)), "AppSettings")
                        , new List<Expression>()
                            new ICSharpCode.NRefactory.Ast.PrimitiveExpression(setting.Key)

        propertyDeclaration.GetRegion = new PropertyGetRegion(new BlockStatement(), null);
        propertyDeclaration.GetRegion.Block.Children.Add(new ReturnStatement(indexer));

    target.Logger.Send("Settings generated !!", 


Well, that's all. I'm proud that my articles are short and fast to do, it shows that they are not complicated!!

I'm very interested to hear about new plug-in ideas from you. I'll be glad to implement them if I'm motivated! ;)


This article, along with any associated source code and files, is licensed under The Microsoft Public License (Ms-PL)


About the Author

Nicolas Dorier
Software Developer Freelance
France France
I am currently the CTO of Metaco, we are leveraging the Bitcoin Blockchain for delivering financial services.

I also developed a tool to make IaaS on Azure more easy to use IaaS Management Studio.

If you want to contact me, go this way Smile | :)

You may also be interested in...


Comments and Discussions

GeneralT4 alternative Pin
GigaGeorge28-Jul-10 6:06
memberGigaGeorge28-Jul-10 6:06 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

Permalink | Advertise | Privacy | Terms of Use | Mobile
Web01 | 2.8.180318.3 | Last Updated 26 Jun 2010
Article Copyright 2010 by Nicolas Dorier
Everything else Copyright © CodeProject, 1999-2018
Layout: fixed | fluid