Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇

时间:2021-10-20 08:47:20
  在前一篇文章中,讲述了配置应用程序块的最简单的介绍,在本篇文章中我主要介绍一下配置应用程序块的响应配置变更通知,保护配置信息(加密配置信息),面向高级人员的扩展机制,配置数据的缓存等几个方面。在剖析篇中我会去分析配置应用程序块的底层设计及类设计。

一.响应配置变更通知:

Configuration Application Block提供了一个事件机制,当存储的配置变更时通知应用程序 ,使用步骤:

1)创建一个EverntHandler

 1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇 /// <summary>
 2Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        /// 创建EventHanler
 3Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        /// </summary>
 4Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        /// <param name="sender"></param>
 5Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        /// <param name="args"></param>

 6 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         private   void  OnConfigurationChanged( object  sender, ConfigurationChangedEventArgs args)
 7 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         {
 8Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            Cursor = System.Windows.Forms.Cursors.WaitCursor;
 9Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
10Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            EditorFontData configData = ConfigurationManager.GetConfiguration("EditorSettings"as EditorFontData;
11Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
12Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            StringBuilder results = new StringBuilder();            
13Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append("Configuration changes in storage were detected. Updating configuration.");
14Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append(Environment.NewLine);
15Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append("New configuration settings:");
16Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append(Environment.NewLine);
17Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append('\t');
18Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append(configData.ToString());
19Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            results.Append(Environment.NewLine);
20Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
21Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            Cursor = System.Windows.Forms.Cursors.Arrow;      
22Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

2)注册事件

1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇 ///注册事件
2 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        ConfigurationManager.ConfigurationChanged  +=   new  ConfigurationChangedEventHandler(OnConfigurationChanged); 

二.配置数据的缓存:

Configuration Application Block在设计时提供了对配置数据的缓存,在读取XML数据后,再次读取它首先会判断缓存是否为空,如果不为空,它会直接从缓存中读取数据(在剖析篇中会有详细的介绍)。

显式的清除掉缓存用下面这句代码即可:

1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇 ///清除缓存数据
2 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         ConfigurationManager.ClearSingletonSectionCache();

三.面向高级人员的扩展机制:

1 除了用XML文件可以存储数据外,还可以创建自己的存储方式,像SQL Server Database,注册表存储等,这时就需要我们自己创建StorageProvider。创建自定义的Storage Provider,需要注意以下几点:

1)要读取和写入数据,需要继承于StorageProvider类和分别实现IStorageProviderReaderIstorageProviderWriter接口:

1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇public   class  XmlFileStorageProvider : StorageProvider, IStorageProviderWriter
2 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         {
3Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            //……
4Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

2)如果实现了IConfigurationProvider接口,则方法Initialize()就不能为空,也必须实现:

1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇public   override   void  Initialize(ConfigurationView configurationView)
2 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         {
3Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            //……
4Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

3)实现Read()Write()方法,记住一定要返回类型为object,否则Transformer将无法使用:

1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇public   override   object  Read()
2 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         {
3Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            //……
4Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

5 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
6 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         public   void  Write( object  value)
7 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇         {
8Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            //……
9Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

2.创建自定义的Transformer

如果我们创建的自定义的Storage Provider不能后支持XMLNode,这时候我们需要创建自己的Transformer,需要注意以下几点:

1)自定义的Transformer如果实现了Itransformer接口;则必须实现方法Serialize()Deserialize();

2)自定义的Transformer如果实现了IConfigurationProvider接口,则方法Initialize()就不能为空,也必须实现;

下面给出一个SoapSerializerTransformer的例子程序(先声名一下,这个例子程序不是我写的,而是Dario Fruk先生^_^):

 1 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇namespace  idroot.Framework.Configuration
 2 Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇 {
 3Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using System;
 4Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using System.Configuration;
 5Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using System.IO;
 6Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using System.Runtime.Serialization.Formatters.Soap;
 7Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using System.Text;
 8Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using System.Xml;
 9Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
10Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using Microsoft.Practices.EnterpriseLibrary.Common;
11Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    using Microsoft.Practices.EnterpriseLibrary.Configuration;
12Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
13Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    /// <summary>
14Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    /// SoapSerializerTransformer is a custom Serialization Transformer for Microsft Enterprise Library 1.0.
15Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    /// </summary>

16Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    public class SoapSerializerTransformer : TransformerProvider
17Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    
18Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        public override void Initialize(ConfigurationView configurationView)
19Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        {
20Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            // Do nothing. This implementation does not require any additional configuration data because SoapFormatter reflects types 
21Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            // during serialization.
22Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

23Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
24Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        public override object Serialize(object value)
25Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        {
26Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            SoapFormatter soapFormatter = new SoapFormatter();
27Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            StringBuilder stringBuilder = new StringBuilder();
28Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            XmlDocument doc = new XmlDocument();
29Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
30Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            stringBuilder.Append("<soapSerializerSection>");
31Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
32Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            string serializedObject = "";
33Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            using (MemoryStream stream = new MemoryStream())
34Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            {
35Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                soapFormatter.Serialize(stream, value);
36Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                byte[] buffer = stream.GetBuffer();
37Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                // quick fix for 0-byte padding
38Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                serializedObject = ASCIIEncoding.ASCII.GetString(buffer).Replace('\0'' ').Trim();
39Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            }

40Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            stringBuilder.Append(serializedObject);
41Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
42Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            stringBuilder.Append("</soapSerializerSection>");
43Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            doc.LoadXml(stringBuilder.ToString());
44Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
45Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            return doc.DocumentElement;
46Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

47Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
48Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        public override object Deserialize(object section)
49Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        {
50Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            ArgumentValidation.CheckForNullReference(section, "section");
51Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            ArgumentValidation.CheckExpectedType(section, typeof(XmlNode));
52Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
53Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            XmlNode sectionNode = (XmlNode)section;
54Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
55Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            XmlNode serializedObjectNode = sectionNode.SelectSingleNode("//soapSerializerSection");
56Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            if (serializedObjectNode == null)
57Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            {
58Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                throw new ConfigurationException("The required element '<soapSerializationSection>' missing in the specified Xml configuration file.");
59Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            }

60Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇
61Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            SoapFormatter soapFormatter = new SoapFormatter();
62Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            try
63Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            {
64Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                object obj = null;
65Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                using (MemoryStream stream = new MemoryStream())
66Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                {
67Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                    using (StreamWriter sw = new StreamWriter(stream, Encoding.ASCII))
68Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                    {
69Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                        sw.Write(serializedObjectNode.InnerXml);
70Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                        sw.Flush();
71Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                        // rewind stream to the begining or deserialization will throw Exception.
72Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                        sw.BaseStream.Seek(0, SeekOrigin.Begin); 
73Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                        obj = soapFormatter.Deserialize(stream);
74Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                    }

75Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                }

76Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                return obj;
77Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            }

78Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            catch (InvalidOperationException e)
79Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            {
80Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                string message = e.Message;
81Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                if (null != e.InnerException)
82Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                {
83Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                    message = String.Concat(message, " ", e.InnerException.Message);
84Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                }

85Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇                throw new ConfigurationException(message, e);
86Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇            }

87Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇        }

88Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇    }

89Enterprise Library Step By Step系列(二):配置应用程序块——进阶篇}
 

3.使用其它的Providers

       SQL Server Provider:使用数据库SQL Server Provider

       Registry Provider:使用注册表Provider

四.保护配置信息:

配置信息直接放在了XML文件里面是不安全,我们可以用加密应用程序块对其进行加密,其实对于所有的应用程序块的配置信息都可以进行加密,我们到加密应用程序块时再详细讨论:)

进阶篇就写到这里了,后面继续剖析篇,在剖析篇里我会从配置应用程序块的底层设计,到类设计等作一些介绍(个人理解^_^