Today I was debugging an issue where in a ghost row is
getting inserted into the grid in level 2 even if the user is not entering any
value for the grid in level 2. There are many instances where you find the
ghost row issue in PeopleSoft. This one was particular to the sequencing number
and which is almost a common case across the product. So I will explain a bit
about the ghost row issue with the particular case.
The page has a structure up to level 3. And my level 2
additional key is a sequence number which is auto populated by the system. Now
when the user goes in add mode and enter any data up to level 1 (assuming he is
adding only one row which is presented by default) and saves the page, then everything
seems fine. The data up to level one is inserted into the database as user has
filled only up to level 1.
Now if he tries to add another row at level one and enter
data only in level 1 or if he just clicks the + button on the level 2 of the
level 1 first row, then a ghost row of level 2 is getting inserted into the
database even though user has not entered any data into the level 2 rows.
Problem
The reason for the ghost row is the sequencing logic written
in RowInsert event. Since the additional key for level 2 is a sequence number
which is populated automatically by the system, whenever the sequencing logic
executes and assigns a value from the RowInsert event, the system automatically
sets that particular row as changed and will mark it for database insert during
the time of save.
Most of the places where auto sequencing is used, the
sequence number field is read only and user cannot delete its value thus
forcing the system to insert the row into database; making the case more
complicated.
PeopleBooks has clearly mentioned that if you change the
value of any field in the RowInit or RowInsert events, the system will mark the
row as changed and will be considered during the save processing.
But in most cases, you are forced to write the logic in
RowInsert event because it is apt to display the next sequence number whenever
user clicks the plus button.
Now back to the issue why there was no ghost row inserted my
first default row at level 1? The reason is pretty straight forward, the
RowInsert event will get fired only when the user adds a row, for default rows
that event is ignored.
Solution
This might be a well known situation so that PeopleTools has
provided the solution for the problem as well. There is a delivered property
for rowset class called ChangeOnInit. All you need to do is to set that
property to false during the component load processing or during the RowInit
processing of the higher level (in my case it is level 1). Once this property
is set to false, the component processor will no longer mark the row as changed
whenever a field value is programmatically updated in RowInit or RowInsert
events, thereby that row will not be considered for database insert until and
unless user updates any value on the field. This is a pretty handy property
which avoids programmatic defaults be inserted into the database when it is not
actually supposed to be inserted. Thus, this one line code will take away the
headache. You can see the sample code given below which will address the given
situation of ghost row.
rem This code should be written on the RowInit of the
primary record one level up;
rem In this case code is written at Level 1 to resolve ghost
row issue at level 2;
GetRow().GetRowset(Scroll.LEVEL2_REC).ChangeOnInit =
False;