The XQuery specification is a formal recommendation from the W3C XQuery Working Group. MarkLogic 8 implements the W3C XQuery 1.0 Recommendation (). To maximize compatibility with MarkLogic Server 3.2 and to offer strict XQuery compliance to those who desire it, as well as to include extensions to the language to make it easier to build applications, MarkLogic Server supports three dialects of XQuery. This chapter describes these dialects, and includes the following sections:
You can use library modules from different dialects together, as described in Rules For Combining the Dialects. Each dialect has a different set of pre-defined namespaces, as described in Predefined Namespace Prefixes for Each Dialect.
Note the semi-colon at the end of the declaration, which is required in
1.0-ml. The enhanced dialect has the XQuery 1.0 syntax and also includes various extensions to the language such as
catch. This dialect is the default for new App Servers, and should be considered the preferred dialect for new applications. For more details on the enhanced
1.0-ml dialect, see MarkLogic Server Enhanced XQuery Language.
Note there is no semi-colon at the end of the declaration for
0.9-ml. The 3.2 compatibility dialect allows you to write code that you can use with both 3.2 and 4.0. Any code you have from 3.2 releases is equivalent to
0.9-ml. To use that code in 4.0, the best practice is to add the
0.9-ml XQuery declaration (shown above) as the first line of each XQuery module.
Note the semi-colon at the end of the declaration, which is required in
1.0. The strict mode is for compatibility with other XQuery 1.0 processors; if you write a library in
1.0, you can use it with MarkLogic Server and you can also use it with other conforming processors. Similarly, you can use modules that are written in standard XQuery with MarkLogic Server.
To use the MarkLogic Server built-in functions in
1.0, you must bind a prefix (for example,
xdmp) to the namespace for the MarkLogic Server functions; there is no need to import a library for these built-in functions, but you do need to bind the namespace to a prefix. To use the
xdmp functions in
1.0, add prolog entries for the namespace bindings you are using in your query, as in the following example:
MarkLogic Server has a very flexible way of combining the three XQuery dialects. You can import a library module written in any of the three dialects into any main or library module. For example, you might find an open source standards-compliant module that you found on the internet which is written in the strict XQuery 1.0 dialect. You can then import this module into any MarkLogic Server XQuery program, regardless of dialect, and then use those functions in your code.
When writing modules of different dialects, the best practice is to always use the XQuery version declaration as the first line, indicating which dialect the module is written in. That way, if the module is written in a different dialect than the default dialect for the App Server or the program, it will still work correctly (for details, see Inheriting the Default XQuery Version From the App Server).
You can use the
xdmp:dialect attribute to specify which dialect expressions are evaluated in an XSLT stylesheet. For details, see xdmp:dialect Attribute.
If you are writing new XQuery code, the best practice is to use the
1.0-ml dialect. If you are updating code that was written in previous versions of MarkLogic Server, you can consider if you want to migrate that code to
1.0-ml. This section describes things to think about when migrating your application code and includes the following parts:
Because of the flexibility of how you can interoperably use the various XQuery dialects, it is really up to you when and how you migrate your XQuery code. The differences between the dialects are mostly syntax changes in the prolog, but there are also some other differences that might cause subtle changes in behavior. For details on the differences between the XQuery dialects in 3.2 (
0.9-ml) and 4.0 (
1.0-ml), see XQuery Changes From Previous MarkLogic Server Releases. When you decide to migrate XQuery code to
1.0-ml (or to
1.0), there are several ways you can go about it:
0.9-mldeclaration to the first line of each XQuery file. Then, as you migrate a module, you can change the declaration to
1.0-mland make any needed syntax changes to that module.
While MarkLogic Server 4.0 includes a compatibility dialect to run your 3.2 code without changes (
0.9-ml), the new enhanced mode offers several important improvements, so it is a good idea to migrate your code to the enhanced dialect (
1.0-ml). Because you can mix modules in the old dialect with modules in the new, you can perform your migration one module at a time. This section highlights the major syntax and semantic changes between the XQuery used in MarkLogic Server 3.2 (
0.9-ml) and MarkLogic Server 4.0 enhanced XQuery dialect (
1.0-ml). Additionally, see the 'Known Incompatibilities' section of the Release Notes. The changes include:
:=syntax (for details and an example, see Declaring Variables).
namespacekeyword and a prefix for the namespace, for example:
0.9-mland returns false in
1.0-ml(and throws an exception in
(: returns true in 0.9-ml, false in 1.0-ml, and throws XDMP-EFFBOOLVALUE in 1.0 :) fn:boolean((fn:false(), fn:false()))
This change might affect applications that have
if/then/else statements where the
if test returns a sequence of boolean values. In these cases, you might see the
if statement evaluating to
false in cases where it previously evaluated to
true, causing the
else statement to be evaluated intead of the
xsnamespace prefix; previously it was the
xdtprefix. Any code you have that uses the
xdtnamespace prefix will require a change to the
xsprefix. For example, if you have code that uses
xdt:dayTimeDuration, you should change that to
0.9-mlare equivalent to
1.0-ml. Any code you have with
element()tests might not match some elements that previously matched. For example, substitution elements previously would match the base element name, but will now only match with
1.0-ml. For more information, see in the 4.0 Release Notes.
fn:node-kinddoes not exist in 1.0 and 1.0-ml (it is replaced by xdmp:node-kind).
Each App Server has a setting for the default XQuery version. Any requests against that App Server that do not have explicitly specify an XQuery version declaration are treated as the default XQuery version value. Because of the way a request inherits it default XQuery version from the App Server environment, requests without an explicit declaration can be treated differently by different App Servers (if the App Servers have different default XQuery values). Therefore, it is best practice to specify the XQuery version in each module.
The task server does not allow you to specify a default XQuery version, and if there is no explicit version declaration in the XQuery code evaluated on the task server, the default XQuery version is determined as follows:
This makes it especially important to use XQuery version declarations in modules used by CPF or modules called from triggers. For details on CPF, see the Content Processing Framework Guide.
To ensure your code is always evaluated in the dialect in which you have written it, regardless of the context in which it is run, the best practice is to begin each XQuery module with a XQuery version declaration. For the syntax of the version declaration, see XQuery Version Declaration.
You specify the dialect for an XQuery module with a version declaration. The version declaration is optional, and comes before the prolog in an XQuery module. It is best practice to put the XQuery version declaration in your code as the first line in the module, as having it there ensures it will work as expected in any environment. For example, to specify
1.0-ml as the XQuery version, begin your XQuery module with the following:
In most cases, porting any XQuery code used in 3.2 to the
1.0-ml dialect will be easy and straightforward. The bulk of the differences are syntax changes in the prolog. As stated earlier, you do not need to port all of your code at one time. A sensible approach is to migrate your code one XQuery module at a time. This section outlines the basic steps you should follow when migrating your XQuery code.
1.0-mland add a semi-colon to the line so it looks as follows
declare, add semi-colons, and so on, as described in XQuery Changes From Previous MarkLogic Server Releases). For the prolog syntax, see XQuery Prolog, the W3C specification (http://www.w3.org/TR/xquery/#id-grammar), or a third-party XQuery book.
local:prefix, which is predefined.
xdtnamespace prefix, change the prefix to
xs(for example, change
fnnamespace prefix. Alternately, you can declare the XQuery functions namespace as the default function namespace in the prolog as follows:
If you do declare the default function namespace, then you will also need to prefix your own function definitions with the prefix defined in your module definition. Note that you can no longer use the XPath functions namespace as the library module namespace.
fnnamespace URI, you must change the namespace URI of that module; you cannot use the URI bound to the
fnnamespace prefix as the URI for a library module in
1.0-ml. If you do change the namespace URI of a library module, you must also change the URI in any
import modulestatements in other modules that call the library.
1.0-ml(see XQuery Changes From Previous MarkLogic Server Releases). Check for any changes due to function mapping, which is described in Function Mapping.