Skip to main content
Last updated January 07, 2014 07:49, by steven.davelaar

ADF Samples from Steve Muench

Main Table of Contents

SMU165 Using a Headless Taskflow to Perform Work in an Autononmous Transaction {] 24-NOV-2011
This example illustrates a technique to use a "headless" taskflow -- that is, one without any view activities -- like a subroutine call. The perform-isolated-work bounded task flow in the example has its Data Control Scope set to "isolated" so that the work it performs is done in a separate transaction. Run the Main.jspx page to try the demo. The example-dept-region bounded task flow includes a button on its ExampleDept.jsff page that navigates to a task flow call activity in the taskflow to perform the work done by the isolated "subroutine" call. The perform-isolated-work includes a method call activity that invokes the performAppModuleLevelWork() client interface method in the AppModule application module. This method accepts an integer representing the department number to modify, and a String representing the value that department's Loc attribute should be updated to, then it commits the changes. The taskflow accepts parameters which it passes into this method call. The af:commandButton includes two nested af:setPropertyListener components to assign values to the requestScope.deptno and requestScope.locValue attributes which are referenced by the task flow call to pass these values into the task flow. The page is configured to pass the current row's Deptno value, and to pass the literal value 'Q' as the value to assign to the Loc attribute in the current row. The net effect is that clicking the button will update the current department row to have the value 'Q' as its LOC column value (in a separate transaction. The checkbox in the page controls whether or not the Router activity will declaratively refresh the DeptView1Iterator iterator in the page, or not, upon returning from the task flow method call. If you leave the box unchecked, you can observe the effect of the update committed by a separate transaction by attempting to update the current row in the UI after having clicked the button. You'll see an error that "Another user has change the row with primary key ...". If you perform the refresh, you'll see that the requery causes the LOC value updated in the separate transaction to be reflected in the web page. The custom PagePhaseListener CalledTaskf­lowErrorRep­orterPagePh­aseListener, which is configured in the adf-settings.xml file, ensures that any exception thrown in the nested taskflow gets reported to the binding container of the page that is marked as an exception handler activity. To see this exception reporting in action, use SQLPlus to lock the row in the DEPT table corresponding to the current row in the web page. Then, when clicking on the button to perform the work in the isolated transaction, you'll see a "Row Already Locked" exception in the UI.
SMU164 Method Action Invoking Managed Bean Method Without Making Bean a DataControl {] 24-NOV-2011
This example illustrates how to configure an ADFM method binding to invoke a managed bean method without having to turn the bean into a data control. Turning a bean into a data control just to invoke a bean method on it is one of the most common mistakes I see ADF developers doing. The MyBean bean is registered in the adfc-config.xml file and the method action binding in the page def for view1.jspx references the bean using the InstanceName property of the binding. Note that the EL expression you provide needs to use the older-style with the dollar-sign rather than the pound-sign. Run the page in the example and click the only button in the page. You'll see the message "Foo" print out in the log window.
SMU163 Binding SelectBooleanRadio to True/False Value in DB Row {] 24-NOV-2011
This example shows how to bind a "T"/"F" value to a data-driven set of selectOneRadio components. Run the CreateTable.sql script to create the DEPT_WITH_BOOLEAN table, then run Example.jspx. When you commit, the "T"/"F" value in the SELECTED column in the table will reflect the change to the selected radio group button
SMU161 Signal RowInconsistentException Correctly Across Activation/Passivation {] 02-NOV-2011
This example illustrates an approach to ensure that the RowInconsisentException is correctly signalled even if the AM used by the second user has undergone passivation and activation since the first user changed the row. First, it's important to understand the potential problem. Assume that two users U1 and U2 query up the DEPT row with DEPTNO=10. User U1 modifies the Dname in that row and commits. At this point user U2 is looking at a "stale" value in the page in her browser. User U2 proceeds to make her edit and clicks (Commit). In an ADF page implemented in the typical way, the user will correctly get a warning that "Another user has changed the row" as long as U2's application module has not undergone passivation and activation. If instead application load forces ADF to activate the AM's passivated state to service user U2's (Commit)-button click request, then the change made by user U2 is silently committed, potentially overwriting the changes that user U1. This occurs because the act of activating the AM state reads in current DB values of the queried rows, which now reflect the changes made by user U1 instead of the values that are in user U2's current browser page. The solution involves using a change indicator attribute and including that change indicator attribute in the web page as a hidden field. In the example, the Dept entity object is based on the DEPT_WITH_OBJ_VERSION table. This is the standard DEPT table to which has been added a single, additional NUMBER column named OBJECT_VERSION. The ObjectVersion attribute in the Dept entity is marked as a 'Change Indicator' attribute, and it's also marked as a 'History Column' of type 'version number'. The history column setting tells ADF to automatically set the value of this column to 1 in a newly created row, and to increment the version number each time the row is modified and saved. The change indicator setting tells ADF to compare only the value of this attribute in order to determine whether the row has been changed by another user or not. In the absence of a change indicator attribute, ADF must compare the values of all persistent attributes which can take longer. The view1.jspx page uses the h:inputHidden component to include the ObjectVersion attribute value in the page. By doing this, the object version of the row being edited by user U2 will be submitted to the server along with the other attribute values, and it will be used to compare against the ObjectVersion attribute value of the row being edited. Since these values differ, the RowInconsistentException is thrown as desired. Try re-enabling the AM Pooling to convince yourself that the technique will work under normal circumstances as well. To run the example, start by running the CreateTables.sql script to create the DEPT_WITH_OBJ_VERSION table. Then run the view1.jspx page. Once the page appears in your default browser, copy the URL http://localh­ost:7101/Signa­lRowInconsiste­nt/faces/view1 and paste it into a different browser. For example, if Google Chrome is your default browser, paste it into Firefox or Internet Explorer. This will allow you to test having two distinct browser users using your application. Both browsers should be looking at the row for DEPTNO=10. In the first browser window, update the value of Dname and click (Commit). Now the second browser is looking at a "stale" value for the Dname. In this second browser, update the value of Loc and click (Commit). The user gets the expected error "Another user has changed the row with primary key oracle.jbo.Key[10]". The AppModule application module in the example has its 'Enable Application Module Pooling' configuration setting (jbo.ampool.doampooling) set to false for testing purposes. Your application module will never have this pooling setting disabled in production, but it is useful for testing the activation-safety of your application module by stress-testing the passivation/activation on each HTTP request.
SMU160 Conditionally Auto-Executing af:query Search Form Based on User Input {] 31-DEC-2010
SMU159 Using ViewAccessor to Perform Attribute-Level Validation {] 11-JAN-2010
This example illustrates two techniques to perform an attribute-level validation based on a view-accessor with a bind variable that needs to be bound to the value that is attempting to be set. For an entity-level validation, you can use a view accessor based list validator for this purpose. However, for the attribute-level use case - since you cannot refer to the newValue expression in the view accessor bind variable default Groovy expression - you need to either use a groovy expression validator, a Java method validator, or a custom validation rule. This workspace provides examples of the first and the last of these three options. The Java method validation alternative is left as an exercise to the reader. The Emp EO has two view accessors: CheckDivisibilityBy3 based on view object definition test.ValidationViewObject, configured to have the VarModulo value set to 3, and CheckDivisibilityBy7 based on the same view object, configured to have the VarModulo value set to 7 The attribute-level Groovy validator on the Sal attribute sets the value of the VarValue bind variable on the view accessor, then executes the query. It returns value if the view accessor's first() function returns a non-null result (i.e. at least one row was found). The example also illustrates a more generic approach that doesn't rely on Groovy. I created a new, reusable validation rule called AttrLevelViewAccessorValidator. I've used an instance of it on the Comm attribute, declaratively configuring the validation rule beans two properties: attrNameToBindNewValueTo = "VarValue" and viewAccessorName = "CheckDivisibilityBy7". Run the AM in the tester, and verify that you must enter a Sal value that is divisible by 3 and a Comm value that is divisible by 7. Of course, the example view object would normally be a more interesting query with one or more bind variables going against a table other than DUAL, but this simple query hopefully will get the basic idea across. If the value being validated were the key attribute of the target view object, you could have used the "Key Exists" validator based on a view accessor instead. This approach is valid when the query you need to validate needs to lookup something that is not the key attribute in the target VO used for validation.
SMU156 Use AutoRefresh VO in Shared AM with Optimized Polling to Show Latest Data in a Table {] 26-DEC-2009
This example illustrates how to use an Auto-Refresh view object in a shared application module to display the latest database changes in a table without eagerly requerying the view object. The DeptView view object has its AutoRefresh property set to true and the Model project defines a shared application module instance named AppModule on the Business Components > Application Module Instances panel of the project properties. The AppModuleDataControl entry in the dataControlUsages section of the DataBindings.cpx file in the ViewController project has been configured to use the AppModuleShared configuration so that the UI works with a shared application module instance. As an optimization, the DeptView view object overrides the processDatabaseChangeNotification() method to keep track of the System.currentTimeMillis() in a local member field. The view object's getLastRequery() is exposed on the client interface and is accessed by the DepartmentPage backing bean's via a method action binding. That bean's onPollTimerExpired() method only bothers to add the table UI component as a partial target if the time the view object was last requeried is greater than the time the table was last PPR'd (which it tracks in a viewScope attribute). To try the demo, run the Departments.jspx page. If you'd like try accessing the same page from several different browsers (e.g. Firefox, Internet Explorer, Chrome) to simulate multiple, distinct user sessions. In SQL Plus (or the JDeveloper SQL Developer worksheet window) try insert, updating, or deleting rows in the DEPT table and committing the changes. Sometime in the next 15 seconds, the different browser user's should update to reflect the changes automatically.
SMU157 Programmatically Displaying Task Flows in the ADF UI Shell {] 26-DEC-2009
This is a ready-built version of the UI Shell demo application that you can build yourself by following the step-by-step tutorial Oracle User Interface Shell. It illustrates various programmatic ways to open a task flow in the ADF UI Shell. Try the demo by running the First.jspx page. Each of the links in the "Choose your activity" area open a separate task flow in a tab in the UI shell. Clicking a second time on a link will activate an existing task flow tab if it already exists, rather than opening a second instance of the same task flow. The Second.jspx page (to which you can navigate by clicking on the "Second" tab) illustrates menu items under the "Action" menu that each opens a distinct task flow. In this case, clicking a second time on a given menu item will open additional instances of the same task flow in the shell if one/some happen to already be open. It also illustrates toolbar icons that perform shell functions. The [1] icon opens the same task flow as the first menu item. The [2] icon marks the current tab as being "dirty". If you try to close a dirty tab, you'll see a warning dialog. The [3] icon marks a tab as not-dirty. The Third.jspx page illustrates opening task flows as the only content in the shell (i.e. no tabs). It also shows that a button in one task flow can open a taskflow in the shell.
SMU158 Performing Custom View Criteria Item Search Form Validation {] 26-DEC-2009
SMU155 Avoid Adding a New Row to a Table Until Its Valid {] 26-DEC-2009
This example illustrates an approach to prevent a newly-created row from getting automatically added to a view object's rowset (shown in a table) until it passes all validation rules. Typically a newly-created row will be added to a rowset for any view object based on the same entity object. This example contains a framework extension class for entity objects NotifyChangeOnValidatedEntityImpl and a framework extension class for view objects OnlyAddNewRowIfValidViewObjectImpl. The entity framework extension class overrides the validateEntity() framework method to send an attribute change notification after the entity object successfully passes validation. The view object framework extension class exposes getter and setter methods for a boolean property named onlyAddNewRowIfValid and the overridden rowQualifies() method ensures that a new row does not qualify for inclusion in the view object's rowsets unless it is valid. The AppModuleImpl class overrides the prepareSession() method to set the property on the DeptView1 view object instance. To run the demo, run the view1.jspx page. Click (Create) to create a new row. A data entry form appears at the top of the page. To cause a validation error to occur, leave the fields blank, or try entering a Dname value of upper-case X and a Loc value of upper-case Y. Notice that until the row validates, it's not added into the table.
SMU154 Two Approaches to Referencing Controller-layer Session State in VO Bind Variables {] 16-DEC-2009 ]
This example illustrates two different approaches to referencing controller layer state inside the default value expression of a view object's bind variable. One typical example is to reference the name of the logged-in user (which in the past web applications would store in a Web session attribute), however since you can use the adf.context.securityContext.userName groovy expression to reference the username of the logged-in user when using ADF Security, I choose a slightly-different example of storing a code representing the user's favorite color. The ViewController project contains a UserInfo bean with a single favoriteColor property. This bean is registered in the adfc-config.xml file as a session-scoped managed bean, and using the JSF managed property feature, the default value of emgreen is injected into the bean at creation time. The Model project contains two view objects that each contain a bind variable named VarFavoriteColor whose default value we'd like to come from the current value of the aforementioned UserInfo managed bean's favoriteColor property. There are two basic approaches: one will appeal more to those who cherish the cleanest logical separation of view/controller and model layers. The other appeals more to developers who like to use the "simplest thing that works" (as long as it's not bad practice). The ExampleVO2 VO instance in the AM data model is of type ExampleVOUsi­ngADFContext­SessionInfoI­nBindVariable. This view object's VarFavoriteColor bind variable references the groovy expression adf.context­.sessionScop­e.UserInfo.f­avoriteColor and represents the "simplest thing that works" approach. This takes advantage of the fact that ADFContext object abstracts access to the four interesting scopes that might be relevant during runtime of an ADF application: applicationScope, sessionScope, viewScope, and requestScope. When running in the web container, these scopes map onto the obvious matching scopes that you are familiar with from the view/controller layer. When running outside the web container, the ADFContext provides a default implementation of these scopes as a set of static maps that are useful for regression testing purposes. The Test class in the Testing project illustrates making use of the ADFContext.getSessionScope() to setup the session-level information the view object is expecting to find at runtime. The ExampleVO in the AM's data model is of type ExampleVOUsingCo­ntrollerSuppliedU­serDataHashtableI­nfoInBindVariable. This view object's bind variable of the same name references the groovy expression adf.userSession.userData.FavoriteColor. In this implementation that defines the more clear separation of view/controller layer and business tier - which is the one I personally prefer and recommend - the ADFBC session's userData map is used to store information that the view object's bind variable will reference. In a customized data control implementation class (CustomDCJboDataControl), the beginRequest method is overridden to invoke a setSessionFavoriteColor() method on the ExampleModule client interface to pass in the value of the UserInfo.favoriteColor into the business tier. The application module stores this information in the user data map, and makes that information activation/passivation-safe by overriding the passivateState() and activateState() methods. The custom data control is configured by setting the fully-qualified name of the CustomDCJboDataControlFactory class in the ExampleModuleDataControl entry's FactoryClass property in the DataBindings.cpx file (in the dataControlUsages section). On each request, the view/controller layer passes this information into the business layer, and the ExampleVOUsingCo­ntrollerSuppliedU­serDataHashtableI­nfoInBindVariable view object references its value from the userData map. Notice the setDefaultV­aluesForSess­ionLevelFav­oriteColor() method in the ExampleModuleImpl class. This is invoked in an overridden prepareSession() method to assign a reasonable default value to both of the favoriteColor elements if their value is currently null. This would ensure that both approaches would work if the respective view object were called from a service or a test client that didn't provide any specific value at runtime. In the Testing project, the Test class illustrates how you can write a standalone regression test (just a simple Java class in this example, not a JUnit test) which mimics the view/controller layer calling of the setSessionFavoriteColor() API in the one case, and which populates a "mock" sessionScope UserInfo bean with a favoriteColor property to make the other view object find its expected information. As mentioned above I prefer the approach that uses the userData hash table set explicitly via an application module method, however at least now you have a good example of both techniques in action so you can decide for yourself which you prefer.
SMU153 Validating Exactly One Detail Row of a Given Type {] 04-NOV-2009 Custom schema
This example illustrates two techniques for validating that a parent entity contains exactly one composed child entity of a given type. Start by running the CreateTables.sql script to create the EMAIL_MESSAGE and EMAIL_MESSAGE_RECIPIENTS tables. The example is a simple "Create an Email" application that allows you to create a new email message and add one or more recipients. Each recipient is of a particular RecipientType (P=Primary, C=CC, B=BCC). The rule being enforced is that there must be exactly one recipient of type "Primary". The validation is performed by an entity-level Script Expression validator on the parent Email entity object. This validator uses Groovy code to work with a view accessor named ValidateOnePrimary which is of type EmailRecipientsView and has the design-time-applied view criteria named PrimaryRecipient (criteria mode "Both") applied to it. This view criteria filters based on the MessageId and the RecipientType='P'. The view accessor is configured to pass the value of the current Email entity's Id attribute as the value of the view criteria's VarMessageId bind variable. Notice that the script validator allows multiple error messages to be defined. The validator's Groovy script executes the view accessor's query, raises one error using adf.error.raise(MESSAGE_KEY) if there are no rows returned and another error if more than one row is returned. If the email and its recipients validate successfully, then they are saved to the tables, but note that no real email is sent anywhere. The default expression for the EmailRecipient.RecipientType attribute uses an alternative approach to the view accessor in order to conditionally assign the default recipient type for a newly created EmailRecipient entity. The default expression is Email.Recipients.count("RecipientType == 'P' ? 1 : null") == 0 ? 'P' : 'C' which accesses the parent email message using the reverse association accessor named Email then accesses its rowset of recipients by references that email entity's Recipients association accessor attribute. Since the value of that expression is a RowSet we can use one of the built-in rowset, in-memory aggregation functions to calculate the count of the child EmailRecipient entity instances which have a RecipientType equal to P. The count() rowset aggregate function evaluates its String argument as a Groovy expression in the context of each row in the rowset over which it iterates. If the expression evaluates to null, then the count does not include that row. If the expression evaluates to non-null, then that row is counted. Finally, it uses a ternary expression so that if the count of EmailRecipient instances having RecipientType equals to P is zero, then it returns the default value of P, otherwise it returns the default value of C to represent a recipient being copied on the mail. The Email entity object includes the MessageText attribute of type ClobDomain, and both the Email.SenderEmail and EmailRecipient.RecipientEmailAddress attributes use a custom domain type EmailAddress which validates the format of an email address. The NewMailMessage.jsff page fragment uses the special <f:converter converterId="oracle.genericDomain"/> component to enable JSF to work properly with these three domain-valued attributes. The MailServer application module defines the custom method createNewMailAndPrimaryRecipient() which creates a new email message and the first email recipient row. The method is exposed on the client interface so that the default method call activity of the create-new-email bounded task flow can invoke it declaratively to prepare the service layer for the creation of a new email. The CustomViewObjectImpl class implement a generic feature to conditionally have rows in a view object's default rowset be inserted at the end. For view objects using this framework extension class as their base class, the feature "kicks in" if the VO has the "InsertRowsAtEnd" custom property set to some non-null value like "true". The EmailRecipientsView in the example uses this framework extension class as its base class and has this custom property set. To run the example, run the TestPage.jspx. You'll need to login as either user userone or usertwo, both of whose password is welcome1. Click on the button to create an "email" and then click (Send) to test the validation.
SMU152 Best Practice Approach for Invoking AM, VO, or VO Row Methods from a Backing Bean {] 18-SEP-2009 SCOTT schema
This example illustrates several interesting points about how the view-controller layer can use ADF action bindings to invoke custom methods exposed on the client interface of application modules, view objects, and view rows. Run the ViewController project to start the demo. Enter a string value and an integer value on the StartPage and click the button to start the emp-task-flow task flow, passing in values for the task flows two parameters stringTaskFlowParam and intTaskFlowParam. In the TestPage.jspx that runs when emp-task-flow starts, the parameter values passed in appear in the title bar of the box at the top. Nine buttons in this page illustrate different combinations of invoking application module, view object, and view row methods using action bindings in the page's pageDefinition. For the methods that accept arguments, the nested elements inside the action binding (which you can see in the structure window) reflect the names of the method arguments and provide a declarative EL expression that ADF will evaluate when the action binding is executed to supply the method arguments. Three of the nine buttons are bound to action event handler methods in the TestPage backing bean. This backing bean illustrates the best-practice technique to invoke methods on the AM, VO, or VO Row client interface, optionally providing some or all of the method arguments in code as well. In particular, it illustrates that you should NOT use the Configurat­ion.createR­ootApplicat­ionModule() API to access an application module in your backing bean. See this blog article for more info on why you should not use it in backing beans. For a bit more information on how the StartPage captures and passes parameters to the task flow, read on. The initial StartPage.jspx uses page definition variables named pageDefStringVariable and pageDefIntVariable to declaratively provide temporary storage for the string- and int-valued parameters in the parameter form. These variables were added to the pageDefinition using the Structure window by selecting the variables node inside the executables section, and choosing { Insert inside variables > variable } from the right-mouse menu. Also in the structure window for the page definition of the Start page, we created two attribute bindings to expose the values of the pageDefinition variables to the UI. One way to create these bindings is to select the bindings folder in the Structure window and choosing { Insert inside bindings > Generic Bindings > attributeValues }. The other way is to use the "Bindings" overview editor tab for the StartPage and click the Create Control Binding icon (green plus-sign) in the Bindings box on the left. When creating the bindings, choose the iterator binding named variables and pick the pageDef variable name whose value you want to bind to as the attribute name. The af:inputText fields in the StartPage bind to this attribute bindings using the EL expressions #{bindings.­pageDefStri­ngVariable1­.inputValue} and #{bindings­.pageDefInt­Variable1.­inputValue}. The button on the StartPage contains two nested af:setActionListener components to assign the values of the pageDefinition variables collected from the user into two request-scope attributes. The value of #{bindings.­pageDefStri­ngVariable1­.inputValue} is assigned to #{requestScope.pageDefStringVariable}, and similarly the value of #{bindings­.pageDefInt­Variable1.­inputValue} is assigned to #{requestScope.pageDefIntVariable}. The task flow call activity named emp-task-flow in the adfc-config.xml unbounded task flow is configured to assign the values of the task flow parameters from these request-scope attributes. The stringTaskFlowParam task flow parameter gets its value from the #{requestScope.pageDefStringVariable}, while the intTaskFlow param gets its value from the #{requestScope.pageDefIntVariable}. As part of its parameter definitions, the emp-task-flow itself defines pageFlowScope attributes that will hold the values of the task flow input parameters for the duration of the task flow. The stringTaskFlowParam parameter value is stored in the attribute #{pageFlowScope.stringTaskFlowParam} while the intTaskFlowParam is stored in the attribute #{pageFlowScope.intTaskFlowParam}. Any pages or backing beans that execute in the context of this task flow can reference the parameter values using these same EL expressions. As noted above, the action bindings in the page definition are configured to reference these pageFlowScope attributes using EL to declaratively pass their values as method arguments to the invoked method.
SMU151 Data-Driven af:selectOneChoice List Bound to a Managed Bean Property {] 17-SEP-2009 SCOTT schema
Page1.jspx in this example illustrates how to bind an af:selectOneChoice dropdown list to a session-scope managed bean property #{myBean.selectedDepartment}. Rather than using an ADF list binding (which is designed to target a row attribute or page definition variable), instead we create a table binding in the page definition (DeptView1) that is bound to the DeptView1Iterator iterator binding and which exposes the attributes we want to use for the label and value in the list of valid choices (Dname and Deptno, respectively). Nested inside the af:selectOneChoice an af:forEach loops over the List-valued rangeSet property that the table/range binding exposes, and create the select list items based on the data in the rows of the DeptView1Iterator (which is bound to the default rowset of the DeptView1 view object instance in the AppModule application module.
SMU150 Filter a Tree Showing Necessary Parent Nodes for Matches {] 15-SEP-2009 SCOTT schema
SMU148 Initialize Task Flow by Setting View Object Bind Vars from Parameters {] 03-SEP-2009 SCOTT schema
This example illustrates how to to use an ExecuteWithParams built-in operation dropped onto a task flow method call activity that is marked as the default activity to initialize the task flow by setting some view object bind variable values based on task flow parameters passed in from the caller. The TestTaskFlow.jspx page has two buttons that are configured to invoke the bounded task flow named show-employees-for-dept, passing in the value of the department number whose employees should be visualized. The task flow defines a parameter named p_deptno whose value is stored into the pageFlowScope attribute named p_deptno using the EL expression #{pageFlowScope.p_deptno}. The ExecuteWithParams operation for the EmployeesByDepartment view object instance (of type EmpView) was dropped onto a method call activity that has been set as the task flow's default activity. The EmployeesByDepartment view object instance has been configured in the application module data model panel to declaratively apply the view criteria named ByDepartment, so when you drop the ExecuteWithParams operation for this view object instance, the list of appropriate bind variables appears in the dialog. The varDeptno bind variable's EL expression is configured on the ExecuteWithParams binding in the page definition to the expression #{pageFlowScope.p_deptno} to pickup the value to assign the bind variable from the task flow parameter passed in. If you right-click on the method call activity and choose "Go to Page Definition" notice that the EmployeesByDepartmentIterator iterator binding's Refresh property is configured to the value never to avoid the ADF framework's performing any implicit refreshing of the iterator binding before the action binding has a chance to set the view object bind variables.
SMU149 Reference View Object and View Row Methods from Groovy {] 03-SEP-2009 SCOTT schema
The EmpView view object in this example features two transient, Groovy calculated attributes. The attribute named ValueUsingVOFunction references a custom myFunctionAtVOLevel() method on the EmpViewImpl class, while the attribute named ValueUsingVORowFunction references a custom myFunctionAtVORowLevel() method on the EmpViewRowImpl class, in both cases passing in the value of the Sal attribute. The methods simply return the value passed in surrounded by either parenthesis or square brackets.
SMU147 ADFBC Application With No Database Connection {] 01-SEP-2009 SCOTT schema
This example illustrates a technique for creating an application module that does not use a database connection. The only reason you might want to do this is that you are exclusively using programmatic view objects and entity objects, which might be an infrequent scenario, but does come up from time to time. The example illustrates a number of lesser-used framework extension classes. The NoDatabaseApplicationPoolImpl is a custom application module pool implementation class. The NonDatabaseConnectionStrategy is a custom connection strategy class . The CustomSessionImpl is a custom session class, which returns a custom transaction handler factory. The CustomTxnHandlerFactoryImpl is a custom transaction handler factory used to return an instance of the custom CustomTxnHandlerImpl class, which is a custom transaction handler implementation. The SessionClass configuration property is set to the name of the custom session implementation class, which in turn bootstraps the custom transaction handler factory and custom transaction handler. The PoolClassName configuration property is set to the name of the custom application module pool implementation class. This class overrides the isSupportsPassivation() method to return false, indicating to the runtime that this particular application module pool does not support passivation. The jbo.ampool.connectionstrategyclass configuration property is set to the name of the custom connection strategy class which overrides the createApplicationModule() method to set some key properties in the environment hashmap before calling super. The StaticVO is a static view object that returns rows whose data is in the file.
SMU146 Programmatically Manipulating a Table's QBE Filter Fields {] 14-AUG-2009 SCOTT schema
SMU145 Using a CheckBox in an Editable Table with Boolean/Button Binding {] 13-JUL-2009 SCOTT schema
This example illustrates how to use the button binding (also known as the boolean binding) in an ADF Table to declaratively handle data entry an attribute whose valid values are one of two choices representing true/false, on/off, yes/no, etc. The CreateDeptWithFlagTable.sql creates a variant of the DEPT table named DEPT_WITH_FLAG that has one additional FLAG column whose valid values are "Y" or "N". The DeptWithFlag EO indicates a UI hint on its Flag attribute to indicate that it prefers to render as a "Checkbox". Dragging and dropping the DeptWithFlagView1 data collection from the data control palette as an "ADF Table", JDeveloper infers the correct selectBooleanCheckbox control for the Flag attribute. However, there is two additional (simple) steps required to make it work correctly in a table. First, using the overview editor for the pageDefinition, I created a new button binding named "Flag" for the Flag attribute, indicating the values of "Y" for selected and "N" for unselected. With the view1PageDef page definition as the active editor, I expanded the DeptWithFlagView1 tree binding, its nodeDefinition folder, and the AttrNames folder inside it to select the Flag attribute of the tree binding node definition. Then, using the Property Inspector, I set the value of the Binds property of this Flag attribute name element to "Flag" (without quotes), which references the name of the button binding created above.

Click here for older samples of Steve Muench

Please Confirm