This article will present a validation attribute for multiple enum value in C#. In C#, generics is not supported in attributes.
The following class therefore specifyes the type of enum and provides a list of invalid enum values as an example of such an attribute.
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
namespace ValidateEnums
{
public sealed class InvalidEnumsAttribute : ValidationAttribute
{
private List<object> _invalidValues = new List<object>();
public InvalidEnumsAttribute(Type enumType, params object[] enumValues)
{
foreach (var enumValue in enumValues)
{
var _invalidValueParsed = Enum.Parse(enumType, enumValue.ToString());
_invalidValues.Add(_invalidValueParsed);
}
}
public override bool IsValid(object value)
{
foreach (var invalidValue in _invalidValues)
{
if (Enum.Equals(invalidValue, value))
return false;
}
return true;
}
}
}
Let us make use of this attribute in a sample class.
public class Snack
{
[InvalidEnums(typeof(IceCream), IceCream.None, IceCream.All )]
public IceCream IceCream { get; set; }
}
We can then test out this attribute easily in NUnit tests for example:
[TestFixture]
public class TestEnumValidationThrowsExpected
{
[Test]
[ExpectedException(typeof(ValidationException))]
[TestCase(IceCream.All)]
[TestCase(IceCream.None)]
public void InvalidEnumsAttributeTest_ThrowsExpected(IceCream iceCream)
{
var snack = new Snack { IceCream = iceCream };
Validator.ValidateObject(snack, new ValidationContext(snack, null, null), true);
}
[Test]
public void InvalidEnumsAttributeTest_Passes_Accepted()
{
var snack = new Snack { IceCream = IceCream.Vanilla };
Validator.ValidateObject(snack, new ValidationContext(snack, null, null), true);
Assert.IsTrue(true, "Test passed for valid ice cream!");
}