Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #43 from justinsa/master
RequiredHttpAttribute and some regular expressions
- Loading branch information
Showing
8 changed files
with
337 additions
and
9 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
87 changes: 87 additions & 0 deletions
87
DataAnnotationsExtensions.Tests/ValidationAttributes/RequiredHttpAttributeTests.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,87 @@ | ||
using System.ComponentModel.DataAnnotations; | ||
using System.Globalization; | ||
using System.IO; | ||
using System.Web; | ||
using DataAnnotationsExtensions.ServerSideValidators; | ||
using Microsoft.VisualStudio.TestTools.UnitTesting; | ||
|
||
namespace DataAnnotationsExtensions.Tests.ValidationAttributes | ||
{ | ||
[TestClass] | ||
public class RequiredHttpAttributeTests | ||
{ | ||
[TestMethod] | ||
public void IsValidFallbackTests() | ||
{ | ||
var attribute = new RequiredHttpAttribute(); | ||
|
||
Assert.IsTrue(attribute.IsValid("A")); | ||
Assert.IsTrue(attribute.IsValid("ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")); | ||
Assert.IsFalse(attribute.IsValid(" ")); | ||
Assert.IsFalse(attribute.IsValid(null)); | ||
Assert.IsFalse(attribute.IsValid(string.Empty)); | ||
} | ||
|
||
[TestMethod] | ||
public void IsValidRequiredTests() | ||
{ | ||
var attribute = new RequiredHttpAttribute() | ||
{ | ||
HttpMethod = "GET" | ||
}; | ||
HttpRequest request = new HttpRequest("test", "http://localhost", string.Empty) | ||
{ | ||
RequestType = "GET" | ||
}; | ||
HttpResponse response = new HttpResponse(HttpWriter.Null); | ||
HttpContext.Current = new HttpContext(request, response); | ||
|
||
Assert.IsTrue(attribute.IsValid("A")); | ||
Assert.IsTrue(attribute.IsValid("ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")); | ||
Assert.IsFalse(attribute.IsValid(" ")); | ||
Assert.IsFalse(attribute.IsValid(null)); | ||
Assert.IsFalse(attribute.IsValid(string.Empty)); | ||
} | ||
|
||
[TestMethod] | ||
public void IsValidMultiMethodRequiredTests() | ||
{ | ||
var attribute = new RequiredHttpAttribute() | ||
{ | ||
HttpMethod = "GeT|PosT" | ||
}; | ||
HttpRequest request = new HttpRequest("test", "http://localhost", string.Empty) | ||
{ | ||
RequestType = "post" | ||
}; | ||
HttpResponse response = new HttpResponse(HttpWriter.Null); | ||
HttpContext.Current = new HttpContext(request, response); | ||
|
||
Assert.IsTrue(attribute.IsValid("A")); | ||
Assert.IsTrue(attribute.IsValid("ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")); | ||
Assert.IsFalse(attribute.IsValid(" ")); | ||
Assert.IsFalse(attribute.IsValid(null)); | ||
Assert.IsFalse(attribute.IsValid(string.Empty)); | ||
} | ||
|
||
[TestMethod] | ||
public void IsValidIgnoreRequiredTests() | ||
{ | ||
var attribute = new RequiredHttpAttribute() | ||
{ | ||
HttpMethod = "POST" | ||
}; | ||
HttpRequest request = new HttpRequest("test", "http://localhost", string.Empty) | ||
{ | ||
RequestType = "Get" | ||
}; | ||
HttpContext context = new HttpContext(request, null); | ||
|
||
Assert.IsTrue(attribute.IsValid("A")); | ||
Assert.IsTrue(attribute.IsValid("ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")); | ||
Assert.IsTrue(attribute.IsValid(" ")); | ||
Assert.IsTrue(attribute.IsValid(null)); | ||
Assert.IsTrue(attribute.IsValid(string.Empty)); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
using System; | ||
using System.ComponentModel.DataAnnotations; | ||
using System.Text.RegularExpressions; | ||
using System.Web; | ||
|
||
namespace DataAnnotationsExtensions.ServerSideValidators | ||
{ | ||
/// <summary> | ||
/// RequiredHttpAttribute class. Identical behavior to the RequiredAttribute class | ||
/// with the additon that it allows for bypassing validation based on the Http | ||
/// method of the current Http request. | ||
/// </summary> | ||
/// <remarks> | ||
/// This class will have identical behavior to the RequiredAttribute class in the scenario | ||
/// where the System.Web.HttpContext.Current property returns null. | ||
/// </remarks> | ||
[AttributeUsageAttribute(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, AllowMultiple = false)] | ||
public sealed class RequiredHttpAttribute : System.ComponentModel.DataAnnotations.RequiredAttribute | ||
{ | ||
/// <summary> | ||
/// Gets or sets the HTTP methods that this attribute will validate on. | ||
/// </summary> | ||
/// <remarks>The value is treated as a regular expression pattern, e.g., GET|POST.</remarks> | ||
public string HttpMethod { get; set; } | ||
|
||
/// <summary> | ||
/// Validates the specified value. | ||
/// </summary> | ||
/// <param name="value">The value to validate.</param> | ||
/// <returns>True if the value is valid and false otherwise.</returns> | ||
public override bool IsValid(object value) | ||
{ | ||
var required = this.RequiredInContext(HttpContext.Current); | ||
return required ? base.IsValid(value) : true; | ||
} | ||
|
||
/// <summary> | ||
/// Validates the specified value with respect to the current validation attribute. | ||
/// </summary> | ||
/// <param name="value">The value to validate.</param> | ||
/// <param name="validationContext">The context information about the validation operation.</param> | ||
/// <returns>An instance of the ValidationResult class.</returns> | ||
protected override ValidationResult IsValid(object value, ValidationContext validationContext) | ||
{ | ||
var required = this.RequiredInContext(HttpContext.Current); | ||
return required ? base.IsValid(value, validationContext) : ValidationResult.Success; | ||
} | ||
|
||
/// <summary> | ||
/// Determines if the provided HTTP context permits validation. | ||
/// </summary> | ||
/// <param name="context">The HTTP context.</param> | ||
/// <returns>True if validation is required and false otherwise.</returns> | ||
protected bool RequiredInContext(HttpContext context) | ||
{ | ||
if (context != null && !string.IsNullOrWhiteSpace(this.HttpMethod)) | ||
{ | ||
if (!Regex.IsMatch(context.Request.HttpMethod, this.HttpMethod, RegexOptions.IgnoreCase)) | ||
{ | ||
return false; | ||
} | ||
} | ||
|
||
return true; | ||
} | ||
} | ||
} |
Oops, something went wrong.