【问题标题】:javax.net.ssl.SSLException: java.security.InvalidAlgorithmParameterException: the trustAnchors parameter must be non-emptyjavax.net.ssl.SSLException: java.security.InvalidAlgorithmParameterException: trustAnchors 参数必须为非空
【发布时间】:2011-12-04 20:07:16
【问题描述】:

我希望解析一个每天更新所述文件的 XML 文件 - 我遇到的唯一问题是他们使用自己的证书 (https://...),我不能使用该特定 URL,也不能使用是否有可用的 http://... 链接。

URL url = new URL("https://...");
...
Document document = db.parse(url.openStream());

此代码在运行我的测试时引发以下异常:

javax.net.ssl.SSLException:java.lang.RuntimeException:意外错误:java.security.InvalidAlgorithmParameterException:trustAnchors 参数必须为非空

我已经看到了各种关于创建各种类来处理这种连接或个人服务器的建议,以及将证书添加到密钥库,然后将该密钥库添加到 Java 项目,但我一直无法做到这一点,我正在寻找一种更简单的方法来在线访问 XML。

【问题讨论】:

标签: java ssl truststore jsse


【解决方案1】:

您需要一个信任库来存储 SSL 证书。您可以使用首选的 Web 浏览器下载证书。要将证书加载到信任库中,您需要 JDK 附带的“keytool”程序。

例如,如果您的证书文件名为“certificate.crt”,并且您想创建一个名为“secure.ts”的信任库,则可以按如下方式调用 keytool:

keytool -importcert -keystore secure.ts -storepass S3cuR3pas$! -file certificate.crt

现在,您必须告诉您的程序密钥库在哪里以及打开它的密码,定义系统属性“javax.net.ssl.trustStore”和“javax.net.ssl.trustStorePassword”之前 打开连接

URL url = new URL("https://...");

System.setProperty("javax.net.ssl.trustStore", "secure.ts");
System.setProperty("javax.net.ssl.trustStorePassword", "S3cuR3pas$!");
...
Document document = db.parse(url.openStream());

【讨论】:

    【解决方案2】:

    这条奇怪的消息表示未找到信任库。

    与 XML BTW 无关。

    【讨论】:

    • @Acetaminophen 请参阅 Javadoc:安全性/JSSE 参考指南。
    • 我之前已将 /lib/security/cacerts 重命名为 /lib/security/cacerts_orig 以尝试将我拥有的证书添加到密钥库 - 我'已修复此问题,现在出现以下错误:javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX 路径构建失败:sun.security.provider.certpath.SunCertPathBuilderException: 无法找到请求目标的有效证书路径
    • @Acetaminophen 所以你的信任库不信任服务器的证书。所以它可能是自签名的。您需要将其导入您的 cacerts,或者更可能将您的 cacerts 复制到本地信任库,将服务器证书导入其中,并将其用作信任库。有关可能的导入解决方案,请参阅forums.oracle.com/forums/…。最好的解决方案是让服务器使用由 CA 签名的证书。
    • @对乙酰氨基酚 (a) 什么问题?它对我来说编译和执行得很好。 (b) 我从来不理解禁用证书验证的热情。如果您不希望它安全,为什么要使用 SSL? (c) 将证书放入 lib/security 不会完成任何事情。
    • @Acetaminophen,到目前为止,您的问题与 XML 无关(@EJP 正确地重新标记了您的问题)。现在,UnknownHostException:我不确定你为什么要删除链接前面的https://NumberFormatException:这可能与您在某个阶段对 XML 文档的处理有关。这可能应该在另一个问题中解决,因为它现在与 SSL 无关。
    【解决方案3】:

    你可以试试这个:

    String javaHomePath = System.getProperty("java.home");
    String keystore = javaHomePath + "/lib/security/cacerts";
    String storepass= "changeit";
    String storetype= "JKS";
    
    String[][] props = {
        { "javax.net.ssl.trustStore", keystore, },
        { "javax.net.ssl.keyStore", keystore, },
        { "javax.net.ssl.keyStorePassword", storepass, },
        { "javax.net.ssl.keyStoreType", storetype, },
    };
    for (int i = 0; i < props.length; i++) {
        System.getProperties().setProperty(props[i][0], props[i][1]);
    }
    // Now you can proceed to connect to call the webservice.
    // SSL will be used automatically if the service endpoint url 
    // starts with <a href="https://." target="_blank"         rel="nofollow">https://.</a>
    // The server will send its certificate signed by verisign and 
    // client will trust and authenticate the server as it recognizes 
    // verisign as one trusted root.
    

    【讨论】:

    • 你救了我的一天,伙计!
    【解决方案4】:

    在开发 Java 6 应用程序时,我的 MAC OSX (Yosemite) 遇到了同样的异常。您需要下载并安装 Apple 的 Java for OSX 2014:

    http://support.apple.com/kb/DL1572

    【讨论】:

      猜你喜欢
      • 2018-06-03
      • 1970-01-01
      • 1970-01-01
      • 2018-06-01
      • 2012-01-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多