1

我无法将参数传递给使用 Java Web Start 启动的 Java 应用程序。我的系统是 Ubuntu Linux 12.04.1 Precise,但同样的情况也发生在 Windows 7 中。两者都使用 Oracle Java 版本 1.7.0_09。

编辑:我正在研究 Web Start 应用程序是否比普通小程序更适合我们的需求。小程序的问题在于,如果用户导航离开我们不想要的页面,它就会关闭。(我们也想看看是否可以通过使用 Web Start 而不是小程序来解决某个安全问题。)我们想从浏览器启动应用程序,以便我们可以将有关经过身份验证的用户的信息传递给Java 应用程序。要求用户登录应用程序似乎是一个糟糕的解决方案(我们可能必须支持 OAuth 之类的东西)。

我有一个示例程序 CommandLineArgs.java:

public class CommandLineArgs {
    public static void main(String[] args)  {
        System.out.println(String.format("Got %d command line args:", args.length));
        for (String arg : args) {
            System.out.println(arg);
        }
    }
}

我把它打包成一个罐子:

javac CommandLineArgs.java
zip cmd.jar CommandLineArgs.class

然后我有一个名为 cmd.jnlp 的 JNLP 文件:

<?xml version="1.0" encoding="utf-8"?>

<!-- Empty codebase means use same directory. -->
<jnlp spec="1.0+" codebase="https://localhost:9876/">
    <information>
        <title>Command Line Args Printer</title>
        <vendor>No one</vendor>
        <homepage href="https://localhost:9876/"/>
        <description>Application that prints the command line arguments that it gets.</description>
    </information>
    <resources>
        <j2se version="1.6+" initial-heap-size="32m" max-heap-size="128m" />
        <property name="jnlp.versionEnabled" value="true"/>

        <jar href="cmd.jar" main="true"/>

    </resources>
    <application-desc main-class="CommandLineArgs">
        <!-- Here are sample arguments I'd like to pass to the program. -->
        <argument>arg1</argument>
        <argument>arg2</argument>
        <argument>arg3</argument>
    </application-desc>
</jnlp>

这是我用于测试的 HTML 页面 cmd.html。div 元素最初是使用 deployjava.js 创建的:deployJava.launchWebStartApplication('https://localhost:9876/cmd.jnlp')

<!DOCTYPE html>

<html>
<head>
    <title>Java web start command line arguments test</title>

    <meta http-equiv="content-type" content="text/html; charset=utf-8" />
</head>
<body>

<div id="div1" style="position: relative; left: -10000px; margin: 0px auto; " class="dynamicDiv">
    <embed type="application/x-java-applet;jpi-version=1.7.0_09" width="0" height="0" launchjnlp="https://localhost:9876/cmd.jnlp" docbase="https://localhost:9876/">
</div>

</body>
</html>

让 https 服务器运行的最快方法是使用 Linux 中常见的 openssl 工具。像这样运行服务器时,当前目录应该包含 cmd.html、cmd.jar 和 cmd.jnlp。

sudo cp /etc/ssl/private/ssl-cert-snakeoil.key .
sudo chmod 666 ssl-cert-snakeoil.key
openssl req -batch -new -x509 -key ssl-cert-snakeoil.key -out ssl-cert-snakeoil.key.crt
openssl s_server -cert ssl-cert-snakeoil.key.crt -key ssl-cert-snakeoil.key -accept 9876 -WWW

现在,如果我上网,https://localhost:9876/cmd.html我可以运行该应用程序。Java 控制台打开并打印出来。请注意,有 0 个命令行参数。

   JNLP Ref (absolute): https://localhost:9876/cmd.jnlp
    Match: beginTraversal
Match: digest selected JREDesc: JREDesc[version 1.6+, heap=33554432-134217728, args=null, href=null, sel=false, null, null], JREInfo: JREInfo for index 0:
    platform is: 1.7
    product is: 1.7.0_09
    location is: http://java.sun.com/products/autodl/j2se
    path is: /opt/jre1.7.0_09/bin/java
    args is: -agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=8001
    native platform is: Linux, amd64 [ x86_64, 64bit ]
    JavaFX runtime is: JavaFX 2.2.3 found at /opt/jre1.7.0_09/
    enabled is: true
    registered is: true
    system is: true

    Match: ignoring maxHeap: 134217728
    Match: selecting InitHeap: 33554432
    Match: digesting vmargs: null
    Match: digested vmargs: [JVMParameters: isSecure: true, args: ]
    Match: JVM args after accumulation: [JVMParameters: isSecure: true, args: ]
    Match: digest LaunchDesc: null
    Match: digest properties: []
    Match: JVM args: [JVMParameters: isSecure: true, args: ]
    Match: endTraversal ..
    Match: JVM args final: -Xms32m
    Match: Running JREInfo Version    match: 1.7.0.09 == 1.7.0.09
     Match: Running JVM args match: have:<-Xms32m     satisfy want:<-Xms32m>
Got 0 command line args:

另一方面,如果我从命令行 ( javaws cmd.jnlp) 运行 javaws,我会在 java 控制台中得到它。现在有 3 个命令行参数。

    Match: beginTraversal
Match: digest selected JREDesc: JREDesc[version 1.6+, heap=33554432-134217728, args=null, href=null, sel=false, null, null], JREInfo: JREInfo for index 0:
    platform is: 1.7
    product is: 1.7.0_09
    location is: http://java.sun.com/products/autodl/j2se
    path is: /opt/jre1.7.0_09/bin/java
    args is: -agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=8001
    native platform is: Linux, amd64 [ x86_64, 64bit ]
    JavaFX runtime is: JavaFX 2.2.3 found at /opt/jre1.7.0_09/
    enabled is: true
    registered is: true
    system is: true

    Match: ignoring maxHeap: 134217728
    Match: selecting InitHeap: 33554432
    Match: digesting vmargs: null
    Match: digested vmargs: [JVMParameters: isSecure: true, args: ]
    Match: JVM args after accumulation: [JVMParameters: isSecure: true, args: ]
    Match: digest LaunchDesc: null
    Match: digest properties: []
    Match: JVM args: [JVMParameters: isSecure: true, args: ]
    Match: endTraversal ..
    Match: JVM args final: -Xms32m
    Match: Running JREInfo Version    match: 1.7.0.09 == 1.7.0.09
     Match: Running JVM args match: have:<-Djnlp.versionEnabled=true -Xms32m     satisfy want:<-Xms32m>
Got 3 command line args:
arg1
arg2
arg3

难道我做错了什么?为什么在浏览器中运行时参数不传递给我的程序?

我发现帖子Java WS 应用程序偶尔忽略参数似乎描述了同样的问题。posdef 的解决方案是从 jnlp 文件中的 jnlp 元素中删除 href 属性,但我没有该属性。

4

3 回答 3

1

我们也有兴趣看看我们是否可以通过使用 Web Start 而不是小程序来解决某个安全问题。

应用于基于 JWS 的应用程序的安全环境。总是与应用于小程序的非常相似。一些小的差异System.exit(n)是始终在小程序(甚至是受信任的小程序)中受到限制,并且 JWS 提供了介于沙盒和受信任之间的中间级别的安全性。

在 Oracle 收购这两种形式的插件之前,Sun 付出了巨大的努力。

所以这个问题的简短回答是,“不”。如果您可以在 JWS 应用程序中执行此操作,那么您应该可以在小程序中执行此操作。

于 2012-10-19T10:07:54.177 回答
1

application-desc用于 WebStart 应用程序,applet-desc用于小程序。

于 2012-10-19T04:49:44.997 回答
0

根据 Oracle 文档

“property 元素定义了一个系统属性,可通过 System.getProperty 和 System.setProperties 方法使用。它有两个必需的属性:名称和值。”

然后给出这个例子:

<property name="key" value="overwritten"/> 

要检索 Java 类中的值:

System.getProperty("key");

于 2012-10-27T06:42:37.177 回答