哥最近准备把网站的登录模块重写,采用ASP.NET自带的Forms验证方式。一直觉得微软的登录肯定要比自己写程序判断Session神马的要完善。

我的场景是这样的:

一个普通的网站,分为前台和后台。前台是给Internet访客看的,无需登录。后台是给管理员发表文章和管理网站的,要求登录才能访问。

这样的网站我们通常这样设计目录结构:

Web -----网站根目录

{

    Console ----- 后台管理入口

    {

        Default.aspx ----- 登录页(一般叫做Login.aspx)

        Welcome.aspx ----- 欢迎页(登录成功就跳转到此页)

        ….aspx -----各种后台页面

    }

    Default.aspx ----- 网站首页(无需登录就能看)

    …..aspx -----各种网站内容页面(也是无需登录就能看)

}

这个例子中我们要求只有Console下的页面才需要登录。这是肿么做的呢?

先来看看最简单的Forms验证:

一、在web.config的system.web节点下加入下面的代码

<authentication mode="Forms">
    <forms loginUrl="Console/Default.aspx" name=".ASPXFORMSAUTH" defaultUrl="Console/Welcome.aspx">
    </forms>
</authentication>
<authorization>
    <deny users="?"/>
</authorization>

 

二、登录页面Default.aspx和欢迎页面Welcome.aspx的代码

这个与本文讨论内容无关,大家自己看一下MSDN的例子:http://msdn.microsoft.com/zh-cn/library/xdt4thhy%28v=VS.80%29.aspx

配置完这些,我们访问网站中的任意页面,都会要求登录了。可是在我们的需求里,我们希望只有Console下的页面才需要登录访问,怎么写呢?

我一开始的想法是在Console目录下建个web.config,并把关于验证的authentication和authorization节点都放在Console/web.config的system.web下。后来发现这样做会引起运行时错误:

It is an error to use a section registered as allowDefinition='MachineToApplication' beyond application level.  This error can be caused by a virtual directory not being configured as an application in IIS.

无奈,查MSDN也没查出个P来。经过一番开荒摸索,我终于找到了最简单的解决办法:

一、把Web根目录下的web.config中allow users的属性值设为“*”,意思是允许任意用户访问根目录下的所有页面。

<authentication mode="Forms">
    <forms loginUrl="Console/Default.aspx" name=".ASPXFORMSAUTH" defaultUrl="Console/Welcome.aspx">
    </forms>
</authentication>
<authorization>
    <allow users="*"/>
</authorization>

 

二、在Console下再建个web.config,这个文件的作用域只是Console目录下的所有页面

Console\Web.config文件全部代码:

<?xml version="1.0"?>
<configuration>
    <system.web>
        <authorization>
            <deny users="?"/>
        </authorization>
    </system.web>
</configuration>

 

最终的目录结构:

现在再访问Web\Default.aspx就不需要登录了:

如果访问Console\Welcome.aspx就会被强制要求登录:

登录之后就可以看Welcome.aspx了:

总结:

以下是我自己的理解,可能会坑爹,大家自己凑合着看吧:

1. authentication节点只能在网站根目录的web.config中定义一次

2. 让Web\Console\Web.Config下的allow users="?" 覆盖掉 Web\Web.Config下的allow users="*"