SAML 2.0 Decrypting EncryptedAssertion удаляет объявление пространства имен?

Я пишу веб-службу, которая получает зашифрованное утверждение SAML. До того, как утверждение SAML было зашифровано, его можно было проверить.

Когда моя служба расшифровывает EncryptedAssertion, она не может проверить подпись утверждения

Чтобы понять, почему это так, я создал небольшой тест, который:

  1. Создает подписанное утверждение (которое можно проверить) — assertion1
  2. Проверена подпись на assertion1 - этот тест проходит
  3. Шифрует assertion1, чтобы получить EncryptedAssertion
  4. Расшифровывает EncryptedAssertion, чтобы вернуть утверждение - assertion2
  5. Проверяет подпись на assertion2 - этот тест не проходит

Если я сравню узлы assertion1 и assertion2, то разница будет только одна. В Assertion1 пространство имен xmldsig объявлено как в корневом элементе Assertion, так и в элементе ds:Signature, в Assertion2 объявление пространства имен xmldsig в ​​элементе Signature было удалено.

С точки зрения XML это совершенно допустимое преобразование, и XML по-прежнему действителен. Моя проблема заключается в том, что когда это изменение внесено, подпись больше не действительна, поскольку подпись в утверждении приняла во внимание отсутствующее объявление префикса.

Есть ли способ, которым я могу указать OpenSAML Encrypter/Decrypter не «улучшать» полученный XML, а просто вернуть то, что изначально использовалось в качестве входных данных для шифровальщика?

Изменение клиента, который создает XML, содержащий два объявления пространства имен xmldsig, на самом деле не вариант для нас. Так оно и есть, но клиент для этого сервиса разработан другой компанией и, если возможно, мы бы предпочли сделать наш сервис устойчивым к такого рода проблемам с вводом.

Вот мой тестовый код, который шифрует assertion1:

public static EncryptedAssertion encryptAssertion(Assertion assertion, Credential credential) {
    EncryptionParameters encParams = new EncryptionParameters();
    encParams.setAlgorithm(EncryptionConstants.ALGO_ID_BLOCKCIPHER_AES128);

    KeyEncryptionParameters kekParams = new KeyEncryptionParameters();
    kekParams.setEncryptionCredential(credential);
    kekParams.setAlgorithm(EncryptionConstants.ALGO_ID_KEYTRANSPORT_RSAOAEP);
    KeyInfoGeneratorFactory kigf =
            Configuration.getGlobalSecurityConfiguration()
                    .getKeyInfoGeneratorManager().getDefaultManager()
                    .getFactory(credential);
    kekParams.setKeyInfoGenerator(kigf.newInstance());

    Encrypter samlEncrypter = new Encrypter(encParams, kekParams);
    samlEncrypter.setKeyPlacement(Encrypter.KeyPlacement.INLINE);

    try {
        return samlEncrypter.encrypt(assertion);
    } catch (Exception e) {
        throw new RuntimeException(e);
    }
}

Это тестовый код, который расшифровывает EncryptedAssertion:

public static Assertion decryptEncryptedAssertion(EncryptedAssertion encryptedAssertion, Credential credentials) throws DecryptionException {
        StaticKeyInfoCredentialResolver staticKeyResolver = new StaticKeyInfoCredentialResolver(credentials);
        InlineEncryptedKeyResolver inlineEncryptedKeyResolver = new InlineEncryptedKeyResolver();

        Decrypter decrypter = new Decrypter(null, staticKeyResolver, inlineEncryptedKeyResolver);

        return decrypter.decrypt(encryptedAssertion);
}

Это начало утверждения1:

<?xml version="1.0" encoding="UTF-8"?><saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" ID="_ede6280e-d094-4b74-a67a-e70bbec6f3e9" IssueInstant="2014-06-23T09:42:33.970Z" Version="2.0" xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
   <saml2:Issuer Format="urn:oasis:names:tc:SAML:2.0:nameidformat:entity">https://sts.sundhed.dk</saml2:Issuer>
   <ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
      <ds:SignedInfo>

Это начало assertion2 — обратите внимание, что по сравнению с assertion1 объявление xmlns:ds на узле Signature отсутствует:

<?xml version="1.0" encoding="UTF-8"?><saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" ID="_ede6280e-d094-4b74-a67a-e70bbec6f3e9" IssueInstant="2014-06-23T09:42:33.970Z" Version="2.0" xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
   <saml2:Issuer Format="urn:oasis:names:tc:SAML:2.0:nameidformat:entity">https://sts.sundhed.dk</saml2:Issuer>
   <ds:Signature>
      <ds:SignedInfo>

Обновление: это исключение, которое я получаю при попытке проверить подпись на assertion2 (когда xmlns: ds отсутствует после расшифровки). При вызове decrypter.setRootInNewDocument(true), как предложено в ответе, вызов проверки успешно завершается:

org.opensaml.xml.validation.ValidationException: Unable to evaluate key against signature
    at org.opensaml.xml.signature.SignatureValidator.validate(SignatureValidator.java:74)
    at dk.itst.oiosaml.sp.model.OIOSamlObject.verifySignature(OIOSamlObject.java:239)
    at dk.medicinkortet.idws.impl.EncryptedAssertionHandlerImplTest.testDecrypt(EncryptedAssertionHandlerImplTest.java:152)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:45)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:42)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
    at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:74)
    at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:83)
    at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:72)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:231)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:88)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:231)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:60)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:229)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:50)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:222)
    at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
    at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:71)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:300)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:174)
    at org.junit.runner.JUnitCore.run(JUnitCore.java:157)
    at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:74)
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:211)
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:67)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:134)
Caused by: org.apache.xml.security.signature.MissingResourceFailureException: The Reference for URI #_944e39b7-37e2-4cd1-baba-865fb17f645b has no XMLSignatureInput
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.utils.resolver.ResourceResolverException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
    at org.apache.xml.security.signature.Manifest.verifyReferences(Manifest.java:414)
    at org.apache.xml.security.signature.SignedInfo.verify(SignedInfo.java:256)
    at org.apache.xml.security.signature.XMLSignature.checkSignatureValue(XMLSignature.java:728)
    at org.opensaml.xml.signature.SignatureValidator.validate(SignatureValidator.java:69)
    ... 34 more
Caused by: org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.utils.resolver.ResourceResolverException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
    at org.apache.xml.security.signature.Reference.calculateDigest(Reference.java:732)
    at org.apache.xml.security.signature.Reference.verify(Reference.java:775)
    at org.apache.xml.security.signature.Manifest.verifyReferences(Manifest.java:336)
    ... 37 more
Caused by: org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.utils.resolver.ResourceResolverException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
    at org.apache.xml.security.signature.Reference.dereferenceURIandPerformTransforms(Reference.java:604)
    at org.apache.xml.security.signature.Reference.calculateDigest(Reference.java:706)
    ... 39 more
Caused by: org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
Original Exception was org.apache.xml.security.utils.resolver.ResourceResolverException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
    at org.apache.xml.security.signature.Reference.getContentsBeforeTransformation(Reference.java:419)
    at org.apache.xml.security.signature.Reference.dereferenceURIandPerformTransforms(Reference.java:597)
    ... 40 more
Caused by: org.apache.xml.security.utils.resolver.ResourceResolverException: Cannot resolve element with ID _944e39b7-37e2-4cd1-baba-865fb17f645b
    at org.apache.xml.security.utils.resolver.implementations.ResolverFragment.engineResolveURI(ResolverFragment.java:85)
    at org.apache.xml.security.utils.resolver.ResourceResolver.resolve(ResourceResolver.java:298)
    at org.apache.xml.security.signature.Reference.getContentsBeforeTransformation(Reference.java:417)
    ... 41 more

person joensson    schedule 23.06.2014    source источник
comment
Одобрили ли вы библиотеки синтаксического анализа XML, поставляемые с OpenSAML, как описано в wiki.shibboleth.net/ слияние/отображение/OpenSAML/?   -  person Vladimír Schäfer    schedule 23.06.2014
comment
И не могли бы вы опубликовать точное исключение, с которым не проходит проверка вашей подписи? На самом деле проблема может быть связана не с разницей в пространстве имен, а с используемым алгоритмом c14n (w3 .org/TR/xml-exc-c14n) должны сделать оба ваших варианта XML-документа эквивалентными во время проверки подписи.   -  person Vladimír Schäfer    schedule 23.06.2014


Ответы (1)


Следующее может решить вашу проблему:

  • Убедитесь, что вы правильно одобряете библиотеки, поставляемые с OpenSAML.
  • Создайте свой Decrypter со свойством rootInNewDocument, установленным в true:

    decrypter.setRootInNewDocument (истина);

person Vladimír Schäfer    schedule 23.06.2014
comment
Я одобрил библиотеки, с которыми поставляется opensaml, но это не помешало удалить xmlns:ds из assertion2. Но вызов decrypter.setRootInNewDocument(true) сделал это. Большое тебе спасибо :) - person joensson; 25.06.2014