Introduction to ADF Security in JDeveloper 10.1.3.2

An Oracle JDeveloper Article
Written by Frank Nimphius, Oracle Corporation
February, 2007

Introduction

Oracle Application Development Framework (ADF) is Oracle's JSR-227 compliant implementation of a generic binding layer for applications that follow the J2EE Model-View-Controller architecture. ADF Security is a key feature of the Oracle ADF binding layer. ADF Security allows developers to declaratively define fine-grained access control to iterators, attributes, and methods exposed by a business services. The goal of ADF Security is to ease and promote secure application development based on standard J2EE security features and the Java Authentication and Authorization Service (JAAS).

Don't put all your eggs into one basket

The defense-in-depth security design pattern demands that application developers implement application security with multiple lines of defense. A typical J2EE application has a minimum of four application layers that can be used to implement security in depth. The layers in the security-in-depth approach behave as follows:

  • The View layer - enforces web authentication and provides field authorization and validation. An authorization strategy performed on the view layer might hide input fields or command components that a user is not allowed to use or it might render components as read only if the authenticated user does not have sufficient update privileges.
  • The Controller - authorizes page to page navigation. Navigation in JavaServer Faces is handled by the NavigationHandler, which in the reference implementation (RI) cannot be extended and modified. To implement authorized page navigation, developers must create their own secure NavigationHandler, use a PhaseListener that checks page access privileges within the request lifecycle, or rely on an underlying application layer to enforce authorization.
  • The Business Service - ensures that business logic is executed in the context of the authenticated user. The security implementation details of the business service varies with the technology (for example, EJB, POJO, ADF Business Components, web services, etc).
  • The Persistence layer - usually the relational database. Database security features can be leveraged with J2EE applications if the authenticated user identity is propagated from the client to the server. A few Oracle database features commonly used in J2EE applications include Virtual Private Database (VPD), Database proxy users, and Enterprise User Security (EUS).

With the Oracle Application Development Framework (ADF), an additional layer, the binding layer, is added to the J2EE application architecture. The ADF binding layer is located between the view/controller layers and the business service.

Multi layer Security in Oracle ADF
Figure 1: ADF web application security architecture

This article outlines how application developers define security on the ADF binding layer using the ADF Security framework. More in-depth technical information about ADF Security is available in the Oracle WebCenter Framework Developer's Guide.

Container-Managed Security in OC4J (Oracle Containers for J2EE)

ADF Security leverages the JAAS security provider (JAZN) in Oracle OC4J for authentication and authorization. JAZN implements container-managed J2EE security in OC4J and is the default policy provider for JAAS (Java Authentication and Authorization Service).

Figure 2: ADF Security authentication and authorization architecture in OC4J

One of the advanced features in OC4J security is the ability to use JAAS authorization with J2EE container-managed authentication. Using this option, applications can authorize user interaction based on URL patterns and Java Permissions. ADF Security runs within OC4J as part of the Oracle ADF runtime libraries and leverages JAAS for authorization to implement fine-grained access control.

ADF Security

ADF Security is a JAAS-based security framework in Oracle ADF that works with all business services. ADF Security requires the Oracle JAAS (JAZN) security provider in Oracle Application Server and OC4J and integrates with Oracle Single Sign-On and Identity Management. User authentication is performed with J2EE container-managed security while access control is through JAAS. During development and testing, ADF Security is configured in system-jazn-data.xml file of the embedded OC4J server in Oracle JDeveloper. The system-jazn-data.xml file is the configuration repository of the JAAS XML provider in OC4J and contains user accounts, user groups, and the ADF Security-generated JAAS permissions. After deployment to OC4J or Oracle Application Server, the security provider can be changed to Oracle Internet Directory (OID), an LDAP v3 compliant directory server.

ADF Security by Example

How ADF Security works at design time and runtime is best explained by a simple example. In this example, the following security policies will be applied to an ADF Faces web application:

  1. All users must be authenticated to work with the example application.
  2. Only the CEO is allowed to create new Departments.
  3. Managers and CEOs can update Departments.
  4. Managers are not allowed to update the Department ID.
  5. All navigation controls are hidden from the user if the user is not authorized to perform the action.
Figure 3: Example application navigation flow

Note that a security best practice is to apply protection to an application during development and not after the fact.

Enabling ADF Security for a Web application

The ADF Security framework is a feature of Oracle ADF since JDeveloper 10.1.3.0. New functionality added in JDeveloper 10.1.3.2 includes the ADF Security wizard that guides developers through the configuration of ADF Security for web applications based on ADF Faces and the ADF binding layer.

Figure 3: Authentication configuration


The first step in the ADF Security wizard defines authentication and authorization for the web application. Authorization is enforced with JAAS, which is enabled by selecting the Enforce Authorization checkbox. Not selecting this option only sets up authentication.

The Redirect Upon Successful Authentication option specifies a page that the authenticated user is redirected to after login. Using this feature, developers enforce a defined entry to an application, independent of the page requested by the user. The Browse button allows the developer to browse the current web project to select a source file that represents the start of the application.

Note: ADF Security may also be configured for web applications built with JSP and Struts. In contrast to JSP applications, that are accessed relative from the J2EE context, JavaServer Faces applications require the Faces Servlet mapping to be part of the requesting URL to ensure a JavaServer Faces context exists. The Faces Servlet mapping "faces/" is not added by the ADF Security wizard and must be added manually in front of the selected page as shown in the image above.

Authentication in ADF Security is enforced through a Servlet that is configured as adfAuthentication in the web.xml deployment descriptor. The servlet is protected by a J2EE security role in which all authorized application users are a member. Using the OC4J role " anyone " ADF Security allows developers to grant access to unauthenticated users, which is useful to maintain public pages and to enforcing lazy authentication.

Figure 5: JAAS provider selection

ADF Security supports both JAZN file-based security and the LDAP security provider for authentication and authorization. For application development the Lightweight XML Provider is the default. Note that selecting the LDAP Provider option in the wizard does not connect to the Oracle Internet Directory instance but configures the JAZN application deployment descriptor ( orion-application.xml) with the realm name and host location of the LDAP instance. The default lightweight XML provider reads its security definitions from system-jazn-data.xml, which at design time is located in JDeveloper_Home\jdev\system\oracle.j2ee.10.1.3.40.66\embedded-oc4j for development and testing.

Figure 6: Configuring the XML based Provider

If authorization is enforced for web applications, the repository location must be chosen as OC4J Default Repository, which points to the system-jazn-data.xml file in the OC4J configuration. The default realm in OC4J is jazn.com. A realm is comparable to a namespace that associates users and groups to a specific security policy. Setting the JAAS Mode to doAsPrivileged enforces permission checks to be performed against the Java permissions generated by the ADF Security design time for ADF iterator, attribute and control bindings. JAAS allows finer-grained authorization than standard J2EE container-managed security constraints defined on URL patterns.

Figure 7: J2EE authentication dialog

ADF Security uses J2EE container-managed authentication with one of the following authentication types: Basic Authentication, Digest Authentication, Forms-Based, Client Certificate.

If selecting Form-Based Authentication, an HTML file or a JSP file is required to define the login page and the error page. The login page contains an HTML form with the action attribute set to j_security_check and two input text fields: j_username and j_password. J2EE containers understand that the j_security_check action is used to perform J2EE authentication.

The Generate Default option generates two HTML files: login.html and error.html in the web application public_html directory. The login.html contains a HTML form element with the required j_security_check action and the j_username and j_password fields. To create files with a file name other than login.html, deselect the Generate Default option and click Browse to locate the desired file name. The files are created when finishing the ADF Security wizard.

If an ADF Faces application is configured to use the JAZN XML provider, then authentication is performed against user accounts defined in the system-jazn-data.xml file. If the LDAP provider is configured, then the authentication realm and user accounts are looked up in OID.

Figure 8: Creating and managing J2EE security roles in web.xml

J2EE security roles are defined in the web.xml deployment descriptor and mapped to users and groups in the system-jazn-data.xml file. If the role name in web.xml matches a group name in system-jazn-data.xml, no further mapping is required. If the names do not match, then the web.xml role name needs to be mapped to the name in the system-jazn-data.xml using the orion-application.xml file. The orion application file is automatically created and deployed with the J2EE application. Though it is possible to edit the web.xml deployment descriptor outside of the ADF Security wizard, it is recommended to use the wizard to configure user access to the ADF Security authentication servlet.

Finishing the ADF Security wizard writes the configuration information to the web.xml deployment descriptor and the orion-application.xml file.

Figure 9: ADF Security configuration in web.xml and orion-application.xml

Within the web.xml deployment descriptor, the ADF authentication servlet is created with a success_url initial parameter. The success_url contains the name of the application start page defined by setting the Redirect Upon Successful Authentication option as shown in Figure 3.

Configuring the embedded OC4J

The embedded OC4J J2EE container has its bootstrapping configuration files located in the JDeveloper_Home\jdev\system\oracle.j2ee.10.1.3.<version>\embedded-oc4j\config directory. The configuration file used for ADF Security development and testing in Oracle JDeveloper is system-jazn-data.xml. The system-jazn-data.xml is an XML-based security repository for Oracle JAAS and contains user accounts and passwords, user groups, and ADF Security JAAS permissions.

To configure the system-jazn-data.xml file for ADF Security from the Oracle JDeveloper IDE, choose the Tools | Embedded OC4J Server Preferences menu option.

Figure 10: Embedded OC4J configuration dialog

To configure ADF Security, the user and group accounts need to be created under the Global node. The jazn.com default realm also contains the OC4J administration accounts and for this reason is pre-defined in the system-jazn-data.xml file. For this how to example, three users sking , ahunold and dfaviet are created and assigned to the application roles users , managers and ceo.

The authentication servlet is protected using the same role names in the web.xml file, granting access to all user roles. If the role names configured in jazn-data.xml differ from the names used in web.xml, then the orion-application.xml file needs to be edited to map web.xml role names to system-jazn-data.xml roles as documented in the OC4J security guide. In this example, the names are the same and thus no extra configuration is needed.

Defining Authorization

Authorization in ADF Security is defined through Java Permissions. The application developer defines authorization declaratively for iterator bindings, action bindings, and method bindings defined in the ADF page definition ( pageDef.xml) file and, alternatively, for the entire page definition itself.

Figure 11: Authorization dialog for iterator bindings

A context menu option Edit Authorization on all bindings that can have authorization defined. The Authorization editor dialog shows all possible actions for the developer to identify which user roles are allowed to perform which actions. In JDeveloper 10.1.3.2 an application either has security configured or it doesn't. This means that if ADF Security is enabled for a web application, all ADF bindings must have grants configured. All security grants are written as permissions to the system-jazn-data.xml file. With ADF Security, the application developer doesn't need to understand how to implement JAAS to develop secure web applications. For deployment, the application specific permissions are defined in the app-jazn-data.xml file that is deployed with the EAR file. The deployment of web applications protected by ADF Security is explained later in this document.

<grant>
  <grantee>
    <principals>
      <principal>
        <realm-name>jazn.com</realm-name>
        <type>role</type>
        <class>oracle.security.jazn.spi.xml.XMLRealmRole</class>
        <name>managers</name>
      </principal>
  </principals>
  </grantee>
    <permissions>
      <permission>
         
<class>oracle.adf.share.security.authorization.RowSetPermission</class>
          <name>AppModuleDataControl.DepartmentsView1</name>
          <actions>read,update</actions>
      </permission>

  </permissions>
</grant>
Example 1: Permissions defined in system-jazn-data.xml

Note: It is important to define authorization for the PageDef.xml files in the web application. Users need to have view privileges to access a JavaServer Faces page. Defining grants on the PageDef.xml file permits developers to set up page-level authorization, a security feature otherwise not available in JavaServer Faces.

Programmatic access control with ADF Security

Developers may need to access user permissions programmatically in their applications for example to hide or to show UI components that execute protected actions or perform navigation. Programmatic access control can be used to implement the 5th security policy in the sample application mentioned above: "All navigation controls are hidden from the user if the user is not authorized to perform the action".

Access through ADF Bindings

ADF Security sets the updateable flag on ADF attribute bindings and action bindings. If, for example, a user is not authorized to update the data displayed in a table, then the table binding's updateable property is automatically set to false. This information can be used with Expression Language to set the disabled property on a command button, as shown in the image below.

Figure 12: Disabling a command button through the updateable flag on the attribute binding
Access through Expression Language using the PermissionInfo object

The PermissionInfo object on the ADF Security Context allows access to ADF Security through Expression Language and Java. The PermissionInfo object is not shown in the Oracle JDeveloper Expression Language editor even though it exists on all binding types. The example of the disabled command button above can also be implemented with the PermissionInfo object as shown below:

#{!bindings.DepartmentsView1.permissionInfo.update}

The general use of PermissionInfo in Expression Language is

#{bindings.<iterator_binding>.permissionInfo.<read|create|delete|update>}
#{bindings.<method_binding>.permissionInfo.invoke}
#{bindings.<attribute_binding>.permissionInfo.<update|view>}

In addition, the PermissionInfo object allows developers to access information from a binding container other than the current one. This is useful to handle page authorization. In the sample application, the create button should only be enabled for managers and CEOs. In the policies defined for the sample application, a rule states that if the authenticated user is not allowed to view the EditCreateDepartmentsPageDef the Create button should be disabled. The Expression Language string that needs to be added to the command button Disabled property is:

#{!bindings.permissionInfo['EditCreateDepartmentsPageDef'].view}

Figure 13: Disabling command buttons based on different user privileges
Access control through calls to hasPermission()

It is also possible to directly check a specific permission grant using the hasPermission() method on the ADF Security Context. In this case the developer is aware of the permission names and actions defined in the system-jazn-data.xml. The example below executes a create operation only if the authenticated user is granted create on the RowSetPermission for the AppModuleDataControl.DepartmentsView1 iterator.

public String createDepartmentsAction() {
 final FacesContext fc = FacesContext.getCurrentInstance();
 final Application fapp = fc.getApplication();
 //get binding
 OperationBinding obind = (OperationBinding) fapp.createValueBinding("#{bindings.CreateDepartment}").getValue(fc);

 if ( ADFContext.getCurrent().getSecurityContext().hasPermission(new RowSetPermission("AppModuleDataControl.DepartmentsView1","create"))){
  obind.execute();
  
if (obind.getErrors() == null || obind.getErrors().size()==0){
   return "editDepartments";
   }
  }
 return null;
 }

Note that using the hasPermission() method for access authorization bears the risk that later changes in the ADF Security permission classes will require modification of the application code. To avoid this dependency on physical implementation classes, the PermissionInfo object exists and should be used. The hasPermission() method makes sense to be used with custom permission classes.

ADF Faces security aware components

ADF Faces components, like af:inputText, are security-aware in that they render read-only if a user is not authorized to update the underlying ADF attribute binding. In the sample policy, rule 4 states that "Managers are not allowed to update the Department ID". The attribute authorization for the DeptId is set on the ADF binding layer through the pagedef.xml file so that managers have no update privilege. The image below shows the form rendering of the EditCreateDepartments.jspx page when i) connecting as a manager and ii) when connecting as the CEO.

Figure 14: Security aware ADF Faces components shows i) read-only text field for unauthorized user and ii) editable text field for authorized user

 

ADF Security Deployment

ADF Security is deployed by configuring the JAZN security provider of the target system with the Java security permissions created during web application development. In a deployment to the file-based provider, the Java Permissions need to be added manually to the system-jazn-data.xml file of the target OC4J instance. In a deployment that uses the Oracle Internet Directory (OID) as the security provider, the security permissions need to be uploaded to OID. The upload is handled through ldiff files, which is a specific file format for updating LDA entries using the ldapadd or ldapmodify command. A utility that migrates jazn-data.xml file entries to ldiff is provided with OC4J and documented in Chapter 7: File-Based Security Provider of the Oracle Containers for J2EE Security Guide.

Figure 15: ADF Security entry in OID

app-jazn-data.xml

The app-jazn-data.xml file is located in the .adf\META-INF folder under the Oracle JDeveloper workspace root folder and is deployed with the application. The JDeveloper_Home\jdev\system\ oracle.j2ee.10.1.3.<version>\embedded-oc4j\config\system-jazn-data.xml file that is used to store the Java Permissions during development is not empty but contains permissions and user accounts needed to run OC4J.

To make ADF Security deployment easier, the app-jazn-data.xml file contains only those Java Permissions of the system-jazn-data.xml file in Oracle JDeveloper that are added by ADF Security. Deploying the app-jazn-data.xml file with the application makes the security definitions available to the system administrator who sets up ADF Security for the production runtime.

To set up ADF Security for the file-based provider, the system administrator copies the user group and permission entries to the system-jazn-data.xml file of the target OC4J instance.

To set up the LDAP provider with ADF Security, the administrator uses the JAZN migration utility to create an ldiff file out of the app-jazn-data.xml file. The ldiff file then is used to configure OID through the ldappadd or ldapmodify command as documented in the OC4J Security Guide.

Summary

ADF Security is a protection framework in Oracle ADF to authorize user access to iterator bindings, action bindings, and attribute bindings. ADF Security implements application security independent of the business service layer and works with EJB, POJO, ADF Business Components, and web services alike.


For further documentation see

Chapter 8: WebCenter Framework Tutorial
Chapter 7: File-Based Security Provider
Chapter 8: Oracle WebCenter Framework Developer's Guide

false ,,,,,,,,,,,,,,,