Hola Habr! Le presento la traducción del artículo 9 del "Java KeyStore" de Jakob Jenkov de una serie de artículos para principiantes que desean aprender los conceptos básicos de la criptografía en Java.
Tabla de contenido:
- Criptografía Java
- Cifrado de Java
- Messagedigest
- Mac
- Firma
- Par de llaves
- Generador de claves
- KeyPairGenerator
- Keystore
- Keytool
- Certificado
- CertificateFactory
- CertPath
Keystore
Java KeyStore es un almacén de claves de estilo de base de datos proporcionado por la clase KeyStore ( java.security.KeyStore ). El almacenamiento se puede escribir en el disco y leer de nuevo, se puede proteger con contraseña y cada registro de clave en el almacén de claves se puede proteger con su propia contraseña, lo que hace que la clase KeyStore
un mecanismo útil para trabajar con claves de cifrado de forma segura. Un almacén de claves puede contener claves de los siguientes tipos:
- Claves privadas
- Claves públicas y certificados (Claves públicas + certificados)
- Llaves secretas
Las claves privadas y públicas se utilizan en cifrado asimétrico. La clave pública puede tener un certificado asociado. Un certificado es un documento que prueba la identidad de una persona, organización o dispositivo que afirma poseer una clave pública. El certificado suele estar firmado digitalmente por la parte que confía como prueba. Las claves privadas se utilizan en cifrado simétrico. En la mayoría de los casos, al configurar una conexión segura, las claves simétricas son inferiores a las asimétricas, por lo que la mayoría de las veces almacenará claves públicas y privadas en el almacén de claves.
Crear un almacén de claves
Puede crear una instancia de KeyStore
llamando a su método getInstance()
. Aquí hay un ejemplo de cómo crear una instancia de una clase:
KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
Este ejemplo crea una instancia predeterminada de KeyStore
. También puede crear instancias de KeyStore con un formato de almacenamiento de clave diferente pasando un parámetro al método getInstance()
. Por ejemplo, crear una instancia del almacén de claves PKCS12
:
KeyStore keyStore = KeyStore.getInstance("PKCS12");
Descargar el almacén de claves
Antes de poder usar una instancia de un almacén de claves, debe descargarla. Las instancias de la clase KeyStore
menudo se escriben en el disco u otro almacenamiento para su uso posterior, porque la clase KeyStore
supone que debe leer sus datos antes de poder usarlos. Sin embargo, puede inicializar una instancia de KeyStore
vacía sin datos, como verá más adelante.
Los datos se cargan desde un archivo u otro almacenamiento llamando al método load()
, que toma dos parámetros:
InputStream
desde el cual se cargarán los datos.char[]
Una matriz de caracteres que contiene la contraseña del almacén de claves.
Aquí hay un ejemplo de cómo cargar un almacén de claves:
char[] keyStorePassword = "123abc".toCharArray(); try(InputStream keyStoreData = new FileInputStream("keystore.ks")){ keyStore.load(keyStoreData, keyStorePassword); }
Este ejemplo carga el archivo de almacén de claves keystore.ks. Si no desea cargar ningún dato en el almacén de claves, simplemente pase null
para el parámetro InputStream
. Así es como se carga un almacén de claves vacío:
keyStore3.load(null, keyStorePassword);
Una instancia de la clase KeyStore
siempre debe cargarse con datos o null
. De lo contrario, el almacén de claves no se inicializa y todas las llamadas a sus métodos arrojarán excepciones.
Recibiendo llaves
Puede obtener las claves de una instancia de la clase KeyStore
través de su método getEntry()
. El registro del almacén de claves se asigna a un alias que identifica la clave y está protegido con contraseña. Por lo tanto, para acceder a la clave, debe pasar el alias de la clave y la contraseña al método getEntry()
. Aquí hay un ejemplo de acceso de escritura a una instancia de KeyStore
:
char[] keyPassword = "789xyz".toCharArray(); KeyStore.ProtectionParameter entryPassword = new KeyStore.PasswordProtection(keyPassword); KeyStore.Entry keyEntry = keyStore3.getEntry("keyAlias", entryPassword);
Si sabe que el registro al que desea acceder es la clave privada, puede convertir la instancia de KeyStore.Entry
a KeyStore.PrivateKeyEntry
. Así es como se ve:
KeyStore.PrivateKeyEntry privateKeyEntry = (KeyStore.PrivateKeyEntry) keyStore3.getEntry("keyAlias", entryPassword);
Después de KeyStore.PrivateKeyEntry
a KeyStore.PrivateKeyEntry
puede acceder a la clave privada, el certificado y la cadena de certificados utilizando los siguientes métodos:
getPrivateKey()
getCertificate()
getCertificateChain()
Almacenamiento de claves
También puede poner claves en una instancia de la clase KeyStore
. Un ejemplo de colocación de una clave secreta (clave simétrica) en una instancia de KeyStore
:
SecretKey secretKey = getSecretKey(); KeyStore.SecretKeyEntry secretKeyEntry = new KeyStore.SecretKeyEntry(secretKey); keyStore3.setEntry("keyAlias2", secretKeyEntry, entryPassword);
Almacenamiento
A veces es posible que desee guardar el almacén de claves en algún tipo de almacenamiento (disco, base de datos, etc.) para poder cargarlo nuevamente en otro momento. Una instancia de la clase KeyStore
guarda llamando al método store()
. Un ejemplo:
char[] keyStorePassword = "123abc".toCharArray(); try (FileOutputStream keyStoreOutputStream = new FileOutputStream("data/keystore.ks")) { keyStore3.store(keyStoreOutputStream, keyStorePassword); }