That seems promising. However, the "Module.NAMESPACE_URI,
Module.PREFIX" part gives me 4 compilation errors, starting with:
[javac] E:\Program\eXist1203\src\com\nps\xquery\request\DocFunction.java:30:
cannot find symbol
[javac] symbol : variable Module
I have not written any extension moduels myself, so I have no idea
about how to fix this.... what could be wrong here?
Regards
Hans
On 1/6/06, Suzan Foster <[EMAIL PROTECTED]> wrote:
> The problem however with using variables is that eXist can only operate
> on it's own persistent DOM implementation within the query. You need to
> create a temporary document to pass to the XQuery. I hit this problem
> when writing an extension function for processing the request as XML
> (sent by an XForm) and wrote the following implementation:
>
> package com.nps.xquery.request;
>
> import org.exist.dom.QName;
> import org.exist.http.servlets.RequestWrapper;
> import org.exist.xquery.functions.request.RequestModule;
> import org.exist.xquery.XQueryContext;
> import org.exist.xquery.BasicFunction;
> import org.exist.xquery.Cardinality;
> import org.exist.xquery.FunctionSignature;
> import org.exist.xquery.XPathException;
> import org.exist.xquery.Variable;
> import org.exist.xquery.value.Sequence;
> import org.exist.xquery.value.SequenceType;
> import org.exist.xquery.value.Type;
> import org.exist.xquery.value.JavaObjectValue;
> import org.exist.dom.NodeProxy;
> import org.exist.dom.DocumentImpl;
> import org.exist.dom.NodeImpl;
> import org.exist.memtree.MemTreeBuilder;
> import org.exist.memtree.DocumentBuilderReceiver;
> import javax.xml.parsers.SAXParserFactory;
>
> import org.xml.sax.InputSource;
> import org.xml.sax.XMLReader;
>
> public class DocFunction extends BasicFunction {
>
> public final static FunctionSignature signature =
> new FunctionSignature(
> new QName("doc", Module.NAMESPACE_URI, Module.PREFIX),
> "",
> null,
> new SequenceType(Type.NODE, Cardinality.ZERO_OR_ONE)
> );
>
> public DocFunction(XQueryContext context) {
> super(context, signature);
> }
>
> public Sequence eval(Sequence[] arg0, Sequence arg1) throws
> XPathException {
> RequestModule requestModule =
> (RequestModule) context.getModule(RequestModule.NAMESPACE_URI);
>
> // request object is read from global variable $request
> Variable var =
> requestModule.resolveVariable(RequestModule.REQUEST_VAR);
> if(var == null)
> throw new XPathException("No request object found in the
> current XQuery context.");
> if (var.getValue().getItemType() != Type.JAVA_OBJECT)
> throw new XPathException("Variable $request is not bound to
> a Java object.");
> JavaObjectValue value = (JavaObjectValue) var.getValue().itemAt(0);
> if (value.getObject() instanceof RequestWrapper) {
> RequestWrapper request = (RequestWrapper)value.getObject();
> try {
> MemTreeBuilder builder = context.getDocumentBuilder();
> DocumentBuilderReceiver receiver = new
> DocumentBuilderReceiver(builder);
> SAXParserFactory factory = SAXParserFactory.newInstance();
> factory.setNamespaceAware(true);
> XMLReader reader = factory.newSAXParser().getXMLReader();
> reader.setContentHandler(receiver);
> reader.parse(new InputSource(request.getInputStream()));
> DocumentImpl doc =
> context.storeTemporaryDoc(builder.getDocument());
> NodeImpl node =
> (NodeImpl)doc.getDocumentElement().getFirstChild();
> return new NodeProxy(doc, node.getGID(),
> node.getInternalAddress());
> }
> catch (Exception e) {
> throw new XPathException(getASTNode(), e.getMessage(), e);
> }
> } else
> throw new XPathException("Variable $request is not bound to
> a Request object.");
> }
> }
>
> I think it should be possible to use such a temporary document as
> context for the XQuery using XQueryService.query(XMLResource, String).
>
> Jean-Baptiste Quenot wrote:
>
> >* Jonas Lundberg:
> >
> >
> >
> >>That might work, but it is not a good solution for me, although
> >>it might work in other cases. My xqueries are very complex. But
> >>this can't end here, can it? Is there really no way of returning
> >>XML in a parameter from a flowscript in Cocoon?
> >>
> >>
> >
> >Sitemap parameters are Strings, not Objects. You cannot pass a
> >DOM. However you can execute an XQuery without the
> >XQueryGenerator, Java snippet follows:
> >
> > public static Node executeXQuery(Collection collection, Source
> > inputSource, Map variables, Logger logger) throws XMLDBException {
> > XQueryService service = (XQueryService)
> > collection.getService(
> > "XQueryService", "1.0");
> > service.setProperty(Serializer.GENERATE_DOC_EVENTS, "false");
> > if (variables != null) {
> > if (logger != null) logger.debug("Executing " +
> > inputSource.getURI() + " with variables " + variables);
> > Iterator it = variables.entrySet().iterator();
> > while (it.hasNext()) {
> > Map.Entry entry = (Map.Entry)it.next();
> >
> > service.declareVariable((String)entry.getKey(), entry.getValue());
> > }
> > } else {
> > if (logger != null) logger.debug("Executing " +
> > inputSource.getURI());
> > }
> > ResourceSet result = service.execute(new
> > CocoonSource(inputSource, true));
> > if (result == null) {
> > if (logger != null) logger.error("null result after
> > executing XQuery!");
> > return null; // a DOM Node cannot be null so null
> > can be used safely for signaling errors
> > }
> > if (result.getSize() == 0) {
> > if (logger != null) logger.error("empty XML result
> > after executing XQuery!");
> > return null; // a DOM Node cannot be null so null
> > can be used safely for signaling errors
> > }
> > XMLResource resource = (XMLResource) result.getResource(0);
> > return resource.getContentAsDOM();
> > }
> >
> >But I think the best solution in order to save directly an XML
> >document in the XML database is to use the XMLDBSource with
> >saveDocumentToSource("xmldb:exist://localhost:8080/exist/xmlrpc/db/file.xml",
> > document),
> >FlowScript snippet follows:
> >
> >/*
> > * Save XML document to source.
> > * Parameters :
> > * outputMode : the desired output mode : 'html', 'xml', or 'text'
> > * Defaults to "xml"
> > */
> >function saveDocumentToSource(source, document, outputMode ) {
> > var tf =
> > Packages.javax.xml.transform.TransformerFactory.newInstance();
> > var outputStream = null;
> >
> > // If no mode is specified, we use XML
> > if(! outputMode) {
> > outputMode = 'xml';
> > }
> >
> > try {
> > if (source instanceof
> > Packages.org.apache.excalibur.source.ModifiableSource
> > &&
> > tf.getFeature(Packages.javax.xml.transform.sax.SAXTransformerFactory.FEATURE))
> > {
> > outputStream = source.getOutputStream();
> > var transformer = tf.newTransformer();
> >
> > transformer.setOutputProperty(Packages.javax.xml.transform.OutputKeys.INDENT,
> > "yes");
> >
> > transformer.setOutputProperty(Packages.javax.xml.transform.OutputKeys.METHOD,
> > outputMode);
> > transformer.transform(
> > new
> > Packages.javax.xml.transform.dom.DOMSource(document),
> > new
> > Packages.javax.xml.transform.stream.StreamResult(outputStream));
> > } else {
> > throw new
> > Packages.org.apache.cocoon.ProcessingException("Cannot write to source " +
> > uri);
> > }
> > } finally {
> > if (outputStream != null) {
> > outputStream.flush();
> > outputStream.close();
> > }
> > }
> >}
> >
> >Best regards,
> >
> >
>
>
> --
>
> Met vriendelijke groet,
>
> Suzan Foster
> Software Engineer
>
> *NEROC'MEDIAWARE *
> De Run 1131
> 5503 LB Veldhoven
> T +31 (0)40 258 66 66
> F +31 (0)40 258 66 77
>
> E [EMAIL PROTECTED] <mailto:[EMAIL PROTECTED]>
>
> ================================================
> De informatie opgenomen in dit bericht kan vertrouwelijk zijn en
> is uitsluitend bestemd voor de geadresseerde. Indien u dit bericht
> onterecht ontvangt, wordt u verzocht de inhoud niet te gebruiken en
> de afzender direct te informeren door het bericht te retourneren.
> ================================================
> The information contained in this message may be confidential
> and is intended to be exclusively for the addressee. Should you
> receive this message unintentionally, please do not use the contents
> herein and notify the sender immediately by return e-mail.
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: [EMAIL PROTECTED]
> For additional commands, e-mail: [EMAIL PROTECTED]
>
>
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]