47

I am trying to build an executable jar program which depends on external jar downloaded. In my project, I included them in the build path and can be run and debug within eclipse.

When I tried to export it to a jar, I can run the program but I can't when I try to press a button which includes function calls and classes from the external jar. I have edited the environment variables (Windows XP) CLASSPATH to include paths of all the external jar, but it doesn't work.

A point to note is that I got compile warnings while exporting my executable jar, but it doesn't show up any description about the warnings.

Would someone kindly provide a thorough guide on how to include an external jar program using eclipse?

  • 3
    Don't do that. Seriously, never depend on your IDE to create build artifact, use scripts (maven, ant) for that purpose. – Marko Feb 02 '09 at 12:04
  • Maven and Ant are mentioned as alternatives. I could list more obscure build tools, but those two are the standard ones. It's no point elaborating further, since there exist a lot of info about them already. – Marko Aug 04 '11 at 11:13

6 Answers6

36

Eclipse 3.5 has an option to package required libraries into the runnable jar. File -> Export... Choose runnable jar and click next. The runnable jar export window has a radio button where you can choose to package the required libraries into the jar.

Bob Tefft
  • 361
  • 3
  • 2
  • 1
    Seems good. Except for the fact that I need to have a launch configuration. But creating a dummy launch configuration is no problem. – Hendy Irawan Dec 23 '10 at 18:00
  • 6
    This (can) also generate an Ant build file, that can be launched later quickly (whether inside IDE or outside IDE). The best of both worlds! – Hendy Irawan Dec 23 '10 at 18:09
14

You can do this by writing a manifest for your jar. Have a look at the Class-Path header. Eclipse has an option for choosing your own manifest on export.

The alternative is to add the dependency to the classpath at the time you invoke the application:

win32: java.exe -cp app.jar;dependency.jar foo.MyMainClass
*nix:  java -cp app.jar:dependency.jar foo.MyMainClass
McDowell
  • 107,573
  • 31
  • 204
  • 267
  • 5
    The latter suggestion won't work. The `-cp` (and `-classpath`) argument is **ignored** when `-jar` is used. – BalusC Mar 21 '11 at 17:18
  • @BalusC - you are correct; the dependency would need to be in the manifest. I'll edit the answer. – McDowell Mar 21 '11 at 17:21
  • I had no idea about this. In class they don't delve into this sort of thing at all... Good tips! – Ethan Aug 29 '12 at 03:31
  • The former suggestion won't work, either. The docs say: `The Class-Path header points to classes or JAR files on the local network, not JAR files within the JAR file or classes accessible over internet protocols. To load classes in JAR files within a JAR file into the class path, you must write custom code to load those classes.` – ashes999 Nov 20 '13 at 17:49
  • @ashes999 There is no requirement that the dependency JAR be bundled inside the executable JAR in the question. The original poster stated that he was trying to add an external file-system JAR to the classpath and you can do this with `Class-Path`. – McDowell Nov 23 '13 at 12:55
  • @McDowell he said he wants to `build an executable jar program which depends on external jar downloaded. In my project, I included them in the build path`. That means he has class dependencies. This won't work. I was also surprised about this behaviour. – ashes999 Nov 23 '13 at 13:32
8

How to include the jars of your project into your runnable jar:

I'm using Eclipse Version: 3.7.2 running on Ubuntu 12.10. I'll also show you how to make the build.xml so you can do the ant jar from command line and create your jar with other imported jars extracted into it.

Basically you ask Eclipse to construct the build.xml that imports your libraries into your jar for you.

  1. Fire up Eclipse and make a new Java project, make a new package 'mypackage', add your main class: Runner Put this code in there.

    enter image description here

  2. Now include the mysql-connector-java-5.1.28-bin.jar from Oracle which enables us to write Java to connect to the MySQL database. Do this by right clicking the project -> properties -> java build path -> Add External Jar -> pick mysql-connector-java-5.1.28-bin.jar.

  3. Run the program within eclipse, it should run, and tell you that the username/password is invalid which means Eclipse is properly configured with the jar.

  4. In Eclipse go to File -> Export -> Java -> Runnable Jar File. You will see this dialog:

    enter image description here

    Make sure to set up the 'save as ant script' checkbox. That is what makes it so you can use the commandline to do an ant jar later.

  5. Then go to the terminal and look at the ant script:

    enter image description here

So you see, I ran the jar and it didn't error out because it found the included mysql-connector-java-5.1.28-bin.jar embedded inside Hello.jar.

Look inside Hello.jar: vi Hello.jar and you will see many references to com/mysql/jdbc/stuff.class

To do ant jar on the commandline to do all this automatically: Rename buildant.xml to build.xml, and change the target name from create_run_jar to jar.

Then, from within MyProject you type ant jar and boom. You've got your jar inside MyProject. And you can invoke it using java -jar Hello.jar and it all works.

Community
  • 1
  • 1
Eric Leschinski
  • 146,994
  • 96
  • 417
  • 335
5

As a good practice you can use an Ant Script (Eclipse comes with it) to generate your JAR file. Inside this JAR you can have all dependent libs.

You can even set the MANIFEST's Class-path header to point to files in your filesystem, it's not a good practice though.

Ant build.xml script example:

<project name="jar with libs" default="compile and build" basedir=".">
<!-- this is used at compile time -->
<path id="example-classpath">
    <pathelement location="${root-dir}" />
    <fileset dir="D:/LIC/xalan-j_2_7_1" includes="*.jar" />
</path>

<target name="compile and build">
    <!-- deletes previously created jar -->
    <delete file="test.jar" />

    <!-- compile your code and drop .class into "bin" directory -->
    <javac srcdir="${basedir}" destdir="bin" debug="true" deprecation="on">
        <!-- this is telling the compiler where are the dependencies -->
        <classpath refid="example-classpath" />
    </javac>

    <!-- copy the JARs that you need to "bin" directory  -->
    <copy todir="bin">
        <fileset dir="D:/LIC/xalan-j_2_7_1" includes="*.jar" />
    </copy>

    <!-- creates your jar with the contents inside "bin" (now with your .class and .jar dependencies) -->
    <jar destfile="test.jar" basedir="bin" duplicate="preserve">
        <manifest>
            <!-- Who is building this jar? -->
            <attribute name="Built-By" value="${user.name}" />
            <!-- Information about the program itself -->
            <attribute name="Implementation-Vendor" value="ACME inc." />
            <attribute name="Implementation-Title" value="GreatProduct" />
            <attribute name="Implementation-Version" value="1.0.0beta2" />
            <!-- this tells which class should run when executing your jar -->
            <attribute name="Main-class" value="ApplyXPath" />
        </manifest>
    </jar>
</target>

Lucas Pottersky
  • 1,844
  • 6
  • 22
  • 38
2

Try the fat-jar extension. It will include all external jars inside the jar.

Marius
  • 57,995
  • 32
  • 132
  • 151
0

look @ java-jar-ignores-classpath-Workaround

Moro
  • 2,088
  • 6
  • 25
  • 34