2017-02-25 46 views
1

如何使用Java StAX API验证XML上的数字签名。我已经知道如何使用DOM进行验证。我有一个非常大的XML文件,我需要一种使用StAX验证签名的方法。请帮助...使用StAX验证数字签名

回答

0

我发现这个blog post,其中指出了一些代码演示一个StAX的实现:

要了解如何配置新的入站的基于StAX的XML签名 功能,看看 测试使用的“verifyUsingStAX”方法。与创建签名一样,有必要创建一个XMLSecurityProperties对象,并告诉它要执行什么“操作”。 另外,你必须调用下面的方法,除非完全 签名密钥被包含在签名的密钥信息:

  • properties.setSignatureVerificationKey(密钥) - 要使用的密钥来验证 签名。

https://github.com/coheigea/testcases/blob/master/apache/santuario/santuario-xml-signature/src/test/java/org/apache/coheigea/santuario/xmlsignature/SignatureUtils.java#L201

/** 
    * Verify the document using the StAX API of Apache Santuario - XML Security for Java. 
    */ 
    public static void verifyUsingStAX(
     InputStream inputStream, 
     List<QName> namesToSign, 
     X509Certificate cert 
    ) throws Exception { 
     // Set up the Configuration 
     XMLSecurityProperties properties = new XMLSecurityProperties(); 
     List<XMLSecurityConstants.Action> actions = new ArrayList<XMLSecurityConstants.Action>(); 
     actions.add(XMLSecurityConstants.SIGNATURE); 
     properties.setActions(actions); 

     properties.setSignatureVerificationKey(cert.getPublicKey()); 

     InboundXMLSec inboundXMLSec = XMLSec.getInboundWSSec(properties); 

     XMLInputFactory xmlInputFactory = XMLInputFactory.newInstance(); 
     final XMLStreamReader xmlStreamReader = xmlInputFactory.createXMLStreamReader(inputStream); 

     TestSecurityEventListener eventListener = new TestSecurityEventListener(); 
     XMLStreamReader securityStreamReader = 
      inboundXMLSec.processInMessage(xmlStreamReader, null, eventListener); 

     while (securityStreamReader.hasNext()) { 
      securityStreamReader.next(); 
     } 
     xmlStreamReader.close(); 
     inputStream.close(); 

     // Check that what we were expecting to be signed was actually signed 
     List<SignedElementSecurityEvent> signedElementEvents = 
      eventListener.getSecurityEvents(SecurityEventConstants.SignedElement); 
     Assert.assertNotNull(signedElementEvents); 

     for (QName nameToSign : namesToSign) { 
      boolean found = false; 
      for (SignedElementSecurityEvent signedElement : signedElementEvents) { 
       if (signedElement.isSigned() 
        && nameToSign.equals(getSignedQName(signedElement.getElementPath()))) { 
        found = true; 
        break; 
       } 
      } 
      Assert.assertTrue(found); 
     } 

     // Check Signing cert 
     X509TokenSecurityEvent tokenEvent = 
      (X509TokenSecurityEvent)eventListener.getSecurityEvent(SecurityEventConstants.X509Token); 
     Assert.assertNotNull(tokenEvent); 

     Assert.assertTrue(tokenEvent.getSecurityToken() instanceof X509SecurityToken); 
     X509SecurityToken x509SecurityToken = (X509SecurityToken)tokenEvent.getSecurityToken(); 
     Assert.assertEquals(x509SecurityToken.getX509Certificates()[0], cert); 
    }