Friday 5 June 2015

Page processing after wpg_docload download_file call

Problems with page refresh when using wpg_docload download_file function

 

APEX 4.2.6 workaround with APEX_UTIL.SET_PREFERENCE


Situation a standard form with report parameters

   
where user have an ability once reports are run result is either saved on shared Network Drive or it is saved temporarily in the custom file table and presented to them on the screen for individual download in a separate page region. See image below. 

Idea was to be able to run report for an account manager that can have multiple Clients and for each of these clients man can have multiple contracts. Sort of Select All Clients and All Contracts for an account manager version of report with download option.

With only one exception that if you select only one client and only one specific contract users would  get document downloaded in a browser in a window familiar to all of us.

All good so basic idea is there and all was working fine except for this one case when individual contract is selected. Let me try to explain why.
When a Run button (that submits the page) would be processed above region would be normally refreshed and users would get the latest report results. But problem with download function for individual contract was in this code:
owa_util.mime_header( 'application/rtf', FALSE );
htp.p('Content-length: ' || t_len);
htp.p('Content-Disposition: attachment; filename="' || p_filename || '"');
owa_util.http_header_close;
wpg_docload.download_file(t_BLOB);
apex_application.g_unrecoverable_error := true;
where apex_application.g_unrecoverable_error would prevent APEX to refresh the page as it is basically stopping APEX engine and users would be left with older version of report in their download region while they would still get to download the latest results. 

To avoid this problem I decided not to use g_unrecoverable_error and to use APEX SET_PREFERENCE with JQuery. More about USER PREFERENCE functionality you can find in any APEX guide and I will not go into details of it. Basically it can be used for temporarily setting values for current user session and is ideal as a global variable for all non standard values within your applications.

How to do this? 

Piece of code above was replaced with this:
owa_util.redirect_url('f?p=:APP_ID:2:APP_SESSION::::'
  || 'P2_REFRESH:REFRESH');
APEX_UTIL.SET_PREFERENCE(
 p_preference => 'download_refresh',
 p_value      => 'YES');
Create a page item in my case it is called P2_REFRESH and Before header process sets the value of your USER preference. 
DECLARE
 l_history_days    VARCHAR2(255);
begin
 IF nvl(:P2_REFRESH, 'cc') != 'YES' THEN
 :P2_REFRESH := 'YES';
 END If;
END;
with its condition set to 
DECLARE
 l_history_days    VARCHAR2(255);
BEGIN
 l_history_days := APEX_UTIL.GET_PREFERENCE(p_preference => 'download_refresh');
IF nvl(:P2_REFRESH, 'cc') != 'NOTSET' and l_history_days = 'YES' THEN
  return true;
END if;
  return false;
END;
Then create a Dynamic action with these settings:
 

Where JavaScript code is

and PL/SQL part of Dynamic action is:
 

Key thing being that JavaScript where after page is submitted and ready for download we trigger a click on Download link using a JQuery. Similar as if user clicked them self.

Maybe not the cleanest option but hopefully it works for you as well and maybe it will save somebodies time.

Thanks,
SLino


No comments:

Post a Comment