Project

Profile

Help

Support #2252 » SaxonIDValidationTest.java

Jason Mihalick, 2014-12-10 23:43

 
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.StringReader;

import javax.xml.transform.ErrorListener;
import javax.xml.transform.Result;
import javax.xml.transform.Source;
import javax.xml.transform.Templates;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerException;
import javax.xml.transform.sax.SAXSource;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamSource;

import net.sf.saxon.Controller;
import net.sf.saxon.TransformerFactoryImpl;

import org.xml.sax.InputSource;

import com.saxonica.Validate;
import com.saxonica.config.EnterpriseConfiguration;

public class SaxonIDValidationTest {

public static class StdErrorListener implements ErrorListener {

@Override
public void warning( TransformerException exception ) throws TransformerException {
System.out.println( String.format( "Transformer WARNING: %s", exception.getMessage() ) );
exception.printStackTrace( System.out );
}
@Override
public void error( TransformerException exception ) throws TransformerException {
System.out.println( String.format( "Transformer ERROR: %s", exception.getMessage() ) );
exception.printStackTrace( System.out );
}
@Override
public void fatalError( TransformerException exception ) throws TransformerException {
System.out.println( String.format( "Transformer FATAL ERROR: %s", exception.getMessage() ) );
exception.printStackTrace( System.out );
}
}

// Place schema.xsd in the working directory that you run this class from
public static final String SCHEMA_LOCATION = "schema.xsd";
// A simple XSL that demonstrates an example of an error that is caught during a parse which is not
// caught when validating during transform.
private static final String XSL_TEXT =
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
+ "<xsl:stylesheet version=\"2.0\" xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" exclude-result-prefixes=\"#all\">"
+ " <xsl:output method=\"xml\" version=\"1.0\" encoding=\"UTF-8\"/>"
+ " <xsl:import-schema schema-location=\"" + SCHEMA_LOCATION + "\"/>"

+ " <xsl:template match=\"@*|node()\">"
+ " <xsl:copy copy-namespaces=\"no\">"
+ " <xsl:apply-templates select=\"@*|node()\"/>"
+ " </xsl:copy>"
+ " </xsl:template>"

+ " <xsl:template match=\"/elementA\">"
+ " <elementA %s>" // Use String.format to turn schema validation on/off
+ " <xsl:attribute name=\"id\" select=\"@id\"/>"
+ " <xsl:namespace name=\"xsi\" select=\"'http://www.w3.org/2001/XMLSchema-instance'\"/>"
+ " <xsl:attribute name=\"xsi:noNamespaceSchemaLocation\" select=\"'" + SCHEMA_LOCATION + "'\"/>"
+ " <xsl:apply-templates select=\"node()\"/>"
+ " </elementA>"
+ " </xsl:template>"
+ "</xsl:stylesheet>"
;
// Substitute in xsl:validation="strict" on elementA in XSL_TEXT
public static final String XSL_WITH_VALIDATION = String.format( XSL_TEXT, "xsl:validation=\"strict\"" );
// Substitute empty string on elementA, which will do the transform without a validation
public static final String XSL_WITHOUT_VALIDATION = String.format( XSL_TEXT, "" );
// The XML to transform and validate
public static final String XML_TEXT =
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
+ "<elementA "
+ " xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\""
+ " xsi:noNamespaceSchemaLocation=\"" + SCHEMA_LOCATION + "\""
+ " id=\"ID001\">"
+ " <elementB>"
+ " <elementID rid=\"ID002\"/>" // ID002 Does not exist
+ " </elementB>"
+ " <elementC>"
+ " </elementC>"
+ "</elementA>";
public void doValidationOnTransform() throws Exception {
TransformerFactoryImpl tf = new TransformerFactoryImpl();
tf.setErrorListener( new StdErrorListener() );
Templates xsltTemplate = tf.newTemplates( new SAXSource( new InputSource( new ByteArrayInputStream( XSL_WITH_VALIDATION.getBytes() ) ) ) );
Transformer xformer = xsltTemplate.newTransformer();
Source xmlSource = new StreamSource( new StringReader( XML_TEXT ) );
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
Result xmlResult = new StreamResult( outputStream );
xformer.transform( xmlSource, xmlResult );
}

public void doValidationAfterTransform() throws Exception {
// Do transformation first
TransformerFactoryImpl tf = new TransformerFactoryImpl();
tf.setErrorListener( new StdErrorListener() );
Templates xsltTemplate = tf.newTemplates( new SAXSource( new InputSource( new ByteArrayInputStream( XSL_WITHOUT_VALIDATION.getBytes() ) ) ) );
Transformer xformer = xsltTemplate.newTransformer();
Source xmlSource = new StreamSource( new StringReader( XML_TEXT ) );
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
Result xmlResult = new StreamResult( outputStream );
xformer.transform( xmlSource, xmlResult );
// Now Validate the result
xmlSource = new StreamSource( new ByteArrayInputStream( outputStream.toByteArray() ) );
EnterpriseConfiguration config = new EnterpriseConfiguration();
Controller controller = new Controller( config );
controller.getExecutable().setSchemaAware(true);
Validate validate = new Validate();
validate.processFile( xmlSource, controller );
}

public static void main( String[] args ) throws Exception {
SaxonIDValidationTest test = new SaxonIDValidationTest();
try {
test.doValidationOnTransform();
System.out.println( "doValidationOnTransform SUCCESS." );
} catch ( Exception ex ) {
System.out.println( "doValidationOnTransform FAILED!" );
ex.printStackTrace();
}
try {
test.doValidationAfterTransform();
System.out.println( "doValidationAfterTransform SUCCESS." );
} catch ( Exception ex ) {
System.out.println( "doValidationAfterTransform FAILED!" );
ex.printStackTrace();
}
}
}
(2-2/2)