cancel
Showing results for 
Search instead for 
Did you mean: 

Stale Data When Viewing Reports

Former Member
0 Kudos

Hi there,

I'm using Crystal Reports 2005 in Visual Studio .NET 2005, and have a Windows Forms application that displays a Crystal Report using the Report Viewer control, and pulling data from an access database.

I'm running into an issue where the report I'm trying to display seems to be displaying stale data. My application is saving the information correctly to the database, but occasionally when the report is displayed in the report viewer control, it contains the data from prior to the updates being saved to the database. If I click the 'Refresh' button on the report viewer control, the updated data appears.

I've tried several different options -- calling Refresh() on the report object after instantiating it, calling 'RefreshReport()' on the Report Viewer control, making sure the report had the 'Save Data with report' option disabled, calling 'VerifyDatabase()', etc. All to no avail.

Anyone run into this issue before? Is there a setting that I'm just missing somewhere?

Thanks in advance.

Accepted Solutions (1)

Accepted Solutions (1)

former_member183750
Active Contributor
0 Kudos

From your description, I believe your app is updating the Access database, then immediately calling Crystal reports.

Sounds like the data being written to the database is not committed at the point your app is calling CR to retrieve the data. A quick test to see if this is the case, would be to place a, say 2 second delay just before you try to view the report. If this helps, there are Access APIs that you can use to ensure the data is committed before calling Crystal reports.

Ludek

0 Kudos

You need to call 'DiscardSavedData' to force the refresh in code.

Former Member
0 Kudos

Hi Ludek,

I had the same suspicion. However, imposing an artificial delay didn't help at all. Also, just to sanity check things I also tried re-querying the access database from within my application just before loading the report, and the query results do indeed contain the correct data. However, when the report comes up it still sometimes displays the stale data.

Thanks,

Craig

Former Member
0 Kudos

Hi Don,

It seems that DiscardSavedData is deprecated and no longer in the Crystal Reports API (as of the VS 2005 version, at least). From what I can tell we're supposed to call 'Refresh' on the report object itself, now. I had tried that before to no avail, but tried it again just in case, and there was no effect. As always, clicking the 'Refresh' button the CrystalReportViewer control once the report comes up seems to do the trick, though.

Thanks,

Craig

former_member183750
Active Contributor
0 Kudos

Looks like the .NET API does not have DiscardSavedData. I would still like you to see if you can implement a simple delay between the data write and processing of the report. I have seen this to be the issue a number of times and there is only one way to see if that is the case here.

Ludek

Former Member
0 Kudos

Hi Ludek,

Thanks. I did already try that, however. I tried delays anywhere from 2 to 5 seconds, trying both a simple Thread.Sleep, as well as a timer (a wait that doesn't block the UI thread, that is).

Also, I have a hard time believing that the data is uncommitted in the Access database, since when I issue a query to that database before the processing the report it comes back with the correct data.

Thanks,

Craig

former_member183750
Active Contributor
0 Kudos

Strange...

Let's try .VerifyDatabase, just before you send the report to the viewer. BTW., how are you connecting to the database, (ODBC, native?).

Ludek

Former Member
0 Kudos

No dice with VerifyDatabase(), either.

In the application I'm using ADO.Net's OleDb provider (through a strongly-typed DataSet). In the Report, I'm not sure how to tell which driver it's using.

former_member183750
Active Contributor
0 Kudos

Two things:

1) Can you copy and paste the code used?

2) Download the modules utility from here:

https://smpdl.sap-ag.de/~sapidp/012002523100006252802008E/modules.zip

and do the following to determine which dll is actually being loaded at runtime;

a) Extract the above file - you will get modules.exe

b) Start modules.exe

c) Run your .NET app, process a report (does not mater if you do refresh or not)

d) Leave the report on the screen

e) Go to the File menu in the modules utility, then select New List -> Memory Modules

f) Under the process find the process running the report and click on that.

g) Look for crdb_*.dll. What is the full name of this dll that is loaded by your app?

Ludek

Former Member
0 Kudos

Hi Ludek,

Looks like I'm using CRDB_DAO.DLL, version 10.2.0.930 within the report.

As far as the application code goes, it's, um, large, and less than optimal The raw ADO.NET code is buried inside a Strongly-Typed DataSet designer file. I can tell you that it uses an OleDbConnection and OleDbCommand, though. What specifically were you hoping to get out of the code? Perhaps if I know that I can try to distill it out of what's there

former_member184995
Active Contributor
0 Kudos

You are using datasets as the datasource for the report?

If so, are you disposing of the dataset after passing it to the report and recreating it and filling it with the new data?

With datasets Crystal is not involved in hitting the database at all, that is handled by you in code.

All Crystal does is take the dataset you pass it and display the data.

Jason

Former Member
0 Kudos

Sorry for the confusion. No, I'm not using the DataSet as the data source for the report. The report is hitting the Access database.

former_member183750
Active Contributor
0 Kudos

Good info Craig. Reason I was looking for the code, was to see if I could get better feel for the original description of the issue:

" My application is saving the information correctly to the database, but occasionally when the report is displayed in the report viewer control, it contains the data from prior to the updates being saved to the database. If I click the 'Refresh' button on the report viewer control, the updated data appears."

Reading over the above, I realized I needed more detail as to how the app works. Perhaps a step by step description of what the app does (almost a pseudocode type of thing) will do as well as any code.

Ludek

Former Member
0 Kudos

The basic flow is this, for the situation in which I'm seeing this issue.

This is a desktop application using an Access database as its data store, with a button that allows the user to view a Crystal Report containing all of the data that's in the screen.

When the user clicks on the button to view the report, the application does the following:

- Builds up a DataRow containing all of the data representing the current 'item' being viewed in the application

- Inserts the row into the Access database using the DataSet / TableAdapter (creates a new database connection each time)

- Creates a new instance of the Crystal Report class to be viewed

- set the database connection info in the report to the access database being used by the application

- create a new form containing a CrystalReportViewer control

- set the ReportSource of the control to the instance of the Crystal Report created above

- show the form / CrystalReportViewer control.

That what you were looking for?

former_member183750
Active Contributor
0 Kudos

Yes, perfect. Now, what happens after:

show the form / CrystalReportViewer control.

To get the new data in the report, are do you do .close and .dispose on the report object, before creating a new instance of the Crystal Report class to be viewed?

And another question. Would you consider sending the dataset to the report directly as opposed to connecting to the Access database?

crReportDocument.SetDataSource(dataSet)

Ludek

Former Member
0 Kudos

Hi Ludek,

No, I don't Close/Dispose of the report object when the preview form closes. I'll try that, thanks.

I can also try binding to the dataset directly, sure, as long as all of the field mappings would stay the same. If we have to re-map all of the fields to the report, then binding to a dataset will have to be a last resort.

Thanks,

Craig

former_member183750
Active Contributor
0 Kudos

I'm betting on the Close/Dispose to be our ticket.

Passing a dataset should also work without any mapping. Only possible issues would be related to large amounts of data - say, over a few thousand records. You' probably start to get performance hits there. But let's see what Close/Dispose does for us.

Ludek

Former Member
0 Kudos

Yep, I agree that Dispose/Close will likely fix our problem. I should've thought of that, sorry. I'll let you know whether it works. Thanks!

Former Member
0 Kudos

Yep. Making sure Dispose() was called on the report did the trick. Thanks again!

Answers (0)