diff --git a/WHATSNEW b/WHATSNEW index 578dfde19..ecd5a136c 100644 --- a/WHATSNEW +++ b/WHATSNEW @@ -560,6 +560,11 @@ Other changes: the "trax" processor included with Ant does support it. Bugzilla Report 18897. + * has two new attributes failOnError and + failOnTransformationError that can be used to not make the build + process proceed if an error occurs. + Bugzilla Report 36260. + Changes from Ant 1.7.0 TO Ant 1.7.1 ============================================= diff --git a/docs/manual/CoreTasks/style.html b/docs/manual/CoreTasks/style.html index 36b56e8e3..af43db68d 100644 --- a/docs/manual/CoreTasks/style.html +++ b/docs/manual/CoreTasks/style.html @@ -230,6 +230,23 @@ element which is used to perform Entity and URI resolution.

Since Ant 1.8.0. No, default is false. + + failOnError + Whether the build should fail if any error + occurs. Note that transformation errors can still be surpressed by + setting failOnTransformationError to false even if this attribute + is true. + Since Ant 1.8.0. + No, default is true. + + + failOnTransformationError + Whether the build should fail if an error occurs + while transforming the document. Note that this attribute has no + effect of failOnError is false. + Since Ant 1.8.0. + No, default is true. +

Parameters specified as nested elements

diff --git a/src/main/org/apache/tools/ant/taskdefs/XSLTProcess.java b/src/main/org/apache/tools/ant/taskdefs/XSLTProcess.java index eb1d4b446..7c69b3295 100644 --- a/src/main/org/apache/tools/ant/taskdefs/XSLTProcess.java +++ b/src/main/org/apache/tools/ant/taskdefs/XSLTProcess.java @@ -176,6 +176,20 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { */ private boolean suppressWarnings = false; + /** + * whether to fail the build if an error occurs during transformation. + * + * @since Ant 1.8.0 + */ + private boolean failOnTransformationError = true; + + /** + * whether to fail the build if an error occurs. + * + * @since Ant 1.8.0 + */ + private boolean failOnError = true; + /** * Creates a new XSLTProcess Task. */ @@ -213,9 +227,10 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { */ public void addMapper(Mapper mapper) { if (mapperElement != null) { - throw new BuildException("Cannot define more than one mapper", getLocation()); + handleError("Cannot define more than one mapper"); + } else { + mapperElement = mapper; } - mapperElement = mapper; } /** @@ -236,10 +251,11 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { */ public void addConfiguredStyle(Resources rc) { if (rc.size() != 1) { - throw new BuildException( - "The style element must be specified with exactly one nested resource."); + handleError("The style element must be specified with exactly one" + + " nested resource."); + } else { + setXslResource((Resource) rc.iterator().next()); } - setXslResource((Resource) rc.iterator().next()); } /** @@ -285,13 +301,16 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { + "or as a nested resource"; if (xslResource == null && xslFile == null) { - throw new BuildException(baseMessage, getLocation()); + handleError(baseMessage); + return; } if (xslResource != null && xslFile != null) { - throw new BuildException(baseMessage + " but not as both", getLocation()); + handleError(baseMessage + " but not as both"); + return; } if (inFile != null && !inFile.exists()) { - throw new BuildException("input file " + inFile + " does not exist", getLocation()); + handleError("input file " + inFile + " does not exist"); + return; } try { Resource styleResource; @@ -331,8 +350,8 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { } if (!styleResource.isExists()) { - throw new BuildException("stylesheet " + styleResource - + " doesn't exist."); + handleError("stylesheet " + styleResource + " doesn't exist."); + return; } // if we have an in file and out then process them @@ -370,7 +389,8 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { } } else { // only resource collections, there better be some if (resources.size() == 0) { - throw new BuildException("no resources specified"); + handleError("no resources specified"); + return; } } processResources(styleResource); @@ -538,6 +558,24 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { return suppressWarnings; } + /** + * Whether transformation errors should make the build fail. + * + * @since Ant 1.8.0 + */ + public void setFailOnTransformationError(boolean b) { + failOnTransformationError = b; + } + + /** + * Whether any errors should make the build fail. + * + * @since Ant 1.8.0 + */ + public void setFailOnError(boolean b) { + failOnError = b; + } + /** * Load processor here instead of in setProcessor - this will be * called from within execute, so we have access to the latest @@ -603,8 +641,7 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { */ private void checkDest() { if (destDir == null) { - String msg = "destdir attributes must be set!"; - throw new BuildException(msg); + handleError("destdir attributes must be set!"); } } @@ -691,8 +728,7 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { if (outF != null) { outF.delete(); } - - throw new BuildException(ex); + handleTransformationError(ex); } } //-- processXML @@ -727,7 +763,7 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { if (outFile != null) { outFile.delete(); } - throw new BuildException(ex); + handleTransformationError(ex); } } @@ -741,8 +777,8 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { File directory = targetFile.getParentFile(); if (!directory.exists()) { if (!directory.mkdirs()) { - throw new BuildException("Unable to create directory: " - + directory.getAbsolutePath()); + handleError("Unable to create directory: " + + directory.getAbsolutePath()); } } } @@ -787,14 +823,14 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { try { resolveProcessor(processor); } catch (Exception e) { - throw new BuildException(e); + handleError(e); } } else { try { resolveProcessor(PROCESSOR_TRAX); } catch (Throwable e1) { e1.printStackTrace(); - throw new BuildException(e1); + handleError(e1); } } } @@ -1026,8 +1062,9 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { if (fp != null) { liaison.setStylesheet(fp.getFile()); } else { - throw new BuildException(liaison.getClass().toString() - + " accepts the stylesheet only as a file", getLocation()); + handleError(liaison.getClass().toString() + + " accepts the stylesheet only as a file"); + return; } } for (Enumeration e = params.elements(); e.hasMoreElements();) { @@ -1038,7 +1075,7 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { } } catch (Exception ex) { log("Failed to transform using stylesheet " + stylesheet, Project.MSG_INFO); - throw new BuildException(ex); + handleTransformationError(ex); } } @@ -1074,12 +1111,58 @@ public class XSLTProcess extends MatchingTask implements XSLTLogger { */ public Factory createFactory() throws BuildException { if (factory != null) { - throw new BuildException("'factory' element must be unique"); + handleError("'factory' element must be unique"); + } else { + factory = new Factory(); } - factory = new Factory(); return factory; } + /** + * Throws an exception with the given message if failOnError is + * true, otherwise logs the message using the WARN level. + * + * @since Ant 1.8.0 + */ + protected void handleError(String msg) { + if (failOnError) { + throw new BuildException(msg, getLocation()); + } + log(msg, Project.MSG_WARN); + } + + + /** + * Throws an exception with the given nested exception if + * failOnError is true, otherwise logs the message using the WARN + * level. + * + * @since Ant 1.8.0 + */ + protected void handleError(Throwable ex) { + if (failOnError) { + throw new BuildException(ex); + } else { + log("Caught an exception: " + ex, Project.MSG_WARN); + } + } + + /** + * Throws an exception with the given nested exception if + * failOnError and failOnTransformationError are true, otherwise + * logs the message using the WARN level. + * + * @since Ant 1.8.0 + */ + protected void handleTransformationError(Exception ex) { + if (failOnError && failOnTransformationError) { + throw new BuildException(ex); + } else { + log("Caught an error during transformation: " + ex, + Project.MSG_WARN); + } + } + /** * The factory element to configure a transformer factory * @since Ant 1.6 diff --git a/src/tests/antunit/taskdefs/xslt-test.xml b/src/tests/antunit/taskdefs/xslt-test.xml index cd9bc12fc..f4b761a82 100644 --- a/src/tests/antunit/taskdefs/xslt-test.xml +++ b/src/tests/antunit/taskdefs/xslt-test.xml @@ -73,4 +73,47 @@ undefined='' style="i-m-not-there.xslt"/> + + + + + + + + + + + + + + + + + + + + + + + + + + + +