ModelBase Property Validation

Topics: Feature requests
Nov 21, 2012 at 1:01 AM

Hi Geert,

my application is preloading a huge hierarchy of ModelBase objects. Currently i'm playing with suspending the validations/change notifications while loading to achieve more speed...

When i suspend the validations they are still executed in the following function:

// Catel.Data.ModelBase
internal void SetValue(string name, object value, bool notifyOnChange, bool validateAttributes)
{
	if (string.CompareOrdinal(name, ModelBase.IsReadOnlyProperty.Name) != 0 && this.IsReadOnly)
	{
		ModelBase.Log.Warning("Cannot set property '{0}', object is currently read-only", new object[]
		{
			name
		});
		return;
	}
	PropertyData property = this.GetPropertyData(name);
	if (value == null && !TypeHelper.IsTypeNullable(property.Type))
	{
		throw new PropertyNotNullableException(name, base.GetType());
	}
	if (value != null && !property.Type.IsInstanceOfTypeEx(value) && !value.GetType().IsCOMObjectEx())
	{
		throw new InvalidPropertyValueException(name, property.Type, value.GetType());
	}
	lock (this._propertyValuesLock)
	{
		object oldValue = this.GetValue(name);
		bool areOldAndNewValuesEqual = ObjectHelper.AreEqual(oldValue, value);
		if (notifyOnChange && (this.AlwaysInvokeNotifyChanged || !areOldAndNewValuesEqual))
		{
			AdvancedPropertyChangingEventArgs propertyChangingEventArgs = new AdvancedPropertyChangingEventArgs(name);
			this.RaisePropertyChanging(this, propertyChangingEventArgs);
			if (propertyChangingEventArgs.Cancel)
			{
				ModelBase.Log.Debug("Change of property '{0}.{1}' is canceled in PropertyChanging event", new object[]
				{
					base.GetType().FullName,
					name
				});
				return;
			}
		}
                                // ------------------ CHANGE ---------------
		//if (validateAttributes)
                                if (validateAttributes && !SuspendValidation)
		{
			this.ValidatePropertyUsingAnnotations(name, value);
		}
		if (!areOldAndNewValuesEqual)
		{
			this._propertyValues[name] = value;
			this.HandleObjectEventsSubscription(oldValue, value);
			this.IsValidated = false;
		}
		if (notifyOnChange && (this.AlwaysInvokeNotifyChanged || !areOldAndNewValuesEqual))
		{
			base.RaisePropertyChanged(name, oldValue, value);
		}
	}
}

 

Could you please add the marked modification?

Thanks a lot!

Nov 26, 2012 at 9:48 AM

Besides it would be really helpful if you could add a GlobalSuspendValidation variable to ModelBase to enable/disable validation for all ModelBase objects....

Many thanks!

Nov 26, 2012 at 9:48 AM

Will look into it asap, but busy ATM.

Nov 26, 2012 at 9:50 AM

The fix you sent is not sufficient. What if you set a value, but later on you enable validation? Then the attribute validation must be enabled delayed thus we also have to keep track of not-yet-validated attribute properties.

I will implement it later this week if I have more time.

Nov 26, 2012 at 2:33 PM

Hi Geert,

many thanks for looking into it.

Just one more question: Are validations triggered on deserialization?

Thanks!

Nov 26, 2012 at 9:42 PM

The global property is implemented. The other feature (disabling attribute validation) will have to wait.

Nov 27, 2012 at 10:20 AM

Thanks a lot. I think this will bring a lot of boost :)

Dec 7, 2012 at 10:31 PM

Priority increasement, will be implemented asap.

Dec 8, 2012 at 12:06 AM

Done.