1

下面是使用 dev 密钥库调用第一个 Web 服务并使用阶段密钥库调用第二个 Web 服务的示例代码。

public static void main(String args[]) {

    System.setProperty("javax.net.ssl.trustStore",
            "C:\\Users\\shahire\\Desktop\\Keystores\\Keystores\\dev\\dev.keystore");
    System.out.println("1st web service call");
            // 1st axis2 web service call code

    System.setProperty("javax.net.ssl.trustStore",
        "C:\\Users\\shahire\\Desktop\\Keystores\\Keystores\\stage\\stage.keystore");
    System.out.println("2nd web service call");
            // 2nd axis2 web service call code

}

我能够调用第一个 Web 服务调用但是我在访问第二个 Web 服务调用时遇到了错误

org.apache.axis2.AxisFault:sun.security.validator.ValidatorException:PKIX 路径构建失败:sun.security.provider.certpath.SunCertPathBuilderException:无法在 org.apache.axis2.AxisFault.makeFault 上找到请求目标的有效认证路径(AxisFault.java:417)

通过查看异常,我觉得它缓存了“javax.net.ssl.trustStore”位置。

当我评论第一个网络服务调用时,我可以访问第二个网络服务。

4

2 回答 2

4

只是要清楚。我不知道Axis2实际上是否由于某种原因“重用”或缓存了您所说的信任库系统属性;我最好的猜测是它初始化了一些读取属性的对象,并且在配置后不需要再次读取它。
但是您可以通过将所有受信任的证书放在同一个信任库中来解决这个问题。这将绝对解决您的问题,因为正如您所说,您实际上可以成功连接到第二个 Web 服务。
你为什么首先使用不同的信任库?
如果必须,由于某些安全要求(您有安全要求吗?),您应该查看是否有其他Axis专门用于您未使用的 ssl 属性。

于 2012-08-24T15:09:51.580 回答
0

您可以尝试另一种方法,而无需修改 JVM 提供的属性。

这是一个示例:

package test.ssl;

import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.security.KeyStore;

import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.KeyManagerFactory;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManagerFactory;

public class SSLClient {

    public void provider() throws Exception {
        // first call
        invokeWebServiceSSL(".../.../.../name.keystore", "changeit",
                "https://../../");
        // second call
        // invokeWebServiceSSL(String keystorePath, String pass, String
        // endpointURL)
    }

    public static void invokeWebServiceSSL(String keystorePath, String pass, String endpointURL) {
        HttpsURLConnection conn = null;
        try {

            char[] password = pass.toCharArray();
            FileInputStream fis = new FileInputStream(keystorePath);
            KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
            ks.load(fis, password);

            KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
            kmf.init(ks, password);

            TrustManagerFactory tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
            tmf.init(ks);
            fis.close();

            SSLContext ctx = SSLContext.getInstance("SSL");
            ctx.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
            SSLSocketFactory sf = ctx.getSocketFactory();

            URL url = new URL(endpointURL);
            conn = (HttpsURLConnection) url.openConnection();
            conn.setSSLSocketFactory(sf);

            InputStream inputstream = conn.getInputStream();
            InputStreamReader inputstreamreader = new InputStreamReader(inputstream);
            BufferedReader bufferedreader = new BufferedReader(inputstreamreader);

            String rs = null;
            while ((rs = bufferedreader.readLine()) != null) {
                System.out.println("Received: " + rs);
            }

        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                conn.getInputStream().close();
            } catch (Exception e) {
            }
        }
    }
}

我希望这有帮助。

于 2012-08-24T16:03:13.293 回答