Hi Folks, 

I saw the "hello world" file on github:
https://github.com/OpenDFDL/examples/blob/master/helloWorld/src/main/java/HelloWorld.java

I got it working. However, for me, it has two disadvantages:

1. It only works with XSLT 1.0
2. The Java code calls the XSLT code. I want it the other way around: I want 
the XSLT code to call the Java code.

I want to have a Java program that can be called from XSLT. The XSLT will pass 
to the Java program the name of the DFDL schema file and the name of the input 
file. I want the Java program to call Daffodil, requesting that it parse the 
input file using the schema file. I want the Java program to return XML. 

I am using Saxon as my XSLT processor. The Saxon web site 
(https://www.saxonica.com/html/documentation/extensibility/functions/staticmethods.html)
 says that, using Saxon, an XSLT program can call static Java methods. 

Below is the Java program (runDaffodil.java) that I created (it is a slight 
modification of the hello world program). I created a static method named 
doTransform. It takes two arguments: the name of a DFDL schema and the name of 
the input file. Does it appear to be correct? It seems to compile okay, 
producing runDaffodil.class.

When I run this XSLT:
-------------------------------------------------------------------------
<xsl:variable name="dfdl" select="doc('csv.dfdl.xsd')"/>
<xsl:variable name="input" select="doc('csv.txt')"/>

<xsl:template match="/">
    <xsl:value-of select="dfdl:doTransform($dfdl, $input)" 
        xmlns:dfdl="java:runDaffodil"/>
</xsl:template>
-------------------------------------------------------------------------
Saxon generates this error:

Static error in {dfdl:doTransform($dfdl, $input...} in expression in 
xsl:value-of/@select on line 10 column 44 of processCSV.xsl: XPST0017: Cannot 
find a 2-argument function named Q{java:runDaffodil}doTransform(). Cannot load 
Java class java:runDaffodil.

I included runDaffodil.class in my classpath.

Any suggestions on how to fix this?  /Roger
----------------------------------------------------
import java.io.File;
import java.io.IOException;
import java.net.URISyntaxException;
import java.net.URL;
import java.util.Collections;
import java.util.List;
import java.util.Map;

import org.jdom2.Content;
import org.jdom2.Document;
import org.jdom2.Namespace;
import org.jdom2.filter.ContentFilter;
import org.jdom2.output.XMLOutputter;
import org.jdom2.transform.XSLTransformException;
import org.jdom2.transform.XSLTransformer;
import org.jdom2.xpath.XPathExpression;
import org.jdom2.xpath.XPathFactory;

import org.apache.daffodil.japi.Compiler;
import org.apache.daffodil.japi.Daffodil;
import org.apache.daffodil.japi.DataProcessor;
import org.apache.daffodil.japi.Diagnostic;
import org.apache.daffodil.japi.ParseResult;
import org.apache.daffodil.japi.ProcessorFactory;
import org.apache.daffodil.japi.UnparseResult;
import org.apache.daffodil.japi.infoset.JDOMInfosetInputter;
import org.apache.daffodil.japi.infoset.JDOMInfosetOutputter;
import org.apache.daffodil.japi.infoset.JsonInfosetOutputter;
import org.apache.daffodil.japi.io.InputSourceDataInputStream;

public class runDaffodil {

    public static XMLOutputter doTransform(String dfdl, String input) throws 
IOException, XSLTransformException, URISyntaxException {

        URL dfdlURL = runDaffodil.class.getResource(dfdl);
        URL inputURL = runDaffodil.class.getResource(input);

        //
        // First, compile the DFDL Schema
        //
        Compiler c = Daffodil.compiler();
        ProcessorFactory pf = c.compileSource(dfdlURL.toURI());
        if (pf.isError()) {
            // didn't compile schema. Must be diagnostic of some sort. 
            List<Diagnostic> diags = pf.getDiagnostics();
            for (Diagnostic d : diags) {
                System.err.println(d.getSomeMessage());
            }
            System.exit(1);
        }
        DataProcessor dp = pf.onPath("/");
        if (dp.isError()) {
            // didn't compile schema. Must be diagnostic of some sort.
            List<Diagnostic> diags = dp.getDiagnostics();
            for (Diagnostic d : diags) {
                System.err.println(d.getSomeMessage());
            }
            System.exit(1);
        }
        //
        // Parse - parse data to XML
        //
        java.io.InputStream is = inputURL.openStream();
        InputSourceDataInputStream dis = new InputSourceDataInputStream(is);
        //
        // Setup JDOM outputter
        // 
        JDOMInfosetOutputter outputter = new JDOMInfosetOutputter();

        // Do the parse
        //
        ParseResult res = dp.parse(dis, outputter);

        // Check for errors
        //
        boolean err = res.isError();
        if (err) {
            // didn't parse the data. Must be diagnostic of some sort.
            List<Diagnostic> diags = res.getDiagnostics();
            for (Diagnostic d : diags) {
                System.err.println(d.getSomeMessage());
            }
            System.exit(2); 
        }
        
        Document doc = outputter.getResult();
        //
        // if we get here, we have a parsed infoset result!
        // Note that if we had only wanted this text, we could have used
        // a different outputter to create XML text directly,
        // but below we're going to transform this JDOM tree.
        //
        XMLOutputter xo = new 
XMLOutputter(org.jdom2.output.Format.getPrettyFormat());
        return xo;
    }
}

Reply via email to