【问题标题】:Preventing XSS Attack on Form防止对表单的 XSS 攻击
【发布时间】:2016-02-05 12:23:27
【问题描述】:

全部:

我正在使用 C# MVC4 处理的项目遇到问题

在项目中,我接受一个用户的URL和其他参数,然后做一些处理,并将处理的结果发送到由用户提供的URL用户。

使用以下代码发送结果:

var context = HttpContext.Current;

context.Response.Write("<html><head>");
context.Response.Write("</head><body>");

context.Response.Write(string.Format("<form name=\"myform\" method=\"post\" action=\"{0}\" >", postUrl));

context.Response.Write("</form>");
context.Response.Write("<script type=\"text/javascript\">document.myform.submit();</script></body></html>");

context.Response.Write("</body>");
context.Response.Flush();
context.Response.Clear();
context.ApplicationInstance.CompleteRequest();

每当用户尝试像传递 javascript%3aalert('xss')%2f%2f 的 url 值这样的 XSS 时,JavaScript 就会运行并显示弹出窗口。

我已经尝试 Antixss.HtmlEncode() 在将 URL 传递到 string.Format 之前对其进行编码,但仍然无法正常工作。我也尝试过 Antixss.UrlEncode(),但这会导致错误,因为表单没有提交到 URL。

请帮帮我,我有什么遗漏吗?我还能做什么?

提前致谢。

【问题讨论】:

  • 将元素对象附加到 dom 并使用用户提供的值设置这些对象的属性,这会避开所有插值攻击...将用户给定的值作为 JSON 发送。
  • 对不起,我没让你好。请提供示例代码。
  • 我没有 c# 经验,但这似乎是一个很好的解决方案:weblogs.asp.net/jongalloway/…

标签: javascript c# asp.net-mvc-4 xss antixsslibrary


【解决方案1】:

尝试使用HttpUtility.UrlEncode

类似Response.Write(HttpUtility.UrlEncode(urlString));

更多步骤请参见How To: Prevent Cross-Site Scripting in ASP.NET =)

【讨论】:

    【解决方案2】:

    您需要三管齐下的方法来解决这个问题。

    防止XSS注入:

    请注意,如果用户注入了 url 值

    " /> <script>alert('xss')</script>
    

    这也会让你容易受到攻击:

    <form name="myform" method="post" action="" /> <script>alert('xss')</script>" >
    

    因此你应该使用HttpUtility.HtmlAttributeEncode函数来解决这个问题。

    但是,不要止步于此。如前所述,您应该针对 javascript: 样式的 URL 进行投影。为此,我会确保 URL 以 http://https:// 开头。如果没有,请抛出 SecurityException,您应该在服务器端记录和处理它,并向用户显示自定义错误页面。

    最后,您要防范Open Redirect Vulnerabilities。这是通过将用户重定向到其他域来阻止网络钓鱼攻击。同样,使用白名单方法并确保重定向到的域是您自己的域。此处的解析要小心,因为很容易出错 - 在许多编写错误的验证例程中,http://example.org?http://example.com 的 URL 将通过 example.com 的验证过滤器。我建议在 .NET 中使用 Uri 对象并通过它检索域,而不是滚动您自己的字符串函数。

    您还可以检查 URL 是否为相对 URL,如果可以接受则允许。使用 this function 之类的东西,它使用内置的 .NET 库来确保它是相对的。

    【讨论】:

      【解决方案3】:

      由于您将 postUrl 添加为表单标签的属性“动作”,您可以尝试在 HttpUtility 中使用 HtmlAttributeEncode 方法

      [ValidateInput(false)]
      public ActionResult Test(string url)
      {
          var context = System.Web.HttpContext.Current;
      
          context.Response.Write("<html><head>");
          context.Response.Write("</head><body>");
      
          context.Response.Write(string.Format("<form name=\"myform\" method=\"post\" action=\"{0}\" >", HttpUtility.HtmlAttributeEncode(url)));
      
          context.Response.Write("</form>");
          context.Response.Write("<script type=\"text/javascript\">document.myform.submit();</script></body></html>");
      
          context.Response.Write("</body>");
          context.Response.Flush();
          context.Response.Clear();
          context.ApplicationInstance.CompleteRequest();
          return null;
      }
      

      http://localhost:39200/home/test?url=https%3A%2F%2Fwww.google.com - 工作 http://localhost:39200/home/test?url=%3Cscript%3Ealert(%27test%27)%3C%2Fscript%3E - 工作(没有显示警报)

      根据输入白名单验证用户输入始终是一种很好的做法,以防止 XSS 攻击。

      【讨论】:

        【解决方案4】:

        只是一个想法 - 尝试将这个脚本放入而不只是 document.myform.submit(并删除表单的 action 属性):

        if("{0}".indexOf('http') !== 0) {
            //this is some sort of injection, or it's pointing at something on your server. Should cover http and https.
            //Specifically, it makes sure that the url starts with 'http' - so a 'javascript' url isn't going to work.
        } else {
            document.myform.action="{0}"
            document.myform.submit();
        }
        

        您还可以做更多事情,但这应该会有所帮助。

        【讨论】:

          猜你喜欢
          • 2022-01-08
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2023-03-04
          • 1970-01-01
          相关资源
          最近更新 更多