17.2 了解Web.config文件
在众多的配置文件中Web.config是最常用到的配置文件,它用于设置应用程序的配置信息。下面将详细介绍Web.config配置文件的优点、创建方法、文件的结构以及其中常用的配置节点等。
17.2.1 Web.config文件的优点
Web.config文件使ASP.NET应用程序的配置变得灵活、高效和容易实现,同时Web.config配置文件还为ASP.NET应用提供了可扩展的配置,使得应用程序能够自定义配置。
Web.config配置文件主要具有如下优点。
1.配置设置易读性
由于Web.config配置文件是基于XML文件类型,所有的配置信息都存放在XML文本文件中,可以使用文本编辑器或者XML编辑器直接修改和设置相应配置节,相比之下,也可以使用记事本进行快速配置而无须担心文件类型。
2.更新的即时性
在Web.config配置文件中某些配置节被更改后,无须重启Web应用程序就可以自动更新ASP.NET应用程序配置。但是在更改有些特定的配置节时,Web应用程序会自动保存设置并重启。
3.本地服务器访问
在更改了Web.config配置文件后,ASP.NET应用程序可以自动探测到Web.config配置文件中的变化,然后创建一个新的应用程序实例。当用户访问ASP.NET应用程序时会被重定向到新的应用程序。
4.安全性
由于Web.config配置文件通常存储的是ASP.NET应用程序的配置,所以Web.config配置文件具有较高的安全性,一般的外部用户无法访问和下载Web.config配置文件。当外部用户尝试访问Web.config配置文件时,会导致访问错误。
5.可扩展性
Web.config配置文件具有很强的扩展性,通过Web.config配置文件开发人员能够自定义配置节,在应用程序中自行使用。
6.保密性
开发人员可以对Web.config配置文件进行加密操作而不会影响配置文件中的配置信息。虽然Web.config配置文件具有安全性,但是通过下载工具依旧可以进行文件下载,对Web.config配置文件进行加密,可以提高应用程序配置的安全性。
17.2.2 创建Web.config文件
所有的.config文件实际上都是一个XML文本文件,Web.config文件也不例外。它可以出现在应用程序的每一个目录中。当创建一个Web应用程序后,默认情况下会自动创建一个默认的Web.config文件,包括默认的配置设置,所有的子目录都继承它的配置设置,如果想要修改子目录的配置设置,可以在该子目录下新建一个Web.config文件,它可以提供除从父目录继承的配置信息以外的配置信息,也可以重写或修改父目录中定义的设置。
【范例1】
例如,当用户新建一个默认的ASP.NET空网站时,自动创建的Web.config文件的配置信息如下。
<?xml version="1.0"? > <!-- For more information on how to configure your ASP.NET application, please visit http://go.microsoft.com/fwlink/? LinkId=169433 --> <configuration> <system.web> <compilation debug="false" targetFramework="4.0" /> </system.web> </configuration>
上述信息非常简单,configuration是节的根元素,其他节都是在它的内部;在该元素下添加一个system.web节点,它用于控制ASP.NT运行时的行为。在system.web节点下创建compilation子节点,compilation中的debug属性指向是否调试程序;targetFramework指向.NET Framework的版本。
一个应用程序中可以包含一个或者多个Web.config文件,因此,用户可以手动创建一个Web.config文件,并且向该文件中自定义配置信息。
【范例2】
新建一个Web.config配置文件时很简单,一种是直接复制根目录中存在的Web.config文件到指定的目录下,在复制后的文件中自定义配置信息;另一种是像创建Web窗体页那样创建一个Web.config配置文件。
创建Web.config配置文件的主要步骤是:选择当前项目后右击,选择【添加新项】菜单项,这时会弹出一个【添加新项】对话框。在弹出的对话框中找到【Web配置文件】项并选中,选中后直接单击【添加】按钮添加,效果如图17-2所示。
图17-2 创建一个新的Web.config配置文件
17.2.3 配置文件结构
所有的ASP.NET配置信息都驻留在.config文件中,位于.NET Framework系统文件夹中的Machine.config文件和根Web.config文件为服务器上运行的所有网站提供默认值。位于网站的根文件夹中的每个网站的Web.config文件提供对这些值的网站特定的重写,可以将其他Web.config文件置于一个网站的子文件夹中,以提供专用于该网站内的文件夹的重写。
Web.config文件包含将configuration元素作为根节点的XML,此元素中的信息分为两个主区域:配置节处理程序声明区域和配置节设置区域。
【范例3】
节处理程序是用来实现ConfigurationSectiono接口的.NET Framework类,声明区域可标识每个节处理程序类的命名空间和类名。节处理程序用于读取和设置与节有关的设置,下面的代码演示Web.config文件的XML结构的简化视图。
<configuration> <!-- Configuration section-handler declaration area. --> <configSections> <section name="section1" type="section1Handler" /> <section name="section2" type="section2Handler" /> </configSections> <!-- Configuration section settings area. --> <section1> <s1Setting1 attribute1="attr1" /> </section1> <section2> <s2Setting1 attribute1="attr1" /> </section2> <system.web> <authentication mode="Windows" /> </system.web> </configuration>
在Web.config文件中,如果在位于配置层次结构中更高级别的.config文件中声明节,则相应的节会在声明区域中尚未声明的设置区域中出现。例如,Machine.config文件中声明了system.web节点。因此,无须在单个网站级Web.config文件中声明此节,如果在位于网站的根文件夹的Web.config文件中声明某个节,则可以包含该节的设置,而无须将其包含在位于子文件夹中的Web.config文件中。
1.配置节处理程序声明
配置节处理程序声明区域位于配置文件中的configSections元素内,它包含在其中声明节处理程序的ASP.NET配置section元素。可以将这些配置节处理程序声明嵌套在sectionGroup元素中,以帮助组织配置信息。通常,sectionGroup元素表示要应用配置设置的命名空间。例如,所有ASP.NET配置节处理程序都分组到system.web节组中。代码如下。
<sectionGroup name="system.web" type="System.Web.Configuration.SystemWebSectionGroup, System.Web,Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a"> <!-- <section /> elements. --> </sectionGroup>
配置节设置区域中的每个配置节都有一个节处理程序声明,节处理程序声明中包含配置设置节的名称(如pages)以及用来处理该节中配置数据的节处理程序类的名称(如System.Web.Configuration.PagesSection)。下面的代码演示映射到配置设置节的节处理程序类。
<section name="pages" type="System.Web.Configuration.PagesSection, System.Web, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a"> </section>
程序员可需要声明配置节处理程序一次,默认ASP.NET配置节的节处理程序已经在Machine.config文件中进行了声明。网站的Web.config文件和ASP.NET应用程序中的其他配置文件都自动继承在Machine.config文件中声明的配置处理程序。只有当创建用来处理自定义设置节的自定义节处理程序类时,才需要声明新的节处理程序。
2.配置节设置
配置节设置区域位于配置节处理程序声明区域之后,它包含实际的配置设置。默认情况下,在当前配置文件或某个根配置文件中,对于configSections区域中的每个section和sectionGroup元素都会有一个配置节元素。可以在systemroot\Microsoft.NET\Framework\versionNumber\CONFIG\Machine.config.comments文件中查看这些默认值。
【范例4】
配置节元素还可以包含子元素,这些子元素与其父元素由同一个节处理程序处理。例如,下面的pages元素包含一个namespace元素,该元素没有相应的节处理程序,这是因为它是由pages节处理程序来处理的。
<pages buffer="true" enableSessionState="true" asyncTimeout="45" <!-- Other attributes. --> > <namespaces> <add namespace="System" /> <add namespace="System.Collections" /> </namespaces> </pages>
17.2.4 Web.config的常用配置节
可以向Web.config文件中自定义配置信息,下面列出了一些常用的配置节以及配置信息。
1.<appSettings>配置节
<appSettings>配置节用于定义应用程序设置项,对一些不确定的设置,还可以让用户根据自己的实际情况进行设置。向该配置节中添加内容时需要通过<add>节点,它常用的属性有两个,分别是key属性和value属性。其中,key属性指定自定义属性的关键字,以方便在应用程序中使用该配置节;value属性表示自定义属性的值。细心的读者可以发现,在介绍模块和处理程序时使用过<appSettings>配置节。
【范例5】
下面向<appSettings>配置节中添加两个<add>节点内容。代码如下。
<appSettings> <add key="ConnectionStr" value="server=.; userid=sa; password=123456; database=mytest; " /> <add key="ErrPage" value="Error.aspx" /> </appSettings>
上述代码第一个<add>节点定义了一个连接字符串常量,并且在实际应用时可以修改连接字符串,不用修改程序代码;第二个<add>节点定义了一个错误重定向页面,它指向Error.aspx页面。
一般情况下,向<appSettings>配置节下添加内容后可以在页面中进行调用,以范例5中ConnectionStr为例,它可以在通用类中进行获取。通过ConfigurationManager对象的AppSettings[int index]或者AppSettings[string key]属性获取对应key的value属性值。其中,index表示在配置节中的索引值;而key则表示配置节中的key值。
【范例6】
下面在后台页面中分别通过索引和key两种形式获取连接字符串的内容,这两种形式的效果是一样的。代码如下。
protected void Page_Load(object sender, EventArgs e) { string conn = ConfigurationSettings.AppSettings[0].ToString(); string conn = ConfigurationSettings.AppSettings["ConnectionStr"]. ToString(); }
2.<configSections>配置节
<configSections>指定了配置节和处理程序声明,虽然ASP.NET不对如何处理配置文件内的设置做任何假设,但是ASP.NET会将配置数据的处理委托给配置节处理程序。该配置节由多个<section>配置节组成,可以将这些配置节处理程序声明嵌套在<sectionGroup>节点中,以帮助组织配置信息。
<configSections>配置节的组成结构如下。
<configSections> <section /> <sectionGroup></sectionGroup> </configSections>
上述结构中,<section/>定义配置节处理程序与配置元素之间的关联;<sectionGroup/>定义配置节处理程序与配置节之间的关联。可以在<sectionGroup>中对<section>进行逻辑分组,以对<section>进行组织,并且避免命名冲突。
【范例7】
<sectionGroup>中包含name和type两个属性,而<section>中这两个属性也经常被使用到。其中,name属性指定配置数据配置节的名称;而type属性指定与name属性相关的配置处理程序类。在本例子中首先向<configSections>中自定义配置信息,然后在页面中进行调用。操作步骤如下。
(1)向Web.config配置文件的在<configuration>根节点下添加一个<configSections>子节点,它必须是根元素下的第一个子元素节点。代码如下。
<configSections> <sectionGroup name="mySectionGroup"> <section name="mySection" requirePermission="true" type="SectionHandler" /> </sectionGroup> </configSections>
(2)在步骤(1)中<sectionGroup>节点中提到了mySectionGroup和mySection,它们是在Web.config中自定义的模块。代码如下。
<mySectionGroup> <mySection> <add key="No1" value="李磊" /> <add key="No2" value="许飞" /> <add key="No3" value="陈艳" /> <add key="No4" value="朱小小" /> <add key="No5" value="陈海风" /> </mySection> </mySectionGroup>
(3)向当前网站下创建一个SectionHandler类,该类实现IConfigurationSectionHandler接口。在该类中为Create()方法添加代码,在代码中创建Hashtable集合类,向该集合对象中读取数据并添加。代码如下。
public class SectionHandler : IConfigurationSectionHandler { public object Create(object parent, object configContext, System.Xml.XmlNode section) { Hashtable ht = new Hashtable(); //创建Hashtable数据 foreach (XmlNode node in section.ChildNodes) { if (node.Name == "add") ht.Add(node.Attributes["key"].Value, node.Attributes ["value"].Value); } return ht; } }
(4)向Web窗体页面的后台Load事件中添加代码,首先通过ConfigurationManager类的GetSection()方法获取Web.config配置文件中mySectionGroup/mySection元素节点下的内容,得到返回的Hashtable对象。然后遍历Hashtable集合对象中的信息,并且将内容输出到网页中。代码如下。
protected void Page_Load(object sender, EventArgs e) { Hashtable ht = ConfigurationManager.GetSection("mySectionGroup/ mySection") as Hashtable; foreach (DictionaryEntry de in ht) { //遍历Hashtable对象 Response.Write(de.Key + " - " + de.Value + "<br>"); } }
(5)运行本次例子的代码查看窗体页的输出结果,最终效果图不再显示。
3.<location>配置节
在Web.config配置文件中的<location>配置节也会被使用到,它可以在同一个配置文件中指定多个设定组,使用<location>元素的path属性可以指定设定应该被应用到的子目录或文件。
【范例8】
多个<location>节点可以存在于同一个配置文件中,并且为相同的配置节指定不同的范围。例如,下面向Web.config配置文件中添加两个<location>节点,设置该节点的path属性,然后分别向<location>节点下添加内容,指定HttpHandler处理时的相关信息。代码如下。
<configuration> <system.web> <sessionState cookieless="true" timeout="10" /> </system.web> <location path="sub1"> <!-- Configuration for the "Sub1" subdirectory. --> <system.web> <httpHandlers> <add verb="*" path="Sub1.Scott" type="Sub1.Scott" /> <add verb="*" path="Sub1.David" type="Sub1.David" /> </httpHandlers> </system.web> </location> <location path="sub2"> <!-- Configuration for the "Sub2" subdirectory. --> <system.web> <httpHandlers> <add verb="*" path="Sub2.Scott" type="Sub2.Scott" /> <add verb="*" path="Sub2.David" type="Sub2.David" /> </httpHandlers> </system.web> </location> </configuration>
4.<connectionStrings>配置节
除了向<appSettings>节点中添加连接字符串的内容外,还可以向<connectionStrings>节点中添加数据库的连接字符串信息。代码如下。
<connectionStrings> <add name="ConnStr" connectionString="server=.; userid=sa; password=123456; database=mytest; "/> </connectionStrings>
在上述代码中通过name指定连接字符串的名称;connectionString属性来指定连接的字符串,包括数据库名称和连接用户名与密码等。
17.2.5 <system.web>配置节
除了17.2.4节介绍的三个配置节外,还有一个配置节被使用到,通过向该配置节中添加子节点不仅可以指定数据库连接字符串,也可以实现身份验证和自定义错误等。下面将详细介绍<system.web>配置节。
1.<authentication>节点
<authentication>节点用来配置ASP.NET身份验证方案,该方案用于识别查看ASP.NET应用程序的用户。此节点中最常用的属性是mode,该属性包含以下4种身份验证模式。
1)Windows(默认验证)
将Windows验证指定为默认的身份验证模式,将它与以下任意形式的Microsoft Internet信息服务(IIS)身份验证结合起来使用:基本、摘要、集成Windows身份验证(NTLM/Kerberos)或证书。在这种情况下,开发人员的应用程序将身份验证责任委托给基础IIS。
2)Forms身份验证
将ASP.NET基于窗体的身份验证指定为默认身份验证模式,Forms身份验证是最常用的一种身份验证方式。
3)Passport身份验证
将Microsoft Passport Network身份验证指定为默认身份验证模式。
4)None
不会指定任何身份验证,允许匿名访问,或手动编码控制用户访问。
【范例9】
例如,下面的代码为基于窗体(Forms)的身份验证配置站点,当没有登录的用户访问需要验证的网页,网页自动跳转到登录页面。代码如下。
<authentication mode="Forms" > <forms loginUrl="logon.aspx" name=".FormsAuthCookie"/> </authentication>
上述代码中loginUrl表示登录网页的名称,即网址;name则表示Cookie的名称。除了loginUrl和name属性外,还可以向该节点中添加其他属性,这些属性说明如下。
(1)name:指定用于身份验证的Cookie名称。
(2)loginUrl:指定为登录而要重定向的URL,默认值为Default.aspx。
(3)defaultUrl:默认页的URL,通过FormsAuthentication.DefaultUrl属性得到该值。
(4)timeout:指定以整数分钟为单位,表单验证的有效时间即是Cookie的过期时间。
(5)path:Cookie的作用路径。默认为正斜杠(/),表示该Cookie可用于整个站点。
(6)requireSSL:在进行Forms身份验证时,与服务器交互是否要求使用SSL。
(7)slidingExpiration:是否启用“弹性过期时间”,如果该属性设置为false,从首次验证之后过timeout时间后Cookie即过期;如果该属性为true,则从上次请求开始过timeout时间才过期,这表示首次验证后,如果保证每timeout时间内至少发送一个请求,则Cookie将永远不会过期。
(8)enableCrossAppRedirects:是否可以将已进行了身份验证的用户重定向到其他应用程序中。
(9)cookieless:定义是否使用Cookie以及Cookie的行为。
(10)domain:Cookie的域。
2.<authorization>节点
<authorization>节点的作用是控制对URL资源的客户端访问(例如允许匿名用户访问),该元素可以在任何级别(计算机、站点、应用程序、子目录或页)上声明,它必须与<authentication>节点配合使用。
【范例10】
下面通过向<authorization>节点中添加内容,禁止匿名用户的访问,允许角色是admin的访问。代码如下。
<system.web> <authorization> <deny users="? "/> <allow roles="admin"/> </authorization> </system.web>
上述代码<authorization>节点下添加deny和allow两个元素,其中deny表示拒绝,allow表示允许。deny和allow中都可以添加user、roles和verbs这三个属性,其说明如下。
(1)user:一个使用逗号进行分隔的用户名列表,列表中的用户被授予(或拒绝)对资源的访问。其中“?”表示匿名用户,而“*”则代表所有用户。
(2)roles:逗号进行分隔的角色列表,这些角色被授予(或拒绝)对资源的访问。
(3)verbs:逗号进行分隔的谓词列表,比如GET、HEAD、POST或DEBUG等。
3.<customErrors>节点
<customErrors>能够指定当出现错误时系统自动跳转到一个错误发生的页面,同时也能够为应用程序配置是否支持自定义错误。添加<customErrors>节点时可以指定它的mode属性和defaultRedirect属性,其中前者表示自定义错误的状态,后者表示应用程序发生错误时所要跳转的页面。mode属性的取值有On、Off和RemoteOnly三个,说明如下。
(1)On:表示启动自定义错误。
(2)Off:表示不启动自定义错误。
(3)RemoteOnly:表示给远程用户显示自定义错误。
【范例11】
下面分别向<customErros>节点中添加两个<error>子节点,这两个节点用于处理访问页面时出现的403和404错误。代码如下。
<system.web> <customErrors mode="RemoteOnly" defaultRedirect="GenericErrorPage.htm"> <error statusCode="403" redirect="NoAccess.htm" /> <error statusCode="404" redirect="FileNotFound.htm" /> </customErrors> </system.web>
从上述代码中可以看出,添加<error>节点时为其指定statusCode属性和redirect属性,statusCode属性用于捕捉发生错误时的状态码。例如,请求资源不可用时的403错误;找不到网页时的404错误;redirect属性表示发生错误后跳转的页面。
4.<httpModules>节点和<httpHandlers>节点
细心的读者对这两个节点一定会很熟悉,在第10章中提到过模块和处理程序,它们就是用来配置与模块和处理程序有关的信息的。
【范例12】
<httpModules>节点定义HTTP请求时与模块有关的信息。代码如下。
<httpModules> <add name="MyHttpModule" type="MyHttpModule"/> </httpModules>
<httpHandlers>节点可以用于根据请求中指定的URL和HTTP谓词(如GET和POST)将传入的请求映射到相应的处理程序,可以针对某个特定的目录下指定的特殊文件进行特殊处理。
【范例13】
下面向<httpHandlers>节点添加内容,针对网站path目录下的所有*.jpg文件来编写自定义的处理程序。代码如下。
<httpHandlers> <add path="path/*.jpg" verb="*" type="HttpHandlerImagePic"/> </httpHandlers>
5.<httpRuntime>节点
<httpRuntime>节点的作用是配置ASP.NET HTTP运行库设置,该节可以在计算机、站点、应用程序和子目录级别声明。
【范例14】
下面向<httpRuntime>节点中添加内容,控制用户上传文件最大为4MB,最长时间为60s,最多请求数为100。代码如下。
<system.web> <httpRuntime maxRequestLength="4096" executionTimeout="60" appRequestQueueLimit="100"/> </system.web>
6.<sessionState>节点
<sessionState>节点的作用是为当前应用程序配置会话状态设置,例如设置是否启用会话状态和会话状态保存位置等。
【范例15】
例如,下面向<sessionState>节点中添加代码,分别指定mode、cookieliess和timeout属性的值。代码如下。
<sessionState mode="InProc" cookieless="true" timeout="20"/> </sessionState>
在上述代码中,mode属性表示在本地储存会话状态;cookieless属性的值表示如果用户浏览器不支持Cookie时启用会话状态(默认为false);timeout表示会话可以处于空闲状态的分钟数。mode属性的取值可以有多个,包括Off、InProc、StateServer和SqlServer这4个,说明如下。
(1)Off:设置为该值时表示禁用该设置。
(2)InProc:表示在本地保存会话状态。
(3)StateServer:表示在服务器上保存会话状态。
(4)SqlServer:表示在SQL Server保存会话设置。
除了上述介绍的向<sessionState>节点中添加的属性外,还可以添加其他的属性,例如用来指定远程存储会话状态的服务器名和端口号的stateConnectionString属性;用来连接SQL Server的连接字符串的sqlConnectionString属性,当在mode属性中设置SqlServer时,则需要使用到该属性。
7.<trace>节点
<trace>节点的作用是配置ASP.NET跟踪服务,主要用来程序测试判断哪里出错。下面的代码为Web.config中的默认配置。
<trace enabled="false" requestLimit="10" pageOutput="false" traceMode="SortByTime" localOnly="true" />
上述代码中enabled表示是否启用连接,默认值为false时表示不启用连接;requestLimit属性表示指定在服务器上存储的跟踪请求的数目;pageOutput属性设置为false时表示只能通过跟踪实用工具访问跟踪输出;traceMode属性指定为SortByTime,表示以处理跟踪的顺序来显示跟踪信息;localOnly属性的值为true,表示跟踪查看器(trace.axd)只用于宿主Web服务器。