2023 lines
73 KiB
C#
2023 lines
73 KiB
C#
|
|
using NUnit.Framework;
|
|||
|
|
using System;
|
|||
|
|
using System.Collections.Generic;
|
|||
|
|
using System.Linq;
|
|||
|
|
using System.Text;
|
|||
|
|
|
|||
|
|
// Tests based on tests from http://roadkill.codeplex.com/
|
|||
|
|
|
|||
|
|
// To create unit tests in this class reference is taken from
|
|||
|
|
// https://www.owasp.org/index.php/XSS_(Cross_Site_Scripting)_Prevention_Cheat_Sheet#RULE_.232_-_Attribute_Escape_Before_Inserting_Untrusted_Data_into_HTML_Common_Attributes
|
|||
|
|
// and http://ha.ckers.org/xss.html
|
|||
|
|
|
|||
|
|
namespace Html
|
|||
|
|
{
|
|||
|
|
/// <summary>
|
|||
|
|
/// Tests for <see cref="HtmlSanitizer"/>.
|
|||
|
|
/// </summary>
|
|||
|
|
[TestFixture]
|
|||
|
|
[Category("Unit")]
|
|||
|
|
public class HtmlSanitizerTests
|
|||
|
|
{
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Xss locator
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void XSSLocatorTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<a href=\"'';!--\"<XSS>=&{()}\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = @"<a href=""'';!--"">=&{()}"></a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector
|
|||
|
|
/// Example <!-- <IMG SRC="javascript:alert('XSS');"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageXSS1Test()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Action
|
|||
|
|
string htmlFragment = "<IMG SRC=\"javascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector without quotes and semicolon.
|
|||
|
|
/// Example <!-- <IMG SRC=javascript:alert('XSS')> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageXSS2Test()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<IMG>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image xss vector with case insensitive.
|
|||
|
|
/// Example <!-- <IMG SRC=JaVaScRiPt:alert('XSS')> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageCaseInsensitiveXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=JaVaScRiPt:alert('XSS')>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<IMG>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Html entities
|
|||
|
|
/// Example <!-- <IMG SRC=javascript:alert("XSS")> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageHtmlEntitiesXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=javascript:alert("XSS")>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<IMG>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with grave accent
|
|||
|
|
/// Example <!-- <IMG SRC=`javascript:alert("RSnake says, 'XSS'")`> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageGraveAccentXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=`javascript:alert(\"RSnake says, 'XSS'\")`>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with malformed
|
|||
|
|
/// Example <!-- <IMG \"\"\"><SCRIPT>alert(\"XSS\")</SCRIPT>\"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageMalformedXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG \"\"\"><SCRIPT>alert(\"XSS\")</SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>">";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with ImageFromCharCode
|
|||
|
|
/// Example <!-- <IMG SRC=javascript:alert(String.fromCharCode(88,83,83))> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageFromCharCodeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=javascript:alert(String.fromCharCode(88,83,83))>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with UTF-8 Unicode
|
|||
|
|
/// Example <!-- <IMG SRC=javascript:alert('XSS')> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageUTF8UnicodeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Long UTF-8 Unicode
|
|||
|
|
/// Example <!-- <IMG SRC=javascript:alert('XSS')> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageLongUTF8UnicodeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Hex encoding without semicolon
|
|||
|
|
/// Example <!-- <IMG SRC=javascript:alert('XSS')> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageHexEncodeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with embedded tab
|
|||
|
|
/// Example <!-- <IMG SRC=\"jav ascript:alert('XSS');\"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageEmbeddedTabXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"jav ascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with embedded encoded tab
|
|||
|
|
/// Example <!-- <IMG SRC="jav	ascript:alert('XSS');"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageEmbeddedEncodedTabXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"jav	ascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with embedded new line
|
|||
|
|
/// Example <!-- <IMG SRC="jav
ascript:alert('XSS');"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageEmbeddedNewLineXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"jav
ascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with embedded carriage return
|
|||
|
|
/// Example <!-- <IMG SRC=\"jav
ascript:alert('XSS');\"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageEmbeddedCarriageReturnXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"jav
ascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Multiline using ASCII carriage return
|
|||
|
|
/// Example <!-- <IMG
|
|||
|
|
/// SRC
|
|||
|
|
/// =
|
|||
|
|
/// "
|
|||
|
|
/// j
|
|||
|
|
/// a
|
|||
|
|
/// v
|
|||
|
|
/// a
|
|||
|
|
/// s
|
|||
|
|
/// c
|
|||
|
|
/// r
|
|||
|
|
/// i
|
|||
|
|
/// p
|
|||
|
|
/// t
|
|||
|
|
/// :
|
|||
|
|
/// a
|
|||
|
|
/// l
|
|||
|
|
/// e
|
|||
|
|
/// r
|
|||
|
|
/// t
|
|||
|
|
/// (
|
|||
|
|
/// '
|
|||
|
|
/// X
|
|||
|
|
/// S
|
|||
|
|
/// S
|
|||
|
|
/// '
|
|||
|
|
/// )
|
|||
|
|
/// "
|
|||
|
|
///> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageMultilineInjectedXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = @"<IMG
|
|||
|
|
SRC
|
|||
|
|
=
|
|||
|
|
""
|
|||
|
|
j
|
|||
|
|
a
|
|||
|
|
v
|
|||
|
|
a
|
|||
|
|
s
|
|||
|
|
c
|
|||
|
|
r
|
|||
|
|
i
|
|||
|
|
p
|
|||
|
|
t
|
|||
|
|
:
|
|||
|
|
a
|
|||
|
|
l
|
|||
|
|
e
|
|||
|
|
r
|
|||
|
|
t
|
|||
|
|
(
|
|||
|
|
'
|
|||
|
|
X
|
|||
|
|
S
|
|||
|
|
S
|
|||
|
|
'
|
|||
|
|
)
|
|||
|
|
""
|
|||
|
|
>
|
|||
|
|
";
|
|||
|
|
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>\n";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Null breaks up Javascript directive
|
|||
|
|
/// Example <!-- perl -e 'print "<IMG SRC=java\0script:alert(\"XSS\")>";' > out -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageNullBreaksUpXSSTest1()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=java\0script:alert(\"XSS\")>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Null breaks up cross site scripting vector
|
|||
|
|
/// Example <!-- <image src=" perl -e 'print "<SCR\0IPT>alert(\"XSS\")</SCR\0IPT>";' > out "> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageNullBreaksUpXSSTest2()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<SCR\0IPT>alert(\"XSS\")</SCR\0IPT>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with spaces and Meta characters
|
|||
|
|
/// Example <!-- <IMG SRC="  javascript:alert('XSS');"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageSpaceAndMetaCharXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"  javascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with half open html
|
|||
|
|
/// Example <!-- <IMG SRC="javascript:alert('XSS')" -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageHalfOpenHtmlXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"javascript:alert('XSS')\"";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with double open angle bracket
|
|||
|
|
/// Example <!-- <image src=http://ha.ckers.org/scriptlet.html < -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageDoubleOpenAngleBracketXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<image src=http://ha.ckers.org/scriptlet.html <";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Dic Xss vector with Javascript escaping
|
|||
|
|
/// Example <!-- <div style="\";alert('XSS');//"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivJavascriptEscapingXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<div style=\"\";alert('XSS');//\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with input image
|
|||
|
|
/// Example <!-- <INPUT TYPE="IMAGE" SRC="javascript:alert('XSS');"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageInputXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<INPUT TYPE=\"IMAGE\" SRC=\"javascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<input type=\"image\">";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Dynsrc
|
|||
|
|
/// Example <!-- <IMG DYNSRC="javascript:alert('XSS')"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageDynsrcXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG DYNSRC=\"javascript:alert('XSS')\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image Xss vector with Lowsrc
|
|||
|
|
/// Example <!-- <IMG LOWSRC="javascript:alert('XSS')"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageLowsrcXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG LOWSRC=\"javascript:alert('XSS')\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Xss vector with BGSound
|
|||
|
|
/// Example <!-- <BGSOUND SRC="javascript:alert('XSS');"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void BGSoundXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<BGSOUND SRC=\"javascript:alert('XSS');\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for BR with Javascript Include
|
|||
|
|
/// Example <!-- <BR SIZE="&{alert('XSS')}"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void BRJavascriptIncludeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<BR SIZE=\"&{alert('XSS')}\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<BR>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for P with url in style
|
|||
|
|
/// Example <!-- <p STYLE="behavior: url(www.ha.ckers.org);"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void PWithUrlInStyleXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<p STYLE=\"behavior: url(www.ha.ckers.org);\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
// intentionally keep it failing to get notice when reviewing unit tests so can disucss
|
|||
|
|
string expected = "<p></p>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image with vbscript
|
|||
|
|
/// Example <!-- <IMG SRC='vbscript:msgbox("XSS")'> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageWithVBScriptXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC='vbscript:msgbox(\"XSS\")'>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image with Mocha
|
|||
|
|
/// Example <!-- <IMG SRC="mocha:[code]"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageWithMochaXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"mocha:[code]\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image with Livescript
|
|||
|
|
/// Example <!-- <IMG SRC="Livescript:[code]"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageWithLivescriptXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG SRC=\"Livescript:[code]\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Iframe
|
|||
|
|
/// Example <!-- <IFRAME SRC="javascript:alert('XSS');"></IFRAME> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void IframeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IFRAME SRC=\"javascript:alert('XSS');\"></IFRAME>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Frame
|
|||
|
|
/// Example <!-- <FRAMESET><FRAME SRC="javascript:alert('XSS');"></FRAMESET> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void FrameXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<FRAMESET><FRAME SRC=\"javascript:alert('XSS');\"></FRAMESET>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Table
|
|||
|
|
/// Example <!-- <TABLE BACKGROUND="javascript:alert('XSS')"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void TableXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<TABLE BACKGROUND=\"javascript:alert('XSS')\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<table></table>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for TD
|
|||
|
|
/// Example <!-- <TABLE><TD BACKGROUND="javascript:alert('XSS')"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void TDXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<TABLE><TD BACKGROUND=\"javascript:alert('XSS')\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<table><tbody><tr><td></td></tr></tbody></table>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div Background Image
|
|||
|
|
/// Example <!-- <DIV STYLE="background-image: url(javascript:alert('XSS'))"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivBackgroundImageXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<DIV STYLE=\"background-image: url(javascript:alert('XSS'))\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div Background Image with unicoded XSS
|
|||
|
|
/// Example <!-- <DIV STYLE="background-image:\0075\0072\006C\0028'\006a\0061\0076\0061\0073\0063\0072\0069\0070\0074\003a\0061\006c\0065\0072\0074\0028.1027\0058.1053\0053\0027\0029'\0029"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivBackgroundImageWithUnicodedXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = @"<DIV STYLE=""background-image:\0075\0072\006C\0028'\006a\0061\0076\0061\0073\0063\0072\0069\0070\0074\003a\0061\006c\0065\0072\0074\0028\0027\0058\0053\0053\0027\0029'\0029"">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div Background Image with extra characters
|
|||
|
|
/// Example <!-- <DIV STYLE="background-image: url(javascript:alert('XSS'))"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivBackgroundImageWithExtraCharactersXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<DIV STYLE=\"background-image: url(javascript:alert('XSS'))\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for DIV expression
|
|||
|
|
/// Example <!-- <DIV STYLE="width: expression(alert('XSS'));"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivExpressionXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<DIV STYLE=\"width: expression(alert('XSS'));\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Image with break up expression
|
|||
|
|
/// Example <!-- <IMG STYLE="xss:expr/*XSS*/ession(alert('XSS'))"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void ImageStyleExpressionXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<IMG STYLE=\"xss:expr/*XSS*/ession(alert('XSS'))\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<IMG>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with break up expression
|
|||
|
|
/// Example <!-- exp/*<A STYLE='no\xss:noxss("*//*");xss:ex/*XSS*//*/*/pression(alert("XSS"))'> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagStyleExpressionXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "exp/*<A STYLE='no\\xss:noxss(\"*//*\");xss:ex/*XSS*//*/*/pression(alert(\"XSS\"))'>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "exp/*<a></a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for BaseTag
|
|||
|
|
/// Example <!-- <BASE HREF="javascript:alert('XSS');//"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void BaseTagXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<BASE HREF=\"javascript:alert('XSS');//\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for EMBEDTag
|
|||
|
|
/// Example <!-- <EMBED SRC="http://ha.ckers.org/xss.swf" AllowScriptAccess="always"></EMBED> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void EmbedTagXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<EMBED SRC=\"http://ha.ckers.org/xss.swf\" AllowScriptAccess=\"always\"></EMBED>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for EMBEDSVG
|
|||
|
|
/// Example <!-- <EMBED SRC="data:image/svg+xml;base64,PHN2ZyB4bWxuczpzdmc9Imh0dH A6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcv MjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hs aW5rIiB2ZXJzaW9uPSIxLjAiIHg9IjAiIHk9IjAiIHdpZHRoPSIxOTQiIGhlaWdodD0iMjAw IiBpZD0ieHNzIj48c2NyaXB0IHR5cGU9InRleHQvZWNtYXNjcmlwdCI+YWxlcnQoIlh TUyIpOzwvc2NyaXB0Pjwvc3ZnPg==" type="image/svg+xml" AllowScriptAccess="always"></EMBED> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void EmbedSVGXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<EMBED SRC=\"data:image/svg+xml;base64,PHN2ZyB4bWxuczpzdmc9Imh0dH A6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcv MjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hs aW5rIiB2ZXJzaW9uPSIxLjAiIHg9IjAiIHk9IjAiIHdpZHRoPSIxOTQiIGhlaWdodD0iMjAw IiBpZD0ieHNzIj48c2NyaXB0IHR5cGU9InRleHQvZWNtYXNjcmlwdCI+YWxlcnQoIlh TUyIpOzwvc2NyaXB0Pjwvc3ZnPg==\" type=\"image/svg+xml\" AllowScriptAccess=\"always\"></EMBED>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for XML namespace
|
|||
|
|
/// Example <!-- <HTML xmlns:xss> <?import namespace="xss" implementation="http://ha.ckers.org/xss.htc"> <xss:xss>XSS</xss:xss></HTML> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void XmlNamespaceXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<HTML xmlns:xss> <?import namespace=\"xss\" implementation=\"http://ha.ckers.org/xss.htc\"> <xss:xss>XSS</xss:xss></HTML>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for XML with CData
|
|||
|
|
/// Example <!-- <XML ID=I><X><C><![CDATA[<IMG SRC="javas]]><![CDATA[cript:alert('XSS');">]]></C></X></xml><SPAN DATASRC=#I DATAFLD=C DATAFORMATAS=HTML></SPAN> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void XmlWithCDataXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<XML ID=I><X><C><![CDATA[<IMG SRC=\"javas]]><![CDATA[cript:alert('XSS');\">]]></C></X></xml><SPAN DATASRC=#I DATAFLD=C DATAFORMATAS=HTML></SPAN>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<SPAN></SPAN>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for XML with Comment obfuscation
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void XmlWithCommentObfuscationXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<XML ID=\"xss\"><I><B><IMG SRC=\"javas<!-- -->cript:alert('XSS')\"></B></I></XML><SPAN DATASRC=\"#xss\" DATAFLD=\"B\" DATAFORMATAS=\"HTML\"></SPAN>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<SPAN></SPAN>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for XML with Embedded script
|
|||
|
|
/// Example <!-- <XML SRC="xsstest.xml" ID=I></XML><SPAN DATASRC=#I DATAFLD=C DATAFORMATAS=HTML></SPAN> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void XmlWithEmbeddedScriptXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<XML SRC=\"xsstest.xml\" ID=I></XML><SPAN DATASRC=#I DATAFLD=C DATAFORMATAS=HTML></SPAN>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<SPAN></SPAN>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Html + Time
|
|||
|
|
/// Example <!-- <HTML><BODY><?xml:namespace prefix="t" ns="urn:schemas-microsoft-com:time"><?import namespace="t" implementation="#default#time2"><t:set attributeName="innerHTML" to="XSS<SCRIPT DEFER>alert("XSS")</SCRIPT>"></BODY></HTML> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void HtmlPlusTimeXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<HTML><BODY><?xml:namespace prefix=\"t\" ns=\"urn:schemas-microsoft-com:time\"><?import namespace=\"t\" implementation=\"#default#time2\"><t:set attributeName=\"innerHTML\" to=\"XSS<SCRIPT DEFER>alert("XSS")</SCRIPT>\"></BODY></HTML>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with javascript link location
|
|||
|
|
/// Example <!-- <A HREF="javascript:document.location='http://www.google.com/'">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagJavascriptLinkLocationXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"javascript:document.location='http://www.google.com/'\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with no filter evasion
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT SRC=http://ha.ckers.org/xss.js></SCRIPT>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivNoFilterEvasionXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT SRC=http://ha.ckers.org/xss.js></SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and no filter evasion
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<SCRIPT SRC=http://ha.ckers.org/xss.js></SCRIPT>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionNoFilterEvasionXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<SCRIPT SRC=http://ha.ckers.org/xss.js></SCRIPT>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with non alpha non digit xss
|
|||
|
|
/// Example <!-- <A HREF="http://www.codeplex.com?url=<SCRIPT/XSS SRC="http://ha.ckers.org/xss.js"></SCRIPT>">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagNonAlphaNonDigitXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=<SCRIPT/XSS SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>">XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with non alpha non digit xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT/XSS SRC=http://ha.ckers.org/xss.js></SCRIPT>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivNonAlphaNonDigitXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT/XSS SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and non alpha non digit xss
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<SCRIPT/XSS SRC="http://ha.ckers.org/xss.js"></SCRIPT>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionNonAlphaNonDigitXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<SCRIPT/XSS SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>)"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with non alpha non digit part 3 xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT/SRC=http://ha.ckers.org/xss.js></SCRIPT>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivNonAlphaNonDigit3XSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT/SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and non alpha non digit part 3 xss
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<SCRIPT/SRC="http://ha.ckers.org/xss.js"></SCRIPT>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionNonAlphaNonDigit3XSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<SCRIPT/SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>)"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with Extraneous open brackets xss
|
|||
|
|
/// Example <!-- <A HREF="http://www.codeplex.com?url=<<SCRIPT>alert("XSS");//<</SCRIPT>">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagExtraneousOpenBracketsXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=<<SCRIPT>alert(\"XSS\");//<</SCRIPT>\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>">XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with Extraneous open brackets xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<<SCRIPT>alert("XSS");//<</SCRIPT>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivExtraneousOpenBracketsXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<<SCRIPT>alert(\"XSS\");//<</SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and Extraneous open brackets xss
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<<SCRIPT>alert("XSS");//<</SCRIPT>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionExtraneousOpenBracketsXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<<SCRIPT>alert(\"XSS\");//<</SCRIPT>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>)"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with No closing script tags xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT SRC=http://ha.ckers.org/xss.js?<B>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivNoClosingScriptTagsXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT SRC=http://ha.ckers.org/xss.js?<B>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and No closing script tags xss
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<SCRIPT SRC=http://ha.ckers.org/xss.js?<B>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionNoClosingScriptTagsXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<SCRIPT SRC=http://ha.ckers.org/xss.js?<B>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with Protocol resolution in script tags xss
|
|||
|
|
/// Example <!-- <A HREF="http://www.codeplex.com?url=<SCRIPT SRC=//ha.ckers.org/.j>">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagProtocolResolutionScriptXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=<SCRIPT SRC=//ha.ckers.org/.j>\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with Protocol resolution in script tags xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT SRC=//ha.ckers.org/.j>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivProtocolResolutionScriptXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT SRC=//ha.ckers.org/.j>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and Protocol resolution in script tags xss
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<SCRIPT SRC=//ha.ckers.org/.j>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionProtocolResolutionScriptXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<SCRIPT SRC=//ha.ckers.org/.j>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with no single quotes or double quotes or semicolons xss
|
|||
|
|
/// Example <!-- <A HREF="http://www.codeplex.com?url=<SCRIPT>a=/XSS/alert(a.source)</SCRIPT>">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagNoQuotesXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=<SCRIPT>a=/XSS/alert(a.source)</SCRIPT>\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with no single quotes or double quotes or semicolons xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT>a=/XSS/alert(a.source)</SCRIPT>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivNoQuotesXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT>a=/XSS/alert(a.source)</SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with style expression and no single quotes or double quotes or semicolons xss
|
|||
|
|
/// Example <!-- <Div style="background-color: expression(<SCRIPT>a=/XSS/alert(a.source)</SCRIPT>)"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivStyleExpressionNoQuotesXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: expression(<SCRIPT>a=/XSS/alert(a.source)</SCRIPT>)\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with US-ASCII encoding xss
|
|||
|
|
/// Example <!-- <A HREF="http://www.codeplex.com?url=¼script¾alert(¢XSS¢)¼/script¾">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagUSASCIIEncodingXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=¼script¾alert(¢XSS¢)¼/script¾\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a href=\"http://www.codeplex.com/?url=¼script¾alert(¢XSS¢)¼/script¾\">XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with Downlevel-Hidden block xss
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagDownlevelHiddenBlockXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=<!--[if gte IE 4]><SCRIPT>alert('XSS');</SCRIPT><![endif]-->\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with Downlevel-Hidden block xss
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivDownlevelHiddenBlockXSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<!--[if gte IE 4]><SCRIPT>alert('XSS');</SCRIPT><![endif]-->\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for AnchorTag with Html Quotes Encapsulation 1 xss
|
|||
|
|
/// Example <!-- <A HREF="http://www.codeplex.com?url=<SCRIPT a=">" SRC="http://ha.ckers.org/xss.js"></SCRIPT>">XSS</A> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void AnchorTagHtmlQuotesEncapsulation1XSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<A HREF=\"http://www.codeplex.com?url=<SCRIPT a=\">\" SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>\">XSS</A>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<a>" SRC="http://ha.ckers.org/xss.js">">XSS</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for Div with Html Quotes Encapsulation 1 xss
|
|||
|
|
/// Example <!-- <Div style="background-color: http://www.codeplex.com?url=<SCRIPT a=">" SRC="http://ha.ckers.org/xss.js"></SCRIPT>"> -->
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DivHtmlQuotesEncapsulation1XSSTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<Div style=\"background-color: http://www.codeplex.com?url=<SCRIPT a=\">\" SRC=\"http://ha.ckers.org/xss.js\"></SCRIPT>\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div>" SRC="http://ha.ckers.org/xss.js">"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// A test for various legal fragments
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void LegalTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<div style=\"background-color: test\">";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div style=\"background-color: test\"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// More tests for legal fragments.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void MoreLegalTest()
|
|||
|
|
{
|
|||
|
|
// Arrange
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
// Act
|
|||
|
|
string htmlFragment = "<div style=\"background-color: test\">Test<img src=\"http://www.example.com/test.gif\" style=\"background-image: url(http://www.example.com/bg.jpg); margin: 10px\"></div>";
|
|||
|
|
string actual = sanitizer.Sanitize(htmlFragment);
|
|||
|
|
|
|||
|
|
// Assert
|
|||
|
|
string expected = "<div style=\"background-color: test\">Test<img style=\"background-image: url(http://www.example.com/bg.jpg); margin: 10px;\" src=\"http://www.example.com/test.gif\"></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// Misc tests.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void MiscTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
var html = @"<SCRIPT/SRC=""http://ha.ckers.org/xss.js""></SCRIPT>";
|
|||
|
|
var actual = sanitizer.Sanitize(html);
|
|||
|
|
var expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<DIV STYLE=""padding: 1px; mar/*xss*/gin: ex/*XSS*/pression(alert('xss')); background-image:\0075\0072\006C\0028\0022\006a\0061\0076\0061\0073\0063\0072\0069\0070\0074\003a\0061\006c\0065\0072\0074\0028\0027\0058\0053\0053\0027\0029\0022\0029"">";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = @"<div style=""padding: 1px""></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<!--[if gte IE 4]><SCRIPT>alert('XSS');</SCRIPT><![endif]--><!-- Comment -->";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<STYLE>@im\port'\ja\vasc\ript:alert(""XSS"")';</STYLE>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div onload!#$%&()*~+-_.,:;?@[/|\]^`=alert(""XSS"")>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<div></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<SCRIPT/XSS SRC=""http://ha.ckers.org/xss.js""></SCRIPT>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = "<IMG SRC=javascript:alert(\"XSS\")>\"";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>"";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = "<IMG SRC=java\0script:alert(\"XSS\")>\"";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>"";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=""jav
ascript:alert('XSS');"">";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=""jav
ascript:alert('XSS');"">";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=""jav	ascript:alert('XSS');"">";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""background-color: red""><sCRipt>hallo</scripT></div><a href=""#"">Test</a>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = @"<div style=""background-color: red""></div><a href=""#"">Test</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=""jav ascript:alert('XSS');"">";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=""  javascript:alert('XSS');"">";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<IMG SRC=javascript:alert('XSS')>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = "<img>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// Tests disallowed tags.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DisallowedTagTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
var html = @"<bla>Hallo</bla>";
|
|||
|
|
var actual = sanitizer.Sanitize(html);
|
|||
|
|
var expected = "";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// Tests disallowed HTML attributes.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DisallowedAttributeTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
var html = @"<div bla=""test"">Test</div>";
|
|||
|
|
var actual = sanitizer.Sanitize(html);
|
|||
|
|
var expected = @"<div>Test</div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// Tests sanitization of attributes that contain a URL.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void UrlAttributeTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
var html = @"<a href=""mailto:test@example.com"">test</a>";
|
|||
|
|
var actual = sanitizer.Sanitize(html);
|
|||
|
|
var expected = @"<a>test</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<a href=""http:xxx"">test</a>";
|
|||
|
|
actual = sanitizer.Sanitize(html);
|
|||
|
|
expected = @"<a>test</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<a href=""folder/file.jpg"">test</a>";
|
|||
|
|
actual = sanitizer.Sanitize(html, @"http://www.example.com");
|
|||
|
|
expected = @"<a href=""http://www.example.com/folder/file.jpg"">test</a>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// Tests disallowed css properties.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void DisallowedStyleTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
var html = @"<div style=""margin: 8px; bla: 1px"">test</div>";
|
|||
|
|
var actual = sanitizer.Sanitize(html);
|
|||
|
|
var expected = @"<div style=""margin: 8px"">test</div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/// <summary>
|
|||
|
|
/// Tests sanitiuation of URLs that are contained in CSS property values.
|
|||
|
|
/// </summary>
|
|||
|
|
[Test]
|
|||
|
|
public void UrlStyleTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
|
|||
|
|
var html = @"<div style=""padding: 10px; background-image: url(mailto:test@example.com)""></div>";
|
|||
|
|
var actual = sanitizer.Sanitize(html);
|
|||
|
|
var expected = @"<div style=""padding: 10px""></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""padding: 10px; background-image: url(folder/file.jpg)""></div>";
|
|||
|
|
actual = sanitizer.Sanitize(html, @"http://www.example.com");
|
|||
|
|
expected = @"<div style=""padding: 10px; background-image: url(http://www.example.com/folder/file.jpg);""></div>";
|
|||
|
|
Assert.That(actual, Is.EqualTo(expected).IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// test below from http://genshi.edgewall.org/
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_unchangedTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<a href=""#"">fo<br />o</a>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<a href=""#"">fo<br>o</a>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<a href=""#with:colon"">foo</a>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<a>foo</a>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_escape_textTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<a href=""#"">fo&</a>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<a href=""#"">fo&</a>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<a href=""#""><foo></a>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<a href=""#""><foo></a>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_entityref_textTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<a href=""#"">foö</a>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<a href=""#"">foö</a>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_escape_attrTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div title=""<foo>""></div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div title=""<foo>""></div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_close_empty_tagTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<a href=""#"">fo<br>o</a>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<a href=""#"">fo<br>o</a>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_invalid_entityTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"&junk;";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"&junk;").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_remove_script_elemTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<script>alert(""Foo"")</script>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"").IgnoreCase);
|
|||
|
|
html = @"<SCRIPT SRC=""http://example.com/""></SCRIPT>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_remove_onclick_attrTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div onclick=\'alert(""foo"")\' />";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_remove_commentsTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div><!-- conditional comment crap --></div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_remove_style_scriptsTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
// Inline style with url() using javascript: scheme
|
|||
|
|
var html = @"<DIV STYLE='background: url(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
// Inline style with url() using javascript: scheme, using control char
|
|||
|
|
html = @"<DIV STYLE='background: url(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
// Inline style with url() using javascript: scheme, in quotes
|
|||
|
|
html = @"<DIV STYLE='background: url(""javascript:alert(foo)"")'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
// IE expressions in CSS not allowed
|
|||
|
|
html = @"<DIV STYLE='width: expression(alert(""foo""));'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
html = @"<DIV STYLE='width: e/**/xpression(alert(""foo""));'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
html = @"<DIV STYLE='background: url(javascript:alert(""foo""));color: #fff'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div style=""color: #fff""></div>").IgnoreCase);
|
|||
|
|
|
|||
|
|
// Inline style with url() using javascript: scheme, using unicode
|
|||
|
|
// escapes
|
|||
|
|
html = @"<DIV STYLE='background: \75rl(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
html = @"<DIV STYLE='background: \000075rl(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
html = @"<DIV STYLE='background: \75 rl(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
html = @"<DIV STYLE='background: \000075 rl(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
html = @"<DIV STYLE='background: \000075
|
|||
|
|
rl(javascript:alert(""foo""))'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div></div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_remove_style_phishingTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
// The position property is not allowed
|
|||
|
|
var html = @"<div style=""position:absolute;top:0""></div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div style=""top: 0""></div>").IgnoreCase);
|
|||
|
|
// Normal margins get passed through
|
|||
|
|
html = @"<div style=""margin:10px 20px""></div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div style=""margin: 10px 20px""></div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_remove_src_javascriptTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<img src=\'javascript:alert(""foo"")\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
// Case-insensitive protocol matching
|
|||
|
|
html = @"<IMG SRC=\'JaVaScRiPt:alert(""foo"")\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
// Grave accents (not parsed)
|
|||
|
|
// Protocol encoded using UTF-8 numeric entities
|
|||
|
|
html = @"<IMG SRC=\'javascript:alert(""foo"")\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
// Protocol encoded using UTF-8 numeric entities without a semicolon
|
|||
|
|
// (which is allowed because the max number of digits is used)
|
|||
|
|
html = @"<IMG SRC=\'javascript:alert(""foo"")\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
// Protocol encoded using UTF-8 numeric hex entities without a semicolon
|
|||
|
|
// (which is allowed because the max number of digits is used)
|
|||
|
|
html = @"<IMG SRC=\'javascript:alert(""foo"")\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
// Embedded tab character in protocol
|
|||
|
|
html = @"<IMG SRC=\'jav\tascript:alert(""foo"");\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
// Embedded tab character in protocol, but encoded this time
|
|||
|
|
html = @"<IMG SRC=\'jav	ascript:alert(""foo"");\'>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<img>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_expressionTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""top:expression(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void capital_expressionTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""top:EXPRESSION(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_url_with_javascriptTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""background-image:url(javascript:alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_capital_url_with_javascriptTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""background-image:URL(javascript:alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_unicode_escapesTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""top:exp\72 ess\000069 on(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_backslash_without_hexTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""top:e\xp\ression(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
html = @"<div style=""top:e\\xp\\ression(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div style=""top: e\\xp\\ression(alert())"">XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_unsafe_propsTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""POSITION:RELATIVE"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""behavior:url(test.htc)"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""-ms-behavior:url(test.htc) url(#obj)"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""-o-link:'javascript:alert(1)';-o-link-source:current"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""-moz-binding:url(xss.xbl)"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_css_hackTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""*position:static"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
|
|||
|
|
html = @"<div style=""_margin:-10px"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_property_nameTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
var html = @"<div style=""display:none;border-left-color:red;user_defined:1;-moz-user-selct:-moz-all"">prop</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div style=""display: none; border-left-color: red;"">prop</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_unicode_expressionTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
// Fullwidth small letters
|
|||
|
|
var html = @"<div style=""top:expression(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
// Fullwidth capital letters
|
|||
|
|
html = @"<div style=""top:EXPRESSION(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
// IPA extensions
|
|||
|
|
html = @"<div style=""top:expʀessɪoɴ(alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
[Test]
|
|||
|
|
public void sanitize_unicode_urlTest()
|
|||
|
|
{
|
|||
|
|
var sanitizer = new HtmlSanitizer();
|
|||
|
|
// IPA extensions
|
|||
|
|
var html = @"<div style=""background-image:uʀʟ(javascript:alert())"">XSS</div>";
|
|||
|
|
Assert.That(sanitizer.Sanitize(html), Is.EqualTo(@"<div>XSS</div>").IgnoreCase);
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
}
|