Hello
I am facing a stack overflow exception when ever i override
public
override bool IsValid{
get { return base.IsValid && this.IsValid; }}
this piece of code in my business object. System keep on calling this code and finally throw exception.
I have tried this with CSLA 3.0.3.0 & CSLA 3.0.4.0 version and the problem still exists. Please help stuck badly.
Regards
Zafar Ullah
What are you trying to accomplish? You're getting recursion because IsValid is essentially calling itself (when you say this.IsValid). Hence your never ending loop.
If you just have a root object with no children, you shouldn't normally override IsValid unless you have other circumstances. The base class behavior is sufficient.
I agree that this.IsValid is the source of the Stack overflow.
I sometimes override IsValid to call specific cases of CheckRules and once the rules have been run then I call into base.IsValid to see if any rules are broken.
In 3.5 the framework should take care of IsValid for the root BO and all of its children. So there is even less of a reason to override it than in previous versions.
Joe
Thanks joe for a quick reply
You have mention that 3.5 framework will take care of IsValid for the root BO and its childrens. Can you or any body tell how to handle this in 3.0.4.0 version of CSLA. I cant use 3.5 because my web application is not using any feature of 3.5 framework so no need to have that.
Basically i am checking it because of custom rules implementation.
Or what u say if i check that manually by making changes in given below method which i call in Add Custom rules method.
ValidationRules.AddRule<
AMEmp>(UniqueName, "Name");private
static bool UniqueName(AMEmp target, Csla.Validation.RuleArgs e){
int result = AMNameList.GetList().Key(target._name+target.number);
if(result != 0)
{
e.Description = "Name must be unique";
return false;
}
else
{
return true;}
}
Thanks
In earlier versions of CSLA you have to override IsValid to call down into any contained child objects. Same for IsDirty.
I wrote code to do this call recursively in my own framework. Rocky has now implemented the same concept in 3.5 so developers no longer have to do this. Other posts (from me and others) have some sample code for how to do this. You can look for thme if you really want to know how to do it.
Also, I am not sure why you are having an issue with the rule. It is attached to a real property and that property changes so the rule should run during the property set in that case. No need to override IsValid just to call that rule.
What I am talking about is the case where a rule needs to be run *after* all properties have been set. Then you can override IsValid, run the extra rule and then call MyBase.IsValid.
An example is the case where you have 5 checkboxes on a form and 1 of them *must* be checked. Rather than write the rule and have it run 5 times - you write it once and call it after all properties are set.
Joe
Joe you are absolutly write that the rule should run during the property set and thats how it does and return false to the caller. Now when the run time environment reach Save() and if i check the IsValid property of the current object then its * true * where as it should be * false* because the rule returns false.
Now during debugging i check base object and its IsValid property is false.
So as the Broken rule collection is beign accesed from the base class that is why i am checking this.
I have 2 options now
1. To check the uniqueness of the columns manually (i.e by calling UniqueName method mentioned in earlier post) just before save and comment out overriden IsValid property.
2. Or what if before save i just check the broken rule collection and throw ValidationException if collectioncount > 0 .
Which option is better. also will you please give a link of other post you are talking about.
Thanks
Thanks Andy,
but if you see my first post thats exectly as u have written and actully its the issue.
I go for the second option i.e i check broken rules collection just before saving my BO and if its count is greater then 0 i just throw exception. here i go...
if
(obj.BrokenRulesCollection.Count > 0) throw new Csla.Validation.ValidationException();obj = obj.Save();
rowsAffected = 1;
}
catch (Csla.Validation.ValidationException ex){
System.Text.
StringBuilder message = new System.Text.StringBuilder(); //message.AppendFormat("{0}.\\n\\n", ex.Message); if (objWell.BrokenRulesCollection.Count == 1)message.AppendFormat(
"* {0}: {1}.",objWell.BrokenRulesCollection[0].Property,
objWell.BrokenRulesCollection[0].Description);
else foreach (Csla.Validation.BrokenRule rule in objWell.BrokenRulesCollection)message.AppendFormat(
"* {0}: {1}.\\n ", rule.Property, rule.Description); WebMsgBox.Show(message.ToString());rowsAffected = 0;
}
catch (Csla.DataPortalException ex){
WebMsgBox.Show(ex.BusinessException.Message);rowsAffected = 0;
}
catch (Exception ex){
WebMsgBox.Show(ex.Message);rowsAffected = 0;
}
Copyright (c) Marimer LLC