org.evosuite.junit.FooTestClassLoader.java Source code

Java tutorial

Introduction

Here is the source code for org.evosuite.junit.FooTestClassLoader.java

Source

/**
 * Copyright (C) 2010-2016 Gordon Fraser, Andrea Arcuri and EvoSuite
 * contributors
 *
 * This file is part of EvoSuite.
 *
 * EvoSuite is free software: you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License as published
 * by the Free Software Foundation, either version 3.0 of the License, or
 * (at your option) any later version.
 *
 * EvoSuite is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with EvoSuite. If not, see <http://www.gnu.org/licenses/>.
 */
package org.evosuite.junit;

import static org.junit.Assert.assertNotNull;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URI;
import java.net.URL;
import java.net.URLClassLoader;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Locale;

import javax.tools.DiagnosticCollector;
import javax.tools.JavaCompiler;
import javax.tools.JavaCompiler.CompilationTask;
import javax.tools.JavaFileObject;
import javax.tools.StandardJavaFileManager;
import javax.tools.ToolProvider;

import org.apache.commons.io.FileUtils;
import org.junit.Test;

import com.examples.with.different.packagename.junit.Foo;

public class FooTestClassLoader {

    private static final String FOO_TEST_CLASS_NAME = "com.examples.with.different.packagename.junit.FooTest";

    @Test
    public void testFooTestClassCreation() throws IOException {
        Class<?> clazz = loadFooTestClass();
        assertNotNull(clazz);
    }

    private static String createFooTestJavaText() {
        StringBuffer buff = new StringBuffer();
        buff.append("package com.examples.with.different.packagename.junit;\n");
        buff.append("import static org.junit.Assert.assertEquals;\n");
        buff.append("import org.junit.Test;\n");
        buff.append("public class FooTest {\n");

        buff.append("   @Test\n");
        buff.append("   public void test1() {\n");
        buff.append("      Foo foo = new Foo();\n");
        buff.append("      int result = foo.add(10, 15);\n");
        buff.append("      assertEquals(25, result);\n");
        buff.append("   }\n");

        buff.append("   @Test\n");
        buff.append("   public void test2() {\n");
        buff.append("      Foo foo = new Foo();\n");
        buff.append("      int result = foo.add(20, 35);\n");
        buff.append("      assertEquals(55, result);\n");
        buff.append("   }\n");

        buff.append("   @Test \n");
        buff.append("   public void test3() {\n");
        buff.append("      Foo foo = new Foo();\n");
        buff.append("      int result = foo.add(10, 35);\n");
        buff.append("      assertEquals(46, result);\n");
        buff.append("   }\n");

        buff.append("}\n");

        return buff.toString();
    }

    private static File createNewTmpDir() {
        File dir = null;
        String dirName = FileUtils.getTempDirectoryPath() + File.separator + "EvoSuite_"
                + JUnitResultBuilderTest.class.getCanonicalName() + "_" + +System.currentTimeMillis();

        //first create a tmp folder
        dir = new File(dirName);
        if (!dir.mkdirs()) {
            return null;
        }

        if (!dir.exists()) {
            return null;
        }

        return dir;
    }

    public Class<?> loadFooTestClass() {

        File tempDir = createNewTmpDir();
        if (tempDir == null) {
            return null; //fail
        }

        String javaSrcDirName = tempDir.getAbsolutePath() + File.separator + "src";

        String javaBinDirName = tempDir.getAbsolutePath() + File.separator + "bin";

        String javaSrcPackageDirName = javaSrcDirName + File.separator
                + "com.examples.with.different.packagename.junit".replace(".", File.separator);

        String javaBinPackageDirName = javaBinDirName + File.separator
                + "com.examples.with.different.packagename.junit".replace(".", File.separator);

        File javaBinDir = new File(javaBinDirName);
        if (!javaBinDir.mkdirs()) {
            return null; //fail
        }

        File packageDir = new File(javaSrcPackageDirName);
        if (!packageDir.mkdirs()) {
            return null; //fail
        }

        String javaFilename = javaSrcPackageDirName + File.separator + "FooTest.java";
        String classFilename = javaBinPackageDirName + File.separator + "FooTest.class";

        String javaSourceText = createFooTestJavaText();
        File javaFile = writeJavaSourceText(javaSourceText, javaFilename);
        if (javaFile == null) {
            return null; //fail
        }

        boolean compiled = compileJavaFile(javaBinDirName, javaFile);
        if (!compiled) {
            return null; //fail
        }

        File classFile = new File(classFilename);
        if (!classFile.exists()) {
            return null; //fail
        }

        Class<?> clazz = loadClass(javaBinDir);
        if (clazz == null) {
            return null; //fail
        }

        //delete class file on exit
        classFile.delete();
        return clazz;
    }

    private static Class<?> loadClass(File javaBinDir) {

        URLClassLoader urlClassLoader = null;
        try {
            URI javaBinURI = javaBinDir.toURI();
            URL javaBinURL = javaBinURI.toURL();
            urlClassLoader = new URLClassLoader(new URL[] { javaBinURL }, Foo.class.getClassLoader());
            Class<?> clazz = urlClassLoader.loadClass(FOO_TEST_CLASS_NAME);
            return clazz;
        } catch (ClassNotFoundException e) {
            return null;
        } catch (MalformedURLException e) {
            return null;
        }
    }

    private static boolean compileJavaFile(String javaBinDirName, File javaFile) {
        JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
        if (compiler == null) {
            return false; //fail
        }

        DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<JavaFileObject>();
        StandardJavaFileManager fileManager = compiler.getStandardFileManager(diagnostics, Locale.getDefault(),
                Charset.forName("UTF-8"));
        Iterable<? extends JavaFileObject> compilationUnits = fileManager
                .getJavaFileObjectsFromFiles(Collections.singletonList(javaFile));

        List<String> optionList;
        optionList = new ArrayList<String>();
        optionList.addAll(Arrays.asList("-d", javaBinDirName));
        CompilationTask task = compiler.getTask(null, fileManager, diagnostics, optionList, null, compilationUnits);
        boolean compiled = task.call();
        try {
            fileManager.close();
        } catch (IOException e) {
            return false;
        }
        return compiled;
    }

    private File writeJavaSourceText(String javaSourceText, String javaFilename) {
        File javaFile = new File(javaFilename);
        if (javaFile.exists()) {
            return null; //fail
        }

        BufferedWriter writer = null;
        try {
            writer = new BufferedWriter(new FileWriter(javaFilename));
            writer.write(javaSourceText);
            writer.close();
        } catch (IOException e) {
            return null;
        }
        return javaFile;
    }
}