rgonek / Ilaro.Admin

Generic admin panel for ASP.NET MVC.
http://admin.ilaro.net/
MIT License
131 stars 36 forks source link

Bug: Can't Save an entity with empty DateTime field #36

Open arsinclair opened 4 years ago

arsinclair commented 4 years ago

Description

So this is easily reproduced at the demo site. The problem is that if Save button clicked for existing entity, and this entity has an empty DateTime field, the entity will not be saved, the DateTime field will be automatically set to 1/1/0001 12:00 AM and the following error will be displayed:

SqlDateTime overflow. Must be between 1/1/1753 12:00:00 AM and 12/31/9999 11:59:59 PM.

Reproduction Steps

To reproduce this, go to the following record http://admin.ilaro.net/Admin/Order/Edit/10249 and clear out Shipped Date field, then try to save the entity. The error will be displayed.

Screenshot of the error

Analysis

This error arises in the Ilaro.Admin.Core.EntityRecordCreator class in GetPropertyValue method at the line 40:

33. private static PropertyValue GetPropertyValue(
34.     Property property,
35.     IValueProvider valueProvider,
36.     Func<Property, object> defaultValueResolver = null)
37. {
38.     var propertyValue = new PropertyValue(property);
39. 
40.     var value = valueProvider.GetValue(property.Name);
41.     if (value != null)
42.     {
43.         if (property.IsForeignKey && property.TypeInfo.IsCollection)
44.         {
45.             propertyValue.Values = value.AttemptedValue
46.                 .Split(',').OfType<object>().ToList();
47.         }
48.         else if (property.TypeInfo.DataType == DataType.DateTime)
49.         {
50.             propertyValue.Raw = ParseDateTime(property, (string)value.ConvertTo(typeof(string)));
51.         }
52.         else
53.         {
54.             propertyValue.Raw = value.ConvertTo(
55.                 property.TypeInfo.OriginalType,
56.                 CultureInfo.CurrentCulture);
57.         }
58.     }

Peek: var value = valueProvider.GetValue(property.Name);

Here valueProvider is of type System.Web.Mvc.FormCollection, and GetValue instead of null value (the date is null in the FormCollection itself), returns an empty string. And later on, DateTime.TryParse instead of working with null, is parsing an empty string.