Package org.apache.ant.antunit.junit3

Source Code of org.apache.ant.antunit.junit3.AntUnitSuite$MyProjectFactory

/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements.  See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership.  The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License.  You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied.  See the License for the
* specific language governing permissions and limitations
* under the License.
*
*/

package org.apache.ant.antunit.junit3;

import java.io.File;
import java.io.PrintStream;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;

import junit.framework.Test;
import junit.framework.TestResult;
import junit.framework.TestSuite;

import org.apache.ant.antunit.AntUnitExecutionNotifier;
import org.apache.ant.antunit.AntUnitScriptRunner;
import org.apache.ant.antunit.ProjectFactory;
import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.DefaultLogger;
import org.apache.tools.ant.MagicNames;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.ProjectHelper;

/**
* A JUnit 3 TestSuite that group a suite of AntUnit targets coming from an ant
* script.
*/
public class AntUnitSuite extends TestSuite {

    private final AntUnitScriptRunner antScriptRunner;
    private final MultiProjectDemuxOutputStream stderr;
    private final MultiProjectDemuxOutputStream stdout;
    private final ErrorTestCase initializationReportingTest;

    /**
     * Create a JUnit TestSuite that when executed will run the given ant
     * script.<br/>
     * Note that it is the responsibility of the caller to give the correct
     * File reference. Namely, if the File is a relative file, it will
     * be resolve relatively to the execution directory (which might be
     * different different from the project root directory).
     *
     * @param scriptFile
     *            AntUnit script file
     * @param rootClass
     *            The test class that creates this suite. This is used to give
     *            a name to the suite so that an IDE can reexecute this suite.
     */
    public AntUnitSuite(File scriptFile, Class rootClass) {
        setName(rootClass.getName()); //This name allows eclipse to reexecute the test
        AntUnitScriptRunner createdScriptRunner = null;
        try {
            MyProjectFactory prjFactory = new MyProjectFactory(scriptFile);
            createdScriptRunner = new AntUnitScriptRunner(prjFactory);
        } catch (BuildException e) {
            antScriptRunner = null;
            stdout = null;
            stderr = null;
            initializationReportingTest = new ErrorTestCase(e);
            addTest(initializationReportingTest);
            return;
        }
        antScriptRunner = createdScriptRunner;
        initializationReportingTest = null;
        stdout = new MultiProjectDemuxOutputStream(antScriptRunner, false);
        stderr = new MultiProjectDemuxOutputStream(antScriptRunner, true);
        List testTargets = antScriptRunner.getTestTartgets();
        for (Iterator it = testTargets.iterator(); it.hasNext();) {
            String target = (String) it.next();
            AntUnitTestCase tc = new AntUnitTestCase(this, scriptFile, target);
            addTest(tc);
        }
    }

    /**
     * Constructor used by AntUnitTestCase when a single test case is created.
     * The difference with the public constructor is this version doesn't set
     * the name.
     * @throws BuildException when the file project can not be create (parsed/read)
     */
    AntUnitSuite(AntUnitTestCase singleTc , File scriptFile) throws BuildException {
        MyProjectFactory prjFactory = new MyProjectFactory(scriptFile);
        antScriptRunner = new AntUnitScriptRunner(prjFactory);
        //the exception is throwed, and it is up to the AntUnitTestCase to handle it.
        initializationReportingTest = null;
        stdout = new MultiProjectDemuxOutputStream(antScriptRunner, false);
        stderr = new MultiProjectDemuxOutputStream(antScriptRunner, true);
        setName(antScriptRunner.getName() + "[" + scriptFile + "]");
        addTest(singleTc);
    }
   
    /**
     * @Override Run the full AntUnit suite
     */
    public void run(TestResult testResult) {
        if (initializationReportingTest!=null) {
            initializationReportingTest.run(testResult);
        } else {
            List testTartgets = antScriptRunner.getTestTartgets();
            JUnitNotificationAdapter notifier = new JUnitNotificationAdapter(
                    testResult, tests());
            runInContainer(testTartgets, notifier);
        }
    }
   
    /**
     * @Override Run a single test target of the AntUnit suite. suiteSetUp,
     *           setUp, tearDown and suiteTearDown are executed around it.
     */
    public void runTest(Test test, TestResult result) {
        if (initializationReportingTest!=null) {
            initializationReportingTest.run(result);
        } else {
            String targetName = ((AntUnitTestCase) test).getTarget();
            List singleTargetList = Collections.singletonList(targetName);
            JUnitNotificationAdapter notifier = new JUnitNotificationAdapter(
                    result, tests());
            runInContainer(singleTargetList, notifier);
        }
    }

    /**
     * Execute the test suite in a 'container' similar to the ant 'container'.
     * When ant executes a project it redirect the input and the output. In this
     * context we will only redirect output (unit test are not supposed to be
     * interactive).<br/>
     *
     * @param targetList
     *            The list of test target to execute
     * @param notifier
     *            The AntUnit notifier that will receive execution notifications
     */
    public void runInContainer(List targetList, AntUnitExecutionNotifier notifier) {       
        PrintStream savedErr = System.err;
        PrintStream savedOut = System.out;
        try {
            System.setOut(new PrintStream(stdout));
            System.setErr(new PrintStream(stderr));
            antScriptRunner.runSuite(targetList, notifier);
        } finally {
            System.setOut(savedOut);
            System.setErr(savedErr);
        }
    }

    /**
     * The antscript project factory that creates projects in a junit context.
     */
    private static class MyProjectFactory implements ProjectFactory {

        private final File scriptFile;
        private final PrintStream realStdErr = System.err;
        private final PrintStream realStdOut = System.out;

        public MyProjectFactory(File scriptFile) {
            this.scriptFile = scriptFile;
        }

        public Project createProject() {
            ProjectHelper prjHelper = ProjectHelper.getProjectHelper();
            Project prj = new Project();
            DefaultLogger logger = new DefaultLogger();
            logger.setMessageOutputLevel(Project.MSG_INFO);
            logger.setErrorPrintStream(realStdErr);
            logger.setOutputPrintStream(realStdOut);
            prj.addBuildListener(logger);
            String absolutePath = scriptFile.getAbsolutePath();
            prj.setUserProperty(MagicNames.ANT_FILE, absolutePath);
            prj.addReference(ProjectHelper.PROJECTHELPER_REFERENCE, prjHelper);
            prj.init();
            prjHelper.parse(prj, scriptFile);
            return prj;
        }
    }

    public boolean hasAntInitError() {
        return this.initializationReportingTest!=null;
    }

    public BuildException getAntInitialisationException() {
        return hasAntInitError() ?
                initializationReportingTest.getAntScriptError() :
                null;
    }
}
TOP

Related Classes of org.apache.ant.antunit.junit3.AntUnitSuite$MyProjectFactory

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.