Java WebStart 的 ClassNotFoundException

Posted

技术标签:

【中文标题】Java WebStart 的 ClassNotFoundException【英文标题】:ClassNotFoundException for Java WebStart 【发布时间】:2021-08-17 16:42:55 【问题描述】:

我正在尝试按照THIS TUTORIAL 学习 Java WebStart,但我遇到了 ClassNotFoundException。我将我的 jar 文件部署到 https://dalayach.github.io/TestClass.jar

这是堆栈跟踪

java.lang.ClassNotFoundException: testPackage.TestClass
    at java.net.URLClassLoader.findClass(Unknown Source)
    at com.sun.jnlp.JNLPClassLoader.findClass(Unknown Source)
    at java.lang.ClassLoader.loadClass(Unknown Source)
    at com.sun.jnlp.JNLPClassLoader.loadClass(Unknown Source)
    at java.lang.ClassLoader.loadClass(Unknown Source)
    at com.sun.javaws.Launcher.doLaunchApp(Unknown Source)
    at com.sun.javaws.Launcher.run(Unknown Source)
    at java.lang.Thread.run(Unknown Source)

这是我的TestClass.jnlp

<?xml version="1.0" encoding="UTF-8"?>
<jnlp spec="1.0+" codebase=
"https://dalayach.github.io"
    href="TestClass.jnlp">
    <information>
        <title>TestClass Title</title>
        <vendor>TestClass Vendor</vendor>
    </information>
    <resources>
        <!-- Application Resources -->
        <j2se version="1.8+"
              href="http://java.sun.com/products/autodl/j2se"/>
        <jar href="TestClass.jar"
            main="true" />

    </resources>
    <application-desc
         name="TestClass application-desc name"
         main-class=
        "testPackage.TestClass"
         
         >
     </application-desc>
     <update check="background"/>
</jnlp>                                   

这是我的TestClass.java

package testPackage;

import javax.swing.JFrame;

public class TestClass


   public static void main(String[] args)
   
   
      JFrame frame = new JFrame();
   
      frame.setTitle("TestClass JFrame title");
      frame.setSize(300, 300);
      frame.setLocation(300, 300);
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    
      frame.setVisible(true);
   
   


这里是mymanifest.txt

Permissions: sandbox
Codebase: dalayach.github.io
Application-Name: TestClass
Main-Class: testPackage.TestClass

最后,这里有一些相关信息

$ javac -version
javac 1.8.0_291

$ java -version
java version "1.8.0_291"
Java(TM) SE Runtime Environment (build 1.8.0_291-b10)
Java HotSpot(TM) 64-Bit Server VM (build 25.291-b10, mixed mode)

$ curl https://dalayach.github.io/TestClass.jnlp
/** It returned my up-to-date jnlp */

$ curl https://dalayach.github.io/TestClass.jar
/** same for jar */

$ curl https://dalayach.github.io/testPackage/TestClass.java
/** same for java */

$ javac testPackage/TestClass.java
/** this is how I compile my class */

$ jar cvfm TestClass.jar mymanifest.txt testPackage/
/** this is how I construct my jar file, per the instructions linked in the beginning */

$ java -jar TestClass.jar
/** my application successfully starts */

$ jar tvf TestClass.jar
     0 Sat May 29 16:46:46 EDT 2021 META-INF/
   185 Sat May 29 16:46:46 EDT 2021 META-INF/MANIFEST.MF
     0 Sat May 29 16:46:18 EDT 2021 testPackage/
   659 Sat May 29 16:46:32 EDT 2021 testPackage/TestClass.class
   385 Sat May 29 16:46:18 EDT 2021 testPackage/TestClass.java

And when I open the MANIFEST.MF, I see this.

Manifest-Version: 1.0
Application-Name: TestClass
Permissions: sandbox
Codebase: dalayach.github.io
Created-By: 1.8.0_291 (Oracle Corporation)
Main-Class: testPackage.TestClass

我已经为 .jnlp 和 .java 尝试了多种选项。你可以看到我尝试过的东西的完整列表HERE。有任何想法吗?它不必解决它,只要有任何取得进展的想法都会有所帮助和赞赏!提前谢谢你。

【问题讨论】:

显示 jar 文件的“jar tvf”。 @ThorbjørnRavnAndersen 完成,谢谢! @ThorbjørnRavnAndersen 我还添加了那个 MANIFEST.MF 文件的内容,只是为了展示它的样子。 @ThorbjørnRavnAndersen 找到了答案——我已经在下面发布了。再次感谢您的帮助!您的建议使我尝试了其他一些命令行选项,这使我得到了正确的答案! 您的问题没有更新。 【参考方案1】:

显然,我的代码没有错,但我做出和测试更改的速度如此之快,以至于我做出更新的速度比 Java WebStart 检查它们的速度还要快。

这是因为我上面的更新策略——如果你在 .jnlp 中设置了 &lt;update check="background"/&gt;,你是在告诉 Java WebStart 下载最新的文件 懒惰。这意味着,如果您在不同的解决方案之间快速来回切换,Java WebStart 可能真的太慢而无法跟上,并且在旧版本最终出现时已经过时了。

有 2 种解决方案中的 1 种可供选择。

将update policy 更改为TestClass.jnlp

如果您希望 Java WebStart 等到所有更新下载完成后再尝试运行您的应用程序,您应该将您的更新策略更改为类似 &lt;update check="always"&gt;。这样,您可以保证您的 jnlp 正在提取最新的文件。

在每次运行应用程序之前使用javaws -uninstall

这个命令clears the cache,这样你的程序就需要重新下载了。这实际上与上述项目符号的结果相同,但这允许您使用首选设置保留 .jnlp 文件。此外,您不必在调试任何设置时来回切换它。只需清除缓存并进行测试。

【讨论】:

为您的 jar 文件名提供每次构建的新时间戳 很好的建议@ThorbjørnRavnAndersen 谢谢!我将在未来的构建中使用它。

以上是关于Java WebStart 的 ClassNotFoundException的主要内容,如果未能解决你的问题,请参考以下文章

Java WebStart 的 ClassNotFoundException

如何将 Java 9 '--permit-illegal-access' 标志传递给 Webstart 应用程序?

将Java Applet迁移到Java WebStart(JNLP)

如何在 Java WebStart (JNLP) 应用程序中获取多个 hprof 转储?

Java webstart max-heap-size 导致JVM无法启动

webstart 应用程序日志记录权限被拒绝