我的一些模型属性由AllowHtml属性标记。有没有办法自动将AntiXss保护(即仅过滤允许的标签)应用于这些字段?
答案 0 :(得分:10)
首先,afaik,没有内置的东西。 但MVC允许通过自定义ModelBinder轻松完成这些操作,您可以定义
public class CustomAntiXssAttribute : Attribute { }
并用它装饰你的属性(如果你愿意,甚至可以从AllowHtmlAttribute
继承)。然后使用模型绑定器,您可以添加特定的防xss保护:
public class CutstomModelBinder : DefaultModelBinder
{
protected override void BindProperty(ControllerContext controllerContext, ModelBindingContext bindingContext, System.ComponentModel.PropertyDescriptor propertyDescriptor)
{
if (propertyDescriptor.Attributes.OfType<CustomAntiXssAttribute>().Any())
{
var valueResult = bindingContext.ValueProvider.GetValue(propertyDescriptor.Name);
var filteredValue = SOME_CUSTOM_FILTER_FUNCTION_HERE(valueResult.AttemptedValue);
propertyDescriptor.SetValue(bindingContext.Model, filteredValue);
}
else // revert to the default behavior.
{
base.BindProperty(controllerContext, bindingContext, propertyDescriptor);
}
}
}
然后在SOME_CUSTOM_FILTER_FUNCTION_HERE
里面你可以使用@Yogiraj建议的东西,或使用Regexp,甚至应用基于HtmlAgilityPack的过滤。
P.S。别忘了将ModelBinders.Binders.DefaultBinder = new CutstomModelBinder();
添加到Application_Start(我忘了:))
答案 1 :(得分:4)
没有自动方式。你最接近的是获得AntiXss Nuget包。然后您可以在控制器中使用它,如下所示:
Microsoft.Security.Application.Sanitizer.GetSafeHtml("YourHtml");
OR
Microsoft.Security.Application.Encoder.HtmlEncode("YourHtml");
如果使用,可以使用
解码 Server.HtmlDecode("HtmlEncodedString");
希望这有帮助。
答案 2 :(得分:1)
我会用AllowHtml
数据注释验证来替换这些RegularExpression
属性。优点是通过这种方式,您可以捕获错误并向用户显示错误,而前者在全局级别触发错误。
对于前。
public class MyViewModel
{
[DataType(DataType.MultilineText)]
[RegularExpression(@"^[^\<\>]*$", ErrorMessage = "May not contain <,>")]
public string Text { get; set; }
}
答案 3 :(得分:0)
未经测试的代码,
public class ADefaultModelBinder : DefaultModelBinder
{
public override object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
if (bindingContext.ModelMetadata.RequestValidationEnabled)
{
var value = bindingContext.ValueProvider.GetValue(bindingContext.ModelName).AttemptedValue;
value = value.Replace("&", "");// replace existing & from the value
var encodedValue = Microsoft.Security.Application.Encoder.HtmlEncode(value);
bindingContext.ModelMetadata.RequestValidationEnabled = encodedValue.Contains("&"); // Whether AntiXss encoded a char to &..
}
return base.BindModel(controllerContext, bindingContext);
}
}
public class MvcApplication : System.Web.HttpApplication
{
protected void Application_Start()
{
ModelBinders.Binders.DefaultBinder = new ADefaultModelBinder();