Библиотека jose в JavaScript предоставляет полный набор инструментов для работы с криптографией в стандартах JWS, JWE и JWT. Одним из фундаментальных этапов является генерация ключевых пар, используемых для подписи и шифрования.
Ключевая пара состоит из:
В контексте тестирования и разработки генерация ключей выполняется программно, без обращения к внешним системам сертификации.
Библиотека jose поддерживает несколько типов
алгоритмов:
RS256, RS384,
RS512, PS256, PS384,
PS512ES256,
ES384, ES512Ed25519,
Ed448RSA-OAEP, RSA-OAEP-256ECDH-ESВыбор алгоритма напрямую влияет на параметры генерируемой ключевой пары.
Для создания ключей используется функция
generateKeyPair:
import { generateKeyPair } from 'jose';
const { publicKey, privateKey } = await generateKeyPair('RS256');
CryptoKey)Пример генерации RSA-ключей с длиной 2048 бит:
const { publicKey, privateKey } = await generateKeyPair('RS256', {
modulusLength: 2048,
});
modulusLength — длина ключа (2048, 3072, 4096)publicExponent — обычно 0x10001const { publicKey, privateKey } = await generateKeyPair('ES256');
ES256 → P-256ES384 → P-384ES512 → P-521Параметры задаются автоматически на основе алгоритма.
const { publicKey, privateKey } = await generateKeyPair('EdDSA');
По умолчанию используется:
Особенности:
Сгенерированные ключи можно экспортировать в различные форматы.
import { exportJWK } from 'jose';
const publicJwk = await exportJWK(publicKey);
const privateJwk = await exportJWK(privateKey);
{
"kty": "RSA",
"n": "...",
"e": "AQAB"
}
publicJwk.kid = 'test-key-id';
Для интеграции с другими системами может понадобиться формат PEM:
import { exportSPKI, exportPKCS8 } from 'jose';
const publicPem = await exportSPKI(publicKey);
const privatePem = await exportPKCS8(privateKey);
Для тестов важно уметь восстанавливать ключи:
import { importJWK } from 'jose';
const publicKey = await importJWK(publicJwk, 'RS256');
Для JWE используется тот же механизм:
const { publicKey, privateKey } = await generateKeyPair('RSA-OAEP-256');
или:
const { publicKey, privateKey } = await generateKeyPair('ECDH-ES');
kid для идентификацииХотя ключевые пары — асимметричная криптография, библиотека поддерживает и симметричные ключи:
import { generateSecret } from 'jose';
const secret = await generateSecret('HS256');
Используется для:
HS256)A256GCM)import {
generateKeyPair,
exportJWK,
exportPKCS8,
exportSPKI
} from 'jose';
const { publicKey, privateKey } = await generateKeyPair('RS256', {
modulusLength: 2048,
});
const publicJwk = await exportJWK(publicKey);
const privateJwk = await exportJWK(privateKey);
const publicPem = await exportSPKI(publicKey);
const privatePem = await exportPKCS8(privateKey);
publicJwk.kid = 'demo-key';
Даже тестовые ключи требуют аккуратного обращения:
Внутри jose используется WebCrypto API, поэтому:
awaitБиблиотека работает:
crypto)SubtleCrypto)Код генерации ключей одинаков в обеих средах.
Для unit-тестирования иногда требуется детерминированность:
jose не поддерживает seed для генерацииawait generateKeyPair('HS256'); // ошибка
HS256 — симметричный алгоритм
await generateKeyPair('RS256'); // иногда требует modulusLength
import { generateKeyPair } from 'jose'; // корректно
Структура для тестов:
/keys
public.jwk.json
private.jwk.json
/tests
auth.test.js
Или динамическая генерация:
beforeAll(async () => {
keys = await generateKeyPair('ES256');
});
После генерации ключей:
import { SignJWT } from 'jose';
const jwt = await new SignJWT({ sub: '123' })
.setProtectedHeader({ alg: 'RS256' })
.sign(privateKey);
jose обеспечивает конвертацию между:
Это позволяет:
Некоторые алгоритмы поддерживают дополнительные настройки:
await generateKeyPair('PS256', {
modulusLength: 3072,
});
import { generateKeyPair, exportJWK } from 'jose';
(async () => {
const { publicKey, privateKey } = await generateKeyPair('ES256');
console.log(await exportJWK(publicKey));
})();
Генерация тестовых ключевых пар: