Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Variables refer to previous record field values #386

Closed
SofieStrumane opened this issue Aug 16, 2023 · 3 comments
Closed

Variables refer to previous record field values #386

SofieStrumane opened this issue Aug 16, 2023 · 3 comments

Comments

@SofieStrumane
Copy link

We've noticed a problem with variables whose reset type is set to Report. The variables are computed using the wrong field values. The previous record values are used.

To illustrate the problem we've create a sample report 'VariableResetProblem.jrxml', added below.

This report requires a CSV Data adaptor to run. The contents of the csv file is:

"id";"name"
id1 ; a
id2 ; b
id3 ; c

The datasource hence contains two fields: "id" and "name". We've created a variable MyVar whose expression is $F{name}. It is simply a copy of the field value. When the reset type of MyVar is set to 'Report', the MyVar prints a wrong value. More precisely, the variable prints the previous record value in the group header of the report instead of the current record of the datasource. The detail band prints the correct records values.

Note that if we set the reset type of MyVar to 'none', the variable contains the correct value.
Archive.zip

@teodord
Copy link
Collaborator

teodord commented Aug 16, 2023

The reset type property of a variable makes sense only when the variable performs a calculation. What calculation do you want your variable to perform? Sum, average, min, max?... If you did not specify any value for the calculation property, then the performed calculation is "Nothing".
When a group header is rendered, the variable value is not yet "incremented". So indeed it has its previous value.

I think it would be more helpful if you just explain what you need to achieve, because the hypothetical test case you gave us does not seem to have a practical value.

@tcleenewerck
Copy link

Hello Teodord.

Sofie is a colleague and we are both working on reporting together. So I'm joining this interesting conversation. We've discussed your answer this morning.

The issue with the reset type came up when we moved a list component that is using a variable from a detail band to a header band. It seemed a simple thing to do. However we then observed that the list was printing information based on the previous record value. We realized that the 'reset' type was causing this.

We are indeed not using a calculation like sum, avg, ... . So indeed a reset type is not necessary. How come we used it anyway? The reset type was 'temporarily' set to the value Report as a work around for a bug (a couple years ago, you and your team solved a bug for us (https://community.jaspersoft.com/jasperreports-library/issues/8701)). As you now 'temporarily' have way becoming 'permanent'. So we ended up in a situation where a reset was used but is not necessary.

We've reported this situation because we didn't expect that the 'reset type' would have an effect on the record that is used to execute the variable expression. In https://jasperreports.sourceforge.net/schema.reference.htm it states that the reset type determines that the variable initial expression is being used (variable is initialized only once, at the beginning of the report).

When the reset type is set to 'none'. Then the group header uses the current record value. Which is exactly what we want. So please do not change this ;-)

In order to better understand how variables works, we are now a bit confused about your statement that the group header uses the previous value. So that only applies when a reset type is entered but no calculation function has been specified?

Thomas

@teodord
Copy link
Collaborator

teodord commented Aug 31, 2023

Hi,

Group headers are rendered in a special moment in time when although the record pointer has moved onto the new record in the data source so the $F{} references return values from the new record, the variables have not yet been incremented.

When I say "variables incremented" I am referring to the ones that have a resetType different than None.

When the group header is rendered, the variables that have the resetType=Group and match the current group would be evaluated using the initValueExpression. But in your case, the resetType=Report means they are not initialised using the initialValueExpression and simply keep whatever value they had from the last detail record.
In your example, we do see the variable initialised using its initialValueExpression, but it happens only once, for the first group header, when the value of variable is null, because your initialValueExpression is returning null.
Subsequent group headers display the value of the variable which has neither been reinitialised, because it does not have group level reset type, and has neither been incremented yet, because variable incrementation occurs after group header rendering and before detail rendering.

So to better understand how variables work we need to be aware of the fact that they are subject to two main events during iteration through the data source records: initialisation/reinitialisation (reset) and incrementation.
Notice there is also the incrementType attribute of a variable which dictates the moment the variable should be incremented. By default they are incremented with each record, but they can actually be incremented from group break to group break or from page break to page break.

I hope this makes sense and I'm pretty sure we are not going to change the way it works because it would be problematic for many people if we do.

Thank you,
Teodor

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants