Monthly Archives: July 2010

Reasons for a C# developer to learn VB.net

I found the above mentioned question at stackoverflow today, it got really lovely answers.

Top reasons:

  1. So that you can read VB code on the blogs.
  2. Because you are designing a new language and you don’t want people to hate it.
  3. Answer Stackoverflow questions to get reputation because Jon Skeet will leave VB alone.
  4. For fun, adventure.
  5. Your girlfriend threatens to leave you if you don’t learn it.

And my favorite:
Because you don’t have enough misery in your life ? :P

Question@stackoverflow


Simplified WCF services

Being an old C++ developer I’ve always found myself doing everything by myself from the bottom and up. I’ve always created my own DAL’s, Socket handling etc etc. I continued doing this when I moved to .net and C#. Didn’t really think about it. A couple of weeks ago I started working as a consultant where I was forced to use existing technologies from Microsoft. Having struggled with buggy MFC classes in the past I was quite reluctant in the beginning.

This time I’ve looked at WCF and frankly I like what I’ve seen so far. I’m using the TCP binding to get my clients to talk with the server (oneway methods and callbacks). Most of the examples out there uses the configuration file for the setup. That’s not my flavor. Therefore I’ve created two classes that does everything for me.

Server side

Heres how the service host generation looks like:

            var uri = new Uri("net.tcp://localhost:9000");
            var loader = new ServiceHostLoader<NetTcpBinding>(uri);
            var hosts = loader.Load(typeof(Program).Assembly);
            foreach (var host in hosts)
                host.Open();

That’s ALL that you have to do. The ServiceHostLoader class scans through all assemblies that you have specified. It looks for all concrete types (classes) that have implemented a interface which have been tagged with the ServiceHostAttribute.

All hosts are registered using the Name property of the ServiceHostAttribute. The interface name (excluding the ‘I’) is used if the Name property has not been specified.

Create multiple loaders if you want to run multiple bindings.

Client side

The proxies are generated in a similiar fashion using a proxy factory:

            Dictionary<Type, object> ioc = new Dictionary<Type, object>();
            var uri = new Uri("net.tcp://localhost:9000");
            var generator = new ProxyGenerator<NetTcpBinding>(uri);
            var assemblies = new List<Assembly>
                                 {
                                     typeof (IEventPublisher).Assembly,
                                     typeof (Program).Assembly
                                 };

            // load proxies into your ioc.
            generator.Create(assemblies, (type, obj) => ioc.Add(type, obj));

            while (true)
            {
                string str = Console.ReadLine();
                IAlarmServer servier = ioc.Resolve<IAlarmServer>();
                servier.RegisterAlarm(DateTime.Now, "aName", str);
            }

As you can see, I use a Dictionary in this example as the IOC. The Resolve method is a extension method that looks like this:

        public static T Resolve<T>(this Dictionary<Type, object> dict) where T : class
        {
            object tmp;
            if (!dict.TryGetValue(typeof(T), out tmp))
                return null;
            return (T)tmp;
        }

Code

ProxyGenerator.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.ServiceModel;
using System.ServiceModel.Channels;
using System.ServiceModel.Description;

namespace Service.Api
{
    /// <summary>
    /// Creates WCF Service proxies.
    /// </summary>
    /// <example>
    /// <code>
    /// var loader = new <![CDATA[ProxyGenerator<NetTcpBinding>]]>("net.tcp://localhost:9000");
    /// loader.Load(Assembly.GetExecutingAssembly(), (service, concrete) => myContainer.Register(concrete).As(service));
    /// </code>
    /// </example>
    /// <remarks>
    /// Scans through all specified assemblies after interfaces that has the ServiceContract attribute.
    /// It then generates proxies for them and their callbacks.
    /// </remarks>
    public class ProxyGenerator<TBinding> where TBinding : Binding, new()
    {
        private readonly Uri _rootUri;
        private IEnumerable<Assembly> _assemblies;
        private Func<Type, object> _callbackFactory;

        /// <summary>
        /// Initializes a new instance of the <see cref="ServiceHostLoader"/> class.
        /// </summary>
        /// <param name="rootUri">Root URI for all services.</param>
        /// <example>
        /// <code>
        /// var loader = new <![CDATA[ProxyGenerator<NetTcpBinding>]]>("net.tcp://localhost:9000");
        /// </code>
        /// </example>
        public ProxyGenerator(Uri rootUri)
        {
            _rootUri = rootUri;
        }

        /// <summary>
        /// Gets or sets factory used to create callback types.
        /// </summary>
        /// <remarks>
        /// Type parameter is the type of callback to create, object
        /// is the created callback.
        /// </remarks>
        /// <example>
        /// <code>
        /// loader.CallbackFactory = (type) => myIOC.Resolve(type);
        /// </code>
        /// </example>
        /// 
        public Func<Type, object> CallbackFactory
        {
            get { return _callbackFactory; }
            set { _callbackFactory = value ?? CreateCallback; }
        }

        /// <summary>
        /// Create proxies for all 
        /// </summary>
        /// <param name="assemblies"></param>
        /// <param name="loader"></param>
        public void Create(IEnumerable<Assembly> assemblies, Action<Type, object> loader)
        {
            _assemblies = assemblies;
            foreach (Assembly assembly in assemblies)
                Create(assembly, loader);
        }

        /// <summary>
        /// Create proxies for all services found in the specified assembly
        /// </summary>
        /// <param name="assembly">Assembly to look in</param>
        /// <param name="loader">Action being invoked for each created proxy.</param>
        /// <remarks>
        /// <para>
        /// Use the action to register each proxy in your inversion of control container. The
        /// type is the service type and the object is the generated proxy.
        /// </para>
        /// <para>
        /// The assembly must also contain the concrete callback type (if you are using
        /// callbacks).
        /// </para>
        /// </remarks>
        public void Create(Assembly assembly, Action<Type, object> loader)
        {
            if (_assemblies == null || !_assemblies.Contains(assembly))
                _assemblies = new List<Assembly> {assembly};

            foreach (Type type in assembly.GetTypes())
            {
                if (!type.IsInterface)
                    continue;

                object[] attributes = type.GetCustomAttributes(typeof (ServiceContractAttribute), false);
                if (attributes.Length != 1)
                    continue;

                var attribute = (ServiceContractAttribute) attributes[0];
                CreateProxy(type, attribute, loader);
            }
        }

        /// <summary>
        /// Creates callback objects using Activator.CreateInstance.
        /// </summary>
        /// <param name="type">Callback type</param>
        /// <returns></returns>
        private static object CreateCallback(Type type)
        {
            return Activator.CreateInstance(type);
        }

        /// <summary>
        /// Creates the proxy
        /// </summary>
        /// <param name="type">Service type</param>
        /// <param name="attribute">Attribute found on the interface</param>
        /// <param name="loader">Action being invoked for each created proxy.</param>
        /// <remarks>
        /// Use the action to register each proxy in your inversion of control container. The
        /// type is the service type and the object is the generated proxy.
        /// </remarks>
        /// <exception cref="InvalidOperationException">Concrete type for the callback was not found.</exception>
        private void CreateProxy(Type type, ServiceContractAttribute attribute, Action<Type, object> loader)
        {
            Type callbackType = null;
            if (attribute.CallbackContract != null)
            {
                callbackType = FindCallback(attribute.CallbackContract);
                if (callbackType == null)
                    throw new InvalidOperationException("Failed to load callback(" + attribute.CallbackContract.FullName +
                                                        ") implementation for service '" + type.FullName + "'.");
            }


            ChannelFactory factory;
            if (callbackType != null)
            {
                object callback = CreateCallback(callbackType);
                Type factoryType = typeof (DuplexChannelFactory<>).MakeGenericType(type);
                factory = (ChannelFactory)Activator.CreateInstance(factoryType,
                                                 callback,
                                                 new TBinding(),
                                                 new EndpointAddress(_rootUri + "/" + attribute.Name));
            }
            else
            {
                Type factoryType = typeof (ChannelFactory<>).MakeGenericType(type);
                factory = (ChannelFactory)Activator.CreateInstance(factoryType,
                                                 new TBinding(),
                                                 new EndpointAddress(_rootUri + "/" + attribute.Name));
            }

            DuplexChannelFactory<object> tmp;
            
            if (Credentials != null)
                factory.GetType().GetProperty("Credentials").SetValue(factory, Credentials, null);

            var proxy = factory.GetType().GetMethod("CreateChannel", new Type[0]).Invoke(factory, null);

            loader(type, proxy);
        }

        public ClientCredentials Credentials
        {
            private get; set;
        }

        /// <summary>
        /// Scans through all assemblies to find the callback
        /// </summary>
        /// <param name="interfaceType"></param>
        /// <returns></returns>
        private Type FindCallback(Type interfaceType)
        {
            foreach (Assembly assembly in _assemblies)
            {
                foreach (Type type in assembly.GetTypes())
                {
                    if (type.IsInterface || type.IsAbstract)
                        continue;

                    if (type.GetInterface(interfaceType.Name, true) == null)
                        continue;

                    return type;
                }
            }

            return null;
        }
    }
}

ServiceHostLoader.cs

using System;
using System.Collections.Generic;
using System.IO;
using System.Reflection;
using System.ServiceModel;
using System.ServiceModel.Channels;

namespace Service.Api
{
    /// <summary>
    /// Loads all service hosts from assemblies
    /// </summary>
    /// <remarks>
    /// <para>
    /// Scans through all specified assemblies after types that implements interfaces tagged with the <c>ServiceContractAttribute</c>. Those
    /// types are then created and returned from this class.
    /// </para>
    /// <para>
    /// The interface name is used as service name if no name is specified in the <see cref="ServiceContractAttribute"/>.
    /// </para>
    /// </remarks>
    public class ServiceHostLoader<TBinding> where TBinding : Binding, new()
    {
        private readonly Uri _rootUri;

        /// <summary>
        /// Initializes a new instance of the <see cref="ServiceHostLoader{TBinding}"/> class.
        /// </summary>
        /// <param name="rootUri">Root URI for all services.</param>
        public ServiceHostLoader(Uri rootUri)
        {
            _rootUri = rootUri;
        }

        private static bool GetServiceContract(Type type, out ServiceContractAttribute attribute,
                                               out Type contractInterface)
        {
            foreach (Type @interface in type.GetInterfaces())
            {
                object[] attributes = @interface.GetCustomAttributes(typeof(ServiceContractAttribute), false);
                if (attributes.Length != 1)
                    continue;

                attribute = (ServiceContractAttribute) attributes[0];
                contractInterface = @interface;
                return true;
            }

            attribute = null;
            contractInterface = null;
            return false;
        }

        /// <summary>
        /// Load all hosts from the specified assemblies
        /// </summary>
        /// <param name="assemblies">Assemblies to scan after classes and the interfaces that they implement.</param>
        /// <returns>A collection of hosts</returns>
        public IEnumerable<ServiceHost> Load(IEnumerable<Assembly> assemblies)
        {
            var hosts = new List<ServiceHost>();
            foreach (Assembly assembly in assemblies)
                Load(assembly, hosts);
            return hosts;
        }

        /// <summary>
        /// Load all hosts from the specified assemblies
        /// </summary>
        /// <param name="assemblies">Assemblies to scan after classes and the interfaces that they implement.</param>
        /// <returns>A collection of hosts</returns>
        public IEnumerable<ServiceHost> Load(params Assembly[] assemblies)
        {
            var hosts = new List<ServiceHost>();
            foreach (Assembly assembly in assemblies)
                Load(assembly, hosts);
            return hosts;
        }

        /// <summary>
        /// Load all hosts from the calling assembly
        /// </summary>
        /// <returns>A collection of hosts</returns>
        public IEnumerable<ServiceHost> Load()
        {
            var hosts = new List<ServiceHost>();
            Load(Assembly.GetCallingAssembly(), hosts);
            return hosts;
        }

        /// <summary>
        /// Load service hosts from the specified assembly
        /// </summary>
        /// <param name="assembly">Assembly containing service host classes and their interfaces.</param>
        /// <returns></returns>
        public IEnumerable<ServiceHost> Load(Assembly assembly)
        {
            var hosts = new List<ServiceHost>();
            Load(assembly, hosts);
            return hosts;
        }

        private void Load(Assembly assembly, ICollection<ServiceHost> hosts)
        {
            foreach (Type type in assembly.GetTypes())
            {
                Console.WriteLine(type);
                ServiceContractAttribute attribute;
                Type contractInterface;
                if (!GetServiceContract(type, out attribute, out contractInterface))
                    continue;

                string name = attribute.Name;
                if (string.IsNullOrEmpty(name))
                    name = contractInterface.Name.Substring(2);

                var host = new ServiceHost(type, _rootUri);
                var binding = new TBinding();
                host.AddServiceEndpoint(contractInterface, binding, name);
                hosts.Add(host);
            }
        }
    }
}

Autofac, starting components

Some of my components need to be started after all have been created. This is quite easy to solve with autofac. The components simply implement this interface:

    public interface IStartable
    {
        void Start();
    }

Then all I need to do is to invoke the start method:

Components.Resolve<IEnumerable<IStartable>>().Each(c => c.Start());

Note that I resolve IEnumerable<IStartable> and not simply IStartable. That’s the way to tell autofac that you expect to get all components that have been registered with the same interface.


Nlog configuration

I’ve switched from my own logging framework to nlog. NLog seems quite flexible is under active development and suits my needs perfectly. I’m logging both to the console and to files using the following configuration file:

  <configSections>
    <section name="nlog" type="NLog.Config.ConfigSectionHandler, NLog" />
  </configSections>

  <nlog xmlns=" http://www.nlog-project.org/schemas/NLog.xsd"   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" throwExceptions="true" internalLogFile=" Nlog.txt">
    <targets>
      <target name="file" xsi:type="File"
              layout="${longdate} ${threadid:padding=3} ${level:padding=-30} ${logger:padding=-30} ${message} ${exception:format=tostring}"
              fileName="${basedir}/logs/${shortdate}.txt"/>
      <target name="errors" xsi:type="File"
              layout="${longdate} ${threadid:padding=3} ${level:padding=-30} ${logger:padding=-30} ${message} ${exception:format=tostring}"
          fileName="${basedir}/logs/${shortdate}.errors.log" />
      <target name="console" xsi:type="ColoredConsole"
              layout="${date:format=HH:MM:ss} ${threadid:padding=3} ${logger:padding=-30} ${message}" />
    </targets>
    <rules>
      <logger name="*" minlevel="Trace" writeTo="file, console" />
      <logger name="*" minLevel="Error" writeTo="errors" />
    </rules>
  </nlog>

The console get’s colored output looking like this:

10:07:41  10 AppDog.Monitor                 Checking AppDog.Monitoring.MonitoredApplication

And file syntax:

2010-07-03 10:22:56.4218  10 Trace           AppDog.Monitor                 Checking AppDog.Monitoring.MonitoredApplication 

Simplified autofac registrations

I’m building an application which will monitor other applications (memory using, start them if they crash etc). I’m trying to stop re-inventing the wheel (ohhh it’s fun to do everything yourself) and start using other components. This time I needed a IoC container and autofac seemed like a good match for me.

To simplify IoC registration I created an attribute which I use on all my components. In this way I don’t have to remember to register each component, it’s done by the help of the attribute.

Using the attribute without constructor parameters will register the component with all interfaces.

    [Component]
    class MyComponent : IConsumer<MonitorEvent>, ISomeService
    {
        //[....]
    }

While using the constructor will only register one interface.

    [Component(typeof(ISomeService)]
    class MyComponent : IConsumer<MonitorEvent>, ISomeService
    {
        //[....]
    }

The autofac registration looks like this:

    internal class Program
    {
        public static IContainer Components { get; private set; }

        private static void Main(string[] args)
        {
            var builder = new ContainerBuilder();

            //i = interface type, c = concrete type
            Assembly[] assemblies = AppDomain.CurrentDomain.GetAssemblies();
            assemblies.Each(assembly => assembly.FindComponents((i, c) => builder.RegisterType(c).As(i).SingleInstance()));

            Components = builder.Build();
        }
    }

Quite smooth, huh?

Extension methods making it possible:

public static class ComponentFinder
    {
        public static void Each<T>(this IEnumerable<T> enumerable, Action<T> action)
        {
            foreach (T item in enumerable)
                action(item);
        }

        public static void FindComponents(this Assembly assembly, Action<Type, Type> action)
        {
            Type componentAttribute = typeof (ComponentAttribute);
            foreach (Type type in assembly.GetTypes())
            {
                object[] attributes = type.GetCustomAttributes(componentAttribute, false);
                if (attributes.Length == 0)
                {
                    type.GetInterfaces().Each(i => action(i, type));
                    continue;
                }

                foreach (object attribute in attributes)
                {
                    Type interfaceType = ((ComponentAttribute) attribute).InterfaceType ?? type;
                    action(interfaceType, type);
                }
            }
        }
    }

Getting components is done by the resolve method:

Program.Components.Resolve<IMyService>.SendMessage("Hello world");