Spec-Zone .ru
спецификации, руководства, описания, API
Содержание документации

XML API Цифровой подписи

Краткий обзор и Учебное руководство

Оглавление

XML Java API Цифровой подписи

Иерархия пакета

Поставщики услуг

Введение в XML-подписи

Пример XML-подписи

XML Примеры API Цифровой подписи

проверьте Примера

Проверка допустимости XML-подписи

Инстанцирование Документа, который Содержит Подпись

Определение Элемента Подписи, который будет Проверен

Создание Контекста Проверки допустимости

Немаршалинг XML-подписи

Проверка допустимости XML-подписи

Что, Если XML-подпись Не в состоянии Проверить?

Используя KeySelectors

Пример genenveloped

Генерирование XML-подписи

Инстанцирование Документа, который будет Подписан

Создание Пары С открытым ключом

Создание Контекста Подписания

Сборка XML-подписи

Генерирование XML-подписи

Печать или Отображение Получающегося Документа


XML Java API Цифровой подписи

XML Java API Цифровой подписи является стандартным API Java для генерирования и проверки допустимости XML-подписей. Этот API был определен при Процессе Сообщества Java как JSR 105 (см. http://jcp.org/en/jsr/detail?id=105). Этот JSR является заключительным и этот выпуск Java, SE содержит реализацию доступа FCS Окончательной версии API.

XML-подписи могут быть применены к данным любого типа, XML или двоичного файла (см. http://www.w3.org/TR/xmldsig-core/). Получающаяся подпись представляется в XML. XML-подпись может использоваться, чтобы защитить Ваши данные и обеспечить целостность данных, аутентификацию сообщений, и аутентификацию подписывающего лица.

После обеспечения краткого обзора XML-подписей и XML API Цифровой подписи, этот документ представляет два примера, которые демонстрируют, как использовать API, чтобы проверить и генерировать XML-подпись. Этот документ предполагает, что у Вас есть элементарные знания криптографии и цифровых подписей.

API разрабатывается, чтобы поддерживать все необходимые или рекомендуемые функции Рекомендации W3C для Синтаксиса XML-подписи и Обработки. API является расширяемым и сменным и является основанным на Архитектуре Поставщика услуг Криптографии Java. API разрабатывается для двух типов разработчиков:

  • Разработчики, которые хотят использовать XML API Цифровой подписи, чтобы генерировать и проверить XML-подписей
  • Разработчики, которые хотят создать конкретную реализацию XML API Цифровой подписи и зарегистрировать это как криптографическую службу a JCA provider

Before getting into specifics, it is important to see how XWS-Security and XML Digital Signature API are related. In this release of the Java SE, XWS-Security is based on non-standard XML Digital Signature APIs.

Java applications and middleware that need to create or process XML Signatures should use this XML Digital Signature API. It can be used by Web Services Security (the goal for a future release) and by non-Web Services technologies (for example, signing documents stored or transferred in XML). Both JSR 105 and JSR 106 (XML Digital Encryption APIs) are core-XML security components. (See http://www.jcp.org/en/jsr/detail?id=106 for more information about JSR 106.)

XWS-Security does not currently use the XML Digital Signature API or XML Digital Encryption APIs. XWS-Security uses the Apache libraries for XML-DSig and XML-Enc. The goal of XWS-Security is to move toward using these APIs in future releases.

--> -->

Иерархия пакета

Эти шесть упомянутых ниже пакетов включают XML API Цифровой подписи:

  • javax.xml.crypto
  • javax.xml.crypto.dsig
  • javax.xml.crypto.dsig.keyinfo
  • javax.xml.crypto.dsig.spec
  • javax.xml.crypto.dom
  • javax.xml.crypto.dsig.dom

javax.xml.crypto пакет содержит общие классы, которые используются, чтобы выполнить XML криптографические операции, такие как генерирование XML-подписи или шифрование данных XML. Два известных класса в этом пакете KeySelector class, который позволяет разработчикам предоставлять реализации, которые определяют местоположение и дополнительно проверяют ключей, используя информацию, содержавшуюся в a KeyInfo объект, и URIDereferencer class, который позволяет разработчикам создавать и определять свои собственные реализации разыменования URI.

javax.xml.crypto.dsig пакет включает интерфейсы, которые представляют базовые элементы, определенные в спецификации цифровой подписи XML W3C. Из основного значения XMLSignature class, который позволяет Вам подписывать и проверять цифровой подписи XML. Большинство структур XML-подписи или элементов представляются соответствующим интерфейсом (за исключением KeyInfo структуры, которые включаются в их собственный пакет и обсуждаются в следующем абзаце). Эти интерфейсы включают: SignedInfo, CanonicalizationMethod, SignatureMethod, Reference, Transform, DigestMethod, XMLObject, Manifest, SignatureProperty, и SignatureProperties. XMLSignatureFactory class является абстрактной фабрикой, которая используется, чтобы создать объекты, которые реализуют эти интерфейсы.

javax.xml.crypto.dsig.keyinfo пакет содержит интерфейсы, которые представляют большинство KeyInfo структуры, определенные в рекомендации цифровой подписи XML W3C, включая KeyInfo, KeyName, KeyValue, X509Data, X509IssuerSerial, RetrievalMethod, и PGPData. KeyInfoFactory class является абстрактной фабрикой, которая используется, чтобы создать объекты, которые реализуют эти интерфейсы.

javax.xml.crypto.dsig.spec пакет содержит интерфейсы, и классы, представляющие входные параметры для обзора, подписи, преобразовывают, или алгоритмы канонизации, используемые в обработке XML-подписей.

Наконец, javax.xml.crypto.dom и javax.xml.crypto.dsig.dom пакеты содержат DOM-специфичные классы для javax.xml.crypto и javax.xml.crypto.dsig пакеты, соответственно. Только разработчики и пользователи, которые создают или используют DOM-на-основе XMLSignatureFactory или KeyInfoFactory реализация должна будет сделать прямое использование этих пакетов.

Поставщики услуг

JSR 105 криптографических служб является конкретной реализацией краткого обзора XMLSignatureFactory и KeyInfoFactory классы и ответственны за создание объектов и алгоритмов, которые анализируют, генерируют и проверяют XML-подписей и KeyInfo структуры. Конкретная реализация XMLSignatureFactory должен оказать поддержку для каждого из необходимых алгоритмов как определено рекомендацией W3C для XML-подписей. Это может дополнительно поддерживать другие алгоритмы как определено рекомендацией W3C или другие спецификации.

JSR 105 рычагов модель провайдера JCA для регистрации и загрузки XMLSignatureFactory и KeyInfoFactory реализации.

Каждый бетон XMLSignatureFactory или KeyInfoFactory реализация поддерживает определенный тип механизма XML, который идентифицирует XML, обрабатывающий механизм, который реализация использует внутренне, чтобы проанализировать и генерировать XML-подпись и KeyInfo структуры. Этот JSR поддерживает один стандартный тип, ДОМА. XML реализация провайдера Цифровой подписи, которая связывается Java SE, поддерживает механизм ДОМА. Поддержка новых стандартных типов, таких как JDOM, может быть добавлена в будущем.

XML реализация API Цифровой подписи должен использовать базовые классы механизма JCA, такой как java.security.Signature и java.security.MessageDigest, выполнять криптографические операции.

В дополнение к XMLSignatureFactory и KeyInfoFactory классы, JSR 105 поддерживает интерфейс поставщика услуг для алгоритмов канонизации и преобразования. TransformService class позволяет Вам разрабатывать и включать реализацию определенного преобразования или алгоритма канонизации для определенного типа механизма XML. TransformService class использует стандартную модель провайдера JCA для регистрации и загрузки реализаций. Каждый JSR 105 реализаций должен использовать TransformService class, чтобы найти провайдера, который поддерживает, преобразовывает и алгоритмы канонизации в XML-подписи, которые он генерирует или проверяет.

Введение в XML-подписи

Можно использовать XML-подпись, чтобы подписать любые произвольные данные, является ли это XML или двоичным файлом. Данные идентифицируются через URI в одном или более Опорных элементах. XML-подписи описываются в один или больше из трех форм: отсоединенный, окутывание, или окутанный. Отсоединенная подпись по данным, которые являются внешними, или за пределами элемента подписи непосредственно. Окутывающие подписи являются подписями по данным, которые являются в элементе подписи, и окутанная подпись является подписью, которая содержится в данных, которые это подписывает.

Пример XML-подписи

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

<Envelope xmlns="urn:envelope">
</Envelope> 

Получающаяся окутанная XML-подпись, расположенная с отступом и отформатированная для удобочитаемости, следующие:

<?xml version="1.0" encoding="UTF-8"?>
<Envelope xmlns="urn:envelope">
  <Signature xmlns="http://www.w3.org/2000/09/xmldsig#">
    <SignedInfo>
      <CanonicalizationMethod 
        Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315#WithComments"/>
      <SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#dsa-sha1"/>
      <Reference URI="">
        <Transforms>
          <Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
        </Transforms>
        <DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
        <DigestValue>uooqbWYa5VCqcJCbuymBKqm17vY=</DigestValue>
      </Reference>
    </SignedInfo>
    <SignatureValue>
      KedJuTob5gtvYx9qM3k3gm7kbLBwVbEQRl26S2tmXjqNND7MRGtoew==
    </SignatureValue>
    <KeyInfo>
      <KeyValue>
        <DSAKeyValue>
          <P>
            /KaCzo4Syrom78z3EQ5SbbB4sF7ey80etKII864WF64B81uRpH5t9jQTxe
            Eu0ImbzRMqzVDZkVG9xD7nN1kuFw==
          </P>
          <Q>li7dzDacuo67Jg7mtqEm2TRuOMU=</Q>
          <G>
            Z4Rxsnqc9E7pGknFFH2xqaryRPBaQ01khpMdLRQnG541Awtx/
            XPaF5Bpsy4pNWMOHCBiNU0NogpsQW5QvnlMpA==
          </G>
          <Y>
            qV38IqrWJG0V/mZQvRVi1OHw9Zj84nDC4jO8P0axi1gb6d+475yhMjSc/
            BrIVC58W3ydbkK+Ri4OKbaRZlYeRA==
          </Y>
        </DSAKeyValue>
      </KeyValue>
    </KeyInfo>
  </Signature>
</Envelope> 

Signature элемент был вставлен в контенте, который он подписывает, таким образом делая это окутанная подпись. Необходимое SignedInfo элемент содержит информацию, которая фактически подписывается:

<SignedInfo>
  <CanonicalizationMethod 
    Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315#WithComments"/>
  <SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#dsa-sha1"/>
  <Reference URI="">
    <Transforms>
      <Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
    </Transforms>
    <DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
    <DigestValue>uooqbWYa5VCqcJCbuymBKqm17vY=</DigestValue>
  </Reference>
</SignedInfo> 

Необходимое CanonicalizationMethod элемент определяет алгоритм, используемый, чтобы канонизировать SignedInfo элемент прежде, чем это будет подписано или проверено. Канонизация является процессом преобразования контента XML к канонической форме, чтобы принять во внимание изменения, которые могут лишить законной силы подпись по тем данным. Канонизация необходима из-за природы XML и способа, которым это анализируется различными процессорами и посредниками, которые могут изменить данные так, что, подпись больше не действительна, но подписанные данные все еще логически эквивалентны.

Необходимое SignatureMethod элемент определяет алгоритм цифровой подписи, используемый, чтобы генерировать подпись, в этом случае DSA с SHA 1.

Один или больше Reference элементы идентифицируют данные, которые перевариваются. Каждый Reference элемент идентифицирует данные через URI. В этом примере значение URI является пустой Строкой (""), который указывает на корень документа. Дополнительное Transforms элемент содержит список один или больше Transform элементы, каждый из которых описывает алгоритм преобразования, используемый, чтобы преобразовать данные прежде, чем это будет переварено. В этом примере есть тот Transform элемент для окутанного алгоритма преобразования. Окутанное преобразование требуется для окутанных подписей так, чтобы элемент самой подписи был удален прежде, чем вычислить значение подписи. Необходимое DigestMethod элемент определяет алгоритм, используемый, чтобы переварить данные, в этом случае SHA1. Наконец необходимое DigestValue элемент содержит фактическое base64-закодированное переваренное значение.

Необходимое SignatureValue элемент содержит base64-закодированное значение подписи подписи по SignedInfo элемент.

Дополнительное KeyInfo элемент содержит информацию о ключе, который необходим, чтобы проверить подписи:

<KeyInfo>
  <KeyValue>
    <DSAKeyValue>
      <P>
        /KaCzo4Syrom78z3EQ5SbbB4sF7ey80etKII864WF64B81uRpH5t9jQTxe
        Eu0ImbzRMqzVDZkVG9xD7nN1kuFw==
      </P>
      <Q>li7dzDacuo67Jg7mtqEm2TRuOMU=</Q>
      <G>
        Z4Rxsnqc9E7pGknFFH2xqaryRPBaQ01khpMdLRQnG541Awtx/
        XPaF5Bpsy4pNWMOHCBiNU0NogpsQW5QvnlMpA==
      </G>
      <Y>
        qV38IqrWJG0V/mZQvRVi1OHw9Zj84nDC4jO8P0axi1gb6d+475yhMjSc/
        BrIVC58W3ydbkK+Ri4OKbaRZlYeRA==
      </Y>
    </DSAKeyValue>
  </KeyValue>
</KeyInfo> 

Это KeyInfo элемент содержит a KeyValue элемент, который поочередно содержит a DSAKeyValue элемент, состоящий из открытого ключа, должен был проверить подписи. KeyInfo может содержать различный контент, такой как сертификаты X.509 и идентификаторы ключа PGP. См. KeyInfo section из Рекомендации XML-подписи для получения дополнительной информации о различном KeyInfo типы.

XML Примеры API Цифровой подписи

Следующие разделы описывают два примера, которые показывают, как использовать XML API Цифровой подписи:

  • Проверьте примера
  • Подписание примера

проверьте Примера

Можно счесть код показанным в этом разделе в Validate.java файл в docs/technotes/guides/security/xmldsig каталог. Файл, на котором это работает, envelopedSignature.xml, находится в том же самом каталоге.

Чтобы скомпилировать и выполнить пример, выполните следующие команды от docs/technotes/guides/security/xmldsig каталог:

$ javac Validate.java
$ java Validate signature.xml

Пример программы проверит подписи в файле signature.xml в текущем рабочем каталоге.

Проверка допустимости XML-подписи

Этот пример показывает Вам, как проверить XML-подписи, используя JSR 105 API. Пример использует ДОМА (Объектная модель документа), чтобы проанализировать XML-документ, содержащий элемент Подписи и JSR 105 реализаций ДОМА, чтобы проверить подписи.

Инстанцирование Документа, который Содержит Подпись

Сначала мы используем JAXP DocumentBuilderFactory проанализировать XML-документ, содержащий Подпись. Приложение получает реализацию по умолчанию для DocumentBuilderFactory вызывая следующую строку кода:

DocumentBuilderFactory dbf = 
  DocumentBuilderFactory.newInstance(); 

Мы должны также сделать фабрику осведомленной о пространстве имен:

dbf.setNamespaceAware(true); 

Затем, мы используем фабрику, чтобы получить экземпляр a DocumentBuilder, который используется, чтобы проанализировать документ:

DocumentBuilder builder = dbf.newDocumentBuilder();  
Document doc = builder.parse(new FileInputStream(argv[0])); 

Определение Элемента Подписи, который будет Проверен

Мы должны определить Signature элемент, которого мы хотим проверить, с тех пор в документе мог быть больше чем один. Мы используем метод ДОМА Document.getElementsByTagNameNS, передача этого URI пространства имен XML-подписи и имя тега Signature элемент, как показано:

NodeList nl = doc.getElementsByTagNameNS
  (XMLSignature.XMLNS, "Signature");
if (nl.getLength() == 0) {
  throw new Exception("Cannot find Signature element");
} 

Это возвращает список всех Signature элементы в документе. В этом примере есть только один Signature элемент.

Создание Контекста Проверки допустимости

Мы создаем XMLValidateContext экземпляр, содержащий входные параметры для того, чтобы проверить подписи. Так как мы используем ДОМА, мы инстанцируем a DOMValidateContext экземпляр (подкласс XMLValidateContext), и передача это два параметра, a KeyValueKeySelector возразите и ссылка на Signature элемент, который будет проверен (который является первой записью NodeList мы генерировали ранее):

DOMValidateContext valContext = new DOMValidateContext
  (new KeyValueKeySelector(), nl.item(0)); 

KeyValueKeySelector объясняется более подробно в Использовании KeySelectors.

Немаршалинг XML-подписи

Мы извлекаем содержание Signature элемент в XMLSignature объект. Этот процесс вызывают, неупорядочивая. Signature элемент неупорядочивается, используя XMLSignatureFactory объект. Приложение может получить реализацию ДОМА XMLSignatureFactory вызывая следующую строку кода:

XMLSignatureFactory factory = 
  XMLSignatureFactory.getInstance("DOM"); 

Мы тогда вызываем unmarshalXMLSignature метод фабрики, чтобы неупорядочить XMLSignature объект, и передача это контекст проверки допустимости мы создали ранее:


XMLSignature signature = 
  factory.unmarshalXMLSignature(valContext); 

Проверка допустимости XML-подписи

Теперь мы готовы проверить подписи. Мы делаем это, вызывая validate метод на XMLSignature объект, и передача это контекст проверки допустимости следующим образом:

boolean coreValidity = signature.validate(valContext); 

validate метод возвращает "true", если подпись проверяет успешно согласно core validation rules в W3C XML Signature Recommendation, и ложь иначе.

Что, Если XML-подпись Не в состоянии Проверить?

Если XMLSignature.validate метод возвращает false, мы можем попытаться сузить причину отказа. В базовой проверке допустимости XML-подписи есть две фазы:

  • Signature validation (криптографическая проверка подписи)
  • Reference validation (проверка обзора каждой ссылки в подписи)

Каждая фаза должна быть успешной для подписи, чтобы быть допустимой. Проверять, можем ли подпись, отказавшая, чтобы криптографически проверить, мы проверить состояние, следующим образом:

boolean sv = 
  signature.getSignatureValue().validate(valContext);
System.out.println("signature validation status: " + sv); 

Мы можем также выполнить итерации по ссылкам и проверить состояние проверки допустимости каждого, следующим образом:

Iterator i =
  signature.getSignedInfo().getReferences().iterator();
for (int j=0; i.hasNext(); j++) {
  boolean refValid = ((Reference) 
    i.next()).validate(valContext);
  System.out.println("ref["+j+"] validity status: " + 
    refValid);
} 

Используя KeySelectors

KeySelectors используются, чтобы найти и выбрать ключи, которые необходимы, чтобы проверить XMLSignature. Ранее, когда мы создали a DOMValidateContext объект, мы передали a KeySelector возразите как первый параметр:

DOMValidateContext valContext = new DOMValidateContext
  (new KeyValueKeySelector(), nl.item(0)); 

Альтернативно, мы, возможно, передали a PublicKey как первый параметр, если мы уже знали, какой ключ необходим, чтобы проверить подписи. Однако, мы часто не знаем.

KeyValueKeySelector конкретная реализация краткого обзора KeySelector class. KeyValueKeySelector реализация пытается счесть соответствующий ключ проверки допустимости использованием данных содержавшийся в KeyValue элементы KeyInfo элемент XMLSignature. Это не определяет, доверяют ли ключу. Это - очень простое KeySelector реализация, разработанная для иллюстрации, а не реального использования. Более практический пример a KeySelector тот, который ищет a KeyStore для доверяемых ключей то соответствие X509Data информация (например, X509SubjectName, X509IssuerSerial, X509SKI, или X509Certificate элементы) содержавшийся в a KeyInfo.

Реализация KeyValueKeySelector следующие:

private static class KeyValueKeySelector extends KeySelector {

  public KeySelectorResult select(KeyInfo keyInfo,
      KeySelector.Purpose purpose,
      AlgorithmMethod method,
      XMLCryptoContext context)
    throws KeySelectorException {

    if (keyInfo == null) {
      throw new KeySelectorException("Null KeyInfo object!");
    }
    SignatureMethod sm = (SignatureMethod) method;
    List list = keyInfo.getContent();

    for (int i = 0; i < list.size(); i++) {
      XMLStructure xmlStructure = (XMLStructure) list.get(i);
      if (xmlStructure instanceof KeyValue) {
        PublicKey pk = null;
        try {
          pk = ((KeyValue)xmlStructure).getPublicKey();
        } catch (KeyException ke) {
          throw new KeySelectorException(ke);
        }
        // make sure algorithm is compatible with method
        if (algEquals(sm.getAlgorithm(), 
            pk.getAlgorithm())) {
          return new SimpleKeySelectorResult(pk);
        }
      }
    }
    throw new KeySelectorException("No KeyValue element 
found!");
  }

  static boolean algEquals(String algURI, String algName) {
    if (algName.equalsIgnoreCase("DSA") &&
        algURI.equalsIgnoreCase(SignatureMethod.DSA_SHA1)) {
      return true;
    } else if (algName.equalsIgnoreCase("RSA") &&
        algURI.equalsIgnoreCase(SignatureMethod.RSA_SHA1)) {
      return true;
    } else {
      return false;
    }
  }
} 

Пример genenveloped

Код, обсужденный в этом разделе, находится в GenEnveloped.java файл в docs/technotes/guides/security/xmldsig каталог. Файл, на котором это работает, envelope.xml, находится в том же самом каталоге. Это генерирует файл envelopedSignature.xml.

Чтобы скомпилировать и выполнить эту выборку, выполните следующую команду от docs/technotes/guides/security/xmldsig каталог:

$ javac GenEnveloped.java
$ java GenEnveloped envelope.xml envelopedSignature.xml

Пример программы генерирует окутанную подпись документа в файле envelope.xml и сохранит это в файле envelopedSignature.xml в текущем рабочем каталоге.

Генерирование XML-подписи

Этот пример показывает Вам, как генерировать XML-подпись, используя XML API Цифровой подписи. Более определенно пример генерирует окутанную XML-подпись XML-документа. Окутанная подпись является подписью, которая содержится в контенте, который она подписывает. Пример использует ДОМА (Объектная модель документа), чтобы проанализировать XML-документ, который будет подписан и JSR 105 реализаций ДОМА, чтобы генерировать получающуюся подпись.

Элементарные знания XML-подписей и их различных компонентов полезны для того, чтобы понять этот раздел. См. http://www.w3.org/TR/xmldsig-core/ для получения дополнительной информации.

Инстанцирование Документа, который будет Подписан

Во-первых, мы используем JAXP DocumentBuilderFactory проанализировать XML-документ, который мы хотим подписать. Приложение получает реализацию по умолчанию для DocumentBuilderFactory вызывая следующую строку кода:

DocumentBuilderFactory dbf =
  DocumentBuilderFactory.newInstance(); 

Мы должны также сделать фабрику осведомленной о пространстве имен:

dbf.setNamespaceAware(true); 

Затем, мы используем фабрику, чтобы получить экземпляр a DocumentBuilder, который используется, чтобы проанализировать документ:

DocumentBuilder builder = dbf.newDocumentBuilder();  
Document doc = builder.parse(new FileInputStream(argv[0])); 

Создание Пары С открытым ключом

Мы генерируем пару с открытым ключом. Позже в примере, мы будем использовать закрытый ключ, чтобы генерировать подпись. Мы создаем пару ключей с a KeyPairGenerator. В этом примере мы создадим DSA KeyPair с длиной 512 байтов:

KeyPairGenerator kpg = KeyPairGenerator.getInstance("DSA");
kpg.initialize(512);
KeyPair kp = kpg.generateKeyPair(); 

Практически, закрытый ключ обычно ранее сгенерирован и сохранен в a KeyStore файл со связанным сертификатом с открытым ключом.

Создание Контекста Подписания

Мы создаем XML Цифровая подпись XMLSignContext содержа входные параметры для того, чтобы генерировать подпись. Так как мы используем ДОМА, мы инстанцируем a DOMSignContext (подкласс XMLSignContext), и передача это два параметра, закрытый ключ, который будет использоваться, чтобы подписать документ и корень документа, который будет подписан:

DOMSignContext dsc = new DOMSignContext
  (kp.getPrivate(), doc.getDocumentElement()); 

Сборка XML-подписи

Мы собираем различные части Signature элемент в XMLSignature объект. Эти объекты все создаются и собрали использование XMLSignatureFactory объект. Приложение получает реализацию ДОМА XMLSignatureFactory вызывая следующую строку кода:

XMLSignatureFactory fac = 
  XMLSignatureFactory.getInstance("DOM"); 

Мы тогда вызываем различные методы фабрики, чтобы создать различные части XMLSignature возразите как показано ниже. Мы создаем a Reference объект, передавая к этому следующее:

  • URI объекта, который будет подписан (Мы определяем URI"", который подразумевает корень документа.)
  • DigestMethod (мы используем SHA1),
  • Сингл Transform, окутанный Transform, который требуется для окутанных подписей так, чтобы сама подпись была удалена прежде, чем вычислить значение подписи
Reference ref = fac.newReference
  ("", fac.newDigestMethod(DigestMethod.SHA1, null),
    Collections.singletonList
      (fac.newTransform(Transform.ENVELOPED,
        (TransformParameterSpec) null)), null, null); 

Затем, мы создаем SignedInfo объект, который является объектом, который фактически подписывается, как показано ниже. Создавая SignedInfo, мы передаем как параметры:

  • CanonicalizationMethod (мы используем включительно и сохраняем комментарии),
  • SignatureMethod (мы используем DSA),
  • Список References (в этом случае, только один)
SignedInfo si = fac.newSignedInfo
  (fac.newCanonicalizationMethod
    (CanonicalizationMethod.INCLUSIVE_WITH_COMMENTS,
      (C14NMethodParameterSpec) null),
    fac.newSignatureMethod(SignatureMethod.DSA_SHA1, null),
    Collections.singletonList(ref)); 

Затем, мы создаем дополнительное KeyInfo объект, который содержит информацию, которая позволяет получателю найти ключ, должен был проверить подписи. В этом примере мы добавляем a KeyValue объект, содержащий открытый ключ. Создать KeyInfo и его различные подтипы, мы используем a KeyInfoFactory объект, который может быть получен, вызывая getKeyInfoFactory метод XMLSignatureFactory, следующим образом:

KeyInfoFactory kif = fac.getKeyInfoFactory(); 

Мы тогда используем KeyInfoFactory создать KeyValue возразите и добавьте это к a KeyInfo объект:

KeyValue kv = kif.newKeyValue(kp.getPublic());
KeyInfo ki = kif.newKeyInfo(Collections.singletonList(kv)); 

Наконец, мы создаем XMLSignature объект, передавая как параметры SignedInfo и KeyInfo объекты, которые мы создали ранее:

XMLSignature signature = fac.newXMLSignature(si, ki); 

Заметьте, что мы еще фактически не генерировали подпись; мы сделаем это в следующем шаге.

Генерирование XML-подписи

Теперь мы готовы генерировать подпись, которую мы делаем, вызывая sign метод на XMLSignature объект, и передача это контекст подписания следующим образом:

signature.sign(dsc); 

Получающийся документ теперь содержит подпись, которая была вставлена как последний дочерний элемент корневого элемента.

Печать или Отображение Получающегося Документа

Можно использовать следующий код, чтобы напечатать получающийся подписанный документ файлу или стандартному выводу:

OutputStream os;
if (args.length > 1) {
  os = new FileOutputStream(args[1]);
} else {
  os = System.out;
} 
TransformerFactory tf = TransformerFactory.newInstance();
Transformer trans = tf.newTransformer();
trans.transform(new DOMSource(doc), new StreamResult(os)); 


Oracle и/или его филиалы Авторское право © 1993, 2012, Oracle и/или его филиалы. Все права защищены.
Свяжитесь с Нами