对ASP.NET网站中所有子文件夹请求的自定义授权

时间:2016-09-06 22:33:37

标签: c# asp.net webforms

我有一个ASP.NET 4.0网站,其中包含一个包含JPG,PNG,MP4,MP3等多媒体文件的子文件夹。

目前,任何拥有文件完整链接的用户都可以无任何限制地访问多媒体文件。我想查找当前登录的用户,并在检查了他们对DB的权限后允许/禁止他们访问所请求的文件。

我已尝试为此目的实现自定义HttpModule,但我无法找到发出请求的当前用户。以下是我的代码:

public class CustomHttpModule : IHttpModule
{
    private const string URL_TO_LOOK_FOR = "/MultiMediaFiles/";

    public CustomHttpModule()
    { }

    public void Init(HttpApplication app)
    {
        app.AuthenticateRequest += CustomAuthenticateRequest;
        //app.EndRequest += CustomAuthenticateRequest;
    }

    void CustomAuthenticateRequest(object source, EventArgs e)
    {
        HttpApplication app = (HttpApplication)source;
        HttpContext context = app.Context;
        Uri url = context.Request.Url;
        if (url.AbsolutePath.StartsWith(URL_TO_LOOK_FOR, StringComparison.OrdinalIgnoreCase))
        {
            var response = context.Response;
            response.Clear();
            response.Write("app.Context.User :");
            if (context.User == null || context.User.Identity == null || context.User.Identity.Name == null)
            {
                response.Write("No user");
            }
            else
            {
                response.Write(context.User.Identity.Name);
            }

            response.End();
            response.Flush();
            response.Close();
        }
    }

    public void Dispose()
    { }
}

我尝试附加到事件:BeginRequestAuthenticateRequestPostAuthenticateRequest甚至EndRequest,但在每种情况下,context.User始终为null即使在我登录我的网站后也是如此。

修改 我正在使用FormsAuthentication,我的web.config包含:

<system.web>
    <authentication mode="Forms">
        <forms name="MyWebFORMAUTH" timeout="60" 
               loginUrl="~/web/logon/default.aspx" cookieless="UseCookies" 
               defaultUrl="~/web/logon/default.aspx" 
               slidingExpiration="true" />
    </authentication>
</system.web>
<system.webServer>
    <modules>
      <add name="CustomHttpModule" type="CustomHttpModule"/>
    </modules>
<system.webServer>

注意:我无法修改多媒体文件的链接。

请帮助。

1 个答案:

答案 0 :(得分:1)

<强>更新

您还需要告诉ASP.NET您不想为某些目录中的某些文件类型执行静态内容处理程序。

以下是 web.config 文件的更新版本:

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
    <system.web>
        <compilation debug="true" targetFramework="4.0" />
        <httpRuntime />
        <authentication mode="Forms">
            <forms name="MyWebFORMAUTH" timeout="60"
                   loginUrl="~/web/logon/default.aspx" cookieless="UseCookies"
                   defaultUrl="~/web/logon/default.aspx"
                   slidingExpiration="true" />
        </authentication>
    </system.web>
    <system.webServer>
        <modules>
            <add name="CustomHttpModule" type="CustomHttpModule" />
        </modules>
        <defaultDocument>
            <files>
                <clear />
                <add value="Default.aspx" />
            </files>
        </defaultDocument>
    </system.webServer>
    <location path="MultiMediaFiles">
        <system.webServer>
            <handlers>
                <!-- This line tells ASP.NET to skip the processing of PNG files
                     by default static content handler. -->
                <add name="SkipStaticPng" path="*.png" verb="GET"
                     type="System.Web.Handlers.TransferRequestHandler"
                     preCondition="integratedMode,runtimeVersionv4.0" />
            </handlers>
        </system.webServer>
    </location>
</configuration>

您的代码应该有效。这是一个例子:

<强> Default.aspx的:

<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="WebForm" %>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
    <title>Test</title>
</head>
<body>
    <form id="form1" runat="server">
        <asp:Label ID="CurrentUserLabel" runat="server" />
        <br />
        <asp:Button ID="LoginButton" runat="server" OnClick="LoginButton_Click" Text="Login" />
    </form>
</body>
</html>

<强> Default.aspx.cs:

using System;
using System.Security.Principal;
using System.Web.Security;

public partial class WebForm : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {
        if (!IsPostBack)
            PopulateCurrentUserName();
    }

    protected void LoginButton_Click(object sender, EventArgs e)
    {
        FormsAuthentication.SetAuthCookie("test_user", false);
        Response.Redirect(Request.Url.AbsoluteUri);
    }

    private void PopulateCurrentUserName()
    {
        IPrincipal user = Request.RequestContext.HttpContext.User;
        if (user != null && user.Identity != null && !String.IsNullOrEmpty(user.Identity.Name))
            CurrentUserLabel.Text = user.Identity.Name;
        else
            CurrentUserLabel.Text = "(null)";
    }
}

<强> CustomHttpModule.cs:

using System;
using System.Web;

public class CustomHttpModule : IHttpModule
{
    private const string URL_TO_LOOK_FOR = "/MultiMediaFiles/";

    public CustomHttpModule()
    {
    }

    public void Init(HttpApplication app)
    {
        app.AuthenticateRequest += CustomAuthenticateRequest;
    }

    void CustomAuthenticateRequest(object source, EventArgs e)
    {
        HttpApplication app = (HttpApplication)source;
        HttpContext context = app.Context;
        Uri url = context.Request.Url;
        if (url.AbsolutePath.StartsWith(URL_TO_LOOK_FOR, StringComparison.OrdinalIgnoreCase))
        {
            var response = context.Response;
            response.Clear();
            response.Write("app.Context.User :");
            if (context.User == null || context.User.Identity == null || context.User.Identity.Name == null)
            {
                response.Write("No user");
            }
            else
            {
                response.Write(context.User.Identity.Name);
            }

            response.End();
            response.Flush();
            response.Close();
        }
    }

    public void Dispose()
    {
    }
}

<强>的web.config:

<?xml version="1.0"?>
<configuration>
    <system.web>
        <compilation debug="true" targetFramework="4.0"/>
        <httpRuntime/>
        <authentication mode="Forms">
            <forms name="MyWebFORMAUTH" timeout="60"
                   loginUrl="~/web/logon/default.aspx" cookieless="UseCookies"
                   defaultUrl="~/web/logon/default.aspx"
                   slidingExpiration="true" />
        </authentication>
    </system.web>
    <system.webServer>
        <modules>
            <add name="CustomHttpModule" type="CustomHttpModule"/>
        </modules>
        <defaultDocument>
            <files>
                <clear/>
                <add value="Default.aspx"/>
            </files>
        </defaultDocument>
    </system.webServer>
</configuration>

这是测试场景:

  1. 清除浏览器中的Cookie。
  2. 导航到起始页面(让我们说它是http://localhost)。
  3. 您将看到当前用户为(null)。
  4. 在第二个标签中打开http://localhost/MultiMediaFiles/
  5. 您将看到&#34; app.Context.User:没有用户&#34;消息。
  6. 切换回上一个标签,然后点击&#34;登录&#34;按钮。
  7. 您将看到当前用户现在是&#34; test_user&#34;。
  8. 切换到第二个标签并刷新页面。
  9. 如果一切正确,那么&#34; app.Context.User:test_user&#34;应显示消息。