Sync or Async? Dynamic Actions in Application Express 5.1.
Since December 16th, 2016, Application Express 5.1 is available on the public evaluation instance apex.oracle.com. So the testing and playing with the new features can begin; and of course, we will see how to articles about the new features in the future.
For years, Application Express users asked for "editible interactive reports". With 5.1, it's here: we have Interactive Grid.
JET Chart integration brings a variety of new chart types to Application Express - all declarative and usable without coding.
Universal Theme has been extended and improved; the new icon library Font APEX is worth a closer look.
Beyond these, there are a number of minor features and improvements. And as always. What's a minor feature for one, is a game changer for another person - so have a look into the Application Express 5.1 documentation - get an overview on the new features and try them out.
Packaged Applications have also been improved and extended with Application Express 5.1. Now there are 40 packaged applications, divided into Sample Apps, which demonstrate how to use Application Express features, and Productivity Apps, which serve a "real" business use case. New features in 5.1 like the interactive Grid or JET Chart integration are represented in the Sample Interactive Grids or the Sample Charts application. The Universal Theme Sample Application can even be accessed live. Other sample applications have been refreshed as well - for instance, the Sample Calendar Application shows a number of new possibilities with the Calendar Component.
This article will not focus on new functionality, but one of the behavior changes in Application Express 5.1, which is important for new as well as for existing applications: the move to asynchronous dynamic actions. We will show the differences between synchronous and asynchronous dynamic actions, what changed in Application 5.1 and what the developer should do.
In Application Express 5.0, only dynamic actions with their Wait for Result attribute set to No would execute in asynchronous mode, otherwise execution is synchronous. Starting with Application Express 5.1, dynamic actions will generally be executed in asynchronous mode. That means, that a dynamic action, which executes an AJAX request to the server, does not block the browser any more. Subsequent dynamic actions can start immediately - while the AJAX request is running. A dynamic action does an AJAX request, when it executes SQL queries or PL/SQL code in the database. With this change, Application Express follows best practice in web application development - asynchronous AJAX requests lead to much better user experience, since the page remains responsive when AJAX requests are running.
Let's have a closer look on this: To play with synchronous versus asynchronous dynamic actions, create a simple Application Express page with a region and two page items: P1_HIDDENVALUE and P1_TEXTVALUE. The first one is, as the name indicates, a hidden element, whereas the second is a plain text field. Add a button to your region, name it Execute Dynamic Actions and add two dynamic actions which execute "on Click" of that button.
The first dynamic action does a Set Value of type SQL Statement. Use select sysdate from dual as the SQL Statement. P1_HIDDENVALUE is the Affected Element. Make sure to set Wait For Result to Yes and Fire on Initialization to No.
Before running this page, navigate to Shared Components, and then to Application Definition Attributes. Set your applications' Compatibility Mode to 5.0 - then run your page and click the Execute Dynamic Action button.
Upon button click, the first dynamic action will be executed. It performs the AJAX request to the server, there the SQL query is executed and the result is passed back. In APEX 5.0, dynamic actions were executed synchronously. So with the compatibility mode set to 5.0, the same happens in 5.1: the second dynamic action fires after the first is completed and the result can be copied to P1_TEXTITEM without problems. So far, so good.
Now change the Compatibility Mode in Shared Components to 5.1 and re-run the page.
With the compatibility mode set to 5.1, dynamic actions will run in asynchronous mode. So, the second dynamic actions starts immediately, while the first is still running. It copies the value from P1_HIDDENVALUE to P1_TEXTVALUE, but the result from the SQL query has not been returned yet. So, the P1_TEXTFIELD item remains blank.
But wait - what about the Wait for Result = Yes setting, some people might ask; we explicitly set that attribute to yes, and that should mean that other dynamic actions have to wait until this one is finished, right?
True is, that this attribute is only valid for multiple TRUE or FALSE actions within one and the same dynamic action definition. TRUE or FALSE actions in one dynamic action will not wait for actions in another dynamic action definition. So, in this very page, this attribute has no effect. One solution for this would be to consolidate the two dynamic actions into only one - but with two TRUE actions. Then, the Wait for Result setting will be honored.
The first step is to make sure that the Compatibility Mode remains at 5.0, which makes sure that dynamic actions behave as before. But this is only a temporary solution, at the end we want to increase compatibility mode to 5.1 to make use of all new features. We also want to have the asynchronous behaviour because of the better end user experience. So we want to review the dynamic actions.
If you have multiple dynamic actions on the same event (same button click), with the same conditions in place, these should be consolidated into only one dynamic action. Within that dynamic action, Wait For Result can be set to Yes. The positive side-effect of this is a cleanup of your Application Express page.
If that is not possible (because different dynamic action definitions might have different conditions), you might change the event, on which the following dynamic actions are fired. In our example, we could fire the second dynamic action on Change of P1_HIDDENVALUE instead of on button click. Then the second dynamic action will fire as intended, when the AJAX request from the first dynamic action returns, setting the P1_HIDDENVALUE item. We have a clean asychronous dynamic action flow - as it should be.
Asynchronous flow of dynamic actions: "P1_TEXTVALUE" is set "on change" of "P1_HIDDENVALUE"
Take special care on dynamic actions which do an AJAX request Before Page Submit. With the new behavior, the page submits before the AJAX request returns. For these kinds of dynamic actions, review whether a dynamic action really is the best solution. When you are about setting item values, a server-side Computation might be the better choice.
If your dynamic actions don't do AJAX request like Show or Hide, there is nothing to do.
With changing the dynamic action behavior from synchronous to asychronous behavior, Application Express follows general best practices for web development; asynchonous execution has a lot of advantages, which now can be leveraged for APEX applications as well.
More information on new features or changes with the latest Application Express release can be found in the Application Express 5.1 documentation or the Release Notes.