2017-10-10 9 views
0

HTTP를 통해 SOAP 메시지를 보낼 때 성공적으로 작동하는 SAAJ에 자바 클라이언트를 작성했지만 클라이언트 인증서가 필요한 HTTPS를 통해 웹 서비스에 SOAP 메시지를 보내려고하면 그렇지 않습니다. 작업. SAAJ Security - - 다음 링크에서 페이지 하단에서SAAJ를 사용하여 키 스토어에서 특정 클라이언트 인증서 선택

다음과 같은 상태 :는 SAAJ 측에서

당신이해야 할 모든 프로토콜로 HTTPS로 사용하는 URL입니다. 인증서가/jre/lib/security/cacerts에 성공적으로 가져온 경우에만 작동합니다. 그렇지 않으면 JSSE는 연결을

을 허용하지 않습니다 그래서 위의 지시로 내 자바 인 cacerts에 관련된 루트 인증서와 함께 클라이언트 인증서를 가져오고 나는 다음과 같은 오류 얻을 그러나 프로그램을 실행 :

java.net.SocketException: Connection reset 

트래픽에 wireshark 추적을 실행하고 서버에서 요청할 때 Java 코드가 클라이언트 인증서를 제공하지 않는다는 것을 알았 기 때문에 다음과 같은 질문이 있습니다.

1) HTTPS URL을 soapConnection .call() 메서드와 함께 cer 가져 오기 내 cacerts 파일에 ts를 전송하면 SAAJ가 자동으로 인증을 처리 할 수 ​​있습니까? 아니면 위의 링크에서 설명하지 않는 더 많은 단계가 필요합니까?

2) 내 JAVA_HOME 내의 cacerts 파일에 인증서를 가져 오면 Java SAAJ 클라이언트가 soapConnection.call()을 호출 할 때 자동으로 여기를 볼 수 있습니까? 아니면 내 코드에 cacerts 파일을 사용하도록 명시 적으로 알려야합니까?

3) Java SAAJ 클라이언트가 JAVA_HOME에서 cacerts 파일을 자동으로 사용하는 경우 사용할 클라이언트 인증서를 어떻게 알 수 있습니까? 다시 말하지만, 명시 적으로이 코드를 작성해야하거나 SAAJ가 자동으로 처리해야합니까?

미리 감사드립니다.

답변

0

나는 이것을 알아 냈습니다. 단지 SAAJ의 soapConnection.call() 메소드 전에

static public void doTrustToCertificates() throws Exception 
{ 

    // Set truststore that contains root/intermediary certs 
    System.setProperty("javax.net.ssl.trustStore", "C:\\cert\\trusted.jks"); 
    System.setProperty("javax.net.ssl.trustStorePassword", "changeit"); 

    // Set keystore that contains private key 
    File pKeyFile = new File("C:\\cert\\privatekey.pfx"); 
    String pKeyPassword = "Password01"; 
    KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance("SunX509"); 
    KeyStore keyStore = KeyStore.getInstance("PKCS12"); 
    InputStream keyInput = new FileInputStream(pKeyFile); 
    keyStore.load(keyInput, pKeyPassword.toCharArray()); 
    keyInput.close(); 
    keyManagerFactory.init(keyStore, pKeyPassword.toCharArray()); 

    // Set ssl context with private key and truststore details 
    SSLContext sc = SSLContext.getInstance("TLSv1"); 
    sc.init(keyManagerFactory.getKeyManagers(), null, new SecureRandom()); 
    SSLSocketFactory sockFact = sc.getSocketFactory(); 

    // Add ssl context to https connection 
    HttpsURLConnection.setDefaultSSLSocketFactory(sockFact); 

} 

그런 다음합니다 (doTrustToCertificates라는) 방법 그렇게처럼 일 : 나는 다음과 같은 코드를 사용

doTrustToCertificates(); 
SOAPMessage soapResponse = soapConnection.call(soapMsgXml, ENDPOINT_URL); 
0

당신은 그렇게 지시하지 않았다 . 지침은 오도 된 내용이지만 서버 인증서가 자체 서명 된 상황에만 적용되며 클라이언트가 인증서를 필요로하는 상황에는 적용되지 않습니다.

이 경우 클라이언트의 키 저장소에 클라이언트 인증서를 만들어야합니다. CSR을 작성하고 서명을 받고 키 쌍과 CSR을 생성 할 때 시작한 것과 동일한 별칭을 사용하여 동일한 키 저장소로 다시 가져 오거나 그렇지 않으면 자체 서명 된 인증서 (yuck)를 ​​생성하고이를 내 보내야합니다 서버의 트러스트 스토어로 가져 오십시오.

코드를 작성할 필요가 없습니다. 시스템 등록 정보 javax.net.ssl.keyStore과 친구들이 JSSE에 클라이언트 키 저장소에 대해 알려주면됩니다.