2015-06-23 101 views
3

我試過使用此link中提供的解決方案。在java中檢索X.509證書的主題替代名稱

我收到以下錯誤,當我試圖讀取X.509的主題備用名稱的證書

java.lang.NoSuchMethodError: org.bouncycastle.asn1.ASN1InputStream.readObject()Lorg/bouncycastle/asn1/DERObject;

在下面的代碼行

ASN1InputStream decoder = new ASN1InputStream((byte[]) item.toArray());

DEREncodable encoded = decoder.readObject();

.der文件的使用方式如下創建證書。

X509Certificate cert=null; 
fis = new FileInputStream(file.getAbsoluteFile());  //.der file 
bis = new BufferedInputStream(fis); 

CertificateFactory cf = CertificateFactory.getInstance("X.509"); 
while (bis.available() > 0) { 
        try{ 
        cert = cf.generateCertificate(bis); 
        } 
        catch (CertificateException e) { 
         e.printStackTrace(); 
        } 
List list=getSubjectAlternativeNames((X509Certificate) cert); 

下面是我從上面提到的鏈接得到的解決方案。

public static List<String> getSubjectAlternativeNames(X509Certificate certificate) { 
    List<String> identities = new ArrayList<String>(); 
    try { 
     Collection<List<?>> altNames = certificate.getSubjectAlternativeNames(); 
     // Check that the certificate includes the SubjectAltName extension 
     if (altNames == null) 
      return Collections.emptyList(); 
     // Use the type OtherName to search for the certified server name 
     for (List item : altNames) { 
      Integer type = (Integer) item.get(0); 
      if (type == 0) 
       // Type OtherName found so return the associated value 
       try { 
        // Value is encoded using ASN.1 so decode it to get the server's identity 
        ASN1InputStream decoder = new ASN1InputStream((byte[]) item.toArray()[1]); 
        DEREncodable encoded = decoder.readObject(); 
        encoded = ((DERSequence) encoded).getObjectAt(1); 
        encoded = ((DERTaggedObject) encoded).getObject(); 
        encoded = ((DERTaggedObject) encoded).getObject(); 
        String identity = ((DERUTF8String) encoded).getString(); 
        // Add the decoded server name to the list of identities 
        identities.add(identity); 
       } 
      catch (UnsupportedEncodingException e) { 
       e.printStackTrace(); 
       // log.error("Error decoding subjectAltName" + e.getLocalizedMessage(),e); 
      } 
      catch (Exception e) { 
       // log.error("Error decoding subjectAltName" + e.getLocalizedMessage(),e); 
       e.printStackTrace(); 
      } 
      // Other types are not good for XMPP so ignore them 
      //log.warn("SubjectAltName of invalid type found: " + certificate); 
     } 
    } 
    catch (CertificateParsingException e) { 
     e.printStackTrace(); 
     // log.error("Error parsing SubjectAltName in certificate: " + certificate + "\r\nerror:" + e.getLocalizedMessage(),e); 
    } 
    return identities; 
} 

難道我沒有使用正確的.jar文件嗎?的.jar我已經使用

是 - > bcprov-jdk16-1.45.jar

推薦我哪裏出了問題。

回答

2

我試着用你的代碼對我來說這是工作,我從Internet Explorer

Internet Explorer -> Tools -> Internet Options -> Content -> Certificates -> Untrusted Publishers -> www.google.com 

我出口這是「.CER」導出證書測試,我做了一些改變你的代碼

public static List<String> getSubjectAlternativeNames(X509Certificate certificate) { 
     List<String> identities = new ArrayList<String>(); 
     try { 
      Collection<List<?>> altNames = certificate.getSubjectAlternativeNames(); 
      if (altNames == null) 
       return Collections.emptyList(); 
      for (List item : altNames) { 
       Integer type = (Integer) item.get(0); 
       if (type == 0 || type == 2){ 
        try { 
         ASN1InputStream decoder=null; 
         if(item.toArray()[1] instanceof byte[]) 
          decoder = new ASN1InputStream((byte[]) item.toArray()[1]); 
         else if(item.toArray()[1] instanceof String) 
          identities.add((String) item.toArray()[1]); 
         if(decoder==null) continue; 
         DEREncodable encoded = decoder.readObject(); 
         encoded = ((DERSequence) encoded).getObjectAt(1); 
         encoded = ((DERTaggedObject) encoded).getObject(); 
         encoded = ((DERTaggedObject) encoded).getObject(); 
         String identity = ((DERUTF8String) encoded).getString(); 
         identities.add(identity); 
        } 
        catch (UnsupportedEncodingException e) { 
         log.error("Error decoding subjectAltName" + e.getLocalizedMessage(),e); 
        } 
        catch (Exception e) { 
         log.error("Error decoding subjectAltName" + e.getLocalizedMessage(),e); 
        } 
       }else{ 
        log.warn("SubjectAltName of invalid type found: " + certificate); 
       } 
      } 
     } 
     catch (CertificateParsingException e) { 
      log.error("Error parsing SubjectAltName in certificate: " + certificate + "\r\nerror:" + e.getLocalizedMessage(),e); 
     } 
     return identities; 
    } 

我將文件保存到c:\ aa1.cer

X509Certificate cert=null; 
     FileInputStream fis = new FileInputStream("c:\\aa1.cer"); 
     BufferedInputStream bis = new BufferedInputStream(fis); 

     CertificateFactory cf = CertificateFactory.getInstance("X.509"); 
     if (bis.available() > 0) 
      try{ 
       cert = (X509Certificate)cf.generateCertificate(bis); 
      } 
      catch (CertificateException e) { 
       e.printStackTrace(); 
      } 
     System.out.println(CertificateInfo.getSubjectAlternativeNames(cert)); 

我得到的輸出[www.google.com,google.com]

請檢查您的證書,我認爲這個問題是你的證書

+0

感謝solution.Yes,它正在爲這是我從IE了.CER文件。我也需要它.der文件。 – user2536077

+0

問題僅在於我的證書。 – user2536077