1

After reviewing several articles and SO questions, I still cannot understand why my validation attributes are not triggering.

For simplicity, I have reduced my model and added the string testing to debug.

using System;
using System.ComponentModel.DataAnnotations;

namespace PublicApi
{
  public class CostStandardRequest
  {
    [DateLessThan("EndDate", ErrorMessage = "StartDate must be less than EndDate")]
    public DateTime StartDate { get; set; }
    public DateTime EndDate { get; set; }

    [Required]
    public string testing { get; set; }
  }
}

In my controller, I test my method by passing a null value to the testing attribute in my CostStandardRequest class. However, ModelState.IsValid returns true despite null values.:

[HttpPost]
public async Task<ActionResult<string>> PostCostingStandard(CostStandardRequest request)
{
  if (ModelState.IsValid)
  {
    // always valid
  }
  else
  {
    // never runs
  }
}

I've reached this point by following the guide in the documentation

Note: ModelState.IsValid is true even when my custom validation attribute [DateLessThan] should be returning a ValidationResult(ErrorMessage). I have not included this code, but I can if it's deemed relevant.

Ben
  • 757
  • 1
  • 7
  • 15
  • It's unclear to me. Are you testing the running code (ie. running it but with a test value you expect to fail)? **Or** are you executing a Unit Test and have created an instance of this controller and passed in a null value to the method? – Igor Nov 05 '18 at 19:50
  • How did you implemented **DateLessThan**? That is a custom attribute. Can you post the code for that class? Did read this page https://msdn.microsoft.com/en-us/library/cc668224.aspx? – Alfredo A. Nov 05 '18 at 19:54
  • This seems like a very similiar approach to your custom **DateLessThan** custom attribute. https://stackoverflow.com/a/18912068/3973463 Verify your implementation is similar to that one. – Alfredo A. Nov 05 '18 at 19:56
  • @AlfredoA. I am using the definition laid out by [this answer](https://stackoverflow.com/a/41901736/4249881) – Ben Nov 05 '18 at 19:58
  • @Igor that right! I'm using a unit test and creating a new instance of my controller, then passing in a request object where `string testing = null` – Ben Nov 05 '18 at 20:00
  • 2
    @BenGraham - Then this is expected because the model validates as a part of the pipeline which you are bypassing in the unit test. This is a good thing because of SoC (separation of concerns) so you are not required to test your model inside the controller (the 2 can be isolated). – Igor Nov 05 '18 at 20:01
  • @Igor ahh that makes sense. I just tested this with the running instance and it works as expected. If you respond with a writeup, I'll accept your answer for other users to find. – Ben Nov 05 '18 at 20:04
  • 1
    You are mixing two concepts here. The controller is not responsible for the validation. The pipeline is, this answer will explain it in much more detail https://stackoverflow.com/a/22563585/3973463 – Alfredo A. Nov 05 '18 at 20:06
  • 1
    @BenGraham - Good deal. I found some existing questions (you are/were not the only one with this question) and marked yours as a duplicate of those. They have much better write ups than I could think of at the moment so it is more helpful that way (IMO). – Igor Nov 05 '18 at 20:08

0 Answers0