1
    public class CustomTrustManager implements X509TrustManager {

   private X509TrustManager trustManager;
   // If a connection was previously attempted and failed the certificate check, that certificate chain will be saved here.
   private Certificate[] rejectedCertificates = null;
   private Certificate[] encounteredCertificates = null;
   private KeyStore keyStore = null;
   private Logger logger;

   /**
    * Constructor
    *
    * @param loggerFactory
    *           see {@link InstanceLoggerFactory}
    */
   public CustomTrustManager(InstanceLoggerFactory loggerFactory) {
      try {
         this.logger = loggerFactory.getLogger(CustomTrustManager.class);
         keyStore = KeyStore.getInstance("JKS");
         // a keyStore must be initialized with load, even if certificate trust is not file based.
         keyStore.load(null, null);

         System.setProperty("com.sun.net.ssl.checkRevocation", "true");
         Security.setProperty("ocsp.enable", "true");
      } catch (Exception ex) {
         logger.error("Problem initializing keyStore", ex);
      }
   }

   /**
    * Returns the rejected certificate based on the last usage
    */
   public Certificate[] getRejectedCertificateChain() {
      return rejectedCertificates;
   }

   /**
    * Returns the encountered certificates based on the last usage
    */
   public Certificate[] getEncounteredCertificates() {
      return encounteredCertificates;
   }

   @Override
   public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
      if (trustManager != null) {
         trustManager.checkClientTrusted(chain, authType);
      }
   }

   /**
    * Checks if a server is trusted, based on the wrapped keyStore's trust
    * anchors. This will also capture the encountered certificate chain and, if
    * trust fails, the rejected certificate chain.
    */
   @Override
   public void checkServerTrusted(X509Certificate[] chain, String authType) throws CustomCertificateException {
      // Capture the certificate if it fails
      try {
         encounteredCertificates = chain;
         if (trustManager != null) {
            trustManager.checkServerTrusted(chain, authType);
         } else {
            throw new RuntimeException("Trust manager is null");
         }
      } catch (CertificateException ex) {
         rejectedCertificates = chain;
         throw new CustomCertificateException(ex, rejectedCertificates);
      } catch (Exception ex) {
         rejectedCertificates = chain;
         throw new CustomCertificateException(new CertificateException(ex), rejectedCertificates);
      }
   }

   @Override
   public X509Certificate[] getAcceptedIssuers() {
      return trustManager == null ? new X509Certificate[0] : trustManager.getAcceptedIssuers();
   }

   /**
    * initializes the internal trust manager with all known certificates
    * certificates are stored in the keyStore object
    */
   private void initTrustManager() {
      try {
         // initialize a new TMF with our keyStore
         TrustManagerFactory tmf = TrustManagerFactory.getInstance("PKIX", "SunJSSE");

         // keyStore must not be empty
         CertPathParameters pkixParams = new PKIXBuilderParameters(keyStore, new X509CertSelector());
         ((PKIXBuilderParameters) pkixParams).setRevocationEnabled(true);

         tmf.init(new CertPathTrustManagerParameters(pkixParams));

         // acquire X509 trust manager from factory
         TrustManager tms[] = tmf.getTrustManagers();
         for (TrustManager tm : tms) {
            if (tm instanceof X509TrustManager) {
               trustManager = (X509TrustManager) tm;
               break;
            }
         }
      } catch (Exception ex) {
         logger.error("Problem initializing trust manager", ex);
      }
   }

 ...
}

在这里,我实现了 X509TrustManager 信任管理器,并尝试将适当的检查调用委托给在运行时找到的 x509 信任管理器。我的问题是我为OCSP设置的属性是否足以确保 Java 在验证证书链时也会执行 OCSP?换句话说,如果设置了属性,checkServerTrusted()方法会自行处理吗?

4

1 回答 1

1

您似乎没有通过 OCSP 检查撤销。这是一个如何执行此操作的示例。您将需要目标证书和响应者 URL。我从一个工作示例中提取了它,并将其修改为尽可能通用。尚未对其进行测试,但它应该可以工作或非常接近工作。您可能必须根据自己的需要对其进行调整,但幅度不大。

    private void validateCertPath(X509Certificate targetCertificate, X509Certificate issuerCertificate, String responderURL, String trustAnchorDirectory) 
            throws  CertPathValidatorException, 
                            InvalidAlgorithmParameterException, 
                            FileNotFoundException, 
                            CertificateException, 
                            NoSuchAlgorithmException {

    List<X509Certificate> certList = new Vector<X509Certificate>();
    certList.add(targetCertificate);
    certList.add(issuerCertificate);

    CertificateFactory cf = CertificateFactory.getInstance("X.509");

    CertPath cp = cf.generateCertPath(certList);

    CertPathValidator cpv = CertPathValidator.getInstance("PKIX");

    Set<TrustAnchor> trustStore = new HashSet<TrustAnchor>();
    TrustAnchor anchor = null;
    X509Certificate cacert = null;
    File directory = new File(trustAnchorDirectory);
    String certFileNames[] = directory.list();

    for (String certFile : certFileNames) {
        cacert = readCert(trustAnchorDirectory +"/" + certFile);
        anchor = new TrustAnchor(cacert, null);
        trustStore.add(anchor);
    }

    PKIXParameters params = new PKIXParameters(trustStore);
    params.setRevocationEnabled(true);

    Security.setProperty("ocsp.enable", "true");
    Security.setProperty("ocsp.responderURL", responderUrl);

    PKIXCertPathValidatorResult result = (PKIXCertPathValidatorResult) cpv.validate(cp, params);
    System.out.println("Certificate validated");
    System.out.println("Policy Tree:\n" + result.getPolicyTree());

}

于 2017-01-11T21:52:36.697 回答