设计 - 记录用户下载

时间:2013-08-14 11:35:03

标签: c# asp.net webforms

我必须记录从网站上抓取的每个文件的下载请求。此日志必须包含员工ID,解决方案ID,IP地址。我使用了很多方法 -

首先,我正在使用我放置文件路径的模型     在锚标签中。每当用户点击这个锚标签时,我     正在生成一个AJAX请求来记录文件下载。

但这样做的一个巨大缺点是用户可以只复制文件并将其粘贴到一个单独的窗口中以获取文件。这样可以确保不记录下载。

第二下, 当我在页面中的web方法中处理ajax请求时。我尝试通过HttpResponse传输文件,但这也不起作用。

HttpContext.Current.Response.TransmitFile("filename");

jQuery ajax调用一直失败,我从来没有在客户端获得该文件。

关键是,我必须在不刷新页面的情况下完成所有工作。

我想知道这是否可能......

3 个答案:

答案 0 :(得分:3)

您可以实现记录请求的IHttpHandler,检索文件并提供服务。这样,即使直接复制和粘贴链接,它仍会记录它。

public class SimpleHandler : IHttpHandler
{
    public bool IsReusable
    {
        get { return false; }
    }

    public void ProcessRequest(HttpContext context)
    {
        string fileToServe = context.Request.QueryString["file"];

        if (!string.IsNullOrEmpty(fileToServe))
        {
            //Log request here...

            context.Response.ContentType = "content type for your file here";
            context.Response.WriteFile("~/path/" + fileToServe);
        }
    }
}

答案 1 :(得分:1)

这非常有可能 - 您需要返回一个文件作为对动作(Mvc)或aspx页面(webforms)的响应。因此,当命中action或aspx页面时,您可以记录请求并将文件写入响应。

修改:对于网络表单示例,请参阅此SO question

对于mvc:

public ActionResult DownloadFile(string fileHint)
{
    // log what you want here.
    string filePath = "determine the path of the file to download maybe using fileHint";
    return File(filePath, "application/octet-stream"); // second argument represents file type; in this case, it's a binary file.
}

答案 2 :(得分:1)

您可以使用AJAX方法,在链接中使用标识符作为参数值来引用文件 - 而不是存储完整路径 - 并让您的Web方法返回文件的序列化数据。 / p>

因此,您的网络方法可能如下所示:

[WebMethod]
public static string GetDownload(string someIdentifier) {
  // get the contents of your file, then...
  // do your logging, and...
  var serializer = new JavaScriptSerializer();
  return serializer.Serialize(fileByteArrayOrSuch);
}

然后在客户端处理文件内容。毫无疑问,为了记录而添加到您的函数中会有一些更微不足道的元素;但最重要的是,您的AJAX既可以处理日志,也可以处理下载请求。