At a forum I read about Master/Detail and updating Detail-DataSet at editing Master-DataSet.
Since build 5.55.1.22 the new condition has appeared.
procedure TDADetailDataLink.RecordChanged (Field: TField);
begin
if ((Field = nil) or (DataSet.Fields.IndexOf (Field)> = 0)) and FDataSet.Active and
{a new condition} not ((Field nil) and (FDataSet.State in [dsEdit, dsInsert]))
then
...
end;
But at editing Master still is updating Detail. The new condition does not work (or not properly).
It occurs because FDataSet is Detail-DataSet and FDataSet has dsBrowse state always.
It is necessary to correct FDataSet to DataSet.
procedure TDADetailDataLink. RecordChanged (Field: TField);
begin
if ((Field = nil) or (DataSet.Fields.IndexOf (Field)> = 0)) and FDataSet.Active and
{the changed condition} not ((Field nil) and ({F!!!}DataSet.State in [dsEdit, dsInsert]))
then
...
end;
Master/Detail bug
-
- Devart Team
- Posts: 925
- Joined: Thu 17 Nov 2005 10:53
Hi,
Let's assume, there are two data sets: MDataSet and DDataSet.
MDataSet is a master for DDataSet.
Let's consider process of editing MDataSet (us interests DataEvent = deRecordChange), thus at change of field MField (a foreign key in DDataSet) there should not be updating DDataSet, i.e. a condition
((Field nil) and (FDataSet.State in [dsEdit, dsInsert])) should accept value True.
As soon as process gets in procedure DADetailDataLink.RecordChanged(Field: TField) we have the following:
-- DataSet is a pointer on MDataSet.
-- FDataSet is a pointer on DDataSet.
-- Field is a pointer on MField.
Therefore:
Field nil = True
FDataSet.State in [dsEdit, dsInsert] = False always since DDataSet.State does not vary
DataSet.State is not taken into account.
Thus the condition ((Field nil) and (FDataSet.State in [dsEdit, dsInsert])) is equivalent ((Field nil) and False) i.e. the condition (FDataSet.State in [dsEdit, dsInsert]) does not work.
If the condition to change ((Field nil) and ({F!!!}DataSet.State in [dsEdit, dsInsert])) so
Field nil = True
DataSet.State in [dsEdit, dsInsert] = True
FDataSet.State is not taken into account since DDataSet does not vary.
And as whole the condition accepts value True. This is valid for an insert process into MDataSet.
Here now actually, MDataSet.State influences process of parameters updating in DDataSet.
Let's assume, there are two data sets: MDataSet and DDataSet.
MDataSet is a master for DDataSet.
Let's consider process of editing MDataSet (us interests DataEvent = deRecordChange), thus at change of field MField (a foreign key in DDataSet) there should not be updating DDataSet, i.e. a condition
((Field nil) and (FDataSet.State in [dsEdit, dsInsert])) should accept value True.
As soon as process gets in procedure DADetailDataLink.RecordChanged(Field: TField) we have the following:
-- DataSet is a pointer on MDataSet.
-- FDataSet is a pointer on DDataSet.
-- Field is a pointer on MField.
Therefore:
Field nil = True
FDataSet.State in [dsEdit, dsInsert] = False always since DDataSet.State does not vary
DataSet.State is not taken into account.
Thus the condition ((Field nil) and (FDataSet.State in [dsEdit, dsInsert])) is equivalent ((Field nil) and False) i.e. the condition (FDataSet.State in [dsEdit, dsInsert]) does not work.
If the condition to change ((Field nil) and ({F!!!}DataSet.State in [dsEdit, dsInsert])) so
Field nil = True
DataSet.State in [dsEdit, dsInsert] = True
FDataSet.State is not taken into account since DDataSet does not vary.
And as whole the condition accepts value True. This is valid for an insert process into MDataSet.
Here now actually, MDataSet.State influences process of parameters updating in DDataSet.
-
- Devart Team
- Posts: 925
- Joined: Thu 17 Nov 2005 10:53
cis-wurzen wrote:
So, correct behavior is only refreshing detail-dataset at change of any amount of master-dataset fields which corresponds to detail-dataset parameters.
You wrote:
Alex wrote:
You wrote:
Besides you can simply add My condition
not (DataSet.State in [dsEdit, dsInsert])
to Yours conditions.
Eventually, Practice is Criterion of True.
If you have desire to understand with this problem I can send an example with demonstration of the given bug.
http://crlab.com/forums/viewtopic.php?t=18992 Tables are linked over Master-Detail-Relationship. The Relationship is set with MasterFields, Detailfields and MasterSource.
Everytime i change a Field (any Field) in the master-dataset the detail-dataset is refreshed. If i change 5 fields 5 times a refresh is called.
So, correct behavior is only refreshing detail-dataset at change of any amount of master-dataset fields which corresponds to detail-dataset parameters.
You wrote:
Here you are right, but change of master fields occurs after Posting, but not right after Editing of a separate field.correct behavior is to refresh detail dataset when master fields are being updated.
Alex wrote:
Maybe in case of cis-wurzen the problem is fixed, but generally the problem is not fixed.We reproduced your problem and fixed it. This fix will be included in the next ODAC build.
You wrote:
My condition does not contradict the given purpose and both conditions (mine and yours) are equivalent.This condition was added to prevent refreshing of detail dataset when both master and detail datasets are in edit mode
Besides you can simply add My condition
not (DataSet.State in [dsEdit, dsInsert])
to Yours conditions.
Eventually, Practice is Criterion of True.
If you have desire to understand with this problem I can send an example with demonstration of the given bug.
-
- Devart Team
- Posts: 925
- Joined: Thu 17 Nov 2005 10:53
I have sent the test project code to [email protected]