3 Adding Business Logic to Data Controls

This chapter describes how to configure your data controls with custom business logic, such as validation rules, UI control hints, and default values for attributes. By configuring your data controls, you can define business logic that is then used whenever UI components are created from those data controls.

3.1 Introduction to Adding Business Logic to Data Controls

When you generate data controls, you can use them without further modification to create bindings between your data model and the UI components in your application. In addition, you can configure the data controls to add business logic and other features to your data model so that those features are applied when you use the Data Controls panel to create UI components. For example, you can configure data controls to do the following things:

3.2 Configuring Data Controls

When you create a data control for an EJB session bean, a standard set of values and behaviors are assumed for the data control. For example, the data control determines how the label for an attribute will display in a client. You can configure these values and behaviors by creating and modifying data control structure files that corresponds to your entity beans. You first generate a data control structure file using the overview editor for the .dcx file.

3.2.1 How to Edit a Data Control

You can make a data control configurable by using the overview editor for the DataControls.dcx file to create data control structure files that correspond to the entity beans. You can then edit the individual data control structure files.

In the overview editor, in the Data Controls tree, select an accessor returned collection for the bean that you would like to configure and click the Edit icon to generate a data control structure file.

In the overview editor of the data control structure file, make the desired modifications.

3.2.2 What Happens When You Edit a Data Control

When you edit a data control based on an EJB session bean, JDeveloper creates a data control structure file that contains metadata for the affected bean and opens that file in the overview editor. This file stores configuration data for the data control that is specific to that bean, such as any UI hints or validators that you have specified for the bean.

A data control structure file has the same base name as the entity bean with which it corresponds. For example, if you click the Edit icon when you have an accessor returned collection node selected that corresponds with the Customer.java entity bean, the data control structure file is named Customer.xml. The data control structure file is generated in a package that corresponds to the package of the bean class, but with persdef prepended to the package name. For example, in the Summit application, the Customer.java bean is in the model package, and the Customer.xml data control definition file is in the persdef.model package. Once a data control structure file has been generated, you can use the overview editor for that file to make further configurations.

A data control structure file contains the following information:

Attributes: Describes all of the attributes on the service. By default, there is an attribute for each bean property that is mapped to a database column. You can also add transient attributes. You can set UI hints that define how these attributes will display in the UI. You can also set other properties, such as whether the attribute value is required, whether it must be unique, and whether it is visible. For information about setting UI hints, see the "Defining Attribute UI Hints for View Objects" section of the Oracle Fusion Middleware Fusion Developer's Guide for Oracle Application Development Framework.

Note:

View objects are ADF Business Components used to encapsulate SQL queries and to simplify working with the results. When reading this section, simply substitute "bean" for "view object."

Accessors: Describes data control elements that return result sets on beans. The Base Accessors section lists accessors that are based on bean properties for which an association to another entity class is defined on the property's field.

Named Criteria: Enables you to create rules to filter the rows that are presented.

Operations: Describes methods on the bean that are used by the data control's built-in operations, such as add and remove methods, which are used by the Create and Delete built-in operations, respectively.

Figure 3-1 shows the data control structure file for the Item bean in the Summit demo application.

Figure 3-1 Data Control Structure File in the Overview Editor

Note:

The overview editor of a data control structure file shows all of the attributes, accessors, and operations that are associated with the bean. However, the data control structure file's XML source only contains definitions for elements that you have edited. The base elements are introspected from the bean. Also, when you make changes to the underlying bean, the data control inherits those changes.

3.3 Working with Attributes

When you create a data control for your EJBs, you can create a data control structure file for the bean in which you can declaratively augment the functionality of the bean's persistent attributes. For example, you can create validation rules and set UI hints to control the default presentation of attributes in UI components. In addition, you can create transient attributes.

In all cases, you set these properties on the Attributes page of the overview editor of the data control structure file. For information on creating a data control structure file, see Section 3.2.1, "How to Edit a Data Control."

3.3.1 How to Control the Updatability of an Attribute

The Updatable property controls whether the value of a given attribute can be updated. You can select the following values for the Updatable property:

In the Application Navigator, double-click the desired data control structure file.

In the overview editor, click the Attributes navigation tab.

On the Attributes page, select the attribute you want to edit, and then click the Details tab.

On the Details page, set the Updatable property.

3.3.2 How to Define a Static Default Value for an Attribute

The Value field in the Details section allows you to specify a static default value for the attribute when the value type is set to Literal. For example, you might set the default value of a ServiceRequest entity bean's Status attribute to Open, or set the default value of a User bean's UserRole attribute to user.

In the Application Navigator, double-click the desired data control structure file.

In the overview editor, click the Attributes navigation tab.

On the Attributes page, select the attribute you want to edit, and then click the Details tab.

On the Details page, select the Literal option.

In the text field below the Literal option, enter the default value for the attribute.

3.3.3 How to Define a Default Value Using a Groovy Expression

You can use a Groovy expression to define a default value for an attribute. This approach is useful if you want to be able to change default values at runtime. However, if the default value is always the same, the value is easier to see and maintain using value field with the Literal type (on the Details tab). For general information about using Groovy, see Section 3.8, "Groovy Language Support."

In the Available list at the bottom of the dialog, select any attributes upon which the value expression or the optional recalculate expression is based and shuttle each to the Selected list.

Click OK to save the expression.

3.3.4 What Happens When You Create a Default Value Using a Groovy Expression

When you define a default value using a Groovy expression, a <TransientExpression> tag is added within the tag for the corresponding attribute in the data control structure file. Example 3-1 shows sample XML code for a Groovy expression that returns the current date for a default value.

3.3.5 How to Set UI Hints on Attributes

You can set UI hints on attributes so that those attributes are displayed and labeled in a consistent and localizable way by any UI components that use those attributes. To create UI hints for attributes, use the overview editor for the bean's data control structure file, which is accessible from the Application Navigator.

View objects are ADF Business Components used to encapsulate SQL queries and to simplify working with the results. When reading this section, simply substitute "bean" for "view object."

3.3.6 What Happens When You Set UI Hints on Attributes

When you set UI hints on an attribute, JDeveloper treats those hints as properties. Tags for the properties are added to the bean's data control structure file and the values for the properties are stored in a resource bundle file. If the resource bundle file does not already exist, it is generated in the data control's package and named according to the project name when you first set a UI hint. For example, in the Summit demo application, the resource bundle is called ModelBundle.properties

Example 3-2 shows the code for the price attribute in the Summit demo application's Item.xml data control structure file, including tags for the Label and Format Type hints which have been set for the attribute.

Example 3-3 shows the corresponding entries for the Label and Format Type hints in the ModelBundle.properties resource bundle file, which contains the values for all of the project's localizable properties.

If the value will be calculated with an expression, set Updatable to Never.

3.4.2 What Happens When You Add a Transient Attribute

When you add a transient attribute, JDeveloper adds a <ViewAttribute> tag to the bean's data control structure file to reflect the new attribute. Example 3-4 shows the XML code for a transient attribute named LineItemTotal that is based on an expression that multiplies the values of the price and quantity attributes.

3.5 Defining Validation Rules on Attributes Declaratively

The easiest way to create and manage validation rules is through declarative validation rules. Declarative validation rules are defined using the overview editor, and once created, are stored in the bean's data control structure file. Encapsulating the business logic this way ensures that your business information is validated consistently in every client that accesses it, and it simplifies maintenance by centralizing where the validation is stored.

When you add a validation rule, you supply an appropriate error message and can later translate it easily into other languages if needed. You can also set the severity level.

Many of the declarative validation features available for beans are also available at the page level, should your application warrant the use of page-level validation in addition to business-layer validation. For more information, see the "Using Validation in the ADF Model Layer" chapter of the Oracle Fusion Middleware Fusion Developer's Guide for Oracle Application Development Framework.

Note:

You can also add validation rules by implementing a custom validation class. This approach is particularly useful if you need to define complex parameterized validation rules (such as for checking credit card numbers) that you will need to use multiple times in your application. For more information, see the "Implementing Custom Validation Rules" section of the Oracle Fusion Middleware Fusion Developer's Guide for Oracle Application Development Framework.

3.5.1 How to Add Validation Rules to Attributes

The process for adding a validation rule to a bean is similar for most of the validation rules, and is done using the Add Validation Rule dialog. You can open this dialog by opening the bean's data control structure file, selecting an attribute on Attributes page, clicking the Validation Rules tab, and then clicking the Add icon

It is important to note that when you define a rule declaratively using the Add Validation Rule dialog, the rule definition you provide specifies the valid condition for the attribute. At runtime, the entry provided by the user is evaluated against the rule definition, and an error or warning is raised if the entry fails to satisfy the specified criteria. For example, if you specify a Length validator on an attribute that requires it to be Less Than or Equal To 12, the validation fails if the entry is more than 12 characters, and the error or warning is raised.

To add a declarative validation rule to a data control structure file, use the Attributes page of the bean's overview editor.

3.5.2 What Happens When You Add a Validation Rule

When you add a validation rule to a bean, JDeveloper updates the bean's data control structure file to include an entry describing what rule you've used and what rule properties you've entered.

For example, if you add a compare validation rule to the dateShipped attribute to ensure that the shipping date does not precede the date in the dateOrdered attribute, this results in a <validation:CompareValidationBean> entry in the XML file, as shown in Example 3-5.

3.5.3 How to Use the Built-in Declarative Validation Rules

The built-in declarative validation rules can satisfy many, if not all, of your business needs. These rules are easy to implement because you don't write any code. You use the user-interface tools to choose the type of validation and how it is used.

Built-in declarative validation rules can be used to:

Make a comparison between an attribute and literal value or expression

Make sure that a value falls within a certain range, or that it is limited by a certain number of bytes or characters

Validate using a regular expression or evaluate a Groovy expression

3.5.3.1 Validating Based on a Comparison

The Compare validator performs a logical comparison between an entity attribute and a value. When you add a Compare validator, you specify an operator and something to compare with. You can compare the following:

Literal value

When you use a Compare validator with a literal value, the value in the attribute is compared against the specified literal value. When using this kind of comparison, it is important to consider data types and formats. The literal value must conform to the format specified by the data type of the entity attribute to which you are applying the rule. In all cases, the type corresponds to the type mapping for the entity attribute.

For example, an attribute of column type DATE maps to the oracle.jbo.domain.Date class, which accepts dates and times in the same format accepted by java.sql.TimeStamp and java.sql.Date. You can use format masks to ensure that the format of the value in the attribute matches that of the specified literal.

3.5.3.4 What Happens When You Validate Using a List of Values

When you validate using a list of values, a <validation:ListValidationBean> tag is added to the bean's data control structure file.

3.5.3.5 Ensuring That a Value Falls Within a Certain Range

The Range validator performs a logical comparison between an entity attribute and a range of values. When you add a Range validator, you specify minimum and maximum literal values. The Range validator verifies that the value of the entity attribute falls within the range (or outside the range, if specified).

3.5.3.7 Validating Against a Number of Bytes or Characters

The Length validator validates whether the string length (in characters or bytes) of an attribute's value is less than, equal to, or greater than a specified number, or whether it lies between a pair of numbers.

3.5.3.8 What Happens When You Validate Against a Number of Bytes or Characters

When you validate using length, a <validation:LengthValidationBean> tag is added to the data control structure file, as shown in Example 3-7. For example, you might have a field where the user enters a password or PIN and the application wants to validate that it is at least 6 characters long, but not longer than 10. You would use the Length validator with the Between operator and set the minimum and maximum values accordingly.

3.5.4.1 Referencing Bean Methods in Groovy Validation Expressions

You can call methods on the bean using the adf.source.dataProvider property of the current object. The adf.source.dataProvider property allows you to access the bean that is being validated.

If the method is a non-boolean type and the method name is getXyzAbc() with no arguments, then you access its value as if it were a property named XyzAbc. For example, the Groovy expression in Example 3-9 would call the getXyzAbc() method.

Example 3-9 Groovy Expression Calling Sample Methods

adf.source.dataProvider.XyzAbc

For a Boolean property, the same holds true but the JavaBeans component naming pattern for the getter method changes to recognize isXyzAbc() instead of getXyzAbc(). If the method on your bean does not match the JavaBeans getter method naming pattern, or if it takes one or more arguments, then you must call it like a method using its complete name.

3.5.4.2 Validating Using a True/False Expression

You can use a Groovy expression to return a true/false statement. The Script Expression validator requires that the expression either return true or false, or that it calls the adf.error.raise/warn() method. A common use of this feature would be to validate an attribute value, for example, to make sure that an account number is valid.

Note:

Using the adf.error.raise() and adf.error.warn() methods (rather than simply returning true or false) allows you to define the message text to show to the user, and to associate a validator with a specific attribute. For more information, see Section 3.5.5, "How to Create Validation Error Messages."

3.5.4.3 What Happens When You Add a True/False Expression

When you create a Groovy expression, it is saved in the bean's data control structure file. The Groovy expression is wrapped by a <TransientExpression> tag. For some Groovy expressions, the <TransientExpression> tag is wrapped by an <validation:ExpressionValidationBean> tag as well.

3.5.5 How to Create Validation Error Messages

Validation error messages provide important information for the user: the message should convey what went wrong and how to fix it.

In the Application Navigator, double-click the desired data control structure file.

In the overview editor, click the Attributes navigation tab.

On the Attributes page, select the attribute for which you want to create the validation error message, and then click the Validation Rules tab.

In the Validation Rules section of the Attributes page, select the validation rule that you want to edit and click the Edit Validation Rule icon.

In the Edit Validation Rule dialog, click the Failure Handling tab.

In the Message Text field, enter your error message.

You can also define error messages in a message bundle file. To select a previously defined error message or to define a new one in a message bundle file, click the Select Message icon to open the Select Text Resource dialog.

Optionally, define a message token by entering the message token's name in curly braces ({}) within the text of the error message. An entry for the token will then appear in the Token Message Expressions section. Then define the value of the message token in the Token Message Expressions list.

3.5.5.2 Localizing Validation Messages

The error message is a translatable string and is managed in the same way as translatable UI control hints in a message bundle file. To view the error message for the defined rule in the message bundle class, locate the String key in the message bundle that corresponds to the ResId property in the data control structure file entry for the validator.

3.5.5.3 Raising Error Message Conditionally Using Groovy

You can use the adf.error.raise() and adf.error.warn() methods to conditionally raise one error message or another depending upon branching in the Groovy expression. For example, if an attribute value is x, then validate as follows, and if the validation fails, raise error messageA; whereas if the attribute value is y, then instead validate a different way and if validation fails, raise error messageB.

If the expression returns false (versus raising a specific error message using the raise() method), the validator calls the first error message associated with the validator.

The syntax of the raise() method takes one required parameter (the msgId to use from the message bundle), and optionally can take the attrName parameter.

3.5.5.4 Embedding a Groovy Expression in an Error Message

A validator's error message can contain embedded expressions that are resolved by the server at runtime. To access this feature, simply enter a named token delimited by curly braces (for example, {2} or {errorParam}) in the error message text where you want the result of the Groovy expression to appear.

After entering the token into the text of the error message (on the Failure Handling tab of the Edit Validation Rule dialog), the Token Message Expressions table at the bottom of the dialog displays a row that allows you to enter a Groovy expression for the token. Figure 3-4 shows the failure message that contains a message token for a validation rule in the Item.xml data control structure file.

The expression shown in Figure 3-4 is a Groovy expression that returns the value of the quantity attribute. You can also use Groovy expressions to access attribute UI hints and other objects that are defined in the data control structure file.

You can use the Groovy expression newValue to return the entered value.

3.5.6 How to Set the Severity Level for Validation Exceptions

You can set the severity level for validation exceptions to either Informational Warning or Error. If you set the severity level to Informational Warning, an error message will display, but processing will continue. If you set the validation level to Error, the user will not be able to proceed until you have fixed the error.

Under most circumstances you will use the Error level for validation exceptions, so this is the default setting. However, you might want to implement a Informational Warning message if the user has a certain security clearance. For example, a store manager may want to be able to make changes that would surface as an error if a clerk tried to do the same thing.

To set the severity level for validation exceptions, use the Failure Handling tab of the Add Validation Rule dialog.

In the Application Navigator, double-click the desired data control structure file.

In the overview editor, click the Attributes navigation tab.

On the Attributes page, select the attribute for which you want to create the validation error message, and then click the Validation Rules tab.

In the Validation Rules section of the Attributes page, select the validation rule that you want to edit and click the Edit Validation Rule icon.

In the Edit Validation Rule dialog, click the Failure Handling tab and select the option for either Error or Informational Warning.

Click OK.

3.6 Filtering Result Sets with Named Criteria

JDeveloper enables you to create named criteria for data control structure files. Named criteria can be used in the application's data model and can be exposed to users as seeded queries in search forms.

You can specify named criteria on an entity bean in order to filter results to display. The named criteria object is a row set of one or more named criteria rows, whose attributes mirror those in the entity bean. The named criteria definition comprises query conditions that function like the WHERE clause of an SQL query.

In the result set of a named criteria, the data type of each attribute is String, which enables the use of Query-by-Example operators. For example, this allows the user to enter conditions such as "OrderId > 304".

You use the Named Criteria page of the overview editor to define named criteria for specific data control structure files.

Note:

In addition to named criteria, there are also implicit criteria that are generated automatically for entity beans when you create a data control. Implicit criteria are based on the "FindAll" service methods that return all data for given tables.

Both named and implicit criteria are available under the Named Criteria node in the Data Controls panel. Implicit criteria appear as All Queriable Attributes.

3.6.1 Use Case for Named Criteria

You create named criteria definitions when you need to filter individual accessor results. Named criteria that you define at design time can be used for easy creation of Query-by-Example search forms that allow the end user to supply values for attributes of the target data control structure file.

For example, the end user might input the value of a customer name and the date to filter the results in a web page that displays the rows of a CustomerOrders collection. The web page designer will see the named criteria in the JDeveloper Data Controls panel and, from them, easily create a search form. For more information about the utilizing the named criteria in the Data Controls panel, see Section 8.1.1, "Query Search Forms."

3.6.2 How to Create Named Criteria Declaratively

To define named criteria for the data control structure file that you wish to filter, you open the data control structure file in the overview editor and use the Named Criteria section of the View Criteria page. A dedicated editor that you open from the Named Criteria section helps you to build the equivalent of a WHERE clause using attribute names (as opposed to SQL column names). You may define multiple named criteria for each bean.

Each named criteria definition consists of the following elements:

One or more named criteria rows consisting of an arbitrary number of named criteria groups or an arbitrary number of references to another named criteria already defined for the current data control structure file.

Optional named criteria groups consisting of an arbitrary number of named criteria items.

Named criteria items consisting of an attribute name, an attribute-appropriate operator, and an operand. Operands can be a literal value when the filter value is defined or a bind variable that can optionally utilize a scripting expression that includes dot notation access to attribute property values.

When you define a named criteria, you control the source of the filtered results. You can limit the results to:

Just the database table specified by the entity bean.

Just the in-memory results of the accessor query.

Both the database and the in-memory results of the accessor query.

Filtering on both database tables and the accessor's in-memory results allows you to filter rows that were created in the transaction but not yet committed to the database.

Named criteria expressions you construct in the Edit View Criteria dialog use logical conjunctions to specify how to join the selected criteria item or criteria group with the previous item or group in the expression:

AND conjunctions specify that the query results meet both joined conditions. This is the default for each named criteria item you add.

OR conjunctions specify that the query results meet either or both joined conditions. This is the default for named criteria groups.

Additionally, you may create nested named criteria to have more control over the logical conjunctions among the various named criteria items. A nested named criteria group consists of an arbitrary number of nested named criteria items. The nested criteria place restrictions on the rows that satisfy the criteria under the nested criteria's parent named criteria group. For example, you might want to query both a list of employees with Salary > 3000 and belonging to DeptNo = 10 or DeptNo = 20. You can define a named criteria with the first group with one item (Salary > 3000) and a nested named criteria with the second group with two items (DeptNo = 10 and DeptNo =20).

In the Application Navigator, double-click the data control structure file for which you want to create the named criteria.

In the overview editor, click the Named Criteria navigation tab.

In the Named Criteria page, expand the Named Criteria section and click the Create new view criteria button.

In the Create View Criteria dialog, enter the name of the named criteria to identify its usage in your application.

In the Criteria Execution Mode dropdown list, decide how you want the named criteria to filter the query results.

You can limit the named criteria to filter the database table specified by the accessor query, the in- memory row set produced by the query, or both the database table and the in-memory results.

Choosing Both may be appropriate for situations where you want to include rows created as a result of enforced association consistency. In this case, in-memory filtering is performed after the initial fetch.

Click one of these Add buttons to define the named criteria.

Add Item to add a single criteria item. The editor will add the item to the hierarchy beneath the current group or named criteria selection. By default each time you add an item, the editor will choose the next attribute to define the criteria item. You can change the attribute to any attribute that the data control structure file defines.

Add Group to add a new group that will compose criteria items that you intend to add to it. When you add a new group, the editor inserts the OR conjunction into the hierarchy. You can change the conjunction as desired.

Add Criteria to add a named criteria that you intend to define. This selection is an alternative to adding a named criteria that already exists in the data control structure file. When you add a new named criteria, the editor inserts the AND conjunction into the hierarchy. You can change the conjunction as desired. Each time you add another named criteria, the editor nests the new named criteria beneath the current named criteria selection in the hierarchy. The root node of the hierarchy defines the named criteria that you are currently editing.

Add Named Criteria to add a named criteria that has already been defined in the data control structure file.

Note:

Search forms that the UI designer will create from named criteria are not able to use named criteria that contain other named criteria.

Select a named criteria item node in the named criteria hierarchy and define the added node in the Criteria Item section.

Select the desired Attribute for the criteria item. By default the editor adds the first one in the list.

Select the desired Operator.

The list displays only the operators that are appropriate for the selected attribute. In the case of String and Date type attributes, the Between and Not between operators require you to supply two operand values to define the range. In the case of Date type attributes, you can select operators that test for a date or date range (with date values entered in the format YYYY-MM-DD). For example, for December 16th, 2010, enter 2010-12-16.

Select the desired Operand for the named criteria item selection.

Select Literal when you want to supply a value for the attribute or when you want to define a default value for a user-specified search field for a Query-by-Example search form. When the named criteria defines a query search form for the user interface, you may leave the Value field empty. In this case, the user will supply the value. You may also provide a value that will act as a search field default value that the user will be able to override. The value you supply in the Value field can include the wildcard characters * or %.

Select Bind Variable when you want the value to be determined at runtime using a bind variable. Click New to display the Bind Variable dialog that lets you create a new bind variable for the data control structure file. For more information about creating bind variables, see Section 3.6.4, "How to Use Bind Variables in Named Criteria."

For each item, group, or nested named criteria that you define, optionally change the default conjunction to specify how the selection should be joined.

AND conjunction specifies that the query results meet both joined conditions. This is the default for each named criteria item or view nested named criteria that you add.

OR conjunction specifies that the query results meet either or both joined conditions. This is the default for named criteria groups.

Optionally, to allow filtering based on the case of the runtime-supplied value, deselect the Ignore Case option. It is selected by default, preventing such filtering.

The criteria item can be a literal value that you define or a runtime parameter that the end user supplies. This option is supported for attributes of type String only. The default disables case sensitive searches.

In the Validation dropdown list, decide whether the named criteria item is a required or an optional part of the attribute value comparison in the generated WHERE clause.

Selectively Required means that the generated WHERE clause will ignore the named criteria item at runtime if no value is supplied and there exists at least one criteria item at the same level that has a criteria value. Otherwise, an exception is thrown.

Optional means the named criteria is added to the WHERE clause only if the value is non-NULL. The default Optional for each new named criteria item means no exception will be generated for null values.

Required means that the WHERE clause will fail to execute and an exception will be thrown when no value is supplied for the criteria item.

If the named criteria uses a bind variable as the operand, decide whether the IS NULL condition is generated in the WHERE clause. This field is enabled only if you have selected Optional for the validation of the bind variable.

Leave Ignore Null Values selected (default) when you want to permit the named criteria to return a result even when the bind variable value is not supplied at runtime. When validation is set to Required or Optionally Required, the named criteria expects to receive a value and thus this option to ignore null values is disabled.

For example, leaving this option selected for a bind variable that is used in a user search form would enable a user to see results from a search without having to fill in a value for the field with that bind variable.

Deselect Ignore Null Values when you expect the named criteria to return a null result when the bind variable value is not supplied at runtime.

Note that the validation settings Required or Optionally Required also remove the null value condition but support a different use case. They should be used in combination with Ignore Null Values feature to achieve the desired runtime behavior.

Click OK.

3.6.3 What Happens When You Create a Named Criteria

When you create a named criteria, the named criteria definition is added to the data control structure file and appears by name on the Named Criteria page of the overview editor.

To view XML code for the named criteria, open the source editor for the data control structure file. Each named criteria definition contains one or more <ViewCriteriaRow> elements corresponding to the number of groups that you define in the Create View Criteria dialog.

3.6.4 How to Use Bind Variables in Named Criteria

Bind variables provide you with the means to supply attribute values that are calculated at runtime to the named criteria.

If the named criteria is to be used in a seeded search, you have the option of making the bind variable updatable by the end user. With this updatable option, end users will be expected to enter the value in the search form.

Named criteria execution need not require the bind variable value if the named criteria item for which the bind variable is assigned is not required. To enforce this desired behavior, the Bind Variable dialog lets you can specify whether a bind variable is required or not.

You can define a default value for the bind variable or write scripting expressions for the bind variable that includes dot notation access to attribute property values. Expressions are based on the Groovy scripting language, as described in Section 3.8, "Groovy Language Support."

To add a named bind variable to a named criteria, use the Named Criteria page of the overview editor for the data control structure file. You can define as many bind variables as you need.

In the Application Navigator, double-click the data control structure file.

In the overview editor, click the Named Criteria navigation tab.

On the Named Criteria page, expand the Bind Variables section and click the Create new bind variable button.

In the Bind Variable dialog, enter the name and data type for the new bind variable.

Because the bind variables share the same namespace as data control structure file attributes, specify names that don't conflict with existing attribute names.

Optionally, specify a default value for the bind variable:

When you want the value to be determined at runtime using an expression, enter a Groovy scripting language expression, select the Expression value type and enter the expression in the Value field. Optionally, click Edit to open the Expression dialog. The Expression dialog gives you a larger text area to write the expression.

When you want to define a default value, select the Literal value type and enter the literal value in the Value field.

In the Bind Variable dialog, click the Control Hints tab and specify hints like Label Text, Format Type, Format mask, and others.

The view layer will use bind variable control hints when you build user interfaces like search pages that allow the user to enter values for the named bind variables. The Updatable option controls whether the end user will be allowed to change the bind variable value through the user interface. If a bind variable is not updatable, then its value can only be changed programmatically by the developer.

Click OK.

3.6.5 What Happens When You Use Bind Variables in Named Criteria

Once you've added one or more named bind variables to a structure definition file, you gain the ability to easily see and set the values of these variables at runtime. Information about the name, type, and default value of each bind variable is saved in the bean's data control structure file. If you have defined UI hints for the bind variables, this information is saved in the model project's message bundle file along with other UI hints for the data control structure file.

3.6.6 What You May Need to Know About Nested Expressions

Search forms that the UI designer will create from named criteria are not able to work with all types of nested expressions. Specifically, search forms do not support expressions with directly nested named criteria. This type of nested expression defines one named criteria as a direct child of another named criteria. Query search forms do support nested expressions where you nest the named criteria as a child of a criteria item which is itself a child of a named criteria. For more information about using named criteria to create search forms, see Section 8.1.1, "Query Search Forms."

3.6.7 How to Set User Interface Hints on Named Criteria

Named criteria that you create for data control structure file collections can be used by the web page designer to create Query-by-Example search forms. Web page designers select your named criteria from the JDeveloper Data Controls panel to create search forms for the web application. In the web page, the search form utilizes an ADF Faces query search component that will be bound initially to the named criteria selected in the Data Controls panel. At runtime, the end user may select among all other named criteria that appear in the Data Controls panel. Named criteria that the end user can select in a search form are known as developer-seeded searches. The query component automatically displays these seeded searches in its Saved Search dropdown list. For more information about creating search forms and using the ADF query search component, see Section 8.2, "Creating Query Search Forms."

Because developer-seeded searches are created in the data model project, the UI Hints page of the Edit View Criteria dialog lets you specify the default properties for the query component's runtime usage of individual named criteria. At runtime, the query component's behavior will conform to the selections you make for the following seeded search properties:

To create a seeded search for use by the ADF query search component, you select Show In List on the UI Hints page of the Edit View Criteria dialog. You deselect Show In List when you do not want the end user to see the named criteria in their search form.

In the Application Navigator, double-click the data control structure file that defines the named criteria you want to use as a seeded search.

In the overview editor, click the Named Criteria navigation tab.

On the Named Criteria page, select the named criteria that you want to allow in seeded searches and click the Edit icon.

In the Edit View Criteria dialog, click the UI Hints tab and ensure that Show In List is selected.

This selection determines whether or not the query component will display the seeded search in its Saved Search dropdown list.

Enter a user-friendly display name for the seeded search to be added to the query component Saved Search dropdown list.

When left empty, the named criteria name displayed in the Edit View Criteria dialog will be used by the query component.

Optionally, enable Query Automatically when you want the query component to automatically display the search results whenever the end user selects the seeded search from the Saved Search dropdown list.

By default, no search results will be displayed.

Optionally, set the Rendered Mode property for each view criteria item in order to determine whether the item is displayed for the user in basic mode or advanced mode.

Note:

When your named criteria includes an item that should not be exposed to the user, use the Rendered Mode setting Never to prevent it from appearing in the search form. For example, a named criteria may be created to search for products in the logged-in customer's cart; however, you may want to prevent the user from changing the customer ID to display another customer's cart contents. In this scenario, the named criteria item corresponding to the customer ID would be set to the current customer ID using a named bind variable. Although the bind variable definition might specify the variable as not required and not updatable, with the UI hint property Display set to Hide, only the Rendered Mode setting determines whether or not the search form displays the value.

Optionally, apply Criteria Item UI Hints to configure whether the query component renders individual criteria items when the end user toggles the search from between basic and advanced mode.

By default, all named criteria items defined by the seeded search will be displayed in either mode.

If a rendered criteria item is of type Date, you must also define UI hints for the corresponding bean attribute. Set the bean attribute's Format Type hint to Simple Date and set the Format Mask to an appropriate value, as described in the "Defining Attribute Control Hints for View Objects" section of the Oracle Fusion Middleware Fusion Developer's Guide for Oracle Application Development Framework guide. This will allow the search form to accept date values.

Click OK.

3.7 Testing Bean Metadata Using the Oracle ADF Model Tester

Before you start designing the views for your application, you can use the Oracle ADF Model Tester to test various aspects of your model. For example, if you have added validation rules or UI control hints to your model, you can test them before binding those objects to a page. Even after you have your UI pages constructed, the Oracle ADF Model Tester can assist you in diagnosing problems when they arise. You can reproduce the issues in the Oracle ADF Model Tester to discover whether the problem lies in the view or controller layers of the application, or whether there is instead a problem in the business service layer application module itself.

3.7.1 How to Run the Oracle ADF Model Tester

To test the metadata that you have defined in your data control, use the Oracle ADF Model Tester, which is accessible from the Application Navigator.

For EJB data controls, the tester only works on data controls for the remote session bean interface. If you created the data control based on the local bean interface, you need to add metadata for the remote bean interface to the DataControls.dcx file in order to use the tester. You can add metadata for the remote bean interface by right-clicking the session bean, choosing Create Data Control, and then selecting the Remote radio button in the Choose EJB Interface dialog.

When you later use the Data Controls panel to add bindings to pages, you will see high-level nodes for both the local and remote interfaces. Each node will contain identical hierarchies of data control collections that reference the same data control structure files. The only difference between the two hierarchies is in which session bean interface is referenced.

To test the bean metadata in your application:

In the Application Navigator, expand the project containing the desired data control.

Right-click the appropriate session bean and choose Run.

Wait for the application server to start and for the bean to be loaded on the server.

The Configure Default Domain dialog displays the first time your run your application and start a new domain in Integrated WebLogic Server. Use the dialog to define an administrator password for the new domain. Passwords you enter can be eight characters or more and must have a numeric character.

Alternatively, choose Debug when you want to run the application in the Oracle ADF Model Tester with debugging enabled. JDeveloper opens the debugger process panel in the Log window and the various debugger windows. For example, when debugging using the Oracle ADF Model Tester, you can view status message and exceptions, step in and out of source code, and manage breakpoints.

Table 3-1 gives an overview of the operations that the Oracle ADF Model Tester toolbar buttons perform when you display an entity bean.

Table 3-1 Oracle ADF Model Tester Toolbar Buttons

Button

Operation

Usage

Move to ... row

Changes the current row displayed by the Oracle ADF Model Tester. Moves to the first, previous, next, or last row.

Insert a new row

Creates and inserts a new row.

Delete the current row

Deletes the current row.

Save changes to the database

Runs the commit operation on any pending transactions. However, for EJB data controls, the changes are not actually committed to the database.

This button is only available when transactional methods are implemented on the session facade.

Discard all changes since last save

Discards any pending transactions and restores the original values.

This button is only available when transactional methods are implemented on the session facade.

Specify view criteria

Displays the View Criteria dialog that you can use to create and apply view criteria to the result set.

Validate row

Validates the current row by applying validation rules defined in the data control structure file. Disabled unless at least one field is editable.

3.7.2 How to Update the Oracle ADF Model Tester to Display Project Changes

When you are testing your data control, you can iteratively modify the data control and retest it without redeploying your whole model project. You can merely close and reopen the Oracle ADF Model Tester in order to reload changes that you have made to the data control structure files.

If you change Java code or any other files that are packaged in the model project JAR file, you also need to rebuild and redeploy that JAR to the internal application server.

To reload the data model metadata in the running Oracle ADF Model Tester:

In the Application Navigator, right-click the DataControls.dcx file and choose Run.

In the Oracle ADF Model Tester, test the data model and determine any changes you want to make.

In JDeveloper, make the desired changes to your project.

If you have made any changes to Java classes or any other artifacts that are part of the session bean's JAR file, rebuild the project. (For example, you can right-click the data model project in the Application Navigator and choose Rebuild. The rebuilt JAR file is then deployed to the server.)

If you have only made changes to data control structure files, you do not need to rebuild the project.

Close the Oracle ADF Model Tester.

In the Application Navigator, right-click the DataControls.dcx file and choose Run to reopen the tester with the updated metadata.

3.7.3 What Happens When You Use the Oracle ADF Model Tester

When you launch the Oracle ADF Model Tester, JDeveloper starts the tester in a separate process and the Oracle ADF Model Tester window appears. The tree at the left of the window displays all of the accessor returned collections in your data model. If the data model defines master-detail view instance relationships, the tree will display them as parent and child nodes. After you double-click the desired collection, the Oracle ADF Model Tester will display a data view page to inspect the query results. For example, Figure 3-6 shows the customerFindAll accessor returned collection that has been double-clicked to display the first record for this collection in the data view page on the right.

You can enter Query-by-Example criteria to find a particular row whose data you want to inspect. By clicking the Specify View Criteria button in the toolbar, the View Criteria dialog displays the list of available Query-by-Example criteria.

For example, you can select a view criteria like CustomerInfoCriteria and enter a query criteria like "H%" for a LastName attribute and click Find to narrow the search to only those users with a last name that begins with the letter H.

3.7.4 How to Test Business Layer Validation

Depending on the validation rules you have defined, you can try entering invalid values to trigger and verify validation exceptions.

In the tester, enter a value for an attribute and click the Validate Row icon.

For example, if you have defined a range validation rule for an attribute, enter a value outside that range, and click the Validate Row icon. You should see an error similar to following:

(oracle.jbo.AttrSetValException) Valid product codes are between 100 and 999

In the toolbar, click the Rollback button to revert data to the previous state.

3.7.5 How to Test Alternate Language Message Bundles and UI Hints

When your application defines alternative languages in your resource message bundles, you can configure the Oracle ADF Model Tester to recognize these languages. In the Oracle ADF Model Tester, you can then display the Locale menu and select among the available language choices.

Testing the language message bundles in the Oracle ADF Model Tester lets you verify that the translations of the data control UI hints are correctly located. Or, if the message bundle defines date formats for specific attributes, the tool lets you verify that date formats change (like 04/12/2007 to 12/04/2007).

To test named criteria and ad hoc query criteria using the Oracle ADF Model Tester:

In the Application Navigator, expand the project containing the desired data control and session bean.

Right-click the session bean, choose Run, and then wait for the bean to be deployed to the built-in application server.

Right-click the DataControls.dcx file and choose Run in order to start the Oracle ADF Model Tester.

In the Oracle ADF Model Tester, double-click the accessor returned collection that you want to filter.

Click the Specify View Criteria toolbar button to test the named criteria.

In the View Criteria dialog, perform one of the following tasks:

To test a named criteria that you added to a data control structure file in your project, shuttle that criteria to the Selected list and click Find. Any additional criteria that you enter in the ad hoc criteria section will be added to the filter.

To test ad hoc criteria attributes from a single named criteria row, enter the desired values for the named criteria and click Find.

For example, Figure 3-7 shows the filter to return all customers who possess a credit rating of POOR.

Figure 3-7 Oracle ADF Model Tester View Criteria Dialog

3.8 Groovy Language Support

Groovy is a scripting language with Java-like syntax for the Java platform. The Groovy scripting language simplifies the authoring of code by employing dot-separated notation, yet still supporting syntax to manipulate collections, Strings, and JavaBeans. Groovy language expressions are dynamically compiled and are executed at runtime. Any Groovy expressions that you create for an ADF application are stored in the data control structure files of the beans for which they are defined.

Oracle ADF supports the use of the Groovy scripting language in places where access to data control objects is useful, including attribute validators, attribute default values, transient attribute value calculations, bind variable default values (in named criteria filters), and placeholders for error messages (in validation rules). Additionally, Oracle ADF provides a limited set of built-in keywords that can be used in Groovy expressions.

Specifically, Oracle ADF provides support for the use of Groovy language expressions to perform the following tasks:

To perform these tasks in JDeveloper, you use expression editor dialogs that are specific to the task. For example, when you want to create a default value for a transient attribute, you use the attribute's Edit Expression Editor dialog to enter an expression that determines a runtime value for the attribute. The same dialog also lets you specify when the value should be calculated (known as a recalculate condition). Although expressions cannot be verified at design time, all expression editors let you test the syntax of the expression before you save it.

For more information about the Groovy language, refer to the following web site:

3.8.1 How to Reference ADF Objects in Groovy Expressions

There is one top-level object named adf that allows you access to objects that the framework makes available to the Groovy script. The accessible Oracle ADF objects consist of the following:

adf.context - to reference the ADFContext object.

adf.object.dataProvider - to reference the bean object on which the expression is being applied. Other accessible member names come from the context in which the Groovy script is applied.

Entity bean attributes and methods: The context is the bean's data control structure file. Through this object you can reference any attributes defined in the data control structure file as well as any attributes and methods that are inherited from the bean class.

adf.error - in validation rules, to access the error handler that allows the validation expression to generate exceptions or warnings

You can reference the current date (time truncated) or current date and time using the following expressions:

adf.currentDate

adf.currentDateTime

You can use the following built-in aggregate functions on rows of data:

rowSetAttr.sum(GroovyExpr)

rowSetAttr.count(GroovyExpr)

rowSetAttr.avg(GroovyExpr)

rowSetAttr.min(GroovyExpr)

rowSetAttr.max(GroovyExpr)

These aggregate functions accept a string-value argument that is interpreted as a Groovy expression that is evaluated in the context of each row in the row set as the aggregate is being computed. The Groovy expression must return a numeric value (or number domain).

3.8.2 How to Reference ADF Methods and Attributes in Groovy Expressions

The simplest example of referencing data control members, including methods and attributes that the bean and the bean's data control structure file define, is to reference attributes that exist in the same bean as the attribute that you apply the expression.

For example, you could define a Groovy expression to calculate the value of a transient attribute AnnualSalary on a bean with an attribute Sal that specifies the employee's monthly salary:

Sal * 12

Or, with Groovy you can write a simple validation rule to compare the attributes of a single data control structure file using syntax like:

Note that the current object is passed in to the script as the this object, so you can reference an attribute in the current object by simply using the attribute name. For example, in an attribute-level or entity-level Script Expression validator, to refer to an attribute named "HireDate", the script can simply reference HireDate.

Similar to referencing attributes, you can invoke methods as part of your expression. For example, to define an attribute default value:

adf.object.dataProvider.getDefaultSalaryForGrade()

A method reference requires the prefix adf.object.dataProvider, which allows you to reference the same entity that defines the attribute on which the expression is applied.

Note that when you want to reference the method of an entity bean in a validation rule, you use source instead of object.

adf.source.dataProvider.getDefaultSalaryForGrade()

Use of the source prefix is necessary in validators because the object keyword implies the validation rule object instead of the entity bean where the method is defined.

To allow you to reference members of the validator object (JboValidatorContext), you can use these keywords in your validation rule expression:

newValue: in an attribute-level validator, to access the attribute value being set

oldValue: in an attribute-level validator, to access the current value of the attribute being set

For example, you might use the following expression to specify a dynamic validation rule check of the salary for a salesman.