Version 3.0

Historical note: Orbeon PresentationServer 3.0 was released on January 17, 2006.


Welcome to Orbeon PresentationServer (OPS) 3.0!

OPS 3.0 features an Ajax-based XForms engine much improved over OPS 2.8's, significant improvements in the Page Flow Controller, and much more!

This document describes changes made between OPS 2.8 and OPS 3.0.1.

Changes in version 3.0.2

Orbeon Forms 3.0.2 was released on April 1, 2007. See also this blog entry.

Changes in version 3.0.1

OPS 3.0.1 is a minor update containing the following changes:

  • The new DMV Forms example (see also the standalone version) shows how to implement web forms the right way with XForms, services and OPS. This example is based on a real-life form (a California Department of Motor Vehicles form) and illustrates data capture, validation, calling up services, repeating sections, generating PDF, page navigation, and localization.
  • Bug-fixes in the XForms engine, including:
  • Fixed XPL performance regression introduced with OPS 3.0.
  • Minor documentation and CSS improvements.

Changes in version 3.0.0

Known limitations of OPS 3.0

The following limitations are known:

  • XForms upload controls only work within forms that are submitted with a reference to a submission element with replace="all". The value of XForms upload controls is ignored when forms are submitted with replace="instance" or replace="none".
  • At most one XML schema is allowed on a particular XForms model.
  • Calculation dependencies are not computed as per the XForms 1.0 specification. With OPS 3.0, first the calculations are evaluated in the order they appear in your XForms model. Then the required, relevant, and readonly model item properties are evaluated, also in the order they appear in your XForms model. This means that you have to be careful with the order in which you declare your <xforms:bind> elements.
  • xforms:message only supports level="modal".
  • The Ajax-based XForms engine currently works with Mozilla Firefox and Microsoft Internet Explorer 6. Support for Safari and Opera is planned.
  • The Orbeon PresentationServer Tutorial has not been updated to reflect the new features and best practices of OPS 3.0.
  • Initial generation of an XForms page may still have poor performance in some circumstances.
  • Not all the OPS examples have been updated to reflect the new XForms engine capabilities.
  • The OPS reference XForms documentation is a work in progress. Please refer to the "XForms NG" examples for details.
  • The OPS reference XForms compliance matrix has not yet been updated to reflect all the changes in OPS 3.0.
  • Migration documentation from 2.8 to 3.0 is not complete yet.
  • The OPS Blog example is not complete.
  • The PDF version of the User Guide does not have page numbers.

Please also visit the OPS bug tracker on the ObjectWeb Forge, and report and discuss issues in the ops-users mailing-list.


New features

The OPS XForms engine introduces a big step towards supporting all of the XForms 1.0 specification. The main changes are described below. Please also visit the new XForms examples, in particular the XForms Controls, the BizDoc NG example, and the XForms Sandbox example. XForms improvements in OPS 3.0 include but are not limited to:

  • Ajax-based engine. The XForms engine is now based on Ajax technologies. This makes the XForms engine much more responsive to user interaction than with OPS 2.8.
  • Standard XHTML integration. The XForms engine works on standard XHTML + XForms documents, without the need for a separately described XForms model as was the case with OPS 2.8. XForms models are simply included in the XHTML page view under the <xhtml:head> element, as recommended by XForms 1.0. In this mode, you don't use the xforms attribute on the PFC <page> elements. The xforms attribute is still supported for backward compatibility, but its use triggers the use of the legacy OPS 2.8 XForms engine.
  • XForms event model. The XForms engine supports the XForms event model, including most XForms events and XForms actions.
  • Multiple XForms models and instances. The XForms engine supports multiple models and multiple instances within models. The instance() function is supported.
  • XForms switch module. The XForms engine supports the XForms switch module.
  • XForms repeat module. The XForms engine supports correctly the current index in repeated sections, including the index() function.
  • XForms submission. The XForms engine supports submitting forms as application/xml with HTTP POST and application/x-www-form-urlencoded with HTTP GET (including to external applications). Support for replace="instance", replace="all", and replace="none" is included.
  • XForms Range control. The XForms engine supports a subset of the functionality of the XForms Range (or slider) control.
  • Extension functions. The XForms engine supports the xxforms:call-xpl() extension function to call arbitrary XPL programs from XForms, as well as some eXforms functions.
  • Dynamic XForms models. The new XForms engine and PFC improvements now allow to easily generate XForms models based on XML submissions. With OPS 2.8, this was much more difficult as this had to be done in a dynamic XForms model pipeline, which did not have access to an XML submission.
  • Simplified theme. The default theme and XForms make more use of CSS so that configuration of your own theme is easier.
  • XForms sandbox. The new XForms Sandbox example allows you to easily try your own XForms examples. Just write and XHTML + XForms example, upload it, and watch the results!
  • Other changes. The XForms engine supports the value attribute on xforms:output, handles inheritance of model item properties, and includes numerous improvements and bug fixes.

Incompatible changes

  • XSLT views now must always use doc('input:instance') to access a submitted XML instance instead of expecting the instance on their main input.

  • With OPS 2.8 if your XForms instance was:


    and your first XForms element under the <xhtml:body> element was:

    <xforms:group ref="credit-card"/>

    then credit-card would evaluate against the document node of the unique XForms instance. The above code worked, but this behavior was incorrect. The XPath evaluation context for top-level XForms controls has to be the root element of the default XForms instance instead. This means that the code above must be changed in one of two ways:

    <xforms:group ref="/credit-card"/>


    <xforms:group ref="."/>

    If you use absolute XPath expressions for your top-level XForms controls, no change is necessary.

  • With OPS 2.8, the "required" model item property did not apply at all to elements validated with XML schemas. If for example a value was of type xs:string but missing and required, it was marked as valid (which was correct) but submission would pass. With OPS 3.0, nodes which are "valid", "required" and empty will cause submission to fail. Be sure to check your types and "required" model item properties.

  • The xxforms:choose, xxforms:when and xxforms:otherwise constructs are no longer supported with the new XForms engine. Instead, use relevance and xforms:group or xforms:switch / xforms:case.

Migrating to the OPS 3.0 XForms engine


Your applications written against OPS 2.8 and run within OPS 3.0 without modifications uses the Classic XForms engine of OPS 3.0. In order to trigger the use of XForms NG and benefit from all the new XForms features of OPS 3.0, some code migration work is required. Note that it is possible to determine on a page by page basis whether XForms Classic or XForms NG is used, and therefore to progressively upgrade your application to XForms NG.

When migrating an application from XForms Classic to XForms NG, a series of tasks need to be performed, as the OPS XForms engine is now much closer from the XForms 1.0 specification. The following list attemps to describe the most common aspects of the migration. It does not intend to be inclusive:

  • XForms model migration. For a given <page> element: if your OPS 2.8 XForms model is static (which is usually the case), copy it under your XHTML page view's xhtml:head element. Then remove the xforms attribute from the <page> element. You can then remove the file containing your XForms model.

    <xhtml:title>My Title</xhtml:title>
    <xforms:model id="my-model">
    <xforms:instance id="main">

    Another possibility is to keep your XForms model file, and to XInclude that file in your XHTML page view under the xhtml:head element.

    <xhtml:title>My Title</xhtml:title>
    <xi:include href="my-model.xml"/>

    Here again, you must remove the xforms attribute from the <page> element.

    If your XForms model is dynamic, then you can use XSLT in your page view to dynamically produce the model:

    <xhtml:title>My Title</xhtml:title>
    <xforms:model id="my-model">
    <xforms:instance id="main">
    <xsl:value-of select="doc('input:data')/*/my-name"/>

    The PFC now provides XML submissions on the page models, views and actions' instance inputs. This allows for easily building dynamic XForms models from an XML submission, including an XForms submission, which was difficult to do before. In the example above, the current XML submission can be accessed from XSLT in the page view with doc('input:instance').

    For more information, visit the XForms Reference's XForms Instance Initialization section and the Page Flow Controller's XML Submission section.

  • Required attributes. Some controls now require certain attributes, as per the XForms 1.0 specification. In particular:

    • xforms:submit now requires a submission attribute.
    • XForms actions, including xforms:setvalue, need an ev:event attribute, or need to be enclosed within and xforms:action element with an ev:event attribute.
    • The xforms:submission element now requires an id attribute to be useful (by being referred from the submission attribute of xforms:submit or xforms:send). Attributes action and method are also mandatory.
  • Validation processing model. As per the XForms specification, invalid XForms instances, or XForms instances with missing required elements cannot be submitted and instead throw xforms-submit-error events. This means that there is no longer a need to check on xxforms:valid attributes in the page flow to determine whether a submitted XForms instance is valid or not.

  • Page flow roundtrips. xforms:repeat updates (threw actions such as xforms:insert and xforms:delete) are no longer visible in the page flow. With XForms Classic, upon inserting or deleting a row with those actions, the entire form would be submitted, giving an opportunity to the page flow to intercept and regenerate the page. With XForms NG, these actions operate within the XForms engine.

    Use XForms submissions with replace="none" or replace="instance" if you need to submit an XForms instance to the page flow before or after performing such actions.

  • XForms events and actions. Many operations can now be performed with XForms events an actions, rather than using xforms:setvalue in an xforms:submit and then performing a complete submission.

  • XML services and page flow. Because the XForms engine now operates completely separately from the page flow, XForms pages must now explicitly perform XForms submissions to interact with pages defined in your page flow.

    In particular, when using an XForms submission with replace="none" or replace="instance", the page flow can now be used to implement XML services, that is services that receive XML (through the XForms submission) and produce XML as a result. Such services are implemented in your page flow as usual with <page> elements, and differ with regular pages only in that they either do not return any result, or return an XML document as result as opposed to return a complete HTML page.

Page flow

New features

Several improvements have been added to the Page Flow Controller, some of them motivated by the new XForms engine. The PFC is now more generic and less tied to the built-in OPS XForms implementation. At the same time it plays better than before with XForms, including client-side XForms engines. The major PFC concepts found with OPS 2.8 have not changed and backward compatibility is kept. The main changes are the following:

  • Documentation. The PFC documentation has been reworked and greatly improved.
  • Standard Epilogue. The standard epilogue has been restructured into three separate files so as to be easier to understand, modify, and extend. It is fully documented.
  • Deprecation of the xforms attribute. Using XForms with OPS no longer implies using an xforms attribute on the <page> element. Instead, XForms models are included in the XHTML page view under the <xhtml:head> element, as recommended by XForms 1.0. The xforms attribute is still supported for backward compatibility, and triggers the use of the legacy OPS 2.8 XForms engine.
  • New XML submission mechanism. The PFC features a new generic XML submission mechanism. Each page in the PFC, instead of supporting native OPS XForms engine submissions, now supports generic XML submissions. You submit XML by POST-ing content with an XML content-type (other types of XML submissions can be added). XML submissions can be performed from external applications (through Web Services, XML-RPC, etc.), client-side XForms engines, the built-in OPS XForms engine, or by the PFC itself when navigating between pages.
  • Deprecation of the <param> element. The PFC's <param> element was used to set values into a submitted XForms instance. A new, more flexible element, <setvalue>, now performs the same task. The <setvalue> element supports extracting information from regular expressions applied to the request path, as well as extracting request parameters. This allows for creating "clean", REST-like URLs in your appliation. param is still supported for backward compatibility.
  • Generic XML submission transformations. The PFC features a new generic and extensible XML submission transformation mechanism. With OPS 2.8, XUpdate code had to be used to transform XML instances between pages. XUpdate support in the PFC is now deprecated. Instead, XSLT or XQuery should be used for that purpose. For more information, please refer to the <result> element section of the PFC documentation.
  • Accessing XML submissions. XML submissions can be accessed from actions, page models, and page views, through the instance input. Users should not assume that XML submission are available from the data inputs.
  • Shorter page flows. Because of the enhanced XForms support, in particular, the XForms switch module and support for application/xml submissions, page flows are typically shorter to write. Compare for example the BizDoc Classic example with the BizDoc NG example.

Incompatible changes

The following incompatible changes have been made:

  • Optional Epilogue Output. Support for the legacy data output of the epilogue has been dropped. With OPS 2.8 and earlier, the epilogue could have a data output. The PFC was then in charge of HTML serialization. This is no longer possible: serialization must occur in the epilogue itself. If you have code relying on this feature, simply remove the epilogue's data output and add an HTML serializer to your epilogue.

XSLT processor

The following improvements have been made to the XSLT processor:

  • Attributes input. The XSLT processor supports a new attributes input, which allows setting JAXP TransformerFactory attributes.
  • Safer defaults. The default XSLT processor (accessed with oxf:xslt, and configured in processors.xml) no longer allows executing external functions. To enable external functions, use oxf:unsafe-xslt, or configure the XSLT processor's attributes input. This makes the XSLT processor safer by default.
  • Default implementation. The default XSLT 1.0 processor implementation, configured in processors.xml, is now Saxon 8 instead of Xalan. The default XSLT 2.0 implementation remains Saxon 8, as was the case before.
  • Deprecated behavior. The XSLT processor used to support a value of DEFAULT or interpreter for the transformer input, for backward compatibility. This is no longer supported. The transformer must provide only a valid JAXP TransformerFactory class name. Most users should not be affected by this change.
NOTE: These changes should not affect applications that used oxf:xslt unless stylesheets use external functions. In this case, you have to use oxf:unsafe-xslt instead.

If you were using oxf:xslt-1.0 or were using XSLT 1.0 stylesheets directly referenced from a page flow, and used Xalan-specific features, you have to either convert your stylesheet to use Saxon features instead, or use oxf:xalan.

XQuery processor

The XQuery processor has been updated:

  • Default implementation. The default implementation of the XQuery processor is now Saxon 8.
  • Safer defaults. This processor is available with oxf:xquery or oxf:unsafe-xquery. The former does not allow calling external functions by default, while the latter does, similar to the new behavior of the XSLT processor.
  • Query format. In addition to XQuery code embedded into XML, the XQuery processor now supports in its config input a text document of the form:
  • PFC integration. XQuery can be used in the PFC to perform XML submission transformations.

XHTML support

XHTML is now much better supported:

  • Simplified theme. There is no need to remove the XHTML namespace from XSLT, as was done before in theme.xsl. Your theme should simply use the XHTML namespace.
  • Switching between XHTML and HTML. The standard epilogue illustrates how to generate XHTML and HTML to different browsers.
  • Using XHTML serialization. The standard epilogue illustrates how to to connect the XHTML serializer.
NOTE: In order to benefit from features such as XForms, you should make sure that your page views generate XHTML. In particular, your XHTML elements must in the XHTML namespace (

SQL processor

New features

The following changes have been made to the SQL processor.

  • Stored Procedures. The SQL processor now uses the JDBC CallableStatement interface when sql:call is used instead of sql:query. This allows for calling stored procedures using the JDBC escape syntax, for example:

    { call SalesByCategory(<sql:param type="xs:string" select="/*/category"/>,
    <sql:param type="xs:int" select="/*/year"/>) }
    NOTE: OUT and INOUT parameters are not yet supported.
  • Multiple Result-Sets. The SQL processor now supports multiple result-sets. It is possible to handle the result-sets returned by a query or call individually for each result-set, or globally for all result-sets, using the sql:result-set element. The optional result-sets attribute specifies how many result-sets are handled by a given sql:result-set element. If not specified, the default is one result-set. If the value is unbounded, the sql:result-set element handles all the remaining result-sets returned by the statement execution. Otherwise, a positive number of result-sets must be specified.

    <!-- Handle the first two result-sets -->
    <sql:result-set result-sets="2">
    <sql:get-columns format="xml"/>
    <!-- Handle All the remaining result-sets -->
    <sql:result-set result-sets="unbounded">
    <sql:get-columns format="xml"/>
    <!-- This will be executed if no row was returned by any result-set -->

    sql:no-results has been updated to execute when none of the previous sql:result-set elements returned rows.

  • Column Iterator. The SQL processor is now able to explicitly iterate over all the columns returned by a result-set with the sql:column-iterator element. A column iterator can be used under the sql:result-set element, or under the sql:row-iterator element. This allows for example easily extracting column metadata:

    <sql:attribute name="index">
    <sql:attribute name="name">
    <sql:attribute name="type">
  • Result-Set Metadata. The SQL processor is now able to retrieve result-set metadata, with the following new elements. The must be used within a sql:column-iterator element, unless a column-name or column-index attribute is explicitly specified:

    • sql:get-column-index: retrieves the current column index.
    • sql:get-column-name: retrieves the current column name.
    • sql:get-column-type: retrieves the current column type name as returned by result-set metadata.
  • Outputting Attributes. The SQL processor is now able to dynamically generate new attributes with the sql:attribute element, for example:

    <sql:attribute name="index">
  • Optional XML Type Information. The XML type (specified with type="xs:int", for example) is now optional on column getters. If not specified, a default type obtained from the result-set metadata is used to determine how to best get the value from the result-set.

  • New Element and Attribute Names. Some element and attributes have been renamed. The old names are still supported for backward compatibility:

    • sql:results has been renamed to sql:result-set.
    • sql:row-results has been renamed to sql:row-iterator.
    • sql:get-column has been renamed to sql:get-column-value, for consistency with the new sql:get-column-* elements.
    • column-name is now the standard attribute name for identifying a column name on the sql:get-column-*, sql:get-column, and sql:group elements.

Incompatible changes

The following incompatible changes have been made:

  • Legacy Types. Backward compatibility with pre-OPS 2.0 int and string types has been removed. Use xs:int and xs:string instead, while declaring the xs prefix as explained below.

  • Implicit Type Prefixes. Legacy support for implicit type prefixes (xs and oxf) is deprecated. Backward compability is enabled with the legacy-implicit-prefixes property as follows:

    <property as="xs:boolean" processor-name="oxf:sql" name="legacy-implicit-prefixes" value="true"/>

    When this property is missing or set to false, type prefixes must be mapped as is customary for XML vocabularies. Add the following namespace declarations: xmlns:xs="" and xmlns:odt="". Doing so then allows using data types as before, for example xs:string or odt:xmlFragment.

  • Stricter Type Checking. Column getters are now checked against result-set column metadata. In the past, using xs:string for a column of type INTEGER was allowed. Now if an XML type is specified, the XML type must match the SQL type. Alternatively, as mentioned above, it is possible to not specify an XML type at all.

File serializer

Incompatible changes

The File serializer now works like the HTTP serializer: it only accepts text and binary documents as input, and no longer handles conversions to XML, HTML, XHTML or text. To serialize to a file XML, HTML, XHTML or plain text, connect the XML, HTML or Text converters to the File serializer.

The legacy, deprecated File serializer is still available as oxf:legacy-file-serializer.

Enhanced error reporting

The following enhancements have been made to the error reporting on OPS:

  • OPS Stack Trace. When a Java exception occurs, OPS now reports the OPS stack trace, which provides useful OPS-oriented information about the events leading to an exception.
  • Java Stack Traces.
  • Separate Stylesheet. The XSLT stylesheet used to format stack traces is not in a separate file: oxf:/config/error.xsl.

Like with OPS 2.8 and earlier, the layout of the stack traces traces can be customized: simply edit oxf:/config/error.xpl and oxf:/config/error.xsl. More advanced configuration can be performed by changing the error processor.

XPL profiling support

  • A trace API has been added. The interface is org.orbeon.oxf.pipeline.api.PipelineContext.Trace
  • OPS ships with two implementations of Trace, org.orbeon.oxf.processor.NetworkTrace and org.orbeon.oxf.processor.StdOutTrace. NetworkTrace sends profiling information to Studio which the displays the data in the trace views. StdOutTrace simply dumps profiling information to standard out.
  • Properties for configuring the tracing have been added.
  • Views for viewing profiling data have been added to Orbeon Studio.

Other changes

The following changes are new in OPS 3.0:

  • HTML Documentation. The OPS User Guide in static HTML format, broken in OPS 2.8, is now working correctly. This format allows you to consult the documentation offline without running OPS or without accessing the online documentation.

  • PDF Documentation. The OPS User Guide in PDF version is back! You can print this book for reference.

  • OPS Blog example. This new example illustrates many of the capabilities of OPS, including:

    • Implementing XML-RPC services
    • Connecting to a native XML database
    • Using XForms
    • Producing XHTML, RSS and other formats from a single data source
    • Implementing configurable themes with XSLT
    • Creating "clean" URLs in a REST perspective
  • Resource Manager. The Flat File and Filesystem resource managers have been merged. The Flat File resource manager is now deprecated, and the Filesystem resource manager should be used instead. The Flat File resource manager can still be used for backward compatibility. The main difference between the two resource managers is that the Filesystem resource manager can be configured with or without a sandbox.

  • Directory Scanner Processor. The purpose of the Directory Scanner processor is to analyse a directory structure in a filesystem and to produce an XML document containing metadata about the files, such as name and size. It is possible to specify which files and directories to include and exclude in the scanning process. The Directory Scanner is also able to optionally retrieve image metadata. Two new command-line examples illustrate the use of this processor.

  • Faster URL Rewriting. In order to improve performance URL rewriting has been re-implemented in Java. The new implemetation is accessed through the new rewrite processors oxf:xhtml-rewrite and oxf:html-rewrite.

  • Disabled Validation. Previously the data input of the oxf:xforms-output processor and the config input of the oxf:portlet-include processor were validated unless one turned off all input parameter validation in OPS. However we found that validation of these two inputs came with at significant price and consequently these inputs are no longer validated by default. To enable the validation one must specify the appropriate schema URI with the schema-uri attribute. For the data input of oxf:xforms-output the URI is and for the config input of oxf:portlet-include the URI is

  • URL Generator. The URL Generator now has an option to specify whether XInclude processing must occur at XML parsing time.

  • JAR and WAR Names. orbeon.jar has been renamed to ops.jar, cli-orbeon.jar has been renamed to cli-ops.jar and orbeon.war has been renamed to ops.war.

  • Delegation Processor. The select attribute on the operation element is now documented. The default behavior when select is not present has changed when calling document-style web services. In that case, now the content of the SOAP body element is returned, instead of the content of the first element contained by the SOAP body.

  • New To-XML Converter. The new To-XML Converter allows producing parsed XML documents from a binary document format.

  • New XInclude Processor. The new XInclude processor allows processing XInclude instructions. XInclude was already supported at the parser level (Xerces support) before OPS 3.0.

  • Email processor. The Email processor now supports setting custom email headers with the new header configuration element.

  • Listeners. The Listeners documentation has been updated to reflect the correct configuration parameters. Listeners now produce better logs.

  • Servlet and Portlet Classes. Servlet and Portlet classes have been renamed as follows:

    • OPSServlet replaces OXFServlet
    • OPSPortlet replaces OXFPortlet
    • OPSServletFilter replaces OXFServletFilter
    • OPSServletContextListener replaces OXFServletContextListener
    • OPSSessionListener replaces OXFSessionListener

    The old names still work for backward compatibility.

Other incompatible changes

The following incompatible changes are new in OPS 3.0:

  • Request Generator. The Request Generator used to return a constructed path for the path-info parameter. It now correctly returns the Servlet API's path info. To get a complete path, use request-path instead.