以前在看一些开源的项目时,发现它们的Web.config文件都做了扩展,让我很是羡慕,也想用在自己的项目中,于是查阅了一些资料和原码。现在做一个总结,同时也整理出来,与大家一同分享。如您发现什么问题或疑问,欢迎留言。
一、Web.config文件
所有的ASP.NET配置信息都驻留在Web.config文件中的configuration元素中。此元素中的配置信息分为两个主区域:配置节处理程序声明区域(configSections节点中的内容)和配置节设置区域(configSections节点以外的内容)。
配置节处理程序声明区域驻留在Web.config文件中的configSections元素内。它包含在其中声明节处理程序的ASP.NET配置section元素。可以将这些配置节处理程序声明嵌套在sectionGroup元素中,以帮助组织配置信息。通常,sectionGroup元素表示要应用配置设置的命名空间。
配置节设置区域位于配置节处理程序声明区域之后,它包含实际的配置设置。配置节元素还可以包含子元素,这些子元素与其父元素由同一个节处理程序处理。
1: <?xml version="1.0"?>
2: <configuration>
3: <configSections>
4: <sectionGroup name="CustomConfiguration">
5: <section name="MyUrls_Declarative" type="Samples.AspNet.Declarative.UrlsSection, CustomConfiguration" />
6: <section name="MyUrls_Programmatic" type="Samples.AspNet.Programmatic.UrlsSection, CustomConfiguration, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" allowDefinition="Everywhere" allowExeDefinition="MachineToApplication" restartOnExternalChanges="true" />
7: </sectionGroup>
8: </configSections>
9:
10: <CustomConfiguration>
11: <MyUrls_Declarative name="MyUrls_Declarative">
12: <simple name="Microsoft" url="http://www.microsoft.com" port="0" />
13: <urls>
14: <clear />
15: <add name="Microsoft" url="http://www.microsoft.com" port="0" />
16: <add name="Contoso" url="http://www.contoso.com/" port="8080" />
17: </urls>
18: </MyUrls_Declarative>
19:
20: <MyUrls_Programmatic name="MyUrls_Programmatic">
21: <simple name="Microsoft" url="http://www.microsoft.com" port="0" />
22: <urls>
23: <clear />
24: <add name="Microsoft" url="http://www.microsoft.com" port="0" />
25: <add name="Contoso" url="http://www.contoso.com/" port="8080" />
26: </urls>
27: </MyUrls_Programmatic>
28: </CustomConfiguration>
29: </configuration>
其中,第10行的CustomConfiguration这个名字要与第4行name中的名字相一致;第11行的MyUrls_Declarative这个名字要与第5行name中的名字相一致;第20行的MyUrls_Programmatic这个名字要与第6行name中的名字相一致。
第5、6行中的type为处理此节点的程序名。
格式为:命名空间.处理的类名,包含这个类的程序集名称(BIN目录下DLL的名称),版本号,文化和公钥。前两项必需,后三项有无。
type="ConfigurationSectionHandlerClass, AssemblyFileName, Version, Culture, PublicKeyToken"
section节点中还可以包括其他一些非必需信息,请参考MSDN。
二、编写处理程序
您可以用自己的XML配置元素来扩展标准的ASP.NET配置设置集。若要完成该操作,您必须创建自己的配置节处理程序。其中配置节处理程序又可分为声明性模型和编程模型。
该处理程序必须是一个用来实现System.Configuration.ConfigurationSection类的.NET Framework类。在.NET Framework 1.0和1.1版中,配置节处理程序必须实现System.Configuration.IConfigurationSectionHandler接口,该接口现在已被否决。
节处理程序解释并处理Web.config文件特定部分中XML配置元素中定义的设置,并根据配置设置返回适当的配置对象。处理程序类返回的配置对象可以是任何数据结构;它不限于任何基配置类或配置格式。ASP.NET使用该配置对象,以对自定义配置元素进行读取和写入。
1、声明性模型处理程序
1: using System;
2: using System.Configuration;
3: using System.Collections;
4:
5: namespace Samples.AspNet.Declarative
6: {
7: // Define a custom section containing a simple element and a collection of the same element.
8: // It uses two custom types: UrlsCollection and UrlsConfigElement.
9: public class UrlsSection : ConfigurationSection
10: {
11: [ConfigurationProperty("name", DefaultValue = "MyUrls_Declarative", IsRequired = true, IsKey = false)]
12: [StringValidator(InvalidCharacters = " ~!@#$%^&*()[]{}/;'\"|\\", MinLength = 1, MaxLength = 60)]
13: public string Name
14: {
15: get
16: {
17: return (string)this["name"];
18: }
19: set
20: {
21: this["name"] = value;
22: }
23: }
24:
25: [ConfigurationProperty("simple")]
26: public UrlConfigElement Simple
27: {
28: get
29: {
30: return (UrlConfigElement)this["simple"];
31: }
32: }
33:
34: [ConfigurationProperty("urls",IsDefaultCollection = false)]
35: public UrlsCollection Urls
36: {
37: get
38: {
39: return (UrlsCollection)this["urls"];
40: }
41: }
42: }
43:
44: // Define the UrlsCollection that contains UrlsConfigElement elements.
45: public class UrlsCollection : ConfigurationElementCollection
46: {
47: protected override ConfigurationElement CreateNewElement()
48: {
49: return new UrlConfigElement();
50: }
51: protected override Object GetElementKey(ConfigurationElement element)
52: {
53: return ((UrlConfigElement)element).Name;
54: }
55: }
56:
57: // Define the UrlConfigElement.
58: public class UrlConfigElement : ConfigurationElement
59: {
60: [ConfigurationProperty("name", DefaultValue = "Microsoft", IsRequired = true, IsKey = true)]
61: public string Name
62: {
63: get
64: {
65: return (string)this["name"];
66: }
67: set
68: {
69: this["name"] = value;
70: }
71: }
72:
73: [ConfigurationProperty("url", DefaultValue = "http://www.microsoft.com", IsRequired = true)]
74: [RegexStringValidator(@"\w+:\/\/[\w.]+\S*")]
75: public string Url
76: {
77: get
78: {
79: return (string)this["url"];
80: }
81: set
82: {
83: this["url"] = value;
84: }
85: }
86:
87: [ConfigurationProperty("port", DefaultValue = (int)0, IsRequired = false)]
88: [IntegerValidator(MinValue = 0, MaxValue = 8080, ExcludeRange = false)]
89: public int Port
90: {
91: get
92: {
93: return (int)this["port"];
94: }
95: set
96: {
97: this["port"] = value;
98: }
99: }
100:
101: public override string ToString()
102: {
103: string output = "urls :";
104: output += string.Format(" name = {0} ", Name);
105: output += string.Format(" url = {0} ", Url);
106: output += string.Format(" port = {0} ", Port);
107: return output;
108: }
109: }
110: }
2、编程模型处理程序
1: using System;
2: using System.Configuration;
3: using System.Collections;
4: using System.ComponentModel;
5:
6: namespace Samples.AspNet.Programmatic
7: {
8: // Define a custom section containing a simple element and a collection of the same element.
9: // It uses two custom types: UrlsCollection and UrlsConfigElement.
10: public class UrlsSection : ConfigurationSection
11: {
12: private static ConfigurationPropertyCollection _Properties;
13: private static ConfigurationProperty _Name;
14: private static ConfigurationProperty _Simple;
15: private static ConfigurationProperty _Urls;
16:
17: static UrlsSection()
18: {
19: // Initialize the _Name
20: _Name = new ConfigurationProperty("name", typeof(string), "MyUrls_Programmatic", ConfigurationPropertyOptions.IsRequired);
21: _Simple = new ConfigurationProperty("simple", typeof(UrlConfigElement));
22: _Urls = new ConfigurationProperty("urls", typeof(UrlsCollection));
23:
24: // Property collection initialization.
25: // The collection (property bag) that contains the properties is declared as:
26: // ConfigurationPropertyCollection _Properties;
27: _Properties = new ConfigurationPropertyCollection();
28: _Properties.Add(_Name);
29: _Properties.Add(_Simple);
30: _Properties.Add(_Urls);
31: }
32:
33: // Return the initialized property bag for the configuration element.
34: protected override ConfigurationPropertyCollection Properties
35: {
36: get
37: {
38: return _Properties;
39: }
40: }
41:
42: [StringValidator(InvalidCharacters = " ~!@#$%^&*()[]{}/;'\"|\\", MinLength = 1, MaxLength = 60)]
43: public string Name
44: {
45: get
46: {
47: return (string)this["name"];
48: }
49: set
50: {
51: this["name"] = value;
52: }
53: }
54:
55: public UrlConfigElement Simple
56: {
57: get
58: {
59: return (UrlConfigElement)this["simple"];
60: }
61: }
62:
63: public UrlsCollection Urls
64: {
65: get
66: {
67: return (UrlsCollection)this["urls"];
68: }
69: }
70: }
71:
72: // Define the UrlsCollection that contains UrlsConfigElement elements.
73: public class UrlsCollection : ConfigurationElementCollection
74: {
75: protected override ConfigurationElement CreateNewElement()
76: {
77: return new UrlConfigElement();
78: }
79: protected override Object GetElementKey(ConfigurationElement element)
80: {
81: return ((UrlConfigElement)element).Name;
82: }
83: }
84:
85: // Define the UrlConfigElement.
86: public class UrlConfigElement : ConfigurationElement
87: {
88: private static ConfigurationPropertyCollection _Properties;
89: private static ConfigurationProperty _Name;
90: private static ConfigurationProperty _Url;
91: private static ConfigurationProperty _Port;
92:
93: static UrlConfigElement()
94: {
95: // Initialize the _Name
96: _Name = new ConfigurationProperty("name", typeof(string), "Microsoft", ConfigurationPropertyOptions.IsKey | ConfigurationPropertyOptions.IsRequired);
97:
98: ConfigurationValidatorBase _UrlValidator = new RegexStringValidator(@"\w+:\/\/[\w.]+\S*");
99: _Url = new ConfigurationProperty("url", typeof(string), "http://www.microsoft.com", TypeDescriptor.GetConverter(typeof(string)), _UrlValidator, ConfigurationPropertyOptions.IsRequired);
100:
101: ConfigurationValidatorBase _PortValidator = new IntegerValidator(0, 8080);
102: _Port = new ConfigurationProperty("port", typeof(int), (int)0, null, _PortValidator, ConfigurationPropertyOptions.None);
103:
104: // Property collection initialization.
105: // The collection (property bag) that contains the properties is declared as:
106: // ConfigurationPropertyCollection _Properties;
107: _Properties = new ConfigurationPropertyCollection();
108: _Properties.Add(_Name);
109: _Properties.Add(_Url);
110: _Properties.Add(_Port);
111: }
112:
113: // Return the initialized property bag for the configuration element.
114: protected override ConfigurationPropertyCollection Properties
115: {
116: get
117: {
118: return _Properties;
119: }
120: }
121:
122: public string Name
123: {
124: get
125: {
126: return (string)this["name"];
127: }
128: set
129: {
130: this["name"] = value;
131: }
132: }
133:
134: public string Url
135: {
136: get
137: {
138: return (string)this["url"];
139: }
140: set
141: {
142: this["url"] = value;
143: }
144: }
145:
146: public int Port
147: {
148: get
149: {
150: return (int)this["port"];
151: }
152: set
153: {
154: this["port"] = value;
155: }
156: }
157:
158: public override string ToString()
159: {
160: string output = "urls :";
161: output += string.Format(" name = {0} ", Name);
162: output += string.Format(" url = {0} ", Url);
163: output += string.Format(" port = {0} ", Port);
164: return output;
165: }
166: }
167: }
三、使用
1: protected void Page_Load(object sender, EventArgs e)
2: {
3: Samples.AspNet.Declarative.UrlsSection dus = (Samples.AspNet.Declarative.UrlsSection)ConfigurationManager.GetSection("CustomConfiguration/MyUrls_Declarative");
4: Response.Write(dus.Name);
5: Response.Write("<br>");
6: foreach (Samples.AspNet.Declarative.UrlConfigElement due in dus.Urls)
7: {
8: Response.Write(due.ToString());
9: Response.Write("<br>");
10: }
11:
12: Response.Write("<br>");
13:
14: Samples.AspNet.Programmatic.UrlsSection pus = (Samples.AspNet.Programmatic.UrlsSection)ConfigurationManager.GetSection("CustomConfiguration/MyUrls_Programmatic");
15: Response.Write(pus.Name);
16: Response.Write("<br>");
17: foreach (Samples.AspNet.Programmatic.UrlConfigElement pue in pus.Urls)
18: {
19: Response.Write(pue.ToString());
20: Response.Write("<br>");
21: }
22:
23: }
上面的代码放在页面代码里。
得到输出:
MyUrls_Declarative urls : name = Microsoft url = http://www.microsoft.com port = 0 urls : name = Contoso url = http://www.contoso.com/ port = 8080 MyUrls_Programmatic urls : name = Microsoft url = http://www.microsoft.com port = 0 urls : name = Contoso url = http://www.contoso.com/ port = 8080
好了,到此为止,相信您已经能自己扩展配置文件了,可以看出,使用声明性模型所需要编写的代码稍微少一些,但是在程序取值时需要用到反射,所以如果取舍,就看你了。
参考文章:
PS:由于本人第一次写比较正规的Blog,组织了几遍词语,最后还是放弃了,索性贴上代码,反而干脆。如您有什么不清楚或有疑问的地方,欢迎您在下面留言。