Building Our Own ESB: Part 5

The dust is settling now after a crazy month, so here we go with Part 5 of the ESB series. There is a lot of excitement building around this project. Keep in mind that the repository on GitHub will always contain the latest code if you want to keep up to date with the latest progress: http://www.github.com/jezell/iserviceoriented.

Our class diagram continues fill out. Here's where we stand today:

Again, a few notes before we start:

  • As the number of classes increases, we need to move some of the support classes into their own namespaces. We don't want to end up with one giant namespace.

  • I've added support for IoC (inversion of control) containers, thanks to the recent release of the "common service locator" interface. We will provide a simple service locator so a full-fledged IoC container is entirely optional.

  • Message delivery has been removed from the service bus core. Previously, we made sure to allow custom message queues, now we will take things one step further, allowing consumers to chose one of our strategies or implement their own. DirectDeliveryCore will allow queues to be bypassed entirely, or to be managed by dispatchers (useful if you want to leave queuing entirely up to NetMsmqBinding on both ends or don't care about queuing at all). QueuedDeliveryCore contains the implementation of previous delivery strategy.

  • DLR hosting and support is started in the IServiceOriented.ServiceBus.Scripting project. This will allow the use of scripts for filters and message transformations.

  • Unit tests have been moved to NUnit from MSTest.

  • Due to the interest in the project, I have attached an official license in the repository. The code is available under the MIT license, which means you are free to use it however you please.

  • The custom formatter for our message queue now supports both MessageContracts and DataContracts.

Our original plan called for RuntimeServices to be able to customize the behavior of our bus. Today, let's look at how we can use RuntimeServices to add functionality to the bus.

 

Subscription Persistence

Being able to persist subscriptions is extremely important. If our bus needs to be restarted, consumers should not have to re-register to receive notifications. The actual persistence logic is defined by the ISubscriptionDb interface:

SqlSubscriptionDb implements this interface for SQL Server using stored procedures and SqlCommand objects, but using the interface allows consumers to implement the same functionality on top of MySql, Oracle, or an ORM like NHibernate if they prefer. With our data layer interface in place, adding subscription persistence to our bus is a snap:

 

Performance Monitoring

When our ESB starts to see some action, performance monitoring will also be a must. By hooking into the MessageDelivered and MessageDeliveryFailed events on the ServiceBusRuntime, we can tap into the excellent performance counter support that Windows provides:

 

Management

Until now, all subscriptions and listeners needed to be programmatically added to the bus. While this works for simple cases, we need to be able to connect to our bus remotely and be able to add or remove subscriptions and change the configuration of our bus. WcfManagementService will host a WCF service that exposes this functionality to consumers. Note that we haven't explicitly written any security checks into the service. This is intentional. We will come back to security soon, but it's worth noting at this that WCF allows role based, claim based, and custom security policies to be injected into services without modifying the core code of our management service. Enough talk, here's the code for our initial management service:

 

Auto registration

Now that we have the ability to remotely register subscriptions with our service bus, wouldn't it be great if consumers could automatically register themselves with our bus the first time they start up, instead of requiring someone to manually add them? By hooking into WCF with custom behaviors, we can provide an attribute that, when added to a service definition, automatically registers services with our bus:

To have any WCF service automatically register itself with our bus, all we have to do is add an [AutoSubscribe] attribute to the class definition.

Linked By

Reader Comments

  • MZ says What is the problem with the code repository? why i am not able to download the code.. yyyyyyy ??.. why it shows a javascript error at the bottom in the IE status bar..

    I am getting really frustrating now.. as i am trying to download the code for the last 2 days.. but all in vain..

    Can you plz upload the latest code in zip file somewhere else where i can downlaod. ?

    Looking forward to your response.. Thanks

    Regards
    MZ
  • Peter says I have problems running the sample chat program. I get the following from the client:

    Starting client...
    Enter name: Peter

    Unhandled Exception: System.InvalidOperationException: Cannot find the X.509 certificate using the following search criteria: StoreName 'My', StoreLocation 'CurrentUser', FindType 'FindBySubjectDistinguishedName', FindValue 'CN=localhost'. at System.ServiceModel.Security.SecurityUtils.GetCertificateFromStoreCore(Sto
    reName storeName, StoreLocation storeLocation, X509FindType findType, Object findValue, EndpointAddress target, Boolean throwIfMultipleOrNoMatch) at System.ServiceModel.Security.SecurityUtils.GetCertificateFromStore(StoreNa
    me storeName, StoreLocation storeLocation, X509FindType findType, Object findValue, EndpointAddress target) at System.ServiceModel.Security.X509CertificateRecipientServiceCredential.Set
    Certificate(StoreLocation storeLocation, StoreName storeName, X509FindType findType, Object findValue) at System.ServiceModel.Configuration.X509RecipientCertificateServiceElement.A
    pplyConfiguration(X509CertificateRecipientServiceCredential cert) at System.ServiceModel.Configuration.ServiceCredentialsElement.ApplyConfigura
    tion(ServiceCredentials behavior) at System.ServiceModel.Configuration.ServiceCredentialsElement.CreateBehavior
    () at System.ServiceModel.Description.ConfigLoader.LoadBehaviors[T](ServiceModelExtensionCollectionElement`1 behaviorElement, KeyedByTypeCollection`1 behaviors, Boolean commonBehaviors)
    at System.ServiceModel.Description.ConfigLoader.LoadServiceDescription(Servic
    eHostBase host, ServiceDescription description, ServiceElement serviceElement, Action`1 addBaseAddress) at System.ServiceModel.ServiceHostBase.LoadConfigurationSectionInternal(Confi
    gLoader configLoader, ServiceDescription description, ServiceElement serviceSection)
    at System.ServiceModel.ServiceHostBase.LoadConfigurationSectionInternal(Confi
    gLoader configLoader, ServiceDescription description, String configurationName) at System.ServiceModel.ServiceHostBase.ApplyConfiguration()
    at System.ServiceModel.ServiceHostBase.InitializeDescription(UriSchemeKeyedCo
    llection baseAddresses) at System.ServiceModel.ServiceHost.InitializeDescription(Type serviceType, UriSchemeKeyedCollection baseAddresses) at System.ServiceModel.ServiceHost.InitializeDescription(Object singletonInstance, UriSchemeKeyedCollection baseAddresses) at System.ServiceModel.ServiceHost..ctor(Object singletonInstance, Uri[] base
    Addresses)
    ...
    ...

    Can you guide me to get the sample running? I haven't found any docs.
    Thanks
Name 
Url
Comments