Контракт поставщика KMS
HsmSignerInterface — это публичный контракт, который реализует сторонний поставщик, предоставляющий NextPDF хранение ключей. Ваш поставщик хранит закрытый ключ. Движок формирует структуру Cryptographic Message Syntax (CMS).
Установка
Заголовок раздела «Установка»composer require nextpdf/core:^3Концептуальный обзор
Заголовок раздела «Концептуальный обзор»NextPDF отделяет сборку подписи от хранения ключей. Движок подготавливает диапазон байтов и собирает структуру CMS SignedData. Закрытый ключ он не хранит. Вместо этого он делегирует хранение ключей серверной части подписания по публичному контракту.
Вы реализуете один из трёх публичных контрактов:
SignerInterface. Базовый контракт. Он возвращаетSignatureResultдля переданных данных, добавляет метку времени и сообщает о поддержке долгосрочной проверки. Используйте этот контракт, когда логика подписания выполняется внутри процесса.HsmSignerInterface. Контракт для хранения ключей. Реализация должна выполнять подписание внутри аппаратной границы. Закрытый ключ не должен покидать эту границу. Этот контракт реализует поставщик системы управления ключами.DeferredSignerInterface. РасширениеSignerInterfaceдля асинхронных серверных частей. Вызывающая сторона передаёт данные, получает идентификатор задания и извлекает результат позже.
Эта страница описывает публичный контракт. Она не описывает конкретную внутреннюю реализацию NextPDF Pro или NextPDF Enterprise. Платная редакция может предоставить поддерживаемую реализацию этого контракта. Ваша интеграция зависит от контракта, а не от реализации.
Требование к хранению ключей
Заголовок раздела «Требование к хранению ключей»Контракт требует, чтобы закрытый ключ никогда не покидал защищённую границу. Устоявшаяся практика управления ключами поддерживает это требование. National Institute of Standards and Technology (NIST) SP 800-57 Part 1 Revision 5 рассматривает управление ключами как работу с ключами на протяжении всего жизненного цикла: безопасную генерацию, хранение, распространение, использование и уничтожение. Public-Key Cryptography Standards #11 (PKCS#11) v3.1 позволяет принудительно обеспечить эту границу. Когда объект закрытого ключа устанавливает CKA_SENSITIVE в true или CKA_EXTRACTABLE в false, токен не должен раскрывать значение ключа в открытом виде за пределами токена.
За соблюдение этого требования отвечает ваша реализация. Движок не может обеспечить его за вас. Если ваш метод sign() способен прочитать необработанные байты ключа в память процесса, контракт теряет своё свойство безопасности.
Поверхность API
Заголовок раздела «Поверхность API»NextPDF\Contracts\HsmSignerInterface (стабильный, начиная с 1.0.0):
| Метод | Возвращает | Назначение |
|---|---|---|
sign(string $data, string $algorithm) | string | Подписывает данные внутри аппаратной границы. Возвращает необработанные байты подписи. При сбое выбрасывает RuntimeException. |
getCertificateDer() | string | Возвращает сертификат подписанта X.509 в формате Distinguished Encoding Rules (DER). |
getCertificateChainDer() | array<string> | Возвращает промежуточные сертификаты, от издателя к корневому, исключая сертификат подписанта. |
getPublicKeyAlgorithm() | string | Возвращает идентификатор алгоритма открытого ключа. |
NextPDF\Contracts\SignerInterface (стабильный, начиная с 1.0.0):
| Метод | Возвращает | Назначение |
|---|---|---|
sign(string $data) | SignatureResult | Возвращает CMS SignedData в DER-кодировке. |
timestamp(string $signatureValue) | string | Возвращает токен метки времени Request for Comments (RFC) 3161 в DER-кодировке. |
supportsLtv() | bool | Сообщает, можно ли встроить данные долгосрочной проверки (LTV). |
NextPDF\Contracts\DeferredSignerInterface (экспериментальный, начиная с 3.0.0) расширяет SignerInterface методами submitForSigning(), retrieveSignature() и isComplete() для асинхронных серверных частей подписания.
Уровни подписи, которые формирует движок, соответствуют профилям PDF Advanced Electronic Signatures (PAdES). European Telecommunications Standards Institute (ETSI) EN 319 142-2 определяет расширенные профили PAdES, построенные на базовых компонентах из EN 319 142-1. Движок сопоставляет уровни B-B, B-T, B-LT и B-LTA с этими компонентами. Ваша реализация подписанта предоставляет криптографическую операцию и материал сертификата, необходимые движку.
Пример кода — быстрый старт
Заголовок раздела «Пример кода — быстрый старт»Этот минимальный поставщик в стиле PKCS#11 делегирует подписание токену. PHP никогда не читает значение ключа.
<?php
declare(strict_types=1);
use NextPDF\Contracts\HsmSignerInterface;
final class TokenSigner implements HsmSignerInterface{ public function __construct(private readonly TokenSession $session) {}
public function sign(string $data, string $algorithm = 'sha256WithRSAEncryption'): string { // The token computes the signature. The key stays inside the token. return $this->session->c_sign($data, $algorithm); }
public function getCertificateDer(): string { return $this->session->readCertificate(); }
/** @return array<string> */ public function getCertificateChainDer(): array { return $this->session->readChain(); }
public function getPublicKeyAlgorithm(): string { return 'rsaEncryption'; }}Пример кода — рабочая среда
Заголовок раздела «Пример кода — рабочая среда»Поставщик для рабочей среды проверяет входные данные, при ошибке токена отказывает в обслуживании и никогда не записывает в журнал материал ключа или подписи.
<?php
declare(strict_types=1);
use NextPDF\Contracts\HsmSignerInterface;use Psr\Log\LoggerInterface;use RuntimeException;
final class KmsSigner implements HsmSignerInterface{ public function __construct( private readonly RemoteKmsClient $kms, private readonly string $keyId, private readonly LoggerInterface $logger, ) {}
public function sign(string $data, string $algorithm = 'sha256WithRSAEncryption'): string { if ($data === '') { throw new RuntimeException('Refusing to sign empty data'); }
try { // The KMS performs the operation. The key never reaches this process. return $this->kms->sign($this->keyId, $data, $algorithm); } catch (\Throwable $error) { // Fail closed. Do not log key material or signature bytes. $this->logger->error('kms.sign.failed', ['key' => $this->keyId]);
throw new RuntimeException('KMS signing failed', previous: $error); } }
public function getCertificateDer(): string { return $this->kms->certificate($this->keyId); }
/** @return array<string> */ public function getCertificateChainDer(): array { return $this->kms->chain($this->keyId); }
public function getPublicKeyAlgorithm(): string { return $this->kms->algorithm($this->keyId); }}Граничные случаи и подводные камни
Заголовок раздела «Граничные случаи и подводные камни»- Формат байтов подписи. Возвращайте необработанные байты подписи. Для Rivest-Shamir-Adleman (RSA) байты представлены в формате DER. Для Elliptic Curve Digital Signature Algorithm (ECDSA) байты состоят из необработанного значения
r, за которым следует значениеs. - Порядок цепочки.
getCertificateChainDer()исключает сертификат подписанта. Упорядочьте промежуточные сертификаты от издателя к корневому. - Идентификаторы алгоритмов.
sign()использует идентификаторы в стиле OpenSSL.getPublicKeyAlgorithm()возвращает имя алгоритма X.509. - Отказ происходит по принципу fail-closed. При любой ошибке токена или KMS выбрасывайте
RuntimeException. Не возвращайте частичную или пустую подпись. - Уничтожение ключа. Когда ключ достигает конца своего криптопериода, уничтожьте его в соответствии с вашей процедурой управления ключами. NIST SP 800-57 Part 1 Revision 5 §8.2.1.2 устанавливает, что ключ следует уничтожить, как только он больше не нужен. Само уничтожение выполняется согласно §8.3.4.
Местонахождение данных и меры защиты персональных данных
Заголовок раздела «Местонахождение данных и меры защиты персональных данных»Контракт передаёт только данные для подписания и материал сертификата. Он не передаёт серверной части подписания содержимое документа или персональные данные. Делайте диапазон байтов минимальным. Не помещайте персональные данные в поля причины или местоположения подписания. Эти поля остаются видимыми в подписанном файле.
Безопасная телеметрия и очистка журналов
Заголовок раздела «Безопасная телеметрия и очистка журналов»Никогда не записывайте в журнал данные, переданные в sign(), возвращённые байты подписи, идентификатор ключа в обратимом виде или любой закрытый компонент сертификата. Записывайте в журнал только результат операции и необратимую ссылку. Хук SignatureAppliedEvent — поддерживаемая точка привязки для аудита. См. Триггеры действий.
Модель угроз
Заголовок раздела «Модель угроз»| Актив | Угроза | Мера защиты |
|---|---|---|
| Закрытый ключ | Утечка в память процесса | Контракт требует подписания внутри границы; PKCS#11 CKA_SENSITIVE / CKA_EXTRACTABLE не позволяют извлечь ключ |
| Оракул подписания | Неограниченные запросы на подписание | Реализация ограничивает частоту запросов и аутентифицирует вызывающие стороны |
| Цепочка сертификатов | Подмена | Реализация возвращает цепочку, ведущую к доверенному корню |
| Байты подписи | Раскрытие через журналы | Путь обработки ошибок по принципу fail-closed; никакого материала подписи в телеметрии |
| Ключ после истечения криптопериода | Продолжение использования | Уничтожение ключа согласно NIST SP 800-57 Part 1 Revision 5 §8.2.1.2 |
Соответствие стандартам
Заголовок раздела «Соответствие стандартам»Уровни подписи соответствуют профилям PAdES. ETSI EN 319 142-2 §5.1 определяет расширенные профили PAdES на базовых компонентах EN 319 142-1. Движок собирает эти компоненты из материала, который предоставляет ваша реализация подписанта. Управление ключами согласовано с жизненным циклом NIST SP 800-57 Part 1 Revision 5, включая требование к уничтожению из §8.2.1.2. Аппаратное хранение ключей согласовано с атрибутами неизвлекаемого ключа PKCS#11 v3.1. Ссылки на источники записаны во вводной части страницы.
Экспортный контроль и управление рецензированием
Заголовок раздела «Экспортный контроль и управление рецензированием»Эта страница охватывает хранение ключей в PKCS#11 и в аппаратном модуле безопасности (HSM), поэтому в её вводной части задано export_control_class: legal-review-required. Согласно политике рецензирования документации (план §17, контроль 6), любая страница, где режим безопасности, путь или содержимое совпадают с PAdES, FIPS, HSM или PKCS#11, требует одобрения от команды GitHub @nextpdf-labs/crypto-reviewers перед публикацией. Это одобрение CODEOWNERS — обязательный контроль слияния: страница остаётся publish: false, пока не завершатся и юридическая проверка экспортного контроля, и рецензирование от @nextpdf-labs/crypto-reviewers.
Коммерческий контекст
Заголовок раздела «Коммерческий контекст»NextPDF Enterprise предоставляет поддерживаемую реализацию этого контракта с хранением ключей в системе управления ключами, сборкой цепочки сертификатов и интеграцией с аудитом. Вы можете самостоятельно реализовать HsmSignerInterface в Core или использовать реализацию Enterprise через тот же публичный контракт без изменений кода.
См. также
Заголовок раздела «См. также»Связанные контракты и модули
Заголовок раздела «Связанные контракты и модули»- Справочник по контрактам подписания —
SignerInterface,HsmSignerInterface,DeferredSignerInterfaceи провайдер метки времени. - Справочник по контракту политики безопасности — родственная критичная для безопасности поверхность Service Provider Interface (SPI).
- Правила стабильности SPI — обещание интерфейса, лежащее в основе
stable-контрактов подписания. - Триггеры действий и слушатели событий —
SignatureAppliedEvent, поддерживаемая точка привязки для аудита. - Обзор разработки расширений — полная публичная поверхность SPI.
В глоссарии определены система управления ключами, криптопериод и HSM; каноническое определение каждого термина см. в опубликованном глоссарии.