Written by: Michael Stephenson (http://geekswithblogs.net/michaelstephenson)
It is a common design decision on BizTalk projects when you are implementing your solution and you find that you need to store some custom configuration. The challenge is where to store it.
For some BizTalk components such as Adapters and Pipelines you can take advantage of the configuration meta data stored in SSO to handle this. This is the proper approach for these components and you have the BizTalk Admin Console and Binding Files to help you manage this. Where the configuration becomes more of a problem is when you have say an orchestration or a helper class which is called by an orchestration. In this case there are a few options which each have their own considerations. The aim of this article is to discuss the common options people tend to use and to provide my thoughts on the best use of each approach.
Before I get into the different options, some of the requirements and considerations you normally need to consider are:
· Do I need a configuration system just for my BizTalk implementation or is it a more strategic solution for the enterprise
· What kind of information will be held in the configuration
· Is there sensitive information held in the configuration
· How often might the values change
· Who will want to change the values, is it likely to be a business user or an administrator
· Does your configuration need to be able to change during the execution of a process of should each instance of a process (orchestration) take a snapshot of the configuration and work with that
The rest of the article will discuss some of my thoughts about each of the options. There is also a sample at the bottom of this article which I will reference on occasion.
Using a Facade Pattern to the Configuration Sub System
The first thing I would say before going into the detail of the different options is that you might want to change the storage mechanism you use for accessing your configuration data so I find it is a good idea to implement a facade pattern in a helper component to abstract your BizTalk components from the details of how you store and access configuration data.
To do this I usually implement a ConfigurationFacade class in a helper assembly which gives me access to my configuration data as static properties and methods, any other component (custom class, orchestration, pipeline component, etc) which wants configuration data would access it via this class.
The benefit of this is I can change or combine the techniques which I will discuss below for the storage of the configuration but the consumer of it has no knowledge of this.
The ConfigurationFacade.cs file in the sample demonstrates this.
The following section will discuss the various options for configuration, and also there is a sample available at the end of the article which provides some examples which I will discuss throughout this article.
Store it in BTSNTSVC.exe.config
This is probably one of the easiest places to store the configuration information from a developers perspective and deployment perspective. Basically you would store information in this config file like you would any other .net config file and it would be available to your application at runtime.
Some of the key factors with this option are:
· The configuration values can only be changed by an administrator
· By default the data will not be encrypted (although it can be)
· You get the full feature set of a .net configuration file such as being able to define custom sections etc
· The configuration will be stored on a separate file on each BizTalk server in your group. You will need to ensure these are in sync
· This file is only available to in process hosts. If you need the same configuration in isolated hosts you end up needing to add the configuration to the config file for that process
· From a developer perspective this is very straight forward approach
· From a deployment perspective you just need to update the files
· From a maintenance perspective it is a little challenging just from the fact of keeping files in sync, and if you have a setting wrong on just 1 server then it can be hard to troubleshoot as HAT doesn’t distinguish which orchestration shape executed on which server
In my opinion this approach is very useful and easy but I would tend to use it more for a POC where you are looking to implement something quickly, or for infrastructure/framework like settings or settings which may need to have a different value on each server. For values which may change frequently it is definitely not suitable. I don’t think it is a good idea to place what I would consider to be a business value here either.
Almost every developer will have experience of doing this, although for completeness I have added part of the sample which shows this. In the ConfigurationFacade class the CustomSetting1 property demonstrates this technique.
Store it in SSO
The second option where you might choose to store your configuration information is in the SSO database. SSO is where configuration for ports are stored so it is certainly somewhere we could consider storing your own configuration information.
Rather than go into a lot of detail about this in my article I would like to refer you to a couple of articles by Jon Flanders and Richard Seroter who discuss using SSO for just this purpose.
Some of the key factors relating to using SSO to store your configuration are:
· You get out of the box encryption
· It is a central store which will service all BizTalk servers within your group
· I believe SSO implements a caching mechanism internally for this data
· You will follow the standard BizTalk processes for back up etc
· From a developer perspective I think it is a bit of a pain to work with this, if you want to use an automated build process during development you will need to build some MsBuild or NANT tasks to manage deployment of the configuration
· From a deployment perspective you would need to use the ssomanage utility to deploy your SSO Application from the command line
· In deployment could not work out how to set the custom property values using the SSO utilities (SSOManage and SSOClient) so I ended up wrapping some of the code from the tools above as an MsBuild task
· From a maintenance perspective it could be a bit of a pain to manage the configuration. There is an MMC snap in for ESSO but it does not seem to allow you to edit your custom property values. Both Richard and Jon had to build sample applications to help them manage the configuration data it is probably a good idea to use these tools to manage it
· Only the users in specific groups can make changes to the data
In the sample the key points relating to the SSO option are as follows:
· The ConfigurationFacade class has a property called CustomSetting3 which demonstrates reading a string from SSO for a configuration setting
· The ConfigurationFacade class has a property called CustomSetting4 which demonstrates reading an xml string from SSO which is then deserialized into an object and returned as a strongly typed object (a bit like in Jon’s article above)
· The SSOConfigurationProvider shows how you can read configuration from SSO
· The build script shows how to create/deploy your SSOApplication with your custom properties
· The build script and my custom task shows how to set the custom property values
In terms of storing custom configuration data in SSO I think it is a good idea for End Point/Application specific information and credentials and potentially configuration information which you also need to write and update at runtime from your code or via an administrator. SSO is where BizTalk stores lots of its own configuration for things like adapters so I think it is perfectly valid to use it for your own custom stuff.
To me the biggest problem with using SSO is the barriers to getting up and running with it. From a maintenance perspective I would recommend using the tool in Richard’s post (link above) to maintain and change your data once is it in SSO. But another challenge is how to develop with this. I always encourage the use of an MsBuild (or at least automated) build process during development to setup your environment. With this in mind I have created some custom MsBuild tasks which are to be integrated into the BizTalk Build Generator tool. The Setup.msbuild file shows how to use these tasks to setup your custom Application in SSO. I’ll also be posting more about this in the coming weeks.
Store it as a Vocabulary in the Rules Engine
In the BizTalk Business Rules Engine you can define a vocabulary which is essentially parameters which can be used within the execution of a rules policy. These vocabularies can be accessed from C# code so the idea here is that you could define constants in a vocabulary which you could deploy to the BRE which you would then access from a helper class to get your configuration data. Some of the factors associated with this choice are:
· Again this provides a central store for configuration information
· I don’t believe the data would be encrypted
· As the configuration is defined as constants they would be read only, however it would follow the BRE deployment/versioning strategy so if you wanted to implement changes you could produce a new policy version
· You could use specific versions or the latest version of a policy
· I think it would be restricted to simple types although I’m sure a string of xml could be provided and then serialized later in your code a bit like for SSO
· You would get the normal BizTalk fail over/back up processes for free
· Again the deployment and developer experience for an automated build isn’t great, but with the tasks in the sample hopefully that makes things simpler
· Without some serious coding or a 3rd party product this is probably the closest option to allowing business users to be able to manage the configuration data. In theory the Business Rules tool can be used by an analyst but it is expected that an administrator would be the one to deploy a new vocabulary version
I quite like the idea of using the vocabulary but mainly for business parameters. If you had something like a parameter called High Value Order Threshold which held a value which indicated that an order was considered to be of high value and a process would react differently if this was the case then I think it would be more appropriate to store this in a Business Rules vocabulary. If you are also using the BRE to execute rules policies then it would make sense to keep this setting here as you could potentially reuse it in your rules as well as your orchestration.
In the sample the key points which relate to this technique are:
· In the ConfigurationFacade class there is a property called CustomSetting2 which gets the configuration from BRE
· The BREConfigurationProvider shows how to read the config values from the business rules vocabulary
· There are some build tasks and the script which show how to manage the deployment etc of the rules policy
Again like the SSO technique there are a couple of barriers to getting up and running with this technique. It is however a lot better than SSO because you have the Business Rules Composer and Business Rules Deployment Wizard, however again with my preference for automated build processes I have wrappered some of this up with some MsBuild tasks to do the deployment etc for the sample. (I will also post more about these in the future)
Store it in a custom database
I’ve seen this technique used quite a bit. Basically the developer will create a custom database with a few simple tables to store the configuration data, this will then be accessed by various components using ADO.net code. Sometimes I’ve also seen a developer implement a caching mechanism to reduce the number of round trips to the database. Some of the considerations and factors related to this option are:
· By storing the configuration in the database you don’t have to worry about consistency of data across servers like you would with a config file
· If you implement caching you need to consider how to refresh and pick up changes to the underlying data and that components may become out of sync
· There will be additional custom development work to create and optimise your database
· You will need to define a maintenance plan and have your DBA manage this database
· You will need to create an interface to allow management of the configuration data
· Custom databases are well known as a cause of bottlenecks in high volume scenarios as they are often not correctly tuned and optimised
I’ve usually seen a custom database used as a quick and dirty way of implementing some configuration requirements, also a note on the caching that I think unless you have a low latency requirement it is probably not worth implementing caching yourself. Or consider implementing your solution without it and if you identify a performance problem then it is something you could add to improve things. The reason I mention this is that often unless there is a low latency requirement then memory usage tends to become an issue before the hit of the additional database hits. I guess this point also depends on the size of your configuration data, and how many hosts would have a cache of it
As a general rule my thoughts around the custom database option is that if you have a configuration storage requirement and no one else can help... and you cant hire the A-Team then a custom database could be your solution. But I prefer not to use this option unless none of the others are feasible.
Store it in a custom file
I don’t think I’ve seen this approach used but I’m sure someone is bound to have done it, basically it would involve a custom file (hopefully in XML) stored in a well known location which you could then read and potentially serialize to get some configuration information in the form of a strongly typed object. This approach has all of the same challanges as using the BizTalk config file except that the API is not as straight forward and it is just one more potential deployment headache. Off the top of my head I can’t really think of any significant advantages of this approach for a BizTalk solution.
Maybe one idea would be that you could have a single file which is accessed by different BizTalk processes. For example if you had a pipeline component running in an isolated host and an orchestration running in an in process BizTalk host. The isolated host would have a different app or web.config file. In this scenario I can imagine some people might look to use a custom file instead. What would probably be a better solution would be to export the common sections to an external config file and import them in the processes config file so you can access them through the normal System.Configuration namespace objects.
3rd Party Solutions
I haven’t really seen many offerings which cover this requirement. The main one I have seen is from Frends (I discussed one of the components of Frends in another article about Scheduling). One of the other components of the Frends product is that it has a centralised MetaData component. In this component you can define types of meta data which is based on a schema. You then can create instances of the types of meta data which can have different values associated with it.
The meta data is accessible via a web service which you can call from BizTalk to get your strongly typed configuration instance. Some of the considerations related to using Frends are:
· The meta data component is not specific to BizTalk so it can be accessed by other applications and systems making it an enterprise level configuration store
· Frends is probably more suited to configuration related to the process such as business values
· A call to Frends would involve a web service call to get the data so there would be a round trip associated with this, although im sure you could implement a caching mechanism. But for processes which don’t have latency requirements you probably don’t want to cache to ensure you always get the latest version of the configuration.
· You would also get the other Frends components
· There is a cost associated with this as it is a 3rd party component
For a while now I’ve felt that a decent reusable configuration data component was missing from the Microsoft BPM suite. This article has aimed to discuss the different options and considerations associated with each. The sample has aimed to show how to use each and help getting over the barriers with some of the techniques.
Id be quite interested in any feedback based on your experiences of what works and what doesn’t. Also if you have any alternative techniques which I have not thought of then let me know.
The sample is available from the following location:
The tasks used in the sample are also available separately as a patch for the BizTalk Build Generator at the location below. The next release of the build generator will include these tasks.