From 70d9a179cdd8d975b44e1815c249e20d9f91097f Mon Sep 17 00:00:00 2001
From: Valery Kharseko <vharseko@3a-systems.ru>
Date: Wed, 16 Sep 2026 08:10:15 +0000
Subject: [PATCH] [#912] Provision the ads-truststore from an existing key store at setup time (#984)
---
opendj-server-legacy/src/main/java/org/opends/server/util/Platform.java | 115 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 115 insertions(+), 0 deletions(-)
diff --git a/opendj-server-legacy/src/main/java/org/opends/server/util/Platform.java b/opendj-server-legacy/src/main/java/org/opends/server/util/Platform.java
index ea304f8..d4267e5 100644
--- a/opendj-server-legacy/src/main/java/org/opends/server/util/Platform.java
+++ b/opendj-server-legacy/src/main/java/org/opends/server/util/Platform.java
@@ -23,6 +23,7 @@
import java.io.FileOutputStream;
import java.io.InputStream;
import java.math.BigInteger;
+import java.security.Key;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.KeyStore;
@@ -56,6 +57,7 @@
import static org.opends.messages.UtilityMessages.ERR_CERTMGR_CERT_REPLIES_INVALID;
import static org.opends.messages.UtilityMessages.ERR_CERTMGR_DELETE_ALIAS;
import static org.opends.messages.UtilityMessages.ERR_CERTMGR_GEN_SELF_SIGNED_CERT;
+import static org.opends.messages.UtilityMessages.ERR_CERTMGR_IMPORT_KEY_ENTRY;
import static org.opends.messages.UtilityMessages.ERR_CERTMGR_KEYSTORE_NONEXISTANT;
import static org.opends.messages.UtilityMessages.ERR_CERTMGR_TRUSTED_CERT;
@@ -190,6 +192,62 @@
}
}
+ private final void importKeyEntry(KeyStore ks, String ksType, String ksPath, String alias, char[] pwd,
+ Key privateKey, Certificate[] chain) throws KeyStoreException
+ {
+ try
+ {
+ if (ks == null)
+ {
+ ks = KeyStore.getInstance(ksType);
+ ks.load(null, pwd);
+ }
+ else if (ks.containsAlias(alias))
+ {
+ // setKeyEntry would silently replace whatever the alias holds.
+ LocalizableMessage msg = ERR_CERTMGR_ALIAS_ALREADY_EXISTS.get(alias);
+ throw new KeyStoreException(msg.toString());
+ }
+ // The key is re-encrypted with the password of this key store: the key managers of
+ // the server are initialised with the store password only, so a key which kept the
+ // password of the key store it comes from could not be read back.
+ ks.setKeyEntry(alias, privateKey, pwd, chain);
+ try (FileOutputStream fileOutStream = new FileOutputStream(ksPath)) {
+ ks.store(fileOutStream, pwd);
+ }
+ }
+ catch (Exception e)
+ {
+ throw new KeyStoreException(ERR_CERTMGR_IMPORT_KEY_ENTRY.get(alias, e.getMessage()).toString(), e);
+ }
+ }
+
+ private final void addTrustedCertificate(KeyStore ks, String ksType, String ksPath, String alias, char[] pwd,
+ Certificate certificate) throws KeyStoreException
+ {
+ try
+ {
+ if (ks == null)
+ {
+ ks = KeyStore.getInstance(ksType);
+ ks.load(null, pwd);
+ }
+ else if (ks.containsAlias(alias))
+ {
+ LocalizableMessage msg = ERR_CERTMGR_ALIAS_ALREADY_EXISTS.get(alias);
+ throw new KeyStoreException(msg.toString());
+ }
+ ks.setCertificateEntry(alias, certificate);
+ try (FileOutputStream fileOutStream = new FileOutputStream(ksPath)) {
+ ks.store(fileOutStream, pwd);
+ }
+ }
+ catch (Exception e)
+ {
+ throw new KeyStoreException(ERR_CERTMGR_TRUSTED_CERT.get(alias, e.getMessage()).toString(), e);
+ }
+ }
+
private static final KeyStore generateSelfSignedCertificate(KeyStore ks,
String ksType, String ksPath, KeyType keyType, String alias, char[] pwd, String dn,
int validity) throws KeyStoreException
@@ -333,6 +391,63 @@
}
/**
+ * Copy a key entry, that is a private key and its certificate chain, into the provided
+ * keystore; creating the keystore with the provided type and path if it doesn't exist.
+ * The private key is re-encrypted with the password of the destination keystore.
+ *
+ * @param ks
+ * The keystore to add the key entry to, may be null if it doesn't exist.
+ * @param ksType
+ * The type to use if the keystore is created.
+ * @param ksPath
+ * The path to the keystore.
+ * @param alias
+ * The alias to store the key entry under.
+ * @param pwd
+ * The keystore password, used for the private key as well.
+ * @param privateKey
+ * The private key to store.
+ * @param chain
+ * The certificate chain of the private key, the certificate it belongs to first.
+ * @throws KeyStoreException
+ * If the alias is already in use, or an error occurred adding the key entry to
+ * the keystore.
+ */
+ public static void importKeyEntry(KeyStore ks, String ksType, String ksPath, String alias, char[] pwd,
+ Key privateKey, Certificate[] chain) throws KeyStoreException
+ {
+ IMPL.importKeyEntry(ks, ksType, ksPath, alias, pwd, privateKey, chain);
+ }
+
+ /**
+ * Add the provided certificate to the provided keystore as a trusted certificate entry;
+ * creating the keystore with the provided type and path if it doesn't exist. Only such
+ * an entry is a trust anchor: the certificate chain of a key entry is not, the trust
+ * managers take the certificate the key belongs to and none of its issuers.
+ *
+ * @param ks
+ * The keystore to add the certificate to, may be null if it doesn't exist.
+ * @param ksType
+ * The type to use if the keystore is created.
+ * @param ksPath
+ * The path to the keystore.
+ * @param alias
+ * The alias to store the certificate under.
+ * @param pwd
+ * The keystore password.
+ * @param certificate
+ * The certificate to trust.
+ * @throws KeyStoreException
+ * If the alias is already in use, or an error occurred adding the certificate
+ * to the keystore.
+ */
+ public static void addTrustedCertificate(KeyStore ks, String ksType, String ksPath, String alias, char[] pwd,
+ Certificate certificate) throws KeyStoreException
+ {
+ IMPL.addTrustedCertificate(ks, ksType, ksPath, alias, pwd, certificate);
+ }
+
+ /**
* Delete the specified alias from the provided keystore.
*
* @param ks
--
Gitblit v1.10.0