1

I've been scratching my head at this for a while now. I have been looking at all related posts on Stack Overflow and the ones I could find with Google but it was to no avail.

I'm trying to build a Java program that has Mancala.java as main class. The directory structure is as follows: a folder called mancala with one subfolder called test and one subfolder called mancala_test. The test folder has the Mancala.java file and other files and the mancala_test folder contains the JUnit test file called MancalaTest.java. In Eclipse the test file runs, but when running via Ant I get the following error:

init:

compile:
    [javac] Compiling 6 source files to C:\Users\[me]\Desktop\build

runjunit:
    [junit] Running mancala_test.MancalaTest
    [junit] Testsuite: mancala_test.MancalaTest
    [junit] Tests run: 1, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 0 sec
    [junit] Tests run: 1, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 0 sec
    [junit]
    [junit]     Caused an ERROR
    [junit] mancala_test.MancalaTest
    [junit] java.lang.ClassNotFoundException: mancala_test.MancalaTest
    [junit]     at java.lang.ClassLoader.loadClass(ClassLoader.java:356)
    [junit]     at java.lang.Class.forName0(Native Method)
    [junit]     at java.lang.Class.forName(Class.java:266)
    [junit]
    [junit] Test mancala_test.MancalaTest FAILED

BUILD SUCCESSFUL
Total time: 1 second

I'm using the following build file in the mancala folder:

<project default="runjunit" name="Compile and run JUnit tests">

  <target name="clean">
     <delete dir="build"/>
  </target>
  <target name="clean2">
     <delete dir="build"/>
  </target>

  <target name="init">
    <record name="build.log" loglevel="verbose" append="false"/>
  </target>

  <target name="runjunit" depends="compile">
    <junit printsummary="on">
      <test name="mancala_test.MancalaTest"/>
      <classpath>
        <pathelement location="build"/>
      </classpath>
   <formatter
      type="plain"
      usefile="false"
    />
    </junit>
  </target> 

  <target name="compile" depends="init">
    <mkdir dir="build"/>
      <javac includeantruntime="false" srcdir="./test" destdir="build"/>
  </target>

</project>

Other possible relevant information is that the Mancala.java file contains two static initializers being the GUI and the Mancala class itself (e.g., static Mancala mancala; static GUI gui; and the Mancala_test.java just uses a Mancala mancala = new Mancala() object in each test.

An example of one test:

@Test
public void testAmountOfSeed() {
    Mancala mancala = new Mancala();        
    mancala.divideBoard();

    int totalAmountOfSeed = 0;
    for (int i = 0; i < mancala.gameBoard.size(); i++) {
        totalAmountOfSeed +=mancala.gameBoard.get(i).getSeed();
    }
    assertTrue("Total amount of seed in initial condition not 48!", totalAmountOfSeed == 48);
}

It probably has something to do with the classpaths (I tried every possible variation I could think of) or the static stuff. I would be very grateful if someone could put me out of my misery.

/edit Directory structure after build: https://i.stack.imgur.com/O2POC.png

user2609980
  • 10,264
  • 15
  • 74
  • 143

1 Answers1

2

You need a target to compile the test_mancala directory and add the destination of that compile to your runjunit target's classpath.

<target name="compile-test_mancala" depends="init, compile">
  <mkdir dir="build-test_mancala"/>
  <javac includeantruntime="false" srcdir="./test_mancala" destdir="build_mancala">
    <classpath>
      <pathelement location="build"/>
      <pathelement location="${junit_lib}"/>
    </classpath>
  </javac>
</target>

<target name="runjunit" depends="compile, compile-test_mancala">
  <junit printsummary="on">
    <test name="mancala_test.MancalaTest"/>
    <classpath>
      <pathelement location="build"/>
      <pathelement location="build-test_mancala"/>
    </classpath>
 <formatter
    type="plain"
    usefile="false"
  />
  </junit>
</target> 
joescii
  • 6,495
  • 1
  • 27
  • 32
  • Thanks a lot! I am progressing. The error I now get is the following: – user2609980 Sep 26 '13 at 14:13
  • compile-mancala_test: [javac] Compiling 1 source file to C:\Users\erooijakkers\Desktop\mancala\build_mancala [javac] C:\Users\erooijakkers\Desktop\mancala\mancala_test\MancalaTest.java:22: error: cannot find symbol [javac] Mancala mancala = new Mancala(); [javac] ^ – user2609980 Sep 26 '13 at 14:21
  • 1
    Whoops... I forgot to put the output of `compile` in the classpath for the new `compile-test_mancala`. Editing now... – joescii Sep 26 '13 at 14:25
  • 1
    Which also reminds me that you will need the junit.jar file in the classpath. I used `${junit_lib}` above as a placeholder for that value. Either replace it with the path, or define the `junit_lib` property with the path. – joescii Sep 26 '13 at 14:29
  • Thanks, I was aware of that and solved it by placing the junit.jar into jre7/lib/ext folder. Unfortunately, the rest of the code is still not compiling since it cannot find classMancala in MancalaTest. – user2609980 Sep 26 '13 at 14:42
  • 1
    Edited again... added `compile` to the list of `depends` targets. – joescii Sep 26 '13 at 15:02
  • Thank you. New error: [junit] Testcase: initializationError took 0.001 sec [junit] Caused an ERROR [junit] org/hamcrest/SelfDescribing [junit] java.lang.NoClassDefFoundError: org/hamcrest/SelfDescribing – user2609980 Sep 27 '13 at 08:23
  • 1
    Looks like you also need a jar from hamcrest.org. Look in your eclipse install directory for it. Add it to the classpath of the junit task. – joescii Sep 27 '13 at 09:50
  • I added to my classpath, but it still gives the same error...? The SelfDescribing does exit in the file at the location org/hamcrest/ but it stil says [junit] java.lang.NoClassDefFoundError: org/hamcrest/SelfDescribing – user2609980 Sep 27 '13 at 11:12
  • 1
    After reading [this question/answer](http://stackoverflow.com/questions/4228047/java-lang-noclassdeffounderror-in-junit), I believe instead of adding hamcrest to the classpath, we should just add the junit jar to the junit task. – joescii Sep 27 '13 at 14:31
  • The reason why I wanted Ant or Maven to work was that a tutorial said you should not upload to Jenkins before your build succeeds locally. It just did not work with the classpath error and then I just gave up. I thought let just upload a simple helloworld application to SVN and get Jenkins to run the unit tests on that. But what happened? I accidentally uploaded the Mancala game. I looked at Jenkins and it started compiling. The tests were coming up and it downloaded a lot of libraries. Then a miracle happened before my eyes: the build and tests succeeded. Unbelievable. What a tool! – user2609980 Sep 27 '13 at 16:31
  • 2
    No problem! Glad to help anyone unfortunate enough to work with Ant. – joescii Sep 27 '13 at 16:42