Need help understanding how a build.xml file works - java

Forewarning: I'm not very bright so the question may seem extremely idiotic.
I need to make an ant file that will compile my source files to a target directory.
In addition, it needs to test all the JUnit files in my project.
However, I understand next to nothing in a build.xml.
At the moment I have my project folder in eclipse contain two separate package folders that hold all my java files.
Would the following be along the right path?
<project name="PersonPersistence" default="compile" basedir=".">
<target name="compile" description="Compiles java source files.">
<mkdir dir="target"/>
<javac srcdir="src" destdir="target"/>
</target>
<target name="test" depends="compile" description="Tests JUnit files.>
<java jar="src/packOne/Test1.java"/>
</target>
</project>
Or do I need to do something else for the "test" portion? Such as putting all my test files into a jar file?

Related

Ant Javac compile subpackage class files to the parent src directory

I would like Ant 1.9 to be able to compile servlet classes to the parent src directory, but the file system has the files in packages. No, the packages are not declared in the servlet files.
The code is deployed with all the servlets in the same directory. I supposed I can create an ant copy command to do this, but I would prefer there be an ant javac solution.
Manually this would be 'javac -d .. *.java' after changing to each subdirectory, not including the files already in the default package. This is highly irregular, but I cannot change the how the packages are defined nor can I change the urls from which the code is executed from.
<target name="compileServlet" description="Compiles Java source files.">
<javac srcdir="${servlets.dir}" destdir="$(servlets.dir}" debug="true" encoding="ISO-8859-1" source="1.7" target="1.7" failonerror="true">
<classpath path="${env.CLASSPATH}" />
<include name="**/*.java"/>
</javac>
</target>
Right now when I run this ant build.xml, no class files are generated. Any thoughts how I can solve this issue?
If you have source files in multiple root directories and want to compile them all into a single root directory, use the <src> element instead of the srcdir attribute.
Here is the example shown in the documentation:
<javac destdir="${build}"
classpath="xyz.jar"
debug="on">
<src path="${src}"/>
<src path="${src2}"/>
<include name="mypackage/p1/**"/>
<include name="mypackage/p2/**"/>
<exclude name="mypackage/p1/testpackage/**"/>
</javac>

How to set up a Java workspace without an IDE

I usually code with IDEs like Intellij Idea or Eclipse, but due to several reasons, I no longer have access to an IDE, and I'd like to be able to code in Java on a remote Linux machine through a ssh terminal.
Making simple progams with only a few classes is easy, but some of my projects have several libraries and several separate .java files. I also need to export to a .jar file.
For example, I have the following file organisation:
project/
src/
a.java
b.java
c.java
libs/
lib1.jar
lib2.jar
out/
export_here.jar
someconfig.conf
The java app consists of the a, b, and c .java files, uses libraries lib1 and lib2, and the file someconfig.conf needs to be inside the export jar.
I want to know how to easily compile and build a project such as this.
In other words, I just want to know how to export my project into a runnable jar the right way.
I expect this can be done with a few commands. If so, I plan to make a shell script to automate everything.
Thanks in advance!
As suggested by other users you need to use a build management tool to do this like Ant, Maven etc. I have used Ant quiet frequently to do these kind of automated tasks. In order to install and Use Ant you can refer How To Install Apache Ant
After that the main task is to write your automation script and that is called a build xml in ant world. Here is a sample build.xml file you can refer to start with:
<project>
<target name="clean">
<delete dir="build"/>
</target>
<target name="compile">
<mkdir dir="build/classes"/>
<javac srcdir="src" destdir="build/classes"/>
</target>
<target name="jar">
<mkdir dir="build/jar"/>
<jar destfile="build/jar/HelloWorld.jar" basedir="build/classes">
<manifest>
<attribute name="Main-Class" value="oata.HelloWorld"/>
</manifest>
</jar>
</target>
<target name="run">
<java jar="build/jar/HelloWorld.jar" fork="true"/>
</target>
</project>
And for more information on the above sample You can visit this
In General you can read more at How to create build.xml
After creating your build.xml you can run ant by ant <path to build.xml> or ant in case your build.xml lies in current directory
Hope this helps you in right direction

Creating a WAR file using Java

How do I create a deployable WAR file for Apache Tomcat servers programmatically with Java?
Is there a library for such a task?
I am working on a small own IDE for special purposes. The IDE is written in Java and JavaScript, so I need to create the WAR file using those.
If you want to build it from code try to do it from the command line with
Runtime rt = Runtime.getRuntime();
Process pr = rt.exec("jar cvf /path/to/your/project/your-file.war");
Of course, the same thing would work using ANT or Maven (as long as those tools are installed on the final platform).
Edit: added improvement suggestion
I don't know of libraries, but a WAR file is just a ZIP file with a different ending.
Just create the inner folder structure and files (google the java code for that) and package as zip (java has methods for that too I think, again google) and rename the file from "myfile.zip" to "myfile.war"
I don't know how you would do it using the IDE you have. But a WAR file has the following structure:
web resources go to the root
project classes (including their package folders) go to a folder WEB-INF/classes
project dependency jars go to WEB-INF/lib
So if you want to build a WAR by hand, you need to create that file structure inside a zip file with a .war extension and you need to copy that to the proper location of the server to deploy it. Most servers also allow 'exploded deployment', meaning that you don't need an actual war file, you can just deploy the stuff to a directory with the same name as your war (IE. 'myapp.war').
You can do this a number of ways, for a quick example if you are using maven you just need to use <packaging>war</packaging>
You could just export the war as has been mentioned, but it's not exactly "programmatic".
If you're using Ant - you can find a tutorial for this here
<?xml version="1.0" ?>
<path id="compile.classpath">
<fileset dir="WebContent/WEB-INF/lib">
<include name="*.jar"/>
</fileset>
</path>
<target name="init">
<mkdir dir="build/classes"/>
<mkdir dir="dist" />
</target>
<target name="compile" depends="init" >
<javac destdir="build/classes" debug="true" srcdir="src">
<classpath refid="compile.classpath"/>
</javac>
</target>
<target name="war" depends="compile">
<war destfile="/APP/jboss-5.1.0.GA/server/all/deploy/DispatchActionEx.war" webxml="WebContent/WEB-INF/web.xml">
<fileset dir="WebContent"/>
<lib dir="WebContent/WEB-INF/lib"/>
<classes dir="build/classes"/>
</war>
</target>
<target name="clean">
</target>
Just write an build.xml file(i have give an example),
change "project name" and "war destfile" which will be ".../apache-tomcat/webapps/projectname.war"
put it in your project folder
open it in eclipse.
right click on it>>run as>>ant build
check whether the war file is created in the webapps folder in apache-tomcat

Java - Ant build (Eclipse) - Could not find the main class: nat.rutherford.DesktopStarter

I am having a little trouble with my first ever ant build in eclipse, here is my build.xml build file.
<project name="Rutherford" default="dist" basedir=".">
<description>
simple example build file
</description>
<!-- set global properties for this build -->
<property name="src" location="src"/>
<property name="build" location="build"/>
<property name="dist" location="dist"/>
<property name="libs" value="libs"/>
<path id="classpath">
<fileset dir="${libs}" includes="**/*.jar"/>
</path>
<target name="init">
<!-- Create the time stamp -->
<tstamp/>
<!-- Create the build directory structure used by compile -->
<mkdir dir="${build}"/>
</target>
<target name="compile" depends="init"
description="compile the source " >
<!-- Compile the java code from ${src} into ${build} -->
<javac srcdir="${src}" destdir="${build}" classpathref="classpath">
<compilerarg line="-encoding utf-8"/>
</javac>
</target>
<target name="dist" depends="compile"
description="generate the distribution" >
<!-- Create the distribution directory -->
<mkdir dir="${dist}/lib"/>
<!-- Put everything in ${build} into the MyProject-${DSTAMP}.jar file -->
<jar jarfile="${dist}/MyProject-${DSTAMP}.jar" basedir="${build}">
<manifest>
<attribute name="Main-Class" value="nat.rutherford.DesktopStarter"/>
</manifest>
</jar>
</target>
<target name="run">
<java jar="${dist}/MyProject-${DSTAMP}.jar" fork="true"/>
</target>
<target name="clean"
description="clean up" >
<!-- Delete the ${build} and ${dist} directory trees -->
<delete dir="${build}"/>
<delete dir="${dist}"/>
</target>
</project>
It compiles ok with no warnings or errors, but when I try to run the .jar it says 'Could not find the main class: nat.rutherford.DesktopStarter. Program will now exit' =(
I have read a ton of pages on the matter but so far nothing conclusive.
I was able to compile it using Eclipse -> File -> Export ->Java -> Runnable Jar File. But I use some UTF-8 encoded .txt files that it seems not to be able to deal with that way and I need them! ie I have greek characters that should read...dσ/dΩ... but currently read... dÃ/d©... which isn't going to work ^^
So basically I need to make my Ant build work, baring in mind that it needs to be able to handle my UTF-8 encoded .txt files too.
The problem is in your task dist when you create your jar. If your compilation is right and there is no problem when you package your jar. Things that are wrong:
<mkdir dir="${dist}/lib"/> -> this don't have mean, you don't use it never
second you are not including your libraries in your jar, then when you try to execute your jar it doesn't work that why you are seeing the error message Could not find the main class: nat.rutherford.DesktopStarter. Program will now exit You could see that your libraries aren't within your jar using Winzip or similar. I suppose that you are seeing your problem when you try to execute the jar directly using windows or similar. A good way to see what is happening, seeing the problem printed in the console is executing your jar in the next way: java -jar MyProject-20120102.jar
See: How to include your libraries in you jar?
And if you want to know more about jar packaging using ant try this.
Another thing that you need to modify the Class-path attribute in your manifest to include the libraries within your ${libs} folder.
It looks like you've added a manifest to your executable JAR that spells out nat.rutherford.DesktopStarter as your main class.
I'd recommend that you open the JAR and verify that the manifest.mf appears and does indeed say what your Ant build.xml does.
I'd also verify that your DesktopStarted.class appears in a folder path nat.rutherford. If it doesn't, the JVM won't find it.

How can I build multiple projects in Ant with one build file?

Can I build multiple projects from one build-file. Example:
<project basedir="." default="all" name="app1">
...
</project>
<project basedir="." default="all" name="app2">
...
</project>
Currently I type ant -f build1.xml compile and it builds my application and I have to use two separate build files. Is there some way to get it running in a way that i have both the projects defined a common build-file and I can type something like ant app1 compile or ant app2 compile?
Here's what my build-file looks like:
<?xml version="1.0" encoding="UTF-8"?>
<project name="azebooster" default="dist" basedir=".">
<!-- Globals -->
<property name="src" location="src/com/aelitis"/>
<property name="build" location="build/azebooster"/>
<property name="jar" location="jar/azebooster"/>
<property name="resources" location="res/azebooster"/>
<!-- Paths -->
<path id="classpath">
<fileset dir="." includes="**/*.jar"/>
</path>
<!-- Start it -->
<target name="init">
<tstamp/>
<mkdir dir="${build}"/>
<mkdir dir="${jar}"/>
</target>
<!-- Build it -->
<target name="compile" depends="init" description="compile the source" >
<javac srcdir="${src}" destdir="${build}">
<classpath>
<path refid="classpath"/>
</classpath>
</javac>
</target>
<!-- Jar it -->
<target name="jar" depends="compile">
<jar destfile="${jar}/${ant.project.name}.jar">
<fileset dir="${build}"/>
<fileset dir="${resources}" />
</jar>
</target>
<!-- Clean it -->
<target name="clean" description="clean up" >
<tstamp/>
<delete dir="${build}"/>
<delete dir="${jar}"/>
</target>
</project>
Thank you.
Yes you can create a default.build file (in this way you don't need to specify the file, because it's used by default). On it you can create the following targets:
<target name="all" depends="app1, app2" />
<target name="app1">
<ant antfile=<app1file> target="compile" />
</target>
<target name="app2">
<ant antfile=<app2file> target="compile" />
</target>
On this way you can use both ant file from one unique file.
And you can do all in only one file, if you replace the app1 and app2 targets, with the needed targets to compile them that you have in the separate files.
EDITED:
You have different ways to include both of them in only one file, maybe the easiest one is include a suffix for each project on each target. And you can call the specific project target or the target for both.
I put you an example with the compile target (and for init target too).
You can use compile for compile both projects (I call the other project other), and compileazeboster to compile the azeboster project.
You can search the common things to avoid the innecesary duplicated code (common paths, targets and so on)
<property name="srcazebooster" location="src/com/aelitis"/>
<property name="buildazebooster" location="build/azebooster"/>
<property name="jarazebooster" location="jar/azebooster"/>
<property name="srcother" location="src/other"/>
<property name="buildother" location="build/other"/>
<property name="jarother" location="jar/other"/>
<!-- Start it -->
<target name="init" depends="initazebooster, initother"/>
<!-- Build it -->
<target name="compile" depends="compileazebooster, compileother" description="compile the source for all" />
<!-- Start azebooster-->
<target name="initazebooster">
<tstamp/>
<mkdir dir="${buildazebooster}"/>
<mkdir dir="${jarazebooster}"/>
</target>
<!-- Build azeboster-->
<target name="compileazebooster" depends="initazebooster" description="compile the source for azebooster" >
<javac srcdir="${srcazebooster}" destdir="${buildazebooster}">
<classpath>
<path refid="classpath"/>
</classpath>
</javac>
</target>
<!-- Start other-->
<target name="initother">
<tstamp/>
<mkdir dir="${buildotherr}"/>
<mkdir dir="${jarother}"/>
</target>
<!-- Build other-->
<target name="compileother" depends="initother" description="compile the source for other" >
<javac srcdir="${srcother}" destdir="${buildother}">
<classpath>
<path refid="classpath"/>
</classpath>
</javac>
</target>
You will probably be able to do what you want using macros (though it depends precisely on what is common between your two projects), though your command is more likely to be
ant compile app1
or
ant compile app2
where compile is a target which calls a macro, using app1/app2 as a parameter to either decide which macro to call or to pass into the macro itself.
I would like to add to the excellent answer of Borja some important steps.
How to organize the common ant files?
Let's say we have some big Project consisting of many Eclipse projects. All of them are in a worspace folder. Thus, the workspace itself makes the global Project. (Notice P/p difference). Very often you already have an Ant build file in the workspace folder. Or you have created the common ant files (build and properties) in it by yourself.
Later you want to launch that global build file. How? Do you want to go into the workspace folder, change to the command line or shell window and run the ant from there, having the output in the external console and switching from Eclipse to that window and back? And the same problem for editing? Having two additional windows? No, surely you want to have all windows, editing and output, in Eclipse. But how can we reference those global build files from inside the Eclipse?
Go to Package Explorer.
Make an empty project(not Java one), let's name it _Global (we want to see it always on the top).
Right click on its name. Choose Import -> General -> File System.
Press Advanced. Check Create links in Workspace, Create virtual folders, create link locations. The last choose for WORKSPACE_LOC.
In From Directory go to the workspace or where you have created the common build. After all, it could be even the common one for several workspaces.
You will see a dialogue with file names on the right with checkfields. Check the files you need. (You will need to import every new common file you created thereafter).
Finish.
Now you see your project with references to the global files. As for properties files, you are ready. But for build files you need some more steps:
Right click your global build file, -> Run -> Run Configurations. You are in the Ant Build group of configurations.
Press the New Launch Configuration button with plus on it (above the launch configurations list). Now you have the run configuration for that global build.
Set its parameters and run/debug it.

Categories