Saturday, September 24, 2016

The good news for those who still missed using Oracle Apex with mod_owa https://oss.oracle.com/projects/mod_owa/dist/documentation/modowa.htm is that it works with Apex 5.

Since Oracle Apex 5.0 was released, people who tried to use this one had troubles with static resources support:



This means that any static application or workspace resource can not be received by browser.

The point is that application and workspace static files now have friendly urls that allows browser caching. The form of url is "apex_location/r/workspace/static/version/file_name". This is why two new parameters was added in dads.conf for mod_plsql https://docs.oracle.com/cd/E59726_01/install.50/e39144/http_server.htm#HTMIG29263:

 PlsqlPathAlias r
 PlsqlPathAliasProcedure wwv_flow.resolve_friendly_url


where "r" is a prefix for static resources and wwv_flow.resolve_friendly_url is a procedure that translates  a friendly URL of APEX resource to corresponding API calls.

Although mod_owa doesn't implement such functionality, it is possible to use combination of OwaDocPath and OwaDocProc parameters (see last paragraph of https://oss.oracle.com/projects/mod_owa/dist/documentation/modowa.htm#_future).

The difference between mod_plsql PlsqlPathAliasProcedure parameter and mod_owa OwaDocProc parameter is that procedure from PlsqlPathAliasProcedure receives p_path argument containing resource url, but, unfortunately, mod_owa calls OwaDocProc procedure without any arguments.

The solution is to create own wrapper procedure that provides proper wwv_flow.resolve_friendly_url call.

Step 1. Creating wrapper procedure. I recommend create it in any user schema different from APEX or other system schemes:

create or replace procedure get_static_resource  is
  /*
  Simple wraps wwv_flow.resolve_friendly_url for using mod_owa with Apex 5
  */  
  l_location                varchar2(30)  := '/apex'; -- equals to apache "Location" parameter,
                                                      -- change it according mod_owa location
  l_static_resources_prefix varchar2(30)  :=  'r';    -- equals to OwaDocPath parameter,
                                                      -- do not change
  l_url varchar2(200);
 begin
  l_url := substr(
    sys.owa_util.get_cgi_env('REQUEST_URI'),
    length(l_location||'/'||l_static_resources_prefix) + 1
    );
  wwv_flow.resolve_friendly_url(l_url);
 end;

create public synonym get_static_resource for YOUR_SCHEME.get_static_resource;
grant execute on YOUR_SCHEME.get_static_resource to APEX_PUBLIC_USER;


Note: mod_owa documentation tells us that OwaDocProc procedure call have six parameters, but in practice I did not see any parameters.

Step 2. Edit mod_owa configuration file to add OwaDocPath and OwaDocProc parameters:

AddType text/xml xbl
AddType text/x-component htc
<Location /apex>
    Options  None
    SetHandler       owa_handler
    OwaUserid        APEX_PUBLIC_USER/**********
    OwaNLS   RUSSIAN_RUSSIA.AL32UTF8
    OwaDiag  COMMAND ARGS TIMING ERROR
    OwaLog   /var/log/apache2/mod_owa.log
    OwaPool  20

    # Add this two parameters for Apex 5 static support
    OwaDocPath      r
    OwaDocProc      get_static_resource

    OwaDocTable     WWV_FLOW_FILE_OBJECTS$ BLOB_CONTENT
    OwaUploadMax 10M
    OwaCharset "UTF-8"
    OwaCharsize 4
    order    deny,allow
    allow    from all
</Location>


Step 3. Restart Apache. That's all.