为什么我的ASP.NET页面在没有发送任何身份验证标头的情况下返回“200 OK”?

时间:2009-06-17 18:37:41

标签: asp.net authentication keep-alive httpconnection

注意:

  

此问题的范围已扩大到以前的修订版。我试图简化这个问题,以便任何人都可以轻松复制。

使用Fiddler,我可以在从HTTP请求中删除Authorization标头后,将任意请求重播到我的默认页面,并且我能够得到200 OK的有效回复数据

赏金更新

以下是重现此确切行为的步骤:

1. 在ASP.NET中创建“新网站”,随意将其命名为“InsecureWebsite”

2. :修改web.config以拒绝所有未经身份验证的用户:

<authentication mode="Windows" />
  <authorization>
    <deny users="?"/>
  <allow users="*"/>
</authorization>

3. 将网站发布到DEV服务器上的任意目录,并为应用程序创建虚拟目录

4. 确保应用程序具有脚本访问权限(.ASP)并启用了集成Windows身份验证

5。打开Fiddler以捕获流量

6。在您喜欢的浏览器中加载页面并查看Fiddler中的“检查员”标签,您会看到类似于以下内容的请求:

GET /InsecureWebsite/ HTTP/1.1
Host: dev.subdomain.example.com
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1) Gecko/20090624 Firefox/3.5 (.NET CLR 3.5.30729)
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Authorization: NTLM
{Base64-encoded authentication data}

Default.aspx的初始请求将返回401 Unauthorized,将进入协商,最后返回200 OK

在Fiddler中,我可以直接从重播请求中删除Authorization标题Default.aspx,然后仍然获得200 OK。怎么可能?

解决方案

事实证明,Fiddler在发出请求时使用相同的底层连接,因此一旦连接通过身份验证,同一连接上的任何请求也将作为与初始请求相同的用户进行身份验证。您可以在Fiddler中关闭此功能:

Screenshot of Fiddler options http://john.cognitivedelay.com/images/fiddler-options.gif

取消选中此内容后,来自Fiddler的任何重播请求都会返回401 Unauthorized,如我所料。

感谢所有提供时间回应的人!

5 个答案:

答案 0 :(得分:2)

编辑:每个更新的问题:

您是在Fiddler本身进行重播,还是直接连接到网络服务器?可能是Fiddler正在重用现有的HTTP连接(它可以做,作为代理)...我认为IWA可能将整个连接标记为已验证,而不仅仅是当前请求,这意味着任何未来的请求都是相同的连接重新使用第一次协商的授权和身份验证...

原始答案: 试试

[WebMethod(EnableSession=true)]  
[PrincipalPermission(SecurityAction.Demand, Authenticated=true)]

看看是否有帮助?

(可能[PrincipalPermission(SecurityAction.Demand, Role="myDevRole")],如果这对你更合适......)

答案 1 :(得分:2)

Ajax调用是在现有经过身份验证的会话的新线程上完成的,这就是您在标头中看不到任何身份验证信息的原因。该会话已经过身份验证。

您可以通过引用System.Threading.Thread.CurrentPrincipal.Identity.Name:

获取经过身份验证的用户身份,然后将其传递给任何角色管理例程。
[WebMethod(EnableSession = true)]   
public static string WhoAmI()
{
    // Return the identity of the authenticated windows user.
    Return System.Threading.Thread.CurrentPrincipal.Identity.Name;
 }

答案 2 :(得分:1)

您可以将身份验证信息添加到邮件标题中,然后在Web方法中对自己进行身份验证。

或者您可以尝试thisthis

之类的内容

答案 3 :(得分:1)

将此属性添加到Web方法 [PrincipalPermissionAttribute( SecurityAction.Demand, Role = "myDevRole" )]

然后在Global.asax事件Application_AuthenticateRequest上,您可以确保正确验证当前线程用户 - 即执行必要的操作以避免欺诈cookie或会话。

答案 4 :(得分:1)

在本地开发计算机上使用Windows身份验证,每个请求都来自经过身份验证的用户。所以,拒绝用户=“?”永远不会在本地拒绝任何要求。

如果您在远程IIS计算机上遇到此问题,但未使用表单身份验证进行身份验证,则需要进行身份验证才能成功请求Default.aspx或页面方法。