From: Ellis Pritchard <[EMAIL PROTECTED]>
Date: Fri, 5 May 2006 08:20:46 +0100
Hi,
The LinkRewritingTransformer might be your thing, but given that you are
using map:redirect, I suspect that it isn't. You could sub-class
XMLFileModule to dynamically provide the configuration you need via
modeConf (LinkRewritingTransformer provides the configuration this way).
Oh. I figured it was the other side of things that needed adapting. So far
as I can see, XMLFileModule can already take its configuration via modeConf,
inasmuch as there's a modeConf parameter to the getAttribute methods and it
does appear to do something with it (looking for a file child element in
getDocument). The problem I have is how to get something passed into the
modeConf from my map:redirect-to and/or sitemap, as that appears to be
specific to each sitemap component.
Judging by the linkrewriter transformer javadocs[1], that looks for
input-module elements inside the map:transformer, and passes their contents
to the relevant module as the modeConf. Whether that's a general thing for
all transformers or specific to that one I'm not sure (though I suspect the
latter, since other transformers may not need to use an input module in the
same way). The global input module appears to be supplied with dynamic
configuration from the global-variables element in the
map:component-configurations part of the sitemap, presumably by the sitemap
tree processor?
As for the map:redirect-to entries, I've no idea if or how those might do
it. redirect-to appears to be merely a treeprocessor ProcessingNode rather
than PipelineEventComponentProcessingNode, and I don't see anything in its
invoke method that would do dynamic input module configuration prior to the
URI resolution.
Am I missing something, or is the only way to configure the xmlfile input
module for use in my map:redirect-to to put it in the cocoon.xconf? Or is
there somewhere else in the sitemap I can configure it? (e.g. something
under map:components or map:component-configurations?)
Asides from trying to configure the module closer to where I'm using it,
I've managed to solve the rest of my problem for now. Rather than messing
around with the directory generator, [x|c]include transformer and xsl to
combine the files, I used the xpathdirectory generator. Much neater; the
whole thing now just has
<map:pipeline internal-only="true">
<map:match pattern="external_links">
<map:generate type="xpathdirectory"
src="link_data">
<map:parameter name="xpath"
value="/link/href"/>
</map:generate>
<map:serialize type="xml"/>
</map:match>
</map:pipeline>
<map:pipeline>
<map:match pattern="goto/*">
<map:act type="resource-exists"
src="link_data/{1}">
<map:redirect-to
uri="{xmlfile://href[../../@name = '{../1}']}"/>
</map:act>
</map:match>
</map:pipeline>
in the sitemap, and
<input-modules>
...
<component-instance
class="org.apache.cocoon.components.modules.input.XMLFileModule"
logger="core.modules.xml" name="xmlfile">
<file src="cocoon://external_links"/>
<reloadable>true</reloadable>
<cacheable>true</cacheable>
</component-instance>
</input-modules>
in cocoon.xconf. If I could just shift the configuration to the sitemap so
I can reuse it with different directories/pipelines in different places,
it'd be even better :-)
Andrew.
[1]
http://cocoon.apache.org/2.1/apidocs/org/apache/cocoon/transformation/LinkRewriterTransformer.html
You need to override the getAttribute() method, and create a
DefaultConfiguration object with an element of 'file' and a 'src'
attribute with the URI of the XML file to read; your suggested xpointer
syntax is nice (although my own version didn't bother with that, and just
used a fragment identifier to separate the URI and the XPath).
i.e. you are programatically providing:
<file src="uri"/>
to the module via the modeConf. See the documentation for Avalon's
DefaultConfiguration object.
Beware of the caching though; document caching doesn't use the Transient
Cache, but instead a memory cache, which isn't even using SoftReferences
(although oddly the XPath cache does), so if you've got a large or
unlimited number of documents, turn caching off entirely (look at the code
for XMLFileModule), else you'll run the risk of running out of memory.
Ellis.
On 2 May 2006, at 18:38, Andrew Stevens wrote:
In the Cocoon javadocs[1] it says that input modules are passed a
dynamic, per-request configuration which will usually override the static
configuration from the cocoon.xconf. However, neither the javadocs nor
the Input Modules Reference[2] in the docs give any indication of how you
actually do this. Is it talking about something you can include in a
pipeline, or somehow within the {foo:bar} string of a sitemap
parameter/attribute? Or is it simply talking about the
<map:component-configurations> section of the pipeline? If the latter,
is it possible to include these within a pipeline matcher, and use any
available sitemap variables in the configured values?
My suspicion is the "dynamic" configuration isn't as dynamic as I need.
I have a number of XML files (using the same DTD) and need to extract a
value from one of them to pass into a map:redirect-to (which file to use
being supplied as part of the request). If I was using a single file, I
think I could handle it with the XMLFileModule; judging from the
URLEncode & decode input modules' docs, it's okay to nest input module
attributes (e.g. src="http://
remote/page?param1={url-encode:{request-param:param1}}"), so I reckon
something along the lines of <map:redirect-to uri="{xmlfile:/
document/[EMAIL PROTECTED]'{../1}'/url}"/> would work. With separate files, I
can just use {xmlfile:/document/link/url}, but how do I specify for each
request which file this is evaluated on?
If the XMLFileModule can't be used in this way, I guess I've got two
options:
- either write my own input module that takes an xinclude-like expression
as the attribute ({myxmlfile:{1}.xml#xpointer(/document/ link/url)})
specifying both the source file and jxpath
- or, (since the XMLFileModule user docs say the XML can be obtained from
any cocoon source) use the directory generator and c/ xinclude transformer
in a separate pipeline to combine all the files and configure the input
module to use that pipeline as its "file".
Or does anyone know of a better way?
Andrew.
[1] see under "Static/dynamic configuration" in http://
cocoon.apache.org/2.1/apidocs/org/apache/cocoon/components/modules/
input/package-summary.html
[2] http://cocoon.apache.org/2.1/userdocs/concepts/modules-ref.html
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]