# Oracle9iAS Portal Developer Kit (PDK)
Understanding the Provider Framework

Creation Date: | July 2, 2001
Status: | Production
Version: | PDK Release 2, (9.0.2 and later)

## Introduction

To the Oracle9iAS Portal, a Web Provider is a server-side Web application that responds to a well defined set of HTTP requests. The requests can be classified as either administrative or runtime. Administrative requests are used to obtain information about the Web Provider and its portlets or to instruct it to perform an administrative operation such as registering a new portlet instance. The runtime requests are those that are issued when the portal needs to render a portal page containing portlets.

The PDK is a Java framework that understands all these requests and provides an architecture that exposes the functionality of a Web Provider in a natural way. The PDK includes the following major components

- The Provider Adapter handles the mechanics of processing the HTTP requests and translating them into simple Java method calls.

- The Provider Runtime defines the methods that a Web Provider must support in order for it to work with the Provider Adapter. The runtime also provides an implementation that allows you to create a provider with the minimum of effort.

- The Provider Utilities are a collection of utilities to simplify the common functions you need when building portlets.

This article describes these components and the primary Java classes you will be working with. Understanding these components and the Java classes they are comprised of will help when you create your own Web Providers or read other articles about using the PDK framework. It will also provide a springboard for learning more about the powerful features available as part of the PDK framework.

## Provider Adapter

As previously mentioned, the Provider Adapter handles the processing of the HTTP requests and translates them into Java method calls. As such, the adapter is essentially a black box that developers never need to delve into. In PDK Release 2 (9.0.2 and later), there is now a clean separation between the code that implements the Provider Adapter and the Provider Runtime. Consequently, the implementation of the Provider Adapter is considered "private" to the PDK framework and the details of its implementation are not exposed to developers in PDK articles or JavaDoc.

## Provider Runtime

The Provider Runtime is a set of classes that together form a structure within which developers can work when building Web Providers. The Provider Runtime can be broken down into two layers:

- interface definition
- implementation

### Interface Definition Layer

The interface definition layer consists of a set of abstract classes and Java interfaces that provide the foundation for the interaction between the Provider Adapter and the Provider Runtime. This foundation layer also determines the basic relationships and interactions between the Java classes that comprise the Provider Runtime. In most cases there are only one or two methods that are actually abstract, the rest have fully functional implementations. The UML class diagram below shows the major components of the interface definition layer.

#### oracle.portal.provider.v2.ProviderLoader

ProviderLoader is the starting point for all interaction between the Provider Adapter and the Provider Runtime. Whenever a request is received, the first thing the Provider Adapter must do is locate the ProviderInstance that the request is intended for. It is the job of the ProviderLoader to locate the correct ProviderInstance (based on the provider ID in the request) from its cache or to create a new ProviderInstance if one does not exist in the cache. In order to create a new ProviderInstance, a ProviderDefinition is required. The ProviderLoader is also responsible for loading, creating or refreshing the ProviderDefinition. Consequently, by extending ProviderLoader, you can control the source of the provider metadata and potentially change the source of the data without impacting the rest of the provider. For example, you may start off by using the DefaultProviderLoader and sometime later decide that you need more flexibility to maintain a large number of providers so you create a ProviderLoader that reads the metadata from a database.

#### oracle.portal.provider.v2.ProviderDefinition

ProviderDefinition encapsulates the metadata that describes your provider. The metadata includes any provider level settings such as the default container renderer to be used for the portlets and PortletDefinitions for each of the portlets managed by your provider.

#### oracle.portal.provider.v2.PortletDefinition

Like its counterpart, ProviderDefinition, PortletDefinition encapsulates the metadata that describes a single portlet. This includes the name and description. The PortletDefinition also includes definitions of the input parameters a portlet requires and the events it generates. Input parameters and events are a key part of the new parameter passing functionality introduced in Oracle9iAS Portal 9.0.2. For a detailed description of input parameters and events, refer to the white papers published on Portal Studio

#### oracle.portal.provider.v2.ProviderInstance

A ProviderInstance represents a specific instance of your provider as registered with a specific portal. ProviderInstance and its counterpart, PortletInstance are the primary interfaces for interaction between the Provider Adapter and the Provider Runtime. ProviderInstance includes all the methods needed to handle all the provider level administrative requests. Requests that must be handled at the portlet level also begin in the ProviderInstance with a request for an appropriate PortletInstance. Once the Provider Adapter has an appropriate PortletInstance, the portlet level request is directed to that PortletInstance. ProviderInstance provides a complete implementation of all the methods so you should not need to change or extend this class.

#### oracle.portal.provider.v2.PortletInstance

A PortletInstance represents a specific instance of a portlet. That is a specific portlet, in a specific location on a specific portal page. PortletInstances handle the portlet level requests that are received from a portal such as rendering, security and personalization. This is an abstract class that includes implementations for some of the methods, but not all of them. For example, the rendering method is not implemented. If you want to use the rendering, personalization and security frameworks that are included with the PDK Release 2 (9.0.2 and later) you should use or extend the DefaultPortletInstance class. These frameworks provide extensive support in each area and it is recommended that you leverage them until you become more familiar with the PDK.

If you do not want to use the rendering, personalization and security frameworks that are included with the PDK, you can simply extend PortletInstance to provide your own implementations or leverage other frameworks you are familiar with.

The PortletInstance class that ultimately gets used is determined by the portlet metadata. For example, DefaultPortletDefinition defaults the PortletInstance implementation to DefaultPortletInstance, but this can be overridden by specifying a different PortletInstance implementation class in the portlet metadata

#### oracle.portal.provider.v2.preference.PreferenceStore

A Preference Store is a generic mechanism for persisting preference data, portlet/provider settings or even portlet data. PreferenceStore is an abstract class and there are 2 implementations, one for file system persistence and a second for database persistence. The PreferenceStore classes also provide the basis for the PrefStorePersonalizationManager described in the Personalization Section of this document.

#### oracle.portal.provider.v2.render.PortletContainerRenderer

PortletContainerRenderer is a rendering utility that can be used to render the headers and footers for portlets. This class is included in this section because a ProviderDefinition includes a reference to a default PortletContainerRender that is used if a PortletDefinition does not provide its own.

### Implementation Layer

Each of the primary classes in the Interface Definition Layer has a corresponding "default" implementation class that supplies implementations for any abstract methods and also adds methods to support the following:

- declarative definition of Providers and Portlets via an XML file
- rendering framework to simplify portlet rendering
- personalization framework to support portlet personalization
- security framework to support portlet security

The implementation layer is often referred to as the "default" implementation because it is just a starting point that you can extend to support your own requirements or replace either partially or completely. In reality, the "default" implementation is fully featured and few developers find it necessary to extend the framework in any significant manner. The diagram below shows the Implementation Layer added to the Interface Definition Layer.

#### oracle.portal.provider.v2.http.DefaultProviderLoader

DefaultProviderLoader is an implementation of ProviderLoader that reads provider metadata from an XML based provider definition file

#### oracle.portal.provider.v2.DefaultProviderDefinition

DefaultProviderDefinition is an extension of ProviderDefinition that allows your provider to be defined declaratively using a provider definition file (provider.xml).

#### oracle.portal.provider.v2.DefaultPortletDefinition

DefaultPortletDefinition is an extension of PortletDefinition that allows you to declaratively define a portlet using an XML based provider definition file. The DefaultPortletDefinitions lets you use the rendering, personalization and security managers that are included with the PDK. The UML class diagram below shows how the rendering, personalization and security frameworks are related to the DefaultPortletDefinition.

#### oracle.portal.provider.v2.DefaultPortletInstance

DefaultPortletInstance completes the implementation of PortletInstance, using the familiar PDK frameworks for rendering, personalization and security. These frameworks are described in the following sections.

### Rendering Framework

The Rendering classes of the Provider Runtime make it easy to create a portlet that uses a variety of different techniques to render content. For example, the Help and About pages may be rendered as static HTML, the Show modes may be JSPs and the Customization pages may be Servlets. This UML class diagram below shows the major classes in the Rendering Framework.

#### oracle.portal.provider.v2.render.RenderContext

RenderContext contains all the generic information you need to render a portlet including the Show mode, rendering hints etc.

#### oracle.portal.provider.v2.render.PortletRenderRequest

PortletRenderRequest wraps a RenderContext, adding information that is needed by the PortletRenderer and its subclasses.

#### oracle.portal.provider.v2.render.PortletRenderer

PortletRenderer is a simple abstract class that defines a single method for rendering a portlet. Any class that extends PortletRenderer can be used as a renderer for a portlet.

Note: The single rendering method is called for all render modes and it is up to the final implementation to determine the correct mode to render based on the render mode from the RenderContext.

#### oracle.portal.provider.v2.render.RenderManager

RenderManager is an extremely flexible implementation of PortletRenderer that lets you associate a different ManagedRenderer with each combination of portlet show mode and content type that your portlet supports. This model lets you:

- choose the most appropriate renderer for each render mode. e.g. you might want to use ResourceRenderer for your portlet's "show" mode and FileRenderer for "help" mode
- provide multiple renderers for each portlet show mode/content type combination. For example, if you need to support users accessing your web provider from both regular web browsers and mobile devices (such as cell phones or hand-held computers that are Internet enabled) your portlet might have 2 renderers defined for its "show" mode - one generating HTML and the other generating Oracle's mobile XML. When a request is received, RenderManager will automatically select the correct renderer based on the render mode and the preferred content type.

#### oracle.portal.provider.v2.render.ManagedRenderer

ManagedRenderer is an abstract class that any pluggable renderer must extend in order to be used with RenderManager

#### oracle.portal.provider.v2.render.http.BaseManagedRenderer

BaseManagedRenderer is an extension of ManagedRenderer that adds common functionality required by many pluggable renderers such as information about the page's content type and cache expiry time. These may be set via calls to the appropriate methods or declared at page level in a provider definition file using the <contentType> and <pageExpires> tags.

#### oracle.portal.provider.v2.render.http.ResourceRenderer

ResourceRenderer is a new renderer introduced in PDK Release 2 ( 9.0.2). This pluggable renderer can be used to render any type of resource (static HTML page, JSP, Servlet, XML file etc.) simply by specifying a relative URI to the resource. The URI should be specified from the root directory of the WAR file in which the web provider is deployed.

#### oracle.portal.provider.v2.render.http.FileRenderer

FileRenderer is a pluggable renderer that can be used to render static content such as HTML or XML files. Even though static content can be rendered using the ResourceRenderer, FileRenderer adds two important functions that is not available in the ResourceRenderer. Those functions are:

- ability to read static content in any character set supported by Java. This allows you to correctly render files that were written using multibyte character sets such as UTF-8 and Shift-JIS (a common Japanese character set).
- ability to cache the file in memory so subsequent requests for the same content can be served very quickly.

#### oracle.portal.provider.v2.render.PortletContainerRenderer

This utility was created to render a portlet container, that is the portlet header and footer. Depending on the mode being rendered, the header/footer may vary. This class provides methods for rendering the header/footer for each mode and it is designed so the parameter list is variable allowing different implementations to use different sets of parameters as needed. A PortletContainerRenderer can be associated with an individual portlet or the provider. The PDK will first look to the Portlet to use its PortletContainerRenderer and then fall back to the Provider if necessary. There are 3 implementations of this class that render slightly different containers. Each is described below.

#### oracle.portal.provider.v2.renderer.DefaultContainerRenderer

DefaultContainerRenderer renders portlet containers that match the current release of Oracle Portal. If the style of the portlet container changes in a particular release of Oracle Portal, this class will be updated to reflect that change and a new container renderer will be created to provide backwards compatibility for those who want to continue using the older style.

#### oracle.portal.provider.v2.renderer.MocContainerRenderer

MocContainerRenderer renders portlet containers that match those used on Oracle's publicly accessible portal "my.oracle.com". If the style of containers used on my.oracle.com changes, this renderer will be updated to reflect that change and a new container renderer will be created to provide backwards compatibility for those who want to continue using the older style.

#### oracle.portal.provider.v2.renderer.ContainerRenderer306

ContainerRenderer306 renders portlet containers that match those used in the 3.0.6 release of Oracle Portal.

### Rendering Utilities

The following classes include utilities to assist with the rendering of a portlet.

#### oracle.portal.provider.v2.render.PortletRendererUtil

This is a collection of useful utilities for rendering including manipulating URLs, generating forms with hidden fields based on URLs and many others. Many of the methods in this class are now deprecated so please take note of deprecation notices and use the suggested alternatives. For example, container rendering utilities have been moved to PortletContainerRenderer and its subclasses.

#### oracle.portal.provider.v2.render.http.HttpPortletRendererUtil

Rendering utilities that directly access or use access to HTTP or Servlet related objects. Generally, the PDK provides an abstraction to hide the underlying implementation from developers. However, for some functionality, the HTTP layer must be exposed.

### Preference Store and Personalization Framework

A Preference Store is a generic mechanism for persisting preference data, portlet/provider settings or even portlet data. The preference store implementations included with the PDK allow you to persist your data to either a file system or a database. Irrespective of the underlying storage mechanism, the API you use to access the preference store is identical and is defined by the PreferenceStore abstract class. The personalization framework utilizes the functionality of a Preference Store to persist the data associated with the Edit Defaults and Customize functions of your portlets.

####
oracle.portal.provider.v2.preference.PreferenceStore

#### PreferenceStore is an abstract class that defines the basic behavior of a Preference Store, but does not implement the methods to read/write data .
oracle.portal.provider.v2.preference.FilePreferenceStore

FilePreferenceStore is the file system implementation of PreferenceStore. In this implementation, data is persisted to the local file system.

#### oracle.portal.provider.v2.preference.DBPreferenceStore

DBPreferenceStore is the database implementation of PreferenceStore. In this implementation, data is persisted to a database table.

#### oracle.portal.provider.v2.personalization.PortletPersonalizationManager

PortletPersonalizationManager defines the methods a personalization manager must support.

#### oracle.portal.provider.v2.personalization.PrefStorePersonalizationManager

PrefStorePersonalizationManager is an implementation of the PersonalizationManager interface that uses a Preference Store to persist data. The Preference Store may be either a FilePreferenceStore or a DBPreferenceStore depending on where you want to persist your data. A PrefStorePersonalizationManager that uses a FilePreferenceStore is compatible with the FilePersonalizationManager from PDK Release 1( 3.0.9). Similarly, a PrefStorePersonalizationManager that uses a DBPreferenceStore is compatible with a DB2PersonalizationManager from PDK Release 1 (3.0.9).

### Security Framework

The Security Classes provide a hook for implementing portlet level security.

####
oracle.portal.provider.v2.security.PortletSecurityManager

PortletSecurityManager is a simple interface that the framework uses to access Security Managers.

#### oracle.portal.provider.v2.security.AuthLevelSecurityManager

AuthLevelSecurityManager is an implementation of the PortletSecurityManager interface that uses a user's authentication level to control access. A user will be granted access to a portlet if his/her authentication level is greater than or equal to the security level that has been specified for the security manager.

### URL-Based Portlets

As an alternative to writing portlets from scratch, existing applications written in any language may be integrated with a Portal via a web provider with only a small amount of configuration work using URL-based portlets. The only requirement is that the application must be accessible via a URL. Having set up a provider definition file to refer to the required application, the provider is registered in the same way as a normal provider. When the portlet receives a "SHOW" request the application content is retrieved from the URL, filtered to remove unwanted content and displayed in the form of a portlet. For example, the article 'How to Build a URL-Based Portlet with HTML Filtering' describes how to link to the Google.com website and filter out everything except the search form itself.

If the remote application requires authentication it must be configured as a Partner Application or External Application within the Portal. Partner Applications share the same Single Sign-On Server as the Portal and External Applications have their own authentication mechanism (which may be also be a Single Sign-On Server, but not the same one used by the Portal).

The following articles describe the structure of the code and give examples describing how to use URL-based portlets.

Understanding the PDK Runtime for URL-Based Portlets

Understanding the provider.xml for URL-Based Portlets

How to Build a URL-Based Portlet with HTML Filtering

How to Build a URL-Based Portlet that uses XML Filtering

### Caching

Caching is used to speed up the response time of a web provider. Three sorts of caching are supported.

Expires based caching is used to cache portlet content in the middle-tier file cache for a fixed length of time. The methods used to set the appropriate response headers are contained in the class HttpPortletRendererUtil. Normally, portlet code is not expected to call these methods directly as the use of expires based caching may be configured in the provider definition file. This is a suitable means for caching content that is static, that changes very rarely or that changes at a predictable time interval. The use of expires based caching is demonstrated by the sample provider portlet, 'Expires Sample'.

Validation, or ping-based, caching causes content to be cached in the middle-tier file cache, but each time the content is requested from the cache a request is sent to the originator of the content to determine if the cached content is still valid. If the content is still valid, then the cached copy is used, otherwise the originator generates a new, up-to-date, copy of the content. The new content then replaces the old or stale content in the cache. Even though the originator of the content has to be contacted with each request, performing a simple validation check is much faster then generating content and returning content. This caching approach is generally used where the content is dynamic or changes unpredictably. Validation caching is demonstrated by the sample provider portlet. 'Validate Sample'.

Invalidation based caching is essentially expires based caching, with the added ability to "expire" or "invalidate" the contents of the cache at any time. Invalidation of cache content is usually triggered by some kind of "event" taking place. This form of caching uses an Oracle Web Cache instance installed in front of the provider to cache portlet content.

This is a very efficient way to cache content because the originator of the content, the web provider, only gets contacted when new content needs to be generated, but you are not bound to a fixed regeneration schedule.

The methods for caching portlet content are once again contained in HttpPortletRendererUtil and under normal circumstances would not be called directly by portlet code since it may be configured in the provider definition file. To actually invalidate the content, the invalidation API is used.

####
oracle.portal.provider.v2.cache.invalidation.ServletInvalidationContextFactory

This class generates an instance of a ServletInvalidationContext implementation class. Portlet code should then use this reference to create invalidation requests. The implementation class returned is of type WebCacheInvalidationContext, although the factory class could be extended to return other class types in the unlikely event that some other form of invalidation caching is implemented.

#### oracle.portal.provider.v2.cache.invalidation.InvalidationContext

This abstract class contains the methods used to set up and send an invalidation request. The content to be invalidated is controlled by setting keys on an instance of this object. So, for example, you might create a calendar portlet used by a number of users. The first time each user used that portlet the content would be cached for an extended period of time. Each time a user accessed the portlet they would get a cached copy of their portlet. The portlet could have a meetings page in which a user could invite several other users. An invalidation request could then be set up to send invalidation requests that would invalidate any content in the Web Cache whose original request parameters included the meeting portlet id and the user names of the attendees. The next time one of these attendees brought up that portlet, the portlet content would be freshly generated. Any other users would continue to retrieve their original cached copies of the portlet.

#### oracle.portal.provider.v2.cache.invalidation.ServletInvalidationContext

This abstract class extends InvalidationContext and adds the methods to set servlet specific attributes such as the provider servlet path and the character encoding. Any portlet code should use a reference of this type created by the ServletInvalidationContextFactory class.

#### oracle.webdb.provider.v2.cache.WebCacheInvalidationContext

This class extends ServletInvalidationContext and implements the abstract methods with Web Cache specific code. Under normal circumstances portlet code would not instantiate one of these directly and should use a ServletInvalidationContext reference created by the ServletInvalidationContextFactory class.

The invalidation sample provided with the PDK demonstrates the use of these classes. For instructions on how to set up and use the invalidation sample refer to Setting up the Invalidation Caching Sample.

## Summary

You should now have a basic understanding of the function and structure of the PDK Release 2 (9.0.2 and later)UR framework and the fundamental ideas behind building web providers and portlets. For more information regarding using the framework and building Web Providers visit the Portal Studio at http://portalstudio.oracle.com/.

Revision History: |
Revision No | Last Update
1.0 | March 19, 2002.
2.0 | April 18, 2002
3.0 | April 26, 2002
4.0 | July 24, 2002
5.0 | September 24, 2002

Oracle Corporation World Headquarters 500 Oracle Parkway Redwood Shores, CA 94065, USA http://www.oracle.com/ | Worldwide Inquiries: 1-800-ORACLE1 Fax 650.506.7200 | Copyright and Corporate Info