PKI Public Key Infrastructure: Зертификаты, CA и TLS/SSL
Это подробный разбор Public Key Infrastructure с фокусом на зертификаты, центры сертификации и реализацию TLS/SSL.
In a Nutshell
PKI представляет собой организационную и техническую инфраструктуру для создания, распространения, проверки и отзыва открытых ключей через зертификаты. Она обеспечивает надежную идентификацию людей, машин и сервисов.
Компактное описание
Public Key Infrastructure (PKI) состоит из Root CA и подчиненных Intermediate CAs, которые выдают, подписывают и отзывают X.509 зертификаты через CRL или OCSP.
Основные компоненты:
- Certificate Authority (CA): выдает зертификаты
- Registration Authority (RA): проверяет идентичность
- Certificate Repository: хранилище зертификатов
- Validation Authority: валидирует зертификаты
Содержимое зертификата:
- Public Key: открытый ключ владельца
- Identity Information: CN, SAN, OU, O, C
- Validity Period: период действия
- Key Usage: назначение ключа
- Digital Signature: подпись выдавшего CA
Модель доверия:
- Chain of Trust: иерархическая структура CA
- Root Certificates: точки доверия в truststores
- Certificate Validation: проверка цепи зертификатов
PKI поддерживает аутентификацию, подписи, шифрование и неотказуемость в TLS, S/MIME, Code Signing и mTLS.
Ключевые моменты
- Root CA и Intermediate CA иерархия
- X.509 формат и содержимое зертификатов
- Chain of Trust и управление Truststore
- CRL (Certificate Revocation List) и OCSP (Online Certificate Status Protocol)
- TLS/SSL handshake с валидацией зертификатов
- CSR (Certificate Signing Request) процесс
- mTLS (Mutual TLS) для аутентификации клиента
- Применимо для IT-безопасности и сетевых технологий
Основные компоненты
- Root Certificate Authority: верхний уровень доверия
- Intermediate Certificate Authority: промежуточные инстанции для делегирования
- End Entity Certificate: зертификат для сервера, клиента или сервиса
- Certificate Signing Request: запрос на выдачу зертификата
- Certificate Revocation List: список отозванных зертификатов
- OCSP Responder: онлайн проверка статуса зертификатов
- Truststore: хранилище доверенных Root-зертификатов
- Keystore: хранилище собственных зертификатов и приватных ключей
Практические примеры
Создание зертификата с OpenSSL
# Генерирование приватного ключа
openssl genrsa -out server.key 2048
# Создание Certificate Signing Request (CSR)
openssl req -new -key server.key -out server.csr \
-subj "/C=DE/ST=Berlin/L=Berlin/O=IRC-Coding/OU=IT/CN=irc-coding.de"
# Self-signed зертификат (для тестирования)
openssl x509 -req -days 365 -in server.csr -signkey server.key -out server.crt
# Просмотр зертификата
openssl x509 -in server.crt -text -noout
# Валидация зертификата
openssl verify -CAfile ca.crt server.crt
Управление Java Keystore
// Создание Keystore с KeyTool
// keytool -genkeypair -alias server -keyalg RSA -keysize 2048 \
// -keystore keystore.jks -validity 365
// Экспорт CSR
// keytool -certreq -alias server -keystore keystore.jks -file server.csr
// Импорт зертификата
// keytool -importcert -alias server -file server.crt \
// -keystore keystore.jks -trustcacerts
// Java код для валидации зертификата
import java.security.cert.*;
import java.io.FileInputStream;
public class CertificateValidator {
public static boolean validateCertificate(String certPath, String caPath) {
try {
// Загрузка зертификата
CertificateFactory cf = CertificateFactory.getInstance("X.509");
X509Certificate cert = (X509Certificate)
cf.generateCertificate(new FileInputStream(certPath));
// Загрузка CA-зертификата
X509Certificate caCert = (X509Certificate)
cf.generateCertificate(new FileInputStream(caPath));
// Валидация цепи зертификатов
cert.checkValidity(); // Проверка периода действия
cert.verify(caCert.getPublicKey()); // Проверка подписи
// Проверка CRL/OCSP (упрощенно)
if (isRevoked(cert)) {
return false;
}
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
private static boolean isRevoked(X509Certificate cert) {
// Реализация проверки CRL или OCSP
return false;
}
}
TLS сервер на Node.js
const https = require('https');
const fs = require('fs');
// Конфигурация TLS сервера
const tlsOptions = {
key: fs.readFileSync('server.key'),
cert: fs.readFileSync('server.crt'),
ca: fs.readFileSync('ca.crt'), // Для аутентификации клиента
requestCert: true, // Требовать mTLS
rejectUnauthorized: true // Отклонять невалидные зертификаты
};
const server = https.createServer(tlsOptions, (req, res) => {
// Информация о зертификате клиента
const clientCert = req.socket.getPeerCertificate();
if (clientCert) {
console.log('Client authenticated:', clientCert.subject.CN);
res.writeHead(200);
res.end('Hello authenticated client!');
} else {
res.writeHead(401);
res.end('Client certificate required');
}
});
server.listen(8443, () => {
console.log('TLS Server listening on port 8443');
});
Python TLS клиент с валидацией зертификата
import ssl
import requests
from requests.adapters import HTTPAdapter
from urllib3.util.ssl_ import create_urllib3_context
class TLSAdapter(HTTPAdapter):
def init_poolmanager(self, *args, **kwargs):
context = create_urllib3_context()
context.check_hostname = True
context.verify_mode = ssl.CERT_REQUIRED
context.load_verify_locations('ca.crt') # Загрузка CA-зертификата
# mTLS с клиентским зертификатом
context.load_cert_chain('client.crt', 'client.key')
kwargs['ssl_context'] = context
return super().init_poolmanager(*args, **kwargs)
# TLS-клиент с валидацией зертификата
session = requests.Session()
session.mount('https://', TLSAdapter())
try:
response = session.get('https://secure-api.example.com/data')
print("Response:", response.json())
except requests.exceptions.SSLError as e:
print("TLS Error:", e)
except Exception as e:
print("General Error:", e)
Отзыв зертификатов (CRL/OCSP)
// Проверка отзыва на основе CRL
import java.security.cert.*;
import java.net.URL;
import java.io.InputStream;
public class CRLValidator {
public static boolean checkRevocation(X509Certificate cert) {
try {
// Извлечение CRL Distribution Points из зертификата
String crlUrl = getCRLDistributionPoint(cert);
if (crlUrl != null) {
// Загрузка CRL
URL url = new URL(crlUrl);
InputStream in = url.openStream();
// Загрузка и валидация CRL
CertificateFactory cf = CertificateFactory.getInstance("X.509");
X509CRL crl = (X509CRL) cf.generateCRL(in);
// Проверка был ли зертификат отозван
return !crl.isRevoked(cert);
}
return true; // CRL недоступна
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
private static String getCRLDistributionPoint(X509Certificate cert) {
// Извлечение CRL Distribution Point из расширений зертификата
// Реализация потребует ASN.1 парсинга
return null;
}
}
PKI иерархия и цепь доверия
Типичная структура PKI
Root CA (самоподписанный)
├── Intermediate CA 1 (для веб-серверов)
│ ├── irc-coding.de
│ └── api.irc-coding.de
├── Intermediate CA 2 (для подписей кода)
│ ├── desktop-app.exe
│ └── mobile-app.apk
└── Intermediate CA 3 (для E-Mail)
├── user1@irc-coding.de
└── user2@irc-coding.de
Цепь валидации зертификатов
public class ChainValidator {
public static boolean validateChain(X509Certificate[] chain,
X509Certificate[] trustedCAs) {
try {
// Инициализация Trust Anchors
Set<TrustAnchor> trustAnchors = new HashSet<>();
for (X509Certificate ca : trustedCAs) {
trustAnchors.add(new TrustAnchor(ca, null));
}
// Конфигурация PKIX-параметров
PKIXParameters params = new PKIXParameters(trustAnchors);
params.setRevocationEnabled(true); // Активировать проверку CRL/OCSP
// Certificate Path Builder
CertPathBuilder builder = CertPathBuilder.getInstance("PKIX");
X509CertSelector selector = new X509CertSelector();
selector.setCertificate(chain[0]);
PKIXBuilderParameters builderParams =
new PKIXBuilderParameters(trustAnchors);
builderParams.setRevocationEnabled(true);
// Валидация цепи зертификатов
CertPathBuilderResult result = builder.build(builderParams);
CertPathValidator validator = CertPathValidator.getInstance("PKIX");
CertPathValidatorResult validatorResult =
validator.validate(result.getCertPath(), params);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
}
Преимущества и недостатки
Преимущества PKI
- Безопасность: мощная криптографическая основа
- Масштабируемость: иерархическая структура для крупных организаций
- Стандартизация: X.509 широко распространен
- Гибкость: применимо к различным сценариям (TLS, Code Signing, и т.д.)
- Неотказуемость: цифровые подписи подтверждают авторство
Недостатки
- Сложность: трудозатратная настройка и обслуживание
- Стоимость: коммерческие CA берут плату
- Операционная нагрузка: ротация ключей, управление зертификатами
- Единая точка отказа: сбой Root CA влияет на всю PKI
Типичные вопросы
-
В чем разница между Root CA и Intermediate CA? Root CA самоподписана и служит точкой доверия, Intermediate CA подписана Root CA и делегирует выдачу зертификатов.
-
Объясните Chain of Trust! Иерархическая валидация от конечного зертификата через Intermediate CAs к Root CA.
-
Какова цель CRL и OCSP? Проверка, был ли зертификат отозван до истечения (компрометация, смена должности, и т.д.).
-
Когда использовать mTLS? Для взаимной аутентификации между сервером и клиентом (APIs, Microservices).
Основные ссылки
- https://de.wikipedia.org/wiki/Public-Key-Infrastruktur
- https://tools.ietf.org/html/rfc5280
- https://www.ietf.org/rfc/rfc5280.txt



