从 Scala 文件创建 jar 文件

2022-08-31 20:57:11

我是Scala的新手,不懂Java。我想从一个简单的Scala文件创建一个jar文件。所以我有我的HelloWorld.scala,生成一个HelloWorld.jar。

Manifest.mf:

Main-Class: HelloWorld

在控制台中,我运行:

fsc HelloWorld.scala
jar -cvfm HelloWorld.jar Manifest.mf HelloWorld\$.class HelloWorld.class
java -jar HelloWorld.jar 
  => "Exception in thread "main" java.lang.NoClassDefFoundError: HelloWorld/jar"

java -cp HelloWorld.jar HelloWorld 
  => Exception in thread "main" java.lang.NoClassDefFoundError: scala/ScalaObject
    at java.lang.ClassLoader.defineClass1(Native Method)
    at java.lang.ClassLoader.defineClass(ClassLoader.java:675)
    at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:124)
    at java.net.URLClassLoader.defineClass(URLClassLoader.java:260)
    at java.net.URLClassLoader.access$100(URLClassLoader.java:56)
    at java.net.URLClassLoader$1.run(URLClassLoader.java:195)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findClass(URLClassLoader.java:188)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:316)
    at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:280)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:251)
    at java.lang.ClassLoader.loadClassInternal(ClassLoader.java:374)
    at hoppity.main(HelloWorld.scala)

答案 1

示例目录结构:

X:\scala\bin
X:\scala\build.bat
X:\scala\MANIFEST.MF
X:\scala\src
X:\scala\src\foo
X:\scala\src\foo\HelloWorld.scala

HelloWorld.scala:

//file: foo/HelloWorld.scala
package foo {
  object HelloWorld {
    def main(args: Array[String]) {
      println("Hello, world!")
    }
  }
}

清单。中频:

Main-Class: foo.HelloWorld
Class-Path: scala-library.jar

构建.bat:

@ECHO OFF

IF EXIST hellow.jar DEL hellow.jar
IF NOT EXIST scala-library.jar COPY %SCALA_HOME%\lib\scala-library.jar .

CALL scalac -sourcepath src -d bin src\foo\HelloWorld.scala

CD bin
jar -cfm ..\hellow.jar ..\MANIFEST.MF *.*
CD ..

java -jar hellow.jar

为了成功使用 -jar 开关,您需要在 META-INF/MANIFEST 中有两个条目。MF 文件:主类;任何依赖项的相对 URL。文档注释:

-罐

执行封装在 JAR 文件中的程序。第一个参数是 JAR 文件的名称,而不是启动类名称。为了使此选项正常工作,JAR 文件的清单必须包含一行,其形式为 Main-Class: classname。在这里,classname 标识具有公共静态 void main(String[] args) 方法的类,该方法用作应用程序的起点。有关使用 Jar 文件和 Jar 文件清单的信息,请参阅 Jar 工具参考页和 Java 教程的 Jar 跟踪。

使用此选项时,JAR 文件是所有用户类的源,而其他用户类路径设置将被忽略。

(注意:JAR文件可以使用大多数ZIP应用程序进行检查;我可能忽略了在批处理脚本中处理目录名称中的空格;Scala 代码运行器版本 2.7.4.final .)


为了完整起见,请使用等效的 bash 脚本:

#!/bin/bash

if [ ! $SCALA_HOME ]
then
    echo ERROR: set a SCALA_HOME environment variable
    exit
fi

if [ ! -f scala-library.jar ]
then
    cp $SCALA_HOME/lib/scala-library.jar .
fi

scalac -sourcepath src -d bin src/foo/HelloWorld.scala

cd bin
jar -cfm ../hellow.jar ../MANIFEST.MF *
cd ..

java -jar hellow.jar

答案 2

因为 Scala 脚本需要安装 Scala 库,所以你必须在 JAR 中包含 Scala 运行时。

有很多策略可以做到这一点,比如jar jar,但最终你看到的问题是你开始的Java进程找不到Scala JAR。

对于一个简单的独立脚本,我建议使用jar jar,否则你应该开始研究依赖管理工具,或者要求用户在JDK中安装Scala。


推荐