1 概述
本文主要介绍如何通过javac和jar命令来对Java项目完成编译、打包和运行。目的是为了加深对整个Java项目的编译、打包和运行过程的了解。
2 项目准备
如上图所示,新增Java项目,其中含有两个模块(module_a和module_b)。module_b内定义了一个User类供module_a使用中的Main类使用。两个类的代码如下:
public class User implements Chinese{
private String name;
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "User{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
import com.test.project.User;
public class Main {
public static void main(String[] args) {
User user = new User();
user.setName("leo");
user.setAge(18);
System.out.println(user);
}
}
public interface Chinese {
}
3 编译和打包
module_a和module_b其实是两个Java项目,module_a中的Main要使用module_b中的User类,首先需要对module_b进行编译打包,然后将打好的jar包引入到module_a中,module_a才能使用module_b中定义的User类。下面详细介绍一下如何module_b的打包过程(不含外部依赖的打包过程)。步骤如下:
1、先将当前目录切换到module_b下然后执行javac命令完成module_b编译;
javac .\src\com\test\project\User.java -sourcepath .\src\ -d .\target\ -encoding UTF-8
可以同时指定多个待编译的源文件(也可以用通配符,或者将待编译的文件写入到文件中然后javac指定对应的文件编译,具体见javac的命令使用介绍),此处未指定Chinese.java是因为使用了sourcepath,要注意的是sourcepath后面的路径要指定成.\src\。编译结果如下:
2、然后将1步中编译的结果打包
将当前目录切换到module_b的target目录下并执行如下打包命令:
jar -cf module_b-1.0.0.jar com
结果如下:
包结构如下:
MANIFEST.MF文件内容如下:
也可以通过jar -t module_b-1.0.0.jar来查看包结构
执行完这一步,module_b项目的包就打好了,可以被module_a使用了。
3、编译module_a项目;
1、将目录切换到module_a下并执行如下命令:
javac .\src\com\test\myproject\Main.java -cp .\lib\module_b-1.0.0.jar -d target -encoding UTF-8
结果如下:
编译成的.class文件在target目录下按照包结构进行组织。
2、将目录切换到module_b\target下,然后对编译结果进行打包;
在target目录下新建META-INF\lib并将module_b-1.0.0.jar复制到下面,如下:
然后执行如下命令:
jar -cfm module_a-1.0.0.jar Manifest.txt com META-INF/lib
注意必须是Manifest.txt文件名,文件内容如下:
Class-Path: META-INF/lib/module_b-1.0.0.jar
Main-Class: com.test.myproject.Main
key之后:和value之间必须有空格,末尾必须空一行。
命令执行的结果如下(生成可执行jar包):
控制台输入如下命令直接运行该jar包:
java -jar .\module_a-1.0.0.jar
结果如下:
当然也可以不把module_b-1.0.0.jar打到module_a-1.0.0.jar中,这样执行module_a-1.0.0.jar中的main方法就需要通过java命令来执行,执行命令中需要指定入口类和classpath(指向module_b-1.0.0.jar)。具体可自行百度。