KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > fop > tools > TestConverter


1 /*
2  * $Id: TestConverter.java,v 1.15.2.4 2003/02/25 15:19:57 jeremias Exp $
3  * ============================================================================
4  * The Apache Software License, Version 1.1
5  * ============================================================================
6  *
7  * Copyright (C) 1999-2003 The Apache Software Foundation. All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without modifica-
10  * tion, are permitted provided that the following conditions are met:
11  *
12  * 1. Redistributions of source code must retain the above copyright notice,
13  * this list of conditions and the following disclaimer.
14  *
15  * 2. Redistributions in binary form must reproduce the above copyright notice,
16  * this list of conditions and the following disclaimer in the documentation
17  * and/or other materials provided with the distribution.
18  *
19  * 3. The end-user documentation included with the redistribution, if any, must
20  * include the following acknowledgment: "This product includes software
21  * developed by the Apache Software Foundation (http://www.apache.org/)."
22  * Alternately, this acknowledgment may appear in the software itself, if
23  * and wherever such third-party acknowledgments normally appear.
24  *
25  * 4. The names "FOP" and "Apache Software Foundation" must not be used to
26  * endorse or promote products derived from this software without prior
27  * written permission. For written permission, please contact
28  * apache@apache.org.
29  *
30  * 5. Products derived from this software may not be called "Apache", nor may
31  * "Apache" appear in their name, without prior written permission of the
32  * Apache Software Foundation.
33  *
34  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES,
35  * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
36  * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
37  * APACHE SOFTWARE FOUNDATION OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
38  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLU-
39  * DING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
40  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
41  * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
42  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
43  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
44  * ============================================================================
45  *
46  * This software consists of voluntary contributions made by many individuals
47  * on behalf of the Apache Software Foundation and was originally created by
48  * James Tauber <jtauber@jtauber.com>. For more information on the Apache
49  * Software Foundation, please see <http://www.apache.org/>.
50  */

51 package org.apache.fop.tools;
52
53 import org.apache.fop.apps.*;
54 import org.apache.fop.configuration.*;
55 import org.apache.fop.messaging.MessageHandler;
56
57 import org.apache.avalon.framework.logger.ConsoleLogger;
58 import org.apache.avalon.framework.logger.Logger;
59
60 import java.io.*;
61 import java.util.*;
62
63 import javax.xml.parsers.*;
64
65 import org.w3c.dom.*;
66 import org.xml.sax.XMLReader JavaDoc;
67 import org.xml.sax.SAXException JavaDoc;
68
69 /**
70  * TestConverter is used to process a set of tests specified in
71  * a testsuite.
72  * This class retrieves the data in the testsuite and uses FOP
73  * to convert the xml and xsl file into either an xml representation
74  * of the area tree or a pdf document.
75  * The area tree can be used for automatic comparisons between different
76  * versions of FOP or the pdf can be view for manual checking and
77  * pdf rendering.
78  *
79  * Modified by Mark Lillywhite mark-fop@inomial.com to use the new Driver
80  * interface.
81  */

82 public class TestConverter {
83     boolean failOnly = false;
84     boolean outputPDF = false;
85     File destdir;
86     File compare = null;
87     String JavaDoc baseDir = "./";
88     HashMap differ = new HashMap();
89     private Logger log;
90
91     /**
92      * This main method can be used to run the test converter from
93      * the command line.
94      * This will take a specified testsuite xml and process all
95      * tests in it.
96      * The command line options are:
97      * -b to set the base directory for where the testsuite and associated files are
98      * -failOnly to process only the tests which are specified as fail in the test results
99      * -pdf to output the result as pdf
100      */

101     public static void main(String JavaDoc[] args) {
102         if (args == null || args.length == 0) {
103             System.out.println("test suite file name required");
104         }
105         TestConverter tc = new TestConverter();
106
107         String JavaDoc testFile = null;
108         for (int count = 0; count < args.length; count++) {
109             if (args[count].equals("-failOnly")) {
110                 tc.setFailOnly(true);
111             } else if (args[count].equals("-pdf")) {
112                 tc.setOutputPDF(true);
113             } else if (args[count].equals("-b")) {
114                 tc.setBaseDir(args[count + 1]);
115             } else {
116                 testFile = args[count];
117             }
118         }
119         if (testFile == null) {
120             System.out.println("test suite file name required");
121         }
122
123         tc.runTests(testFile, "results", null);
124     }
125
126     public TestConverter() {
127         setupLogging();
128     }
129
130     private void setupLogging() {
131         log = new ConsoleLogger(ConsoleLogger.LEVEL_ERROR);
132         MessageHandler.setScreenLogger(log);
133     }
134
135     public void setOutputPDF(boolean pdf) {
136         outputPDF = pdf;
137     }
138
139     public void setFailOnly(boolean fail) {
140         failOnly = fail;
141     }
142
143     public void setBaseDir(String JavaDoc str) {
144         baseDir = str;
145     }
146
147     /**
148      * Run the Tests.
149      * This runs the tests specified in the xml file fname.
150      * The document is read as a dom and each testcase is covered.
151      */

152     public HashMap runTests(String JavaDoc fname, String JavaDoc dest, String JavaDoc compDir) {
153         log.debug("running tests in file:" + fname);
154         try {
155             if (compDir != null) {
156                 compare = new File(baseDir + "/" + compDir);
157             }
158             destdir = new File(baseDir + "/" + dest);
159             destdir.mkdirs();
160             File f = new File(baseDir + "/" + fname);
161             DocumentBuilderFactory factory =
162                 DocumentBuilderFactory.newInstance();
163             DocumentBuilder db = factory.newDocumentBuilder();
164             Document doc = db.parse(f);
165
166             NodeList suitelist = doc.getChildNodes();
167             if (suitelist.getLength() == 0) {
168                 return differ;
169             }
170
171             Node testsuite = null;
172             testsuite = doc.getDocumentElement();
173
174             if (testsuite.hasAttributes()) {
175                 String JavaDoc profile =
176                     testsuite.getAttributes().getNamedItem("profile").getNodeValue();
177                 log.debug("testing test suite:" + profile);
178             }
179
180             NodeList testcases = testsuite.getChildNodes();
181             for (int count = 0; count < testcases.getLength(); count++) {
182                 Node testcase = testcases.item(count);
183                 if (testcase.getNodeName().equals("testcases")) {
184                     runTestCase(testcase);
185                 }
186             }
187         } catch (Exception JavaDoc e) {
188             e.printStackTrace();
189         }
190         return differ;
191     }
192
193     /**
194      * Run a test case.
195      * This goes through a test case in the document.
196      * A testcase can contain a test, a result or more test cases.
197      * A test case is handled recursively otherwise the test is run.
198      */

199     protected void runTestCase(Node tcase) {
200         if (tcase.hasAttributes()) {
201             String JavaDoc profile =
202                 tcase.getAttributes().getNamedItem("profile").getNodeValue();
203             log.debug("testing profile:" + profile);
204         }
205
206         NodeList cases = tcase.getChildNodes();
207         for (int count = 0; count < cases.getLength(); count++) {
208             Node node = cases.item(count);
209             String JavaDoc nodename = node.getNodeName();
210             if (nodename.equals("testcases")) {
211                 runTestCase(node);
212             } else if (nodename.equals("test")) {
213                 runTest(tcase, node);
214             } else if (nodename.equals("result")) {}
215
216         }
217
218     }
219
220     /**
221      * Run a particular test.
222      * This runs a test defined by the xml and xsl documents.
223      * If the test has a result specified it is checked.
224      * This creates an XSLTInputHandler to provide the input
225      * for FOP and writes the data out to an XML are tree.
226      */

227     protected void runTest(Node testcase, Node test) {
228         String JavaDoc id = test.getAttributes().getNamedItem("id").getNodeValue();
229         Node result = locateResult(testcase, id);
230         boolean pass = false;
231         if (result != null) {
232             String JavaDoc agreement =
233                 result.getAttributes().getNamedItem("agreement").getNodeValue();
234             pass = agreement.equals("full");
235         }
236
237         if (pass && failOnly) {
238             return;
239         }
240
241         String JavaDoc xml = test.getAttributes().getNamedItem("xml").getNodeValue();
242         Node xslNode = test.getAttributes().getNamedItem("xsl");
243         String JavaDoc xsl = null;
244         if (xslNode != null) {
245             xsl = xslNode.getNodeValue();
246         }
247         log.debug("converting xml:" + xml + " and xsl:" +
248                   xsl + " to area tree");
249
250         try {
251             File xmlFile = new File(baseDir + "/" + xml);
252
253             try {
254                 Configuration.put("baseDir",
255                                   xmlFile.getParentFile().toURL().toExternalForm());
256             } catch (Exception JavaDoc e) {
257                 log.error("Error setting base directory");
258             }
259
260             InputHandler inputHandler = null;
261             if (xsl == null) {
262                 inputHandler = new FOInputHandler(xmlFile);
263             } else {
264                 inputHandler = new XSLTInputHandler(xmlFile,
265                                                     new File(baseDir + "/"
266                                                              + xsl));
267             }
268
269             XMLReader JavaDoc parser = inputHandler.getParser();
270             setParserFeatures(parser);
271
272             Logger logger = log.getChildLogger("fop");
273             Driver driver = new Driver();
274             driver.setLogger(logger);
275             if (outputPDF) {
276                 driver.setRenderer(Driver.RENDER_PDF);
277             } else {
278                 driver.setRenderer(Driver.RENDER_XML);
279             }
280
281             HashMap rendererOptions = new HashMap();
282             rendererOptions.put("fineDetail", new Boolean JavaDoc(false));
283             rendererOptions.put("consistentOutput", new Boolean JavaDoc(true));
284             driver.getRenderer().setOptions(rendererOptions);
285             driver.getRenderer().setProducer("Testsuite Converter");
286
287             String JavaDoc outname = xmlFile.getName();
288             if (outname.endsWith(".xml")) {
289                 outname = outname.substring(0, outname.length() - 4);
290             }
291             driver.setOutputStream(new BufferedOutputStream(
292                                        new FileOutputStream(new File(destdir,
293                                        outname + (outputPDF ? ".pdf" : ".at.xml")))));
294             log.debug("ddir:" + destdir + " on:" + outname + ".pdf");
295             driver.render(parser, inputHandler.getInputSource());
296
297             // check difference
298
if (compare != null) {
299                 File f1 = new File(destdir, outname + ".at.xml");
300                 File f2 = new File(compare, outname + ".at.xml");
301                 if (!compareFiles(f1, f2)) {
302                     differ.put(outname + ".at.xml", new Boolean JavaDoc(pass));
303                 }
304             }
305         } catch (Exception JavaDoc e) {
306             e.printStackTrace();
307         }
308     }
309
310     /**
311      * Compare files.
312      * Returns true if equal.
313      */

314     protected boolean compareFiles(File f1, File f2) {
315         if(f1.length() != f2.length()) {
316             return false;
317         }
318         try {
319             InputStream is1 = new BufferedInputStream(new FileInputStream(f1));
320             InputStream is2 = new BufferedInputStream(new FileInputStream(f2));
321             while (true) {
322                 int ch1 = is1.read();
323                 int ch2 = is2.read();
324                 if (ch1 == ch2) {
325                     if (ch1 == -1) {
326                         return true;
327                     }
328                 } else {
329                     return false;
330                 }
331             }
332         } catch (Exception JavaDoc e) {}
333
334         return false;
335     }
336
337     public void setParserFeatures(XMLReader JavaDoc parser) throws FOPException {
338         try {
339             parser.setFeature("http://xml.org/sax/features/namespace-prefixes",
340                               true);
341         } catch (SAXException JavaDoc e) {
342             throw new FOPException("Error in setting up parser feature namespace-prefixes\n"
343                                    + "You need a parser which supports SAX version 2", e);
344         }
345     }
346
347     protected Node locateResult(Node testcase, String JavaDoc id) {
348         NodeList cases = testcase.getChildNodes();
349         for (int count = 0; count < cases.getLength(); count++) {
350             Node node = cases.item(count);
351             String JavaDoc nodename = node.getNodeName();
352             if (nodename.equals("result")) {
353                 String JavaDoc resultid =
354                     node.getAttributes().getNamedItem("id").getNodeValue();
355                 if (id.equals(resultid)) {
356                     return node;
357                 }
358             }
359         }
360         return null;
361     }
362
363 }
364
Popular Tags