Learn XQuery 10
Learn XQuery 10
By: Dr. Michael Kay This article is for all those people who really want to know what XQuery is, but don't have the time to find out. We all know the problem: so many exciting new technologies, so little time to research them. To be honest, I hope that you'll spend more than ten minutes on it but if you really have to leave that soon, I hope you'll learn something useful anyway.
Game for something more interesting? Try: 2+2 and be amazed by the answer: 4 Finally, just to check that things are working properly, enter: current-time() Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
and you'll see how much time you have left to read the rest of this article: 17:22:04-05:00 For that one, of course, mileage may vary. The precision of the time value (fractions of a second) depends on the XQuery processor you are using, and the timezone (5 hours before GMT in this case) depends on how your system is configured. None of these is a very useful query on its own, of course, and what they demonstrate isn't exactly rocket science. But within a query language, you need to be able to do little calculations, and XQuery has this covered. Further, XQuery is designed so that expressions are fully nestable any expression can be used within any other expression, provided it delivers a value of the right type and this means that expressions that are primarily intended for selecting data within a where clause can also be used as free-standing queries in their own right.
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
If you're working in Stylus Studio, click on XQuery / Scenario Properties, and under Main Input (optional), browse to the input file and select it. You can now refer to this document in your query simply as "." (dot).
If you're working directly with a command line processor such as Saxon, I suggest that you copy the file to somewhere local, let's say c:\query\videos.xml, and work with it from that location. Use the command line option -s c:\query\videos.xml and you will again be able to refer to the document within your query as "." (dot).
The file contains a number of sections. One of them is an <actors> element, which we can select like this: .//actors This produces the result: <actors> <actor id="00000015">Anderson, Jeff</actor> <actor id="00000030">Bishop, Kevin</actor> <actor id="0000000f">Bonet, Lisa</actor> <actor id="00000024">Bowz, Eddie</actor> <actor id="0000002d">Curry, Tim</actor> <actor id="00000033">Dullea, Keir</actor> <actor id="00000042">Fisher, Carrie</actor> <actor id="00000006">Ford, Harrison</actor> <actor id="00000045">Foster, Jodie</actor> ...etc... </actors> That was our first "real" query. If you're familiar with XPath, you might recognize that all the queries so far have been valid XPath expressions. We've used a couple of functions current-time() and doc() that might be unfamiliar because they are new in XPath 2.0, which is still only a draft; but the syntax of all the queries so far is plain XPath syntax. In fact, the XQuery language is designed so that every valid XPath expression is also a valid XQuery query. This means we can also write more complex XPath expressions like this one: .//actors/actor[ends-with(., 'Lisa')] which gives the output: <actor id="0000000f">Bonet, Lisa</actor> <actor id="0000001b">Spoonhauer, Lisa</actor>
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
Different systems might display this output in different ways. Technically, the result of this query is a sequence of two element nodes in a tree representation of the source XML document, and there are many ways a system might choose to display such a sequence on the screen. Stylus Studio gives you the choice of a text view and a tree view: you use the buttons next to the Preview window to switch from one to the other. Here's what the text view looks like:
This example used another function ends-with() that's new in XPath 2.0. We're calling it inside a predicate (the expression between the square brackets), which defines a condition that nodes must satisfy in order to be selected. This XPath expression has two parts: a path .//actors/actor that indicates which elements we are interested in, and a predicate [endswith(., 'Lisa')] that indicates a test that the nodes must satisfy. The predicate is evaluated once for each selected element; within the predicate, the expression "." (dot) refers to the node that the predicate is testing, that is, the selected actor. The "/" in the path informally means "go down one level", while the "//" means "go down any number of levels". If the path starts with "./" or ".//" you can leave out the initial "." (this assumes that the selection starts from the top of the tree, which is always the case in our examples). You can also use constructs like "/.." to go up one level, and "/@id" to select an attribute. Again, this will all be familiar if you already know XPath.
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
XPath is capable of doing some pretty powerful selections, and before we move on to XQuery proper, let's look at a more complex example. Let's suppose we want to find the titles of all the videos featuring an actor whose first name is Lisa. Each video in the file is represented by a video element like this one: <video id="647599251"> <studio></studio> <director>Francesco Rosi</director> <actorRef>916503211</actorRef> <actorRef>916503212</actorRef> <title>Carmen</title> <dvd>18</dvd> <laserdisk></laserdisk> <laserdisk_stock></laserdisk_stock> <genre>musical</genre> <rating>PG</rating> <runtime>125</runtime> <user_rating>4</user_rating> <summary>A fine screen adaptation of Bizet's popular opera. </summary> <details>Placido Domingo does it again, this time in Bizet's popular opera.</details> <vhs>15</vhs> <beta_stock></beta_stock> <year>1984</year> <vhs_stock>88</vhs_stock> <dvd_stock>22</dvd_stock> <beta></beta> </video> We can write the required query like this: //video[actorRef=//actors/actor[ends-with(., 'Lisa')]/@id]/title Again, this is pure XPath (and therefore a valid XQuery). You can read it from left-to-right as: Start at the implicitly-selected document (videos.xml) Select all the <video> elements at any level Choose those that have an actorRef element whose value is equal to one of the values of the following: o o Select all the <actors> elements at any level Select all their <actor> child elements
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
o o
Select the element only if its value ends with 'Lisa' Select the value of the id attribute
Select the <title> child element of these selected <video> elements The result is:
<title>Enemy of the State</title> <title>Clerks</title> Many people find that at this level of complexity, XPath syntax gets rather mind-boggling. In fact, this example is just about stretching XPath to its limits. For this kind of query, and for anything more complicated, XQuery syntax comes into its own. But it's worth remembering that there are many simple things you can do with XPath alone, and that every valid XPath expression is also valid in XQuery. Note that Stylus Studio also provides a built-in XPath analyzer for visually editing and testing complex XPath expressions, and it supports both version 1.0 and 2.0.
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
The for clause defines two range variables: one processes all the videos in turn, the other processes all the actors in turn. Taken together, the FLWOR expression is processing all possible pairs of videos and actors.
The where clause then selects those pairs that we are actually interested in. We're only interested if the actor appears in that video, and we're only interested if the actor's name ends in 'Lisa'.
Finally the return clause tells the system what information we want to get back. In this case we want the title of the video.
If you've been following very closely, you might have noticed one little XPath trick that we've retained in this query. Most videos will feature more than one actor (though this particular database doesn't attempt to catalog the bit-part players). The expression $v/actorRef therefore selects several elements. The rules for the = operator in XPath (and therefore also in XQuery) are that it compares everything on the left with everything on the right and returns true if there's at least one match. In effect, it's doing an implicit join. If you want to avoid exploiting this feature, and to write your query in a more classically relational form, you could express it as: let $doc := . for $v in $doc//video, $va in $v/actorRef, $a in $doc//actors/actor where ends-with($a, 'Lisa') and $va eq $a/@id return $v/title This time I've used a different equality operator, eq, which follows more conventional rules than = does: it strictly compares one value on the left with one value on the right. (But like comparisons in SQL, it has special rules to handle the case where one of the values is absent.) What about the O in FLWOR? That's there so you can get the results in sorted order. Suppose you want the videos in order of their release date. Here's the revised query: let $doc := . for $v in $doc//video, $a in $doc//actors/actor where ends-with($a, 'Lisa') and $v/actorRef = $a/@id order by $v/year return $v/title
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
And if you're wondering why it isn't a LFWOR expression: the for and let clauses can appear in any order, and you can have any number of each. That, and LFWOR doesn't exactly fall trippingly off the tongue, now does it?. There's much more to the FLOWR expression then what's covered in this brief XQuery tutorial for more information be sure to check out the XQuery FLWOR tutorial.
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved
java net.sf.saxon.Query sample.xquery firstName=Lisa This is how the output looks now: <videos featuring="Lisa"> <video year="1999"> <title>Enemy of the State</title> </video> <video year="1999"> <title>Clerks</title> </video> </videos> (Not a very well-designed query, since the two videos feature different actresses both named Lisa; but if your ten minutes aren't up yet, perhaps you can improve it yourself.)
in, take a look at DataDirect XQuery, which supports access to Oracle, DB2, SQL Server and Sybase.
Time's Up!
Congratulations on finishing XQuery in 10 Minutes. As you might have suspected, there's more to XQuery than we had time to present in this brief XQuery primer. But this article is just the first in a series of upcoming technical XQuery articles that we plan to make available through the Stylus Studio newsletter, the Stylus Scoop. So if you're interested in learning more, sign up for the Stylus Scoop. We'll feature new XQuery articles each month, for example, this new FLWOR tutorial, as well as information on other topics of interest to the XML-curious, too! Can't wait that long? Then check out the XQuery tutorial written by Jonathan Robie of DataDirect Technologies, the first chapter of the book XQuery from the Experts, which provides an in-depth understanding of the design behind the XQuery language. The book also contains a chapter by the author of this article, Michael Kay, about the relationship of XQuery to XSLT. It's a great way to get your feet wet with this powerful new XML technology. If you want to get your hands dirty right away, Stylus Studio provides a ton of XQuery tools, including an XQuery editor, an XQuery Debugger with integrated support for the Saxon XQuery Processor, an XQuery Mapper for visually developing XQuery projects, and an XQuery Profiler for benchmarking and optimizing XQuery expressions. Best of all, Stylus Studio provides several online video demonstrations to get you aquainted with these and other tools, and you can try out Stylus Studio for free. Finally, if you're more academically inclined, you can find the XQuery specification itself at http://www.w3.org/TR/XQuery. As standards documents go, it's actually quite readable, and it has lots of examples. The specification is part of a raft of documents on XQuery, which are all listed in its References section, but the one you're likely to find especially useful is the Functions and Operators specification at http://www.w3.org/TR/xpath-functions. This document lists all the functions in the XQuery library, but a word of warning only those prefixed fn: are directly available to end users. (You'll often see XQuery users writing the fn: prefix, but it's never necessary.)
Learn XQuery in 10 Minutes, By Dr. Michael Kay. 2006 DataDirect Technologies, Inc. All Rights Reserved