Tuesday, April 21, 2009

Call Stoered Procedure /Stored Function with ARRAY Parameters

PL/SQL
create or replace type EMP_REC as object
(
employee_id number(6),
last_name varchar2(25),
job_id varchar2(10)
)
=============================
create or replace
TYPE EMP_TABLE AS TABLE OF EMP_REC
================================
create or replace
PACKAGE BODY PK_PROD AS

PROCEDURE INSERT_PROD(p_iorec IN EMP_TABLE) AS
BEGIN
/* TODO implementation required */
FOR i IN 1..p_iorec.count LOOP
--get p_iorec(i).EMP_NAME
insert into productmaster values(p_iorec(i).employee_id, p_iorec(i).last_name, p_iorec(i).job_id);
END LOOP;

END INSERT_PROD;

PROCEDURE INSERT_PROD1 AS
dt varchar2(20);
BEGIN
/* TODO implementation required */

--select sysdate into dt from dual;
insert into productmaster values(2,'as', 'asd');
END INSERT_PROD1;

END PK_PROD;
Java Code:
con = uow.getAccessor().getConnection();
//code to create the struct+array
oracle.sql.StructDescriptor structDesc = StructDescriptor.createDescriptor("EMP_REC", con);
oracle.sql.ArrayDescriptor arrayDesc = ArrayDescriptor.createDescriptor("EMP_TABLE", con);
...
oracle.sql.ARRAY newArray = new ARRAY(arrayDesc, con, arr.toArray());

//code to create and execute the query:
StoredProcedureCall call = new StoredProcedureCall();
call.setProcedureName("PK_PROD.INSERT_PROD");
call.addUnamedArgument("in_array");

DataModifyQuery query = new DataModifyQuery();
query.setShouldBindAllParameters(true);
query.setCall(call);
query.addArgument("in_array");
Vector args = new Vector(1);
args.addElement(newArray);

getSession().executeQuery(query, args);



If using TopLink 11, you can have TopLink create the Array and Struct objects for you - so you don't need to get the connection and build the objects yourself. The following code assumes that the EMP_REC struct is mapped to an Employee object using a TopLink Descriptor, see http://www.oracle.com/technology/products/ias/toplink/doc/10131/main/_html/prjdaun003.htm for details on how to do this.

//code to create the java objects representing the ARRAY and STRUCT
emptable= new Vector(); //represents the ARRAY
//build each employee and add it to the emptable
Employee emp = new Employee();
..
emptable.add(emp);

StoredProcedureCall call = new StoredProcedureCall();
call.setProcedureName("PK_PROD.INSERT_PROD");
//Tell TopLink what the ARRAY contains
ObjectRelationalDatabaseField ordf = new ObjectRelationalDatabaseField("");
ordf.setSqlType(Types.STRUCT);
ordf.setSqlTypeName("EMP_REC");
ordf.setType(Employee.class);
call.addUnamedArgument("in_array", Types.ARRAY, "EMP_TABLE", ordf);
//build the reusable query
DataModifyQuery query = new DataModifyQuery();
query.setShouldBindAllParameters(true);
query.setCall(call);
query.addArgument("in_array");

Vector args = new Vector(1);
args.addElement(emptable);

getSession().executeQuery(query, args);

Create and Insert BLOB into Database using Java

This will Create BLOB Object For you
DriverManager.registerDriver(new oracle.jdbc.driver.OracleDriver());
con = DriverManager.getConnection("jdbc:oracle:thin:@d2.bs-cochin.com:1521:orcl", "scott", "tiger");
File = new File("D:\\ADF.pdf");
FileInputStream fis = new FileInputStream(f);
BufferedInputStream bin=new BufferedInputStream(fis);
fblob =BLOB.createTemporary(con,true,BLOB.DURATION_SESSION);
BufferedOutputStream bout = new BufferedOutputStream(fblob.getBinaryOutputStream());
IOUtils.copy(bin,bout);
System.out.println("========BLOB======>"+fblob.length());
it also works in TOPLINK.

Wednesday, April 15, 2009

ADF Faces: Building a search form showing the results in a taskflow using an af:popup component

One of the areas that really rocks in JDeveloper 11 is taskflows. To program usecases that involve taskflows can keep you busy for weeks if the goal is to provide a library of code examples.
A JSF page has a textfiled and a search button. The user enters a department number and hits the "search" button. The result of this search, which uses ExecuteWithParams in ADF Business Components, shows in a popup dialog on the same page. To enforce reuse - one of the big themes in JDeveloper 11 - the popup content is a taskflow that shows in a region.
The challenges solved in this usecase are:
1) The input argument is of type String - as everything on the web starts as a string before it gets converted - whereas the bind variable used within the ExecuteWithParams operation is of type oracle.jbo.domain.Number. Because of this, the result oage cannot be called directly and instead a method needs to be called first to prepare the model before the result page is called


2) The search string needs to be passed to the region as an input parameter. Further, the region needs to be updated whenever a new parameter is passed.
3) The popup needs to be closed programmatically. This part is easy and I am reusing the code from another blog entry of mine
At runtime, the application works as shown below


A tiny bit that I haven't yet got working using the af:showPopupBehavior, which works if launching the popup using the af:clientListener with JavaScript, is to proper adjust the position of the popup. However, JDeveloper 11 is not production yet, so no need to worry too much about this yet.
Pressing the close button on the popup will dismiss the popup window. Pressing the search button again will re-open it with the query result of the new search input.
The query is performed within the method activity, which is the default activity in the taskflow and that routes the request to the page fragment that displays the result table once finished.

CODE:
public void executeQuery(){

FacesContext fctx = FacesContext.getCurrentInstance();
ELContext elctx = fctx.getELContext();
Application jsfapp = fctx.getApplication();
ExpressionFactory exprfct = jsfapp.getExpressionFactory();

ValueExpression adfDataVexpr = exprfct.createValueExpression(elctx,"#{data}",BindingContext.class);
BindingContext adfdata = (BindingContext) adfDataVexpr.getValue(elctx);
ValueExpression deptIdDataVexpr = exprfct.createValueExpression(elctx,"#{pageFlowScope.deptIdTaskFlowParam}",Object.class);
if (deptIdDataVexpr.getValue(elctx) != null){

String deptIdStr = (String) deptIdDataVexpr.getValue(elctx);
try {

Integer deptIdInt = Integer.parseInt(deptIdStr);
BindingContainer bindings = adfdata.findBindingContainer("BrowseEmployeesPageDef");
bindings.getOperationBinding("ExecuteWithParams").getParamsMap().put("deptId",new Number(deptIdInt.intValue()));
bindings.getOperationBinding("ExecuteWithParams").execute();

} catch (NumberFormatException ex) {
ex.printStackTrace();
}


}
return;
}
The initial code lines are there to get a hold of the ExecuteWithParams method that is contained in the pagedef file associated with the page fragment. Theinteresting bits start with line 10. In here, the parameter that is passed from the calling page to the region (taskflow) is accessed and then converted to oracle.jbo.domain.Number before it is used to execute the ExecuteWithParams operation.
When you drag a taskflow as a region onto a page, then - if the taskflow requires an input parameter, the pagedef file of the page on which the region is added, is updated with the region definition and input parameter binding


In the image above, you see that the input parameter that is defined on the taskflow, reads its value from #{pageFlowScope.deptIdSearch}, an attribute added to the pageFlowScope of the calling page. The attribute is updated by the search field on the page

XML:
value="#{pageFlowScope.deptIdSearch}"/>
So anything that the user types into the search field, gets written to the pageFlowScope attribute when pressing the search button, which performs the form submit. Important to note is that if you want to launch a popup dialog from a button, you must ensure that the button uses a partial submit instead of performing a full page refresh

XML:
partialSubmit="true">


So what do we have until here, and what is missing still ? We have a task flow that starts with a method call to prepare the query for the table. The method takes an input argument that is passed to the taskflow from the region. The region accesses the parameter value from an attribute in the pageFlowScope of the calling page. The remaining job is to make sure the taskflow input parameter writes the input parameter to its own pageFlowScope so the Java method can access it using EL.

XML:
1. adfc-config xmlns="http://xmlns.oracle.com/adf/controller" version="1.2">

ExecuteEmployeesQuery

deptIdTaskFlowParam
#{pageFlowScope.deptIdTaskFlowParam}



EmployeesBean
adf.sample.EmployeesBean
pageFlow


/BrowseEmployees.jsff


#{pageFlowScope.EmployeesBean.executeQuery}

showEmployees



ExecuteEmployeesQuery

showEmployees
BrowseEmployees





The taskflow source shows the following
The default activity - and thus the first action performed when entering the taskflow - is the method call to a managed bean. ExecuteEmployeesQuery
The input parameter is defined as "deptIdTaskFlowParam", which is the same name used in the region binding, and writes the obtained value to #{pageFlowScope.deptIdTaskFlowParam} from where it is accessed by the managed bean method

XML:

deptIdTaskFlowParam
#{pageFlowScope.deptIdTaskFlowParam}


The remaining information to give is that I set the "Refresh" property on the region binding in the pagedef file of the calling page to "ifNeeded", which makes sure that the region binding is updated whenever the input parameter changes.

Thursday, April 9, 2009

Some handy code for backing beans ( ADF & JSF )

Here some code which you can use in your backing beans, I use this code all the time. With this you can retrieve the data or actions from the ADF page definition or create new uicomponents with ADF definitions and some JSF methods.

I'll keep this page up to date. Let me know if you have some code.

// print the roles of the current user
for ( String role : ADFContext.getCurrent().getSecurityContext().getUserRoles() ) {
System.out.println("role "+role);
}


// get the ADF security context and test if the user has the role users
SecurityContext sec = ADFContext.getCurrent().getSecurityContext();
if ( sec.isUserInRole("users") ) {
}
// is the user valid
public boolean isAuthenticated() {
return ADFContext.getCurrent().getSecurityContext().isAuthenticated();
}
// return the user
public String getCurrentUser() {
return ADFContext.getCurrent().getSecurityContext().getUserName();
}


// get the binding container
BindingContainer bindings = BindingContext.getCurrent().getCurrentBindingsEntry();

// get an ADF attributevalue from the ADF page definitions
AttributeBinding attr = (AttributeBinding)bindings.getControlBinding("test");
attr.setInputValue("test");

// get an Action or MethodAction
OperationBinding method = bindings.getOperationBinding("methodAction");
method.execute();
List errors = method.getErrors();

method = bindings.getOperationBinding("methodAction");
Map paramsMap = method.getParamsMap();
paramsMap.put("param","value") ;
method.execute();


// Get the data from an ADF tree or table
DCBindingContainer dcBindings = (DCBindingContainer)BindingContext.getCurrent().getCurrentBindingsEntry();

FacesCtrlHierBinding treeData = (FacesCtrlHierBinding)bc.getControlBinding("tree");
Row[] rows = treeData.getAllRowsInRange();

// Get a attribute value of the current row of iterator
DCIteratorBinding iterBind= (DCIteratorBinding)dcBindings.get("testIterator");
String attribute = (String)iterBind.getCurrentRow().getAttribute("field1");

// Get the error
String error = iterBind.getError().getMessage();


// refresh the iterator
bindings.refreshControl();
iterBind.executeQuery();
iterBind.refresh(DCIteratorBinding.RANGESIZE_UNLIMITED);

// Get all the rows of a iterator
Row[] rows = iterBind.getAllRowsInRange();
TestData dataRow = null;
for (Row row : rows) {
dataRow = (TestData)((DCDataRow)row).getDataProvider();
}

// Get the current row of a iterator , a different way
FacesContext ctx = FacesContext.getCurrentInstance();
ExpressionFactory ef = ctx.getApplication().getExpressionFactory();
ValueExpression ve = ef.createValueExpression(ctx.getELContext(), "#{bindings.testIter.currentRow.dataProvider}", TestHead.class);
TestHead test = (TestHead)ve.getValue(ctx.getELContext());

// Get a session bean
FacesContext ctx = FacesContext.getCurrentInstance();
ExpressionFactory ef = ctx.getApplication().getExpressionFactory();
ValueExpression ve = ef.createValueExpression(ctx.getELContext(), "#{testSessionBean}", TestSession.class);
TestSession test = (TestSession)ve.getValue(ctx.getELContext());

// main jsf page
DCBindingContainer dc = (DCBindingContainer)BindingContext.getCurrent().getCurrentBindingsEntry();
// taskflow binding
DCTaskFlowBinding tf = (DCTaskFlowBinding)dc.findExecutableBinding("dynamicRegion1");
// pagedef of a page fragment
JUFormBinding form = (JUFormBinding) tf.findExecutableBinding("regions_employee_regionPageDef");
// handle to binding container of the region.
DCBindingContainer dcRegion = form;



// return a methodexpression like a control flow case action or ADF pagedef action
private MethodExpression getMethodExpression(String name) {
Class [] argtypes = new Class[1];
argtypes[0] = ActionEvent.class;
FacesContext facesCtx = FacesContext.getCurrentInstance();
Application app = facesCtx.getApplication();
ExpressionFactory elFactory = app.getExpressionFactory();
ELContext elContext = facesCtx.getELContext();
return elFactory.createMethodExpression(elContext,name,null,argtypes);
}

//
RichCommandMenuItem menuPage1 = new RichCommandMenuItem();
menuPage1.setId("page1");
menuPage1.setText("Page 1");
menuPage1.setActionExpression(getMethodExpression("page1"));

RichCommandButton button = new RichCommandButton();
button.setValueExpression("disabled",getValueExpression("#{!bindings."+item+".enabled}"));
button.setId(item);
button.setText(item);
MethodExpression me = getMethodExpression("#{bindings."+item+".execute}");
button.addActionListener(new MethodExpressionActionListener(me));
footer.getChildren().add(button);


// get a value
private ValueExpression getValueExpression(String name) {
FacesContext facesCtx = FacesContext.getCurrentInstance();
Application app = facesCtx.getApplication();
ExpressionFactory elFactory = app.getExpressionFactory();
ELContext elContext = facesCtx.getELContext();
return elFactory.createValueExpression(elContext, name, Object.class);
}
// an example how to use this
RichInputText input = new RichInputText();
input.setValueExpression("value",getValueExpression("#{bindings."+item+".inputValue}"));
input.setValueExpression("label",getValueExpression("#{bindings."+item+".hints.label}"));
input.setId(item);
panelForm.getChildren().add(input);



// catch an exception and show it in the jsf page
catch(Exception e) {
FacesMessage msg = new FacesMessage(FacesMessage.SEVERITY_ERROR, e.getMessage(), "");
FacesContext.getCurrentInstance().addMessage(null, msg);
}


FacesMessage msg = new FacesMessage(FacesMessage.SEVERITY_WARN, msgHead , msgDetail);
facesContext.addMessage(uiComponent.getClientId(facesContext), msg);


// reset all the child uicomponents
private void resetValueInputItems(AdfFacesContext adfFacesContext,
UIComponent component){
List items = component.getChildren();
for ( UIComponent item : items ) {

resetValueInputItems(adfFacesContext,item);

if ( item instanceof RichInputText ) {
RichInputText input = (RichInputText)item;
if ( !input.isDisabled() ) {
input.resetValue() ;
adfFacesContext.addPartialTarget(input);
};
} else if ( item instanceof RichInputDate ) {
RichInputDate input = (RichInputDate)item;
if ( !input.isDisabled() ) {
input.resetValue() ;
adfFacesContext.addPartialTarget(input);
};
}
}
}

// redirect to a other url
ExternalContext ectx = FacesContext.getCurrentInstance().getExternalContext();
HttpServletResponse response = (HttpServletResponse)ectx.getResponse();
String url = ectx.getRequestContextPath()+"/adfAuthentication?logout=true&end_url=/faces/start.jspx";

try {
response.sendRedirect(url);
} catch (Exception ex) {
ex.printStackTrace();
}

// PPR refresh a jsf component
AdfFacesContext.getCurrentInstance().addPartialTarget(UIComponent);


// find a jsf component
private UIComponent getUIComponent(String name) {
FacesContext facesCtx = FacesContext.getCurrentInstance();
return facesCtx.getViewRoot().findComponent(name) ;
}


// get the adf bc application module
private OEServiceImpl getAm(){
FacesContext fc = FacesContext.getCurrentInstance();
Application app = fc.getApplication();
ExpressionFactory elFactory = app.getExpressionFactory();
ELContext elContext = fc.getELContext();
ValueExpression valueExp =
elFactory.createValueExpression(elContext, "#{data.OEServiceDataControl.dataProvider}",
Object.class);
return (OEServiceImpl)valueExp.getValue(elContext);
}


// change the locale
Locale newLocale = new Locale(this.language);
FacesContext context = FacesContext.getCurrentInstance();
context.getViewRoot().setLocale(newLocale);


// get the stacktrace of a not handled exception
private ControllerContext cc = ControllerContext.getInstance();

public String getStacktrace() {
if ( cc.getCurrentViewPort().getExceptionData()!=null ) {
StringWriter sw = new StringWriter();
PrintWriter pw = new PrintWriter(sw);
cc.getCurrentViewPort().getExceptionData().printStackTrace(pw);
return sw.toString();
}
return null;
}


// get the selected rows from a table component
RowKeySet selection = resultTable.getSelectedRowKeys();
Object[] keys = selection.toArray();
List receivers = new ArrayList(keys.length);
for ( Object key : keys ) {
User user = modelFriends.get((Integer)key);
}

// get selected Rows of a table 2
for (Object facesRowKey : table.getSelectedRowKeys()) {
table.setRowKey(facesRowKey);
Object o = table.getRowData();
JUCtrlHierNodeBinding rowData = (JUCtrlHierNodeBinding)o;
Row row = rowData.getRow();
Test testRow = (Test)((DCDataRow)row).getDataProvider() ;
}

Sunday, April 5, 2009

About Me


My name is Vipin K R. I am currently working with the development team at SBN Technologics,Cochin. I am passionate about what I’m doing every day. For me, a business build upon good software must not automatically succeed, but a business built upon bad implemented or designed software is condemned to fail on the long run. Good software is built upon strong components, is well designed and therefore easily extendable and reusable. Performance, security and scalability have high priority to suit business requirements.
The phase of software design is the phase of basic directions: wrong decisions will backslide for sure and that is why I emphasize this phase.
To ensure product quality, testing is important. Every piece of functionality must be proven to be working and this proof must be automatically reproducible. This is why I take unit testing and continuous integration as an integral part of software development.

Software development is more than just my profession: I am an active contributor to various software projects including Logistic management, Legal Managements, Accounting systems, and many more.
Being a software developer is not everything: with my overview in different areas I evade the danger of getting constricted.

If you think, this sound interesting, you can use the social network tool Orkut

Or you can mail me on vipinkraghav@gmail.com

UIComponent has the function getFacetsAndChildren()


public Iterator getFacetsAndChildren() {
Iterator result;
int childCount = this.getChildCount(),
facetCount = this.getFacetCount();
// If there are neither facets nor children
if (0 == childCount && 0 == facetCount) {
result = EMPTY_ITERATOR;
}
// If there are only facets and no children
else if (0 == childCount) {
Collection unmodifiable =
Collections.unmodifiableCollection(getFacets().values());
result = unmodifiable.iterator();
}
// If there are only children and no facets
else if (0 == facetCount) {
List unmodifiable =
Collections.unmodifiableList(getChildren());
result = unmodifiable.iterator();
}
// If there are both children and facets
else {
result = new FacetsAndChildrenIterator(this);
}
return result;
}

March 10, 2009 Posted by careeritdevelopers | Uncategorized | , | No Comments

You can put a button on Template Def and do reset all inputText irrespective of pages, which implemented the same template

You can put a button on Template Def and do reset all inputText irrespective of pages, which implemented the same template.
Here you can design a Template that be applied to your entire project, from the same template you can access the all pages and its controls.
here is the sample code check it out , let me know your feedback.

private void resetValueInputItems(AdfFacesContext adfFacesContext, UIComponent component){
Map m ;

Iterator IC=component.getFacetsAndChildren();
while ( IC.hasNext() ) {
UIComponent item =IC.next();
if ( item instanceof RichInputText ) {
RichInputText input = (RichInputText)item;
if ( !input.isDisabled() ) {
System.out.println(input.getValue());
input.resetValue() ;
adfFacesContext.addPartialTarget(input);
};
} else if ( item instanceof RichInputDate ) {
RichInputDate input = (RichInputDate)item;
System.out.println(”got Date”);
if ( !input.isDisabled() ) {
input.resetValue() ;
adfFacesContext.addPartialTarget(input);
};
}
resetValueInputItems(adfFacesContext,item);
}

}

public void resetForm(ActionEvent actionEvent) {
AdfFacesContext adfFacesContext = AdfFacesContext.getCurrentInstance();
//resetValueInputItems(adfFacesContext,vvFormBinding );

}

March 10, 2009 Posted by careeritdevelopers | Uncategorized | , , , , , | No Comments

We can access all Controls page in ADF

Using this function you can do reset all inputtext in a page without knowing them.

private void resetValueInputItems(AdfFacesContext adfFacesContext, UIComponent component){
List items = component.getChildren();
for ( UIComponent item : items ) {

resetValueInputItems(adfFacesContext,item);

if ( item instanceof RichInputText ) {
RichInputText input = (RichInputText)item;
if ( !input.isDisabled() ) {
input.resetValue() ;
adfFacesContext.addPartialTarget(input);
};
} else if ( item instanceof RichInputDate ) {
RichInputDate input = (RichInputDate)item;
if ( !input.isDisabled() ) {
input.resetValue() ;
adfFacesContext.addPartialTarget(input);
};
}
}
}

public void resetForm(ActionEvent actionEvent) {
AdfFacesContext adfFacesContext = AdfFacesContext.getCurrentInstance();
resetValueInputItems(adfFacesContext,vvFormBinding );
testMap.put(”TEST”, “initial value”);
}

Dumping out pageFlowScope

One of the biggest issues we see with complex applications based on ADF R11 and is the debugging of complex task flows which are nested within regions in pages. Many of these problems resolve down into the task flow simply not having the state that you thought. So you need a simple way to inspect the pageFlowScope variables. Debugging is one option but I also like to have a little interactive output onto the console whilst I’m in the process of running the app. So I put together this simple utility method which I call as the default activity in my bounded task flows:

public String dumpTaskFlowState(){
AdfFacesContext afctx = AdfFacesContext.getCurrentInstance();
Map flowScopeMap = afctx.getPageFlowScope();
String viewPortName =
ControllerState.getInstance().getCurrentViewPort().getClientId(); System.out.println(”—————————————————-”);
System.out.println(”Dumping pageFlowScope Variables for: “);
System.out.println(viewPortName);
Iterator iter = flowScopeMap.entrySet().iterator();
while (iter.hasNext()){
Map.Entry entry = (Map.Entry)iter.next();
String mapKey = entry.getKey().toString();
Object mapValue = entry.getValue();
StringBuilder bldr = new StringBuilder(” “);
bldr.append(mapKey);
bldr.append(”=”);
bldr.append((mapValue==null)?”":mapValue.toString());
System.out.println(bldr.toString());
}
return “continue”;
}

The corresponding method activity that calls this is registered in the task flow xml thus:

#{debugUtil.dumpTaskFlowState}

when the class containing the dump method is defined in the debugUtil managed bean in the same task flow thus:

debugUtil
com.tuhra.ddt.view.util.TaskFlowUtils
request

Finally to wire everything up we set the dumpState method as the default activity and wire up the “continue” outcome to the real start point of the flow.
In time I’ll look at moving this onto a listener rather than having to have it in the flow itself, but it works pretty well as it is.
The output for this thing just appears in the console because I’ve used println() you could use a logger instead. Here’s a sample of the output:

————————————————————
Dumping pageFlowScope Variables for:
data.mainShellPageDef.tabletabflowdefinition1.tableTabContentsPageDef.dynamicQueryRegionflowdefinition1
currentOwner=FOD
currentObject=ADDRESSES
currentType=TABLE
currentSQL=

ADF Faces RC: Dynamic Table

Example

I have seen a number of posts in the forums concerning “How to create dynamic tables with RCF?”. As such, here is code example that creates an af:table with commandButtons that allow a user to dynamically add both rows and columns to a table, creating the oh so desired Ajax goodness.
Now, there a couple of things to note about this example. Namely, this example does not dynamically create components in a backing bean. Instead, a “best practices” approach is taken that enforces better separation between data and UI manipulation. Thus, the dynamic nature of the table is driven by updates to the model rather directly manipulating UI components.
JSPX File
Managed Bean: DynaTableBean.java
JAVA:
1.package com.thepeninsulasedge.view.dynatable.managed;
2.
3.import java.util.ArrayList;
4.import java.util.Collection;
5.import java.util.HashMap;
6.import java.util.List;
7.
8.import java.util.Map;
9.
10.import javax.faces.event.ActionEvent;
11.
12.import org.apache.myfaces.trinidad.model.CollectionModel;
13.import org.apache.myfaces.trinidad.model.SortableModel;
14.
15.public class DynaTableBean {
16. private SortableModel model;
17. private List columnNames;
18.
19.public DynaTableBean() {
20. columnNames = new ArrayList();
21. }
22.
23.// Add a new row to the model
24. public void addRow(ActionEvent evt){
25.if(!columnNames.isEmpty()){
26. Map newRow = createNewRowMap();
27.((List)model.getWrappedData()).add(newRow);
28.}
29.}
30.
31.// Get table model
32. public CollectionModel getCollectionModel(){
33. if(model == null){
34. model = new SortableModel(new ArrayList());
35. }
36. return model;
37. }
38.
39.// Get Column Names
40.public Collection getColumnNames(){
41. return columnNames;
42. }
43.
44.// Add column
45.public void addColumn(ActionEvent evt){
46. // Create new column name
47.String colName = (columnNames.size()+1) + “”;
48.// Add column name to list of names
49. columnNames.add(colName);
50. // Create new row
51. Map newRow = createNewRowMap();
52. // Add new column name to new row
53. newRow.put(colName,null);
54.// Update existing model
55.addColumnToCurrentModel(colName);
56.}
57.
58.// Add column to existing rows
59. private void addColumnToCurrentModel(String name){
60. List list = (List)model.getWrappedData();
61. for(Map row:list){
62. row.put(name,null);
63. }
64. }
65.
66. private Map createNewRowMap(){
67.Map newRow = new HashMap();
68. for(String colName:columnNames){
69. newRow.put(colName,null);
70. }
71.return newRow;
72.}
73.
74.}
IN BACKING BEAN
In backing I have set ‘DynamicTable’ to instantiate it manually, if the session bean might not be get right.
public void setDocument1(RichDocument document1) {
this.document1 = document1;
FacesContext ctx = FacesContext.getCurrentInstance();
Application app = ctx.getApplication();
ValueBinding bind = app.createValueBinding(”#{DynamicTable}”);//session bean name which has given in adf-config
Object o = bind.getValue(ctx);
DynaTableBeantemp = (DynaTableBean) o;
// temp.setUserName(”Test “);
// temp.setDateAndTime(Calendar.getInstance().getTime().toString());

}