| Kongregate Registration for Free Flash Games and Chat with solprovider | |
![]() |
Useful Commands for XMAPs | |
|
This article explains useful functions that can be handled by XMAPs and integrated into XSL. There are several other basic tutorials available; this just describes what I found most useful.
Cocoon refers to XMAP files as "Sitemaps". Since "sitemap" has a different ubiquitous definition for the web, this website refers to them as XMAPs. They are files with the extension ".xmap" containing XML with the top-level tag of <map:sitemap>. Each XMAP contains many elements, but almost all customization is handled by "Pipelines" with the occasional "Resource". Almost anything added to other elements requires calling Java. Some elements may already exist; some may be written for your site; but everything outside the pipelines and resources require programming outside the XMAP and XSL. The one useful exception is creating Forms and calling JavaScript functions from an XMAP, which is explained in the chapter Flow PipelinesEvery XMAP has a section formatted: <map:pipelines>
Many people use unnecessary </map:pipeline><map:pipeline> pairs. There are only two reasons to have multiple The first is to change caching: <map:pipeline type="caching">
Cocoon likes to cache everything. Try setting the pipeline to noncaching if your results are not updating correctly. The second reason is handling errors. You can only have one <map:handle-errors> per <map:pipeline>. Multiple <map:pipeline> allow each <map:match> to have its own error handling. <map:pipeline>
An error during processing immediately jumps to the error handling, discarding the current work. <map:handle-errors> must be a complete pipeline (defined next), such as a <map:generate/><map:serialize type="html"/> sequence. Error handling can branch based on the error: <map:handle-errors>
See Cocoon's <map:handle-errors> and examples in publication-sitemap.xmap in the default pub. MatchesWhile the <map:pipeline> tag exists, we refer to the process of responding to a request as a "Pipeline", even though the Pipelines usually refers to just the <map:match> elements. The <map:match> tags are unnecessary if there is only one process. A normal Pipeline has four parts: 1. A pattern. It could match a URL, called from another pipeline by name, or be for handling errors. 2. Get some content. This is usually a Generator or an Aggregator. 3. (Optional) Transform the content using XSL, or pass control elsewhere. 4. Serialize the content into either XML or HTML. The final pipeline should return HTML; all others should return XML for further processing. The tags are: <map:match pattern="myPattern">
Generator and AggregatorsThe Generator is the simplest method for getting data. The basic choices are: <map:generate src="someFile"/>
Aggregators are used to combine data from several sources into one XML file for further processing. The tags are similar to the Generator: <map:aggregate element="rootElementOfNewContent">
Most XMAPs have: <map:generators default="file"> so the <map:part src="file:///someFile"/>
can be just: <map:part src="someFile"/>
There are other protocols, such as for getting data from a database. Research them if needed. When using the file protocol to get the results of an XSP, add: type="serverpages"
to both generators and map:parts so the XSP is processed, otherwise you are adding the XML of the XSP. Type can have other values. "request" returns XML describing the request. "directory" returns XML describing the contents of a directory and its subdirectories. See Generators for more details. There are additional parameters allowed for map:part: <map:part src="..." strip-root="true" element="newRootElement" ns="fakePathToNewNamespace" prefix="newNamespace"/>
Example: XMAP: <map:aggregate element="newRootElement">
test.xml <?xml version="1.0" encoding="UTF-8"?>
output: <?xml version="1.0" encoding="UTF-8"?>
If you want to transform one part being aggregated before aggregation, and these parameters cannot do it, then do the transformation in another pipeline and call that pipeline from the part: <map:match pattern="getTransformedPage">
TransformerThe tag is: <map:transform src="xslt/myXslt.xsl">
Parameters are used in the XSLT by adding at the top: <xsl:param name="myParameter"/>
and using: <xsl:value-of select="$myParameter"/>
or <TAG VALUE="{$myParameter}/>
where needed. See Variables for example code. RedirectionTo tell the browser to go somewhere else, use the RedirectTo command: <map:redirect-to uri="REQUIRED: new url" session="false" global="false" permanent="false"/> This is usually used to append "index.html" to the server's root because Lenya did not handle that automatically. I am not certain if this is bad design in Lenya, or if Cocoon makes it difficult to fix the Request. Lenya creates PageEnvelope, but then processes the Request without modification. There is a RequestWrapper class where the override would be simple. Binary FilesTo read any file and send it to the visitor, use this: <map:read type="resource" src="path/finame.ext" mime-type="text/css">
It reads the Resource (a file), and wraps it with the appropriate HTML headers including the specified mimie-type. It immediately stops all other processing, meaning no <map:serialize> is needed. This is often used for Assets, and CSS and JS files. IF StatementsThere are several useful IF statements. The first requires Java to create an Action. An example would be: <map:act type="authenticator">
If the Action returns true, Lenya does what is within the tags. There is no ELSE. There is no NOT. Redirection to other pipelines must be used to work around these limitations. (Do not blame the Lenya devs; it is the Cocoon devs who were not thinking.) Useful without Java is the Selector: <map:select type="parameter">
This allows the IF-ELSEIF-ELSEIF-ELSE format by adding map:whens. You can set any parameter. The above gets "myParameter" from the querystring of the request, and checks it for "myValue". You can use any variable available. A list of useful variable is available here. Also see the official documentation. ResourcesThe Resources section contains subroutines for use in pipelines. Anything repeated in two Pipelines in the same XMAP should be turned into a Resource. Example: <map:resources> <map:resource name="SerializeXML"> <map:serialize type="xml" /> </map:resource> </map:resources> Then use this line in a pipeline: <map:call resource="SerializeXML"/> A resource can contain any code used in a pipeline (between the map:match tags), and a call to the resource is replaced by that code. This is very useful for maintenance because code that would be repeated can be kept in one place. Passing Control to another XMAPYou can pass control to another XMAP using: <map:mount src="otherXMAP.xmap" check-reload="true" reload-method="synchron" uri-prefix="newprefix-"/>
The uri-prefix tells Cocoon where to start the match earlier. The uri-prefix must exist in the match. It will error "The current URI doesn't start with given prefix "If the uri-prefix does not exist in the match. uri-prefix="" means use the entire match. The new XMAP must contain matches for whatever is sent. Example: <map:match pattern="test/**">
To pass variables to another XMAP, use a generator to change the match: <map:generate src="cocoon:/mount/myVariable1/myVariable2"/>
In this example, another.xmap must have match="mount/*/*", and can use the variables {1} and {2}. FunctionsXMAPs have access to JXPath functions using the SessionModule. This is very useful for string manipulation. <A HREF="http://www.w3.org/TR/xpath#section-String-Functions">Click here for the official documentation.</A> You can nest functions and variables: {session:substring-after('{page-envelope:document-id}','/')}
|