Wednesday, June 16, 2010

Model driven approach for building Dynamic UI

One of the great feature of ADF Rich Client is that support for building User Interfaces on the fly. These dynamic components are smart enough to read the binding metadata and render themselves on the fly. Please read this topic 22.7 Using a Dynamic Form to Determine Data to Display at Runtime, to learn more about this feature. When we talk about the dynamism provided by the ADF Rich Client, story is incomplete without referring support from the ADF BC (business service) layer. You can create dynamic EntityObject, ViewObject and wire them to UI components declaratively, without much effort. In this post, I'm discussing some common 'dynamic UI' based use case requirements and their solutions using ADF.

Case 1: Dynamic UI Table built using dynamic ViewObject(database table and attribute definitions change for each invocation)

Use case requirement: UI needs to be populated from different database tables, based on various business conditions. Number of displayed attributes may vary based on source database table.

Solution : Solution is pretty straight forward. Let us start from the business service layer and then move towards UI layer.

Business Service Layer

You can make use of ApplicationModule::createViewObjectFromQueryStmt(java.lang.String voName, java.lang.String sqlStatement) to define dynamic ViewObjects using the query supplied by the run time.

Binding Layer

Next step is to wire this dynamic ViewObject with UI. Define the necessary binding in your page definition file. You may need to do it manually as we are creating the ViewObject dynamically.

Sample page definition is shown below.
    <variableIterator id="variables"/>
    <iterator Binds="DynamicQueryVO" DataControl="AppModuleDataControl"
    <tree IterBinding="DynamicVOIterator" id="DynamicVO">
      <nodeDefinition Name="Dummy"></nodeDefinition>

UI Layer

For building dynamic UI, either you can use <af:table> along with <af:foreach> to populate table on the fly, or simply leave the job to <dynamic:table> component. Let the component do the job for you. If you need to display the data in a dynamic parameter form, you can use <dynamic:form>

Dynamic components differ from standard components in that all the binding metadata is created at run time. This dynamic building of the bindings allows you set display information using control hints on a view object instead of configuring the information in the Edit Form Fields dialog as you drop the control onto the page

Table populated using <af:foreach> is shown below
 <af:table rows="#{bindings.DynamicVO.rangeSize}"
    emptyText="#{bindings.DynamicVO.viewable ? 'No data to display.' : 'Access Denied.'}"
    var="row" rowBandingInterval="0"
    rowSelection="single" id="t1">
    <af:forEach items="#{bindings.DynamicVOIterator.attributeDefs}"
      <af:column headerText="#{}" sortable="true"
         sortProperty="#{}" id="c1">
    <af:outputText value="#{row[]}" id="ot1"/>
Using dynamic:table to display dynamic contents is shown below.
<dynamic:table value="#{bindings.DynamicVOIterator}" id="t3"/>

Case 2: Dynamic UI Table built using ViewObject with dynamic query(Only database table changes, attribute definitions/column types may remain same)

Use case requirement: UI needs to be populated from different database tables, but attribute definition remains same. In other words, only the table changes, number of columns and types remain same.

Solution :

Business Service Layer

Here you just need to swap only the query part of the ViewObject. The attribute definitions remains same for all cases. You can use ViewObject::setQuery(java.lang.String query) to set Sets the user-defined query.

Building UI and the binding this with ViewObject remains same as for the normal implementation.

Case 3: Updatable Dynamic UI Table built using Dynamic EntityObject and ViewObject

Use case requirement: Needs to build an updatable UI based on the database table and attributes which are decided at run time.

Solution : This is a bit tricky situation. As the table is updatable, there should be an EntityObject to post the changes back to database.

Business Service Layer

Solution is to build EntityObject and corresponding ViewObject dynamically based on the metadata supplied by the run time.(Thanks to Steve who shared a sample on similar topic)

Below given sample code builds EntityObjects and corresponding ViewObject on the fly.
EntityDefImpl newEntity = new EntityDefImpl(DYNAMIC_EO);
AttributeDefImpl newAttrDef1 =
newEntity.addAttribute("EmployeeId", "EMPLOYEE_ID", Number.class,
true, false, true);
ViewDefImpl newView = new ViewDefImpl(DYNAMIC_VO);
newView.addEntityUsage("e", DYNAMIC_EO, false, false);

Binding Layer

'UI Wiring' part is same as discussed under Case 1.

UI Layer

Same as discussed under Case 1.


ADF offers a library of dynamic components which may help you to build dynamic UI without much effort. You may need to choose the right implementation strategy based on your use case requirement.

You can download the sample workspace from here.
[Runs with Oracle JDeveloper 11g R1 PS2 + HR Schema]

How to run this sample?

Run the main.jspx. Main page display menu(link) for each case that we discussed here. You can select Department/Employee from the drop down list and then opt for one of the three cases by clicking the corresponding links. This takes you to a result page where data is rendered in a tabular form. This UI is generated on the fly based on the item selected from the drop down.

Learn More ...
There are a lot more points like this. If  you are curious to learn the internals of the ADF Business Components and ADF Binding Layer,  the following book is for you - Oracle ADF Real World Developer’s Guide.
More details about this book can be found in this post-


shankar said...

Its a very nice post indeed and a real-time scenario. Thank you, but some problems in the UI part I think, as I am getting error with the sample,
ADF: Adding the following JSF error message: ORA-00942: table or view does not exist

java.sql.SQLSyntaxErrorException: ORA-00942: table or view does not exist

I just ran as written on the blog.

Jobinesh said...

You may need to have HR schema (sample schema comes along with Oracle DB) installed in your DB/ Or change the 'Connection' to reflect your local settings

shankar said...

I got it working for my app thanks a lot.
Very good example for creating dynamic view objects.

Can I link to dynamic view objects having transient attributes as primary keys ?

Jobinesh said...

Theoretically answer is Yes. Personally I've not noticed such use-cases before.

Anonymous said...

Thanks for this post. I am able to create a dynamic EO and dynamic VO based on this dynamic EO.
This works fine. But when I am testing my application for the passivation safe I am getting NullPointer error when AM is activating. Do we need to handle such VO in special way?

oracle.jbo.JboException: JBO-29000: Unexpected exception caught: java.lang.NullPointerException, msg=null
at oracle.jbo.server.Serializer.activate(
at oracle.jbo.server.DBSerializer.activateRootAM(
at oracle.jbo.server.ApplicationModuleImpl.activateState(
at oracle.jbo.server.ApplicationPoolMessageHandler.doPoolMessage(
at oracle.jbo.server.ApplicationModuleImpl.doPoolMessage(
at oracle.jbo.common.ampool.ApplicationPoolImpl.sendPoolMessage(
at oracle.jbo.common.ampool.ApplicationPoolImpl.prepareApplicationModule(
at oracle.jbo.common.ampool.ApplicationPoolImpl.doCheckout(
at oracle.jbo.common.ampool.ApplicationPoolImpl.useApplicationModule(
at oracle.jbo.common.ampool.SessionCookieImpl.useApplicationModule(
at oracle.jbo.http.HttpSessionCookieImpl.useApplicationModule(
at oracle.jbo.common.ampool.SessionCookieImpl.useApplicationModule(
at oracle.jbo.common.ampool.SessionCookieImpl.useApplicationModule(
at oracle.adf.model.bc4j.DCJboDataControl.initializeApplicationModule(
at oracle.adf.model.bc4j.DCJboDataControl.getApplicationModule(
at oracle.adf.model.binding.DCBindingContainer.findDataControl(
at oracle.jbo.uicli.binding.JUCtrlActionBinding.getDataControl(
at oracle.jbo.uicli.binding.JUCtrlActionBinding.invoke(

Is there something which I will be missing?

Jobinesh said...

There was a product bug#9271129 (fixed in internal builds) with similar symptoms. You may be able to uptake the fix with next immediate release.

Anonymous said...

Hi Jobnish,

Thanks for the bug no. but when I try to check this bug number using I am not able to view the details.

Just wanted to confirm the details of the bug.

I was just thinking (though didn't try yet) can we create a dummy eo and vo and then at the runtime define the definition of eo and vo in there definition classes will solve this problem or not. The only problem I can see is that since in my case the eo and vo has xml files it will try to load the eo and vo based on the eo.xml or vo.xml file instead of my runtime definition. Please suggest.

sunil said...

Hi Jobinesh,

I tried created case 2 in the model driven approach to building dynamic ui.

First i created a DynamicInvTable1 view object with a bind variable

"select ji.invoice_id from invoices ji where ji.invoice_number= :selectInvoiceNumber"

Then in the AM, i try to dynamically set it to a new query with the same attributes

query = "select ji.invoice_id from invoices ji ,jobs ii where ji.invoice_id = ii.invoice_id"

I follow it up in the AM

ViewObjectImpl vo = (ViewObjectImpl)findViewObject("DynamicInvTable1");



but i get the error
"ADF: Adding the following JSF error message: Attempt to set a parameter name that does not occur in the SQL: selectInvoiceNumber
java.sql.SQLException: Attempt to set a parameter name that does not occur in the SQL: selectInvoiceNumber"

Should it not "forget" the previous query ?

Any idea why this is happening ?

Jobinesh said...

You may need to try removing the bind variable before modifying the query. ViewObjectImpl::ensureVariableManager().removeVariable(name)

Alfons Åberg said...

Hi Jobinesh,

Thanx for a great sample - but I keep getting an this error - when I try to switch from Employee to Department in Usecase #3

Server Exception during PPR, #1
javax.el.PropertyNotFoundException: Target Unreachable, 'DepartmentId' returned null
at com.sun.el.parser.AstValue.getTarget(
at com.sun.el.parser.AstValue.isReadOnly(
at com.sun.el.ValueExpressionImpl.isReadOnly(

Removed the rest of the logging....

Thanks, Henrik

Jobinesh said...

I'm sorry, look like you hit this bug#10028224. This is fixed in the internal builds.

Anonymous said...

Nice post, thanks.

But when I run the sample with unchecked "Enable Application Module Pooling" in AM settings I keep receiving strange error:
<_handleException> ADF_FACES-60098:Faces - cykl życia otrzymuje nieobsługiwane wyjątki w fazie APPLY_REQUEST_VALUES 2

javax.el.PropertyNotFoundException: Target Unreachable, 'DynamicForm_dynamic_VO_f2' returned null
at com.sun.el.parser.AstValue.getTarget(Unknown Source)
at com.sun.el.parser.AstValue.isReadOnly(Unknown Source)
at com.sun.el.ValueExpressionImpl.isReadOnly(Unknown Source)

I tried with new ADF and error still occurs.
Can you check if contains fix for bug#10028224?

Do you know any workarounds?

Jobinesh said...

Thanks for pointing it out.However,I'm not able to reproduce it when I tried my sample(attached with the post) on the build you mentioned. Can you please help me by detailing the steps needs to followed( assuming the issue is reproducible on my sample) for reproducing the error you mentioned.

Anonymous said...

A little mistake: I have used sample workspace from your another great post (Enabling LOVs for Dynamic ViewObject attributes - file
Reproducing is simple:
- uncheck AM pooling,
- run sample,
- go to Departments,
- click "Take me back"
and error should occur.


bakki77 said...

Hi Jobinesh,

This is nice one. but i want to generate the UI component also dynamically. for eg:- instead of output text for all the columns in a grid, for some column i want to display it as boolean check it possible.


Jobinesh said...

You can give a try using dynamic:table + Dynamic VO with proper cntrl hints, personally I've never tried though.

Anonymous said...

I am Alexandr.
Good blog;
Can I dynamically create the ViewObject from xml?
1. Create the ViewObject Wizard Jdeveloper.
2. Post the xml to another ApplicationModuleImpl
3. Get access to it.

Jobinesh said...

Can you please detail the use case. Is this Desing Time(development phase) requirement? Are you looking for some automated VO generation mechanism as part of build process. If not, the example in the blog for generating VO at run time holds good for you.

Anonymous said...

xml more.
For example set Control Hints
< PropertiesBundle
in Label text or set the column name.
(I want to apply your example for ADF Swing Desctop ... with dynamic xml i have finished screen forms and JTable)

Anonymous said...

Hi Jobinesh
Nice Post. Just going thru it as Im a adf newbie. While debugging I found that the Lifecyle phase doesnt consider the overriden preparerenderer method in the page controller - DynamicBindingEnabledPageController.
please correct me if I shouldnt expect it to fire the prepare renderr method. I also added some debug statements (sops) before super was called and nothing seems to get printed in the logs. I am expecting the preparerenderer method to fire before a page is rendered. will be nice to hear from you. thanks

Jobinesh said...

I'm not using DynamicBindingEnabledPageController in the sample(not added to pageDefinition file as a ControllerClass). A custom page controller is required if you have page which posts request to itself and changes underlying VO while processing the request.In other words an action changes underlying VO used by the binding and displays modified 'view' - Here ControllerClass can be used to clear the previous binding before displaying new comp. tree bound to the updated VO defn.

Anonymous said...

Hi Jobinesh,

I need to create a dynamic table based on arraylist. As mentioned by you I used for doin this. To the table added a binding too. From the binding setter i'm calling createdynamictable() method which take cares of creating a table programmatically. This is working fine indiviually. Now I addef two SOC on the page. After selecting the value from the first list it again calls the createdynamictable() method which leads to null pointer. I think the collectionModel is the reason for the complete page refresh on performing some other action. So I removed the table binding and added the createdynamictable() method call to getCollectiomModel(). Now the SOC is working fine and not leading to the null pointer. But the table is not being created. Can you please suggest a solution in which both the table and SOC would work fine..

Jobinesh said...

If you can share a sample, I'll take a look

Anonymous said...

Thanks alot... I have shared the code on

Anonymous said...


Helpful post, thanks.

I have an issue with af:forEach with VO from query stmt.

My page def is similar to yours. At run-time ADF Dynamic Table (forEach) displays empty rows.
If there are 10 results(rows) for the query, I see 10 empty rows with a single column. Column doesn't have header either.


<tree IterBinding="DynamicVO1Iterator" id="DynamicVO1">
<nodeDefinition Name="Dummy"></nodeDefinition>


<af:table rows="#{bindings.DynamicVO1.rangeSize}"
emptyText="#{bindings.DynamicVO1.viewable ? 'No data to display.' : 'Access Denied.'}"
rowSelection="single" id="t1" styleClass="AFStretchWidth"
columnStretching="blank" autoHeightRows="24"
<af:column minimumWidth="10" width="10" rowHeader="true" id="c2"/>
<af:forEach items="#{bindings.DynamicVO1.attributeDefs}"
<af:column headerText="#{bindings.DynamicVO1.labels[]}"
sortable="true" sortProperty="#{}" id="c1">
<af:outputText value="#{row[]}" id="ot1"/>

Bibs said...
This comment has been removed by the author.
Bibs said...

Nice Article, Jibonesh.
I have a requirement where we have to define the layout in a UI(which is stored in a database) for labels and corresponding fields for a form so that they can be loaded dynamically when the page renders.
Any suggestions on how to do it?

Jobinesh said...

ADF Faces support dynamic:form for this

Bibs said...

Thanks Jobonesh.
Do you have any article or any link to look more into dynamic:form?


Kristaps said...

Hi! Can You please say what I need to do to insert new row in USE CASE 3?

Best regards, Kristaps

Kristaps said...

Any idea?

Jobinesh said...

Client side usage is like normal VO/EO. EO will have logic to push updated data to custom data store by overriding doDML()

Hemant said...

Hi Jobinesh,

Very nice post. Thanks.
But,not getting an idea incase we need to create multiple dynamic tables on a page!!

Like we are getting the data in object form and based on that "n" tables would be getting created at run time!!

Jobinesh said...

Eaiear solution is to embed this logic in a task flow and use multi task flow approach for embedding them on a page at rurimr

Jobinesh said...

Eaiear solution is to embed this logic in a task flow and use multi task flow approach for embedding them on a page at rurimr

Anonymous said...

Nice Blog and Posts. Many thanks.

I have a requirement as in Case 1(Dynamic UI Table built using dynamic ViewObject(database table and attribute definitions change for each invocation))

So I have followed steps listed for Case1.

My page is like

--Input Text Box---

===Dynamic Table(using af:foreach)===

When user clicks the link, dynamic table details are displayed according to input text.

So, what I have done is make rendered attribute of 'Dynamic Table' initially false .

When user clicks the link(action listener is ), call AM method (passing query stmt)which does createViewObjectFromQueryStmt,
then make rendered true for dynamic table.

Every thing is working fine, but when page loads I get error popup

Object DynamicQueryVO of type View Object is not found.

Same pop up comes when link is clicked.

Stack trace of the error popup :

ADF: Adding the following JSF error message: Object DynamicQueryVO of type View Object is not found.
oracle.jbo.NoObjException: JBO-25003: Object DynamicQueryVO of type View Object is not found.
at oracle.adf.model.binding.DCIteratorBinding.getViewObject(
at oracle.adf.model.binding.DCIteratorBinding.getViewObject(
at oracle.adf.model.binding.DCIteratorBinding.initSourceRSI(
at oracle.adf.model.binding.DCIteratorBinding.callInitSourceRSI(
at oracle.adf.model.binding.DCIteratorBinding.internalGetRowSetIterator(
at oracle.adf.model.binding.DCIteratorBinding.refresh(
at oracle.adf.model.binding.DCExecutableBinding.refreshIfNeeded(
at oracle.adf.model.binding.DCIteratorBinding.getAttributeDefs(
at oracle.adf.model.binding.DCIteratorBinding.getAttributeDefs(
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(
at sun.reflect.DelegatingMethodAccessorImpl.invoke(
at java.lang.reflect.Method.invoke(
at oracle.jbo.common.JboBeanUtils.getProperty(
at oracle.jbo.common.JboAbstractMap.internalGet(
at oracle.adf.model.binding.DCExecutableBinding.internalGet(
at oracle.adf.model.binding.DCIteratorBinding.internalGet(
at oracle.adf.model.binding.DCExecutableBinding.get(
at javax.el.MapELResolver.getValue(

Here, should I need to create a proxy VO and replace it in run time ?will proxy VO works if database table and attribute definitions change for each invocation?

Could you please help in knowing why I get that error popup and how to resolve it

Many Thanks

dtmrp said...

Hi Jobinesh,

I have to generate the UI components in the table dynamically.I have boolean check box in the table.

As you said in the blog i dont know about much about control hints.

But i tried in this way..

it is displaying good in the UI whatever values from the dab..But problem is It is showing as 'READ_ONLY' not able to update selectBox...Is ther any properties do need to set it to became updatable...Thanks

Ankit Gupta said...

Hi Jobinesh,

Please confirm if Case# 3 holds valid to create a dynamic editable form?

Best Regards,
Ankit Gupta

łukaszG said...
This comment has been removed by the author.
łukaszG said...

Hi Jobinesh,
very helpful post.

I have one question concerning entity cache. In your example you are using this technique to remove the view and clear the cache:


so why do you clear the cache at all if it is removed in the next line? Is this necessary? In my case it is causing:

JBO-25303: Cannot clear entity cache dynamic.EO because it has modified rows

on dbTrans.clearEntityCache(DYNAMIC_EO) when I want to reset the view object.

The problem is solved when I call




Is this ok?

Jobinesh Purushothaman said...

Thanks for pointing it out.
Alternatively, you can try calling getTransaction().rollback(); as first statement before clearing cache. As you pointed out there is redundant call in my code- sorry for that.So either of the below will work
the way you tried - no need to call
getDBTransaction().clearEntityCache(DYNAMIC_EO); in that case.

btw, you can take a look at some new samples as well which make use of some 12 C features

Ankit Gupta said...

Hi Jobinesh,

To create an editable dynamic form, I used the similar approach and wired the "value" property of input text field to "#bindings[].inputValue}", however during form render, no value is shown.

Please advise if additional steps are required to achieve the same.

Best Regards,
Ankit Gupta

German Santana said...

Hi Jobinesh,

Nice Article, Do you know if this approach is safe on a multiuser enviroment? Because the view definition and view instance are created with the same name. Could two users at the same time , view the view object definition created on another user session?


Neha said...

Hi Jobinesh
This is really a very good article and solved most of my issues at hand.
I downloaded the sample and ran it and it runs well.
I tried to replicate it and my adf read only dynamic table does not let me sort it. It says that the attribute (which I am trying to sort) is not found in the DynamicVO.
I tried to find what the issue might be but could not find it.
Only difference between your demo and my application is that the string that I pass for dynamic VO creation(input text) and the table itself is on the same page.
So for the dynamic vo to work , I have a default activity in my taskflow which creates the dynamic VO from "Select * from dual" query. Then when the user has entered the actual query on the page, I create the VO again with that query.

Any pointers as to why I am getting oracle.jbo.NoDefException: JBO-25058 and your sample app does not?