/* * The MIT License (MIT) * * Copyright (c) 2007-2015 Broad Institute * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. * * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ package util; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.types.Parameter; import org.junit.Ignore; import org.w3c.dom.Document; import org.w3c.dom.NamedNodeMap; import org.w3c.dom.Node; import org.w3c.dom.NodeList; import org.xml.sax.SAXException; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import java.io.*; import java.util.HashSet; import java.util.Set; /** * Selector for re-running failed tests. * Examines the provided reports and only accepts files * which match tests that previously failed (or had an error) * * Reports must use standard JUnit XML. * User: jacob * Date: 2012-Jul-18 */ @Ignore public class FailedTestSelector extends org.apache.tools.ant.types.selectors.BaseExtendSelector{ /** * The directory containing reports. Required input. */ private String reportDir = null; /** * The filename of the test report. If * null, will look at every .xml file in the directory */ private String reportFile = null; private Exception errorParsingReportFile = null; private Set<String> failingTests = new HashSet<String>(); public FailedTestSelector(){ super(); } @Override public void setParameters(Parameter[] parameters){ super.setParameters(parameters); for(Parameter p: getParameters()){ if(p.getName().equalsIgnoreCase("reportDir")){ reportDir = p.getValue(); } if(p.getName().equalsIgnoreCase("reportFile")){ reportFile = p.getValue(); } } if(reportDir == null){ throw new RuntimeException("reportDir is required"); } if(reportFile != null){ //Parse a single file, throw exception if fail File checkFile = new File(reportDir, reportFile); try { checkReportFile(checkFile.getAbsolutePath()); } catch (IOException e) { e.printStackTrace(); errorParsingReportFile = e; } catch (SAXException e) { e.printStackTrace(); errorParsingReportFile = e; } catch (ParserConfigurationException e) { e.printStackTrace(); errorParsingReportFile = e; } }else{ File dir = new File(reportDir); File[] files = dir.listFiles(new FilenameFilter() { @Override public boolean accept(File dir, String name) { return name.endsWith(".xml"); } }); for(File fi: files){ try{ checkReportFile(fi.getAbsolutePath()); } catch (SAXException e) { //Don't care, might be other xml file } catch (ParserConfigurationException e) { // } catch (IOException e) { e.printStackTrace(); errorParsingReportFile = e; } } } } private void checkReportFile(String filePath) throws IOException, SAXException, ParserConfigurationException{ InputStream inStream = new FileInputStream(filePath); Document doc = createDOMDocumentFromXmlStream(inStream); NodeList nodes = doc.getElementsByTagName("testsuite"); for(int nn=0; nn < nodes.getLength(); nn++){ Node node = nodes.item(nn); NamedNodeMap attribs = node.getAttributes(); int errors = Integer.parseInt(attribs.getNamedItem("errors").getTextContent()); int failures = Integer.parseInt(attribs.getNamedItem("failures").getTextContent()); if(errors > 0 || failures > 0){ //This may be a full package name, or just the class //All we really need is the class name String testName = attribs.getNamedItem("name").getTextContent(); String[] pieces = testName.split("\\."); if(pieces.length > 1){ testName = pieces[pieces.length - 1]; } failingTests.add(testName); } } } @Override public boolean isSelected(File directory, String filename, File file) throws BuildException { if(errorParsingReportFile != null){ throw new BuildException("Error processing result file", errorParsingReportFile); } //Strip extension, only check file name (not full path) String baseFileName = file.getName().split("\\.", 2)[0]; return failingTests.contains(baseFileName); } /** * Reads an xml from an input stream and creates DOM document. * * @param inStream * @return * @throws ParserConfigurationException * @throws IOException * @throws SAXException */ public static Document createDOMDocumentFromXmlStream(InputStream inStream) throws ParserConfigurationException, IOException, SAXException { DocumentBuilder documentBuilder = DocumentBuilderFactory.newInstance().newDocumentBuilder(); Document xmlDocument = documentBuilder.parse(inStream); return xmlDocument; } }