Date: 20-May-2010 (I am little late for posting this article)
Background:
One very respected gentleman (who's blog we all would have visited while working on OAF.. keep guessing !!) asked a question in interview to a dear friend of mine.
How can we have two regions in a page in such a way that if you commit data in one region it shouldn't commit the data in other regions of the page?
In other words the requirement is to have two transactions in one OAF page.
First Reaction:
Shock!!
Root Application Module provides transaction context.
We can have only one Root Application Module in a page, then how can we have two transactions?
Why we need it?
I don't think we need it at all.
We can handle scenarios like this using combinations of Read-Only and Updatable VOs.
My strict recommendation is you try this only at home and never at work. You'll not be always available for your code's maintenance.
An observation that led to answer:
Application Behavior:
After some brainstorming, I remembered an observation while navigating between pages with retainAM=Y and with different Root AM, state of the page is getting retained.
Learning:
Somewhere system was retaining both Root AMs.
Two Root AMs means two transactions.
Test Case Tried:
On a relatively free day at work. I discussed this testcase with my colleague, one of the better technical resources I have ever worked with.
Tried passing AM object of one page to next page using Request and Session scope. Tried out things with both AMs in second page.
It worked like magic.
Snippet:
------------
------------
Page 1: Empty Page
Controller 1:
pageContext.putSessionValueDirect("xxfirstAM", pageContext.getApplicationModule(webBean));
//You can try passing it in Request also.
//We'll get this value in second CO and update data in VO's in this AM, call APIs by getting OADBTransaction
pageContext.forwardImmediately(<url of second page>);
Page 2: Transaction Page
Controller 2:
OAApplicationModule secondPageAM = pageContext.getRootApplicationModule();
OAApplicationModule firstPageAM = (OAApplicationModule)pageContext.getSessionValueDirect("xxfirstAM");
// This way we'll be having two AMs in our Controller.
// Both these AMs will have their own transactions.
// Changes commited from one of them will not commit changes in other.
very very nice article...its a shame tht google does nt list ur posts in search ...nt sure why because of which people like us are missing critical information
ReplyDeleteThanks for your generous and motivating comments.
ReplyDelete-Prince
That's fantastic and very useful. On a different note I wanted to check with you if its possible to embed a seeded page in a custom page? The requirement is to use couple of relevant seeded pages and tie them up together in custom pages using Basic/Interactive train. Is this possible at all?
ReplyDeleteThanks,
Praveen
if its possible to embed a seeded page in a custom page?
Delete-Yes
Never tried your requirements, it can be tried with URL Include.
* URL value should be set dynamically using a profile value for Server URL.
You try it and we can do some web conference and discuss it.
-Prince
princekapoor82@gmail.com
I also agreay this was a very fantastic and useful article.
ReplyDeleteAnd as an added advantage, after I read this I could use the same logic of putting AM as session value to restrict reloading base page when navigating back from an attachment page.
Hi Kapoor,, I have attached two diffrent AMs to two different Header Regions in a page.. When I commit with one AM, other AM trxs also getting committe. Please help me!!
ReplyDeleteThanks in advance!!
Dear Vamsi,
ReplyDeleteThere is only one transaction for a page by default, that transaction is attached to root application module.
By having multiple application module, you don't get multiple transactions. All Application modules applied to regions within a page share single transaction provided by Root application module (AM Definition set at the Page Layout Region).
Regards,
Prince
SO it means , with in the page its not possible to handle multiple transactions.
DeleteThere is another way to achieve similar behavior, more clean approach perhaps.
ReplyDeleteFollowing is the brief outline of the solution:
1) Instead of one VO have two VOs, one EO based for commiting the transaction, another one read-only VO.
2) Let user modify the read-only VO, manipulate the Updatable EO-based VO in backend and commit.
With second step depending on which region's data you wish to commit, you can control the data that goes into the Updatable VO from read-only VO.
Yet another approach for finer control is to have all read-only VOs and use PLSQL to manipulate the data.
ReplyDeletePass entire region data as a PLSQL record and manipulate there.
This comment has been removed by a blog administrator.
ReplyDelete