# Junit-Tests in Java Klasse ausführen



## TJava (30. Jul 2011)

Hallo , ich möchte gerne eine Liste von JUnit-Tests in einer Klasse ausführen und die Ergebebnisse in dieser Klasse verarbeiten. Wie geht so etwas? welche Befehle muss ich verwenden?

Ich erstelle im Moment ein Testframework und Junit ist auch Bestandteil des ganzen.


----------



## turtle (30. Jul 2011)

Ich gebe zu die Frage nicht ganz zu verstehen, aber...

In jUnit gibt es das Interface TestRunListener mit dem Du über Start, Stop,  Ende und Status informiert wirst.


----------



## TJava (30. Jul 2011)

hehe ok.
Also die Tests liegen in einer Datenbank, von dort hole ich sie und möchte sie ausführen.
Die Tests müssen also automatisch ausgeführt werden und ausgewertet, nicht manuell.
Die Ergebnisse werden dann ausgewertet und in eine Html-Seite transformiert.


----------



## turtle (30. Jul 2011)

Das ist ja das Schöne an Open-Source. Man kann sich anschauen, wie jUnit alles macht.

Wenn ich das richtig sehe, lädt jUnit eine Testklasse und ruft dann Contructor und Testmethoden via Reflection auf. Es sieht so aus, dass nur die Classdatei gefunden werden muss. Und diese kannst Du doch, hoffentlich, aus der DB laden, oder?

Wenn es "nur" um das Anwerfen eines Testlaufes geht, da solltest Du einen eigenen Runner schreiben können, der sich selbst als Listener registriert.


----------



## TJava (30. Jul 2011)

Ok hast du dafür ein Beispiel, verstehe nicht ganz was du sagst 
Ich gucke gerade die Junit-API an, es steht alles im Package org.junit.runner  oder?


Also muss ich eine Instanz vom JunitCore erstellen und dort die run-Methode benutzen.
Der Methoden werden class Files übergeben.Ist das eine Collection die dort übergeben wird?


public Result run(java.lang.Class<?>... classes)

    Run all the tests in classes.


----------



## turtle (30. Jul 2011)

Ich habe mir die junit-4.8.2-src.jar geladen.

Schau Dir da mal die Klasse junit.runner.BaseTestRunner an.


----------



## TJava (30. Jul 2011)

Und wie erstelle ich einen Test den ich dem Runner übergeben kann?

Result r = org.junit.runner.JUnitCore.runClasses(TestReader.class);
so geht es auch nur wie bekomme ich diese class?


----------



## turtle (30. Jul 2011)

Class.forName(className)?


----------



## TJava (30. Jul 2011)

org.junit.runner.Result result = jUnitCore.run((Class.forName("./config/JunitTest/Test.java")));

so?


----------



## turtle (30. Jul 2011)

Nein, der Klassenname enthält keine Pfad-Angabe, sondern "nur" den Klassennamen. Diese Klasse muss über den Classpath gefunden werden können.


----------



## TJava (30. Jul 2011)

geht das auch anders?Der Ordner in den die Testklassen abgelegt werden ist variabel und wird vom Benutzer über eine Konfiguration angegeben.


----------



## turtle (30. Jul 2011)

Klar geht das anders. Da musst Dir einen eigenen Classloader schreiben.


----------



## TJava (30. Jul 2011)

und wie geht das?


----------



## turtle (30. Jul 2011)

Der Quelltext ist Dein Freund. Schau Dir java.net.URLClassLoader an.


----------



## TJava (30. Jul 2011)

Gibt es keinen einfacheren Weg, Junit Tests auszuführen? 
Wenn es keine Class Files sind oder würde das Class-loader dann auch .java- Dateien umwandeln.


----------



## turtle (30. Jul 2011)

> Gibt es keinen einfacheren Weg, Junit Tests auszuführen?


Das weisst nur Du.


> Wenn es keine Class Files sind oder würde das Class-loader dann auch .java- Dateien umwandeln.


Nein.

Ist aber auch nicht so schwer einen Classloader zu schreiben. Guckst Du hier


----------



## TJava (30. Jul 2011)

```
URL[] url = new URL[1];
		try {
			url[0] = new URL("./config/Junit/");
		} catch (MalformedURLException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		URLClassLoader classloader = new URLClassLoader(url);
```

so aber irgendwie gehts nicht..


----------



## turtle (30. Jul 2011)

Erstens ist das keine URL in Deinem Beispiel.

Zweitens: was spricht gegen den FileClassLoader aus meinem Link?


----------



## TJava (30. Jul 2011)

Also meinst du denn hier?
Ich teste das ganze morgen weiter.
Vielen Dank für deine Hilfe.


```
import java.io.*;
import java.net.*;
import java.util.*;

public class FileClassLoader extends /* superclass */ {

  private String root;

  public FileClassLoader (String rootDir) {
    if (rootDir == null)
      throw new IllegalArgumentException ("Null root directory");
    root = rootDir;
  }

  protected Class loadClass (String name, boolean resolve) 
    throws ClassNotFoundException {

    // Since all support classes of loaded class use same class loader
    // must check subclass cache of classes for things like Object

    // Class loaded yet?

    if (c == null) {
      // Convert class name argument to filename
      // Convert package names into subdirectories
      String filename = name.replace ('.', File.separatorChar) + ".class";

      try {

        // Load class data from file and save in byte array

        // Convert byte array to Class

        // If failed, throw exception

      } catch (IOException e) {
        throw new ClassNotFoundException ("Error reading file: " + filename);
      }
    }

    // Resolve class definition if approrpriate

    // Return class just created

    return /* ? */ ;
  }
  private byte[] loadClassData (String filename) 
      throws IOException {

    // Create a file object relative to directory provided
    File f = new File (root, filename);

    // Get size of class file
    int size = (int)f.length();

    // Reserve space to read
    byte buff[] = new byte[size];

    // Get stream to read from
    FileInputStream fis = new FileInputStream(f);
    DataInputStream dis = new DataInputStream (fis);

    // Read in data
    dis.readFully (buff);

    // close stream
    dis.close();

    // return data
    return buff;
  }
}
```


----------



## turtle (30. Jul 2011)

Das ist ein Versuch wert.Viel Glück


----------



## TJava (1. Aug 2011)

So habe nun den Classloader erstellt, aber es kommt eine Fehlermeldung

Error reading file: Test\java.class

Was mache ich bei den Angaben falsch?


```
FileClassLoader fileClassLoader = new FileClassLoader("./config/Junit");
		try {
			fileClassLoader.loadClass("Test.java");
									
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
```


----------



## turtle (1. Aug 2011)

Du musst natürlich in ./config/Junit die kompilierte Class-Datei von Test.java abgelegt haben.

Daher ist Dein Aufruf
fileClassLoader.loadClass("Test.java");
auch falsch und muss heissen

```
fileClassLoader.loadClass("Test");
```


----------



## TJava (1. Aug 2011)

mmh jetzt scheint er den Ordner nicht zu finden. 
Da lag der Test ursprünglich mal (wrong name: de/usu/foxtrot/autoit/Test)
:bahnhof:


```
Exception in thread "main" java.lang.NoClassDefFoundError: AutoItConfigurationImplementationTest (wrong name: de/usu/foxtrot/autoit/Test)
	at java.lang.ClassLoader.defineClass1(Native Method)
	at java.lang.ClassLoader.defineClassCond(ClassLoader.java:632)
	at java.lang.ClassLoader.defineClass(ClassLoader.java:616)
	at java.lang.ClassLoader.defineClass(ClassLoader.java:466)
	at de.usu.foxtrot.junit.util.FileClassLoader.loadClass(FileClassLoader.java:38)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:248)
	at de.usu.foxtrot.junit.JUnitExecutorImplementation.run(JUnitExecutorImplementation.java:43)
	at de.usu.foxtrot.autoit.CopyOfStart.main(CopyOfStart.java:33)
```


----------



## TJava (1. Aug 2011)

Der Ordner muss scheinbar im Class-Path zufinden sein? Das ist aber etwas schlecht, da dieser Ordner jedes mal anders ist. Was kann ich da tun?


----------



## turtle (1. Aug 2011)

Schon wieder andere Namen... Warum änderst Du da ständig was?

Jedenfalls muss die class-Datei im Ordner de/usu/foxtrot/autoit zu finden sein. Der FileClassLoader gibt ja nur den Root-Folder an. Darunter muss natürlich die Klasse "package"-konform zu finden sein. Im Beispiel wird da kein Package angegeben


----------



## TJava (1. Aug 2011)

Das verstehe ich nicht ganz. Wieso muss sie dort zu finden sein? de/usu/foxtrot/autoit
Root Folder ist das Projekt ? 
Ich möchte aber den Ordner mit den Tests an beliebiger Stelle erstellen können. Hast du dafür einen Tipp?


----------



## TJava (1. Aug 2011)

Aber wahrscheinlich wird das eh nicht funktionieren oder? 
Es müssen ja die ganzen Klassen,Jars etc. vorhanden sein.


----------

