Java Forum / General / August 2006
Running java programs from class files
mark13.pl@gmail.com - 29 Aug 2006 17:23 GMT Hello,
I have created two class: ClassOne & ClassTwo (with main) in MyClass package. When I run it in eclipse everything goes okay. When I create jar and choose ClassTwo as Main everything goes okay. But now I am interested in running it just from class files. What is a correct syntax for such example?!? I tried: "java -classpath . ClassTwo" and similar but never run it getting all the time: NoClassDefFoundError.
Regards, mark
Knute Johnson - 29 Aug 2006 17:45 GMT > Hello, > [quoted text clipped - 8 lines] > > Regards, mark If your classes are in a package, then you must be in the directory above the package to run from class files. So if you package is called MyPackage, your class file is called MyClass.class and the MyPackage directory is located in /xyz/abc then you must be in /xyz/abc. To execute your program then you must type java MyPackage.MyClass.
 Signature Knute Johnson email s/nospam/knute/
Babu Kalakrishnan - 29 Aug 2006 18:21 GMT > > Hello, > > [quoted text clipped - 14 lines] > directory is located in /xyz/abc then you must be in /xyz/abc. To > execute your program then you must type java MyPackage.MyClass. Not 100% correct - though that is indeed the easiest way to do it. One could actually be in any working directory as long as your commandline while executing the "java" command also includes a -classpath argument that points to the base of your package hierarchy.,
The commandline for the above example in that case would be :
java -classpath /xyz/abc MyPackage.MyClass
BK
Knute Johnson - 29 Aug 2006 18:58 GMT >>> Hello, >>> [quoted text clipped - 25 lines] > > BK That doesn't work for me although I have seen reference to it before like that. Could it be that it doesn't work on Windows like that?
 Signature Knute Johnson email s/nospam/knute/
Oliver Wong - 29 Aug 2006 19:25 GMT >> The commandline for the above example in that case would be : >> >> java -classpath /xyz/abc MyPackage.MyClass > > That doesn't work for me although I have seen reference to it before like > that. Could it be that it doesn't work on Windows like that? It works for me on WinXP SP2:
java -cp "D:\Oliver's Documents\Workspace\Test\bin" D
to run a class called "D" with no package whose classfile is in "D:\Oliver's Documents\Workspace\Test\bin"
- Oliver
Knute Johnson - 30 Aug 2006 03:02 GMT >>> The commandline for the above example in that case would be : >>> [quoted text clipped - 11 lines] > > - Oliver That does for me too. But put it in a package and it won't.
 Signature Knute Johnson email s/nospam/knute/
Babu Kalakrishnan - 30 Aug 2006 04:20 GMT > >>> The commandline for the above example in that case would be : > >>> [quoted text clipped - 13 lines] > > That does for me too. But put it in a package and it won't. Interesting - Seems to work for me even with classes within a package -
Running TCPServer.class in package test :
java -classpath "C;\Documents and Settings\Babu\workspace\TestServer\classes" test.TCPServer Main: Listening for connections on port 2345
Testing on XP Home SP2
BK
Knute Johnson - 30 Aug 2006 05:34 GMT >>>>> The commandline for the above example in that case would be : >>>>> [quoted text clipped - 23 lines] > > BK package test;
public class Test { public static void main(String[] args) { System.out.println("It works!"); } }
C:\>javac test/Test.java
C:\>java test.Test It works!
C:\>cd test
C:\test>java -cp "C:\test" test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\test>java -cp /test test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\test>java test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\test>java -cp "C:/test" test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\test>cd \
C:\>java -cp "C:\test" test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\>java -cp /test test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\>java -cp test test.Test Exception in thread "main" java.lang.NoClassDefFoundError: test/Test
C:\>
What am I doing wrong here?
 Signature Knute Johnson email s/nospam/knute/
Andrew Thompson - 30 Aug 2006 06:07 GMT > >>>>> The commandline for the above example in that case would be : > >>>>> [quoted text clipped - 21 lines] > > > > Testing on XP Home SP2 ...
> package test; > [quoted text clipped - 13 lines] > C:\test>java -cp "C:\test" test.Test > Exception in thread "main" java.lang.NoClassDefFoundError: test/Test Here you need to add the 'test' package to the classpath, as opposed to ..anything it contains.
So on my system -
C:\test>java -cp .. test.Test It works!
___
Note that in your original post, there was a *slight* wording mistake (AFAIU). I did not point it out at the time, since I felt the OP had enough to mull over, but since I've jumped into this thread..
Initially you said that a test.Test dould be run from the 'parent directory'.. OK that *is* correct, but I feel it would have been better to say that it could be run from the 'root of the package structure'.
In your example, of course, they *are* the same place.
BUT.. if you consider the class test.junit.Test, the latter advice is correct, while the 'parent' directory of the test.junit.Test class is also a package, rather than the 'root' and will not work (in the same way).
Andrew T.
Knute Johnson - 30 Aug 2006 20:21 GMT >>>>>>> The commandline for the above example in that case would be : >>>>>>> [quoted text clipped - 68 lines] > > Andrew T. Andrew:
Thanks very much. Please see my response to Babu (and you).
 Signature Knute Johnson email s/nospam/knute/
Babu Kalakrishnan - 30 Aug 2006 06:51 GMT >>>>>> The commandline for the above example in that case would be : >>>>>> [quoted text clipped - 35 lines] > > C:\>javac test/Test.java I'd assume that you now have Test.java and Test.class inside C:\test.
> C:\>java test.Test > It works! OK - here the default classpath assumed by the JVM is "." (which is "C:\"), so it works
> C:\>cd test > > C:\test>java -cp "C:\test" test.Test > Exception in thread "main" java.lang.NoClassDefFoundError: test/Test Your commandline here should be :
java -cp "C:\" test.Test
because the classpath is to be set to the root of the package hierarchy - which is C:\ in your case.
With the commandline you used, the class file is expected to be C:\test\test\Test.class
BK
Knute Johnson - 30 Aug 2006 20:20 GMT >>>>>>> The commandline for the above example in that case would be : >>>>>>> [quoted text clipped - 60 lines] > > BK Thank you so much guys, this has confused the s**t out of me for years. I think the most confusing part is the root business.
So now that you solved that one, show me how to use a jar library on the command line when I run a java program. I can make it compile but I can't make it run. I can get it to work if I put the jar file in the Class-Path: line in the manifest and put the jar file in the same directory as the program jar file but not from the command line.
Test is my slightly modified class that calls a static method in lib.Lib. The Lib class has been compiled and put into a jar file, lib.jar in the /lib directory. I then compile Test.java from the /test directory and run the .class file with no problems. You will see that the lib.Lib class can't be found once I jar it.
package test;
public class Test { public static void main(String[] args) { System.out.println("It works!"); lib.Lib.lib(); } }
package lib;
public class Lib { public static void lib() { System.out.println("lib"); } }
C:\lib>dir Volume in drive C has no label. Volume Serial Number is 7C27-9663
Directory of C:\lib
08/30/2006 12:15 PM <DIR> . 08/30/2006 12:15 PM <DIR> .. 08/30/2006 11:06 AM 728 Lib.jar 08/30/2006 10:46 AM 116 Lib.java 2 File(s) 844 bytes 2 Dir(s) 62,081,531,904 bytes free
C:\lib>
C:\test>dir Volume in drive C has no label. Volume Serial Number is 7C27-9663
Directory of C:\test
08/30/2006 12:12 PM <DIR> . 08/30/2006 12:12 PM <DIR> .. 08/30/2006 11:51 AM 162 Test.java 1 File(s) 162 bytes 2 Dir(s) 62,081,544,192 bytes free
C:\test>javac -cp /lib/Lib.jar Test.java
C:\test>java -cp /lib/Lib.jar;/ test.Test It works! lib
C:\test>cd \
C:\>jar cvfe test/Test.jar test.Test test/*.class added manifest adding: test/Test.class(in = 452) (out= 310)(deflated 31%)
C:\>java -cp /lib/Lib.jar -jar test/Test.jar It works! Exception in thread "main" java.lang.NoClassDefFoundError: lib/Lib at test.Test.main(Test.java:6)
C:\>
 Signature Knute Johnson email s/nospam/knute/
Andrew Thompson - 31 Aug 2006 03:17 GMT ...
> So now that you solved that one, show me how to use a jar library on the > command line when I run a java program. I'll have a closer look at the rest if needed, but for starters, could you give us the output of .. jar -tf Test.jar ?
I suspect it will reveal the problem.
Andrew T.
Knute Johnson - 31 Aug 2006 03:46 GMT > ... >> So now that you solved that one, show me how to use a jar library on the [quoted text clipped - 8 lines] > > Andrew T. C:\test>jar tf Test.jar META-INF/ META-INF/MANIFEST.MF test/Test.class
I know what you are looking for and it's not here!
When I get this all figured out, I'm going to write a paper on how to do these things because I know that I won't remember and that there must be more idiots out there than just me :-).
 Signature Knute Johnson email s/nospam/knute/
Andrew Thompson - 31 Aug 2006 04:09 GMT > > ... > >> So now that you solved that one, show me how to use a jar library on the [quoted text clipped - 6 lines] > > > > I suspect it will reveal the problem. ....
> C:\test>jar tf Test.jar > META-INF/ > META-INF/MANIFEST.MF > test/Test.class > > I know what you are looking for Yep. Just wanted to check the internal structure, specifically the directory sstructure.
>....and it's not here! OK.. I was wrong! I'll look more closely into the details you posted.
Andrew T.
Knute Johnson - 31 Aug 2006 16:19 GMT >>> ... >>>> So now that you solved that one, show me how to use a jar library on the [quoted text clipped - 22 lines] > > Andrew T. No problem.
 Signature Knute Johnson email s/nospam/knute/
Andrew Thompson - 31 Aug 2006 12:43 GMT ...
> C:\test>cd \ > > C:\>jar cvfe test/Test.jar test.Test test/*.class Aha! I did miss thid command that makes the Jar when I first read (OK.. skimmed) this, but...
'e'? 'cvfe' as the options, what is 'e'?
I don't see it in the options for either the Win or *nix version of the jar command.
And, while I'm here, I understand the meaning of 'test/Test.jar' as the output file, and 'test/*.class' as the input file(s), but what is 'test.Test' doing in there?
Andrew T.
Knute Johnson - 31 Aug 2006 16:20 GMT > ... >> C:\test>cd \ [quoted text clipped - 14 lines] > > Andrew T. The e option is the entry point. Same as setting Main-Class in the manifest file. I'm using the 1.6 beta2 so it may have come with that set of code. Much simpler than making all those manifest files when you don't have anything else to put in them.
 Signature Knute Johnson email s/nospam/knute/
Andrew Thompson - 31 Aug 2006 16:27 GMT > > ... > >> C:\test>cd \ [quoted text clipped - 5 lines] > > > > 'e'? 'cvfe' as the options, what is 'e'? ...
> The e option is the entry point. Same as setting Main-Class in the > manifest file. That's handy.
>..I'm using the 1.6 beta2 so it may have come with that > set of code. I expect so - I am still using the 1.5 SDK.
>..Much simpler than making all those manifest files when you > don't have anything else to put in them. Heck yeah. Especially for dealing with that darn 'last line must be blank' crap that they specify for the mainfest. I wonder how many hundreds of man-hours have been wasted due to that alone?
Andrew T.
Babu Kalakrishnan - 31 Aug 2006 12:57 GMT > So now that you solved that one, show me how to use a jar library on the > command line when I run a java program. I can make it compile but I [quoted text clipped - 7 lines] > directory and run the .class file with no problems. You will see that > the lib.Lib class can't be found once I jar it. I don't think it is possible to achieve that if you're using -jar option of java. Once the -jar option is specified, whatever you specify as a -classpath or -cp option is essentially ignored, and the effective user classpath of the JVM becomes the specified jar file and the jars specified in that jar's manifest.
An alternative would be to not use the -jar option, but to run it as :
java -cp /path_to_lib_jar/lib.jar:/path_to_test_jar/test.jar test.Test
(i.e by explicitly specifying the main class to invoke, and specifying all the jar files in the classpath option)
BK
Knute Johnson - 31 Aug 2006 16:29 GMT >> So now that you solved that one, show me how to use a jar library on >> the command line when I run a java program. I can make it compile but [quoted text clipped - 22 lines] > > BK I did try that and it does work just fine. I think you are correct that you can't do what I was trying to do. See Nigel's post below.
Thanks very much Babu.
 Signature Knute Johnson email s/nospam/knute/
Nigel Wade - 31 Aug 2006 15:48 GMT >>>>>>>> The commandline for the above example in that case would be : >>>>>>>> [quoted text clipped - 69 lines] > Class-Path: line in the manifest and put the jar file in the same > directory as the program jar file but not from the command line. You can't. It is specifically mentioned in the java man page. When running a jar with the java -jar command syntax, the -cp flag is ignored. The jar file is the sole definition of the classpath.
If your executable jar requires classes from other jars, those jars must be added to the Class-Path: section of the executable jar's manifest. To further annoy you the paths in Class-Path: should be relative paths (although absolute paths do work, at least on Linux). I'm not surprised you're confused, you're not the only one. I suppose it does offer some measure of security in that a user of your application can't change the classpath to inject their own jar's to intercept private information from within the application. Although there's nothing to stop them unpacking the jar, and re-packaging it with a different manifest. So what the purpose really is, other than to annoy and confuse, escapes me.
 Signature Nigel Wade, System Administrator, Space Plasma Physics Group, University of Leicester, Leicester, LE1 7RH, UK E-mail : nmw@ion.le.ac.uk Phone : +44 (0)116 2523548, Fax : +44 (0)116 2523555
Knute Johnson - 31 Aug 2006 16:23 GMT >>>>>>>>> The commandline for the above example in that case would be : >>>>>>>>> [quoted text clipped - 70 lines] > with the java -jar command syntax, the -cp flag is ignored. The jar file is the > sole definition of the classpath. Well that's a relief. At least I know now that I'm not going completely nuts.
> If your executable jar requires classes from other jars, those jars must be > added to the Class-Path: section of the executable jar's manifest. To further [quoted text clipped - 6 lines] > manifest. So what the purpose really is, other than to annoy and confuse, > escapes me. Thanks very much Nigel.
 Signature Knute Johnson email s/nospam/knute/
Matt Rose - 29 Aug 2006 18:20 GMT > Hello, > [quoted text clipped - 8 lines] > > Regards, mark Your class files need to live in directory structures that mimic the package names, tokenised along dots, e.g. java.lang.String would be in java/lang/String.class. Whichever directory has the java directory (in the above example) as a child is the only one that needs to be in the classpath to find that class.
In your example,
mkdir MyClass mv ClassOne.class ClassTwo.class MyClass/ java -classpath . ClassTwo
should do the trick.
Matt
Matt Rose - 29 Aug 2006 18:22 GMT > > Hello, > > [quoted text clipped - 24 lines] > > Matt Oops, you'll need to qualify the name of your class when you invoke it. The last line should read:
java -classpath . MyClass.ClassTwo
Matt
Free MagazinesGet these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...
|
|
|