Reputation: 20831
I have a simple login page with the view model below. It used to work just fine, but seemingly suddenly, ModelState
will contain an error for the ReturnUrl
field if it wasn't supplied to the action. It states, "The ReturnUrl field is required."
public class LoginViewModel
{
[Required(ErrorMessage = TextValidation.RequiredErrorMessage)]
[Display(Name = "User")]
public string Username { get; set; }
[Required(ErrorMessage = TextValidation.RequiredErrorMessage)]
[DataType(DataType.Password)]
[Display(Name = "Password")]
public string Password { get; set; }
public string ReturnUrl { get; set; }
}
Why would it do that for a string
field (i.e. nullable) that does not have a [Required]
annotation?
Here's the beginning of the controller action that makes use of that model.
[HttpPost]
[AllowAnonymous]
public async Task<IActionResult> Login(LoginViewModel model)
{
if (!ModelState.IsValid)
{
return View(); // <-- It returns here.
}
...
}
If I debug, I see the following:
ModelState.Results[2].Key = "ReturnUrl"
ModelState.Results[2].Value.AttemptedValue = null
ModelState.Results[2].Value.Errors[0].ErrorMessage = "The ReturnUrl field is required."
One more detail I can add is that I have the same model and action in another project, and in that project, it works fine. If I debug the Login action in that project, I see that ModelState.Results
only contains 2 elements: "Username" and "Password". The third element ("ReturnUrl") is not there, which is what I would expect since it shouldn't be getting validated.
Upvotes: 2
Views: 1145
Reputation: 1730
In latest versions of .NET, you have to declare string as nullable (string?) or change project build properties to accept strings as nullable.
Upvotes: 1
Reputation: 20831
Apparently, reference types had been set to non-nullable for the project. I don't know how it happened, but in <Project>.csproj
, there was this entry:
<Nullable>annotations</Nullable>
Here's more info on the 4 options for that field:
https://learn.microsoft.com/en-us/dotnet/csharp/nullable-references
If you delete the entry, you get the default: disable
. And note that these nullability contexts can also be controlled at the file or line level via #nullable <context>
. The above link covers that as well.
If I had to guess, I'd say I must have misclicked while viewing Visual Studio's graphical interface for the project's properties:
Upvotes: 3