diff --git a/api/src/main/java/org/apache/cloudstack/api/command/admin/direct/download/UploadTemplateDirectDownloadCertificateCmd.java b/api/src/main/java/org/apache/cloudstack/api/command/admin/direct/download/UploadTemplateDirectDownloadCertificateCmd.java index 416d26452e7..c93fca2d300 100755 --- a/api/src/main/java/org/apache/cloudstack/api/command/admin/direct/download/UploadTemplateDirectDownloadCertificateCmd.java +++ b/api/src/main/java/org/apache/cloudstack/api/command/admin/direct/download/UploadTemplateDirectDownloadCertificateCmd.java @@ -16,11 +16,6 @@ // under the License. package org.apache.cloudstack.api.command.admin.direct.download; -import com.cloud.exception.ConcurrentOperationException; -import com.cloud.exception.InsufficientCapacityException; -import com.cloud.exception.ResourceAllocationException; -import com.cloud.exception.ResourceUnavailableException; -import com.cloud.exception.NetworkRuleConflictException; import org.apache.cloudstack.acl.RoleType; import org.apache.cloudstack.api.APICommand; import org.apache.cloudstack.api.ApiConstants; @@ -62,15 +57,15 @@ public class UploadTemplateDirectDownloadCertificateCmd extends BaseCmd { private String hypervisor; @Override - public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException, ResourceAllocationException, NetworkRuleConflictException { + public void execute() { if (!hypervisor.equalsIgnoreCase("kvm")) { throw new ServerApiException(ApiErrorCode.PARAM_ERROR, "Currently supporting KVM hosts only"); } - SuccessResponse response = new SuccessResponse(getCommandName()); try { LOG.debug("Uploading certificate " + name + " to agents for Direct Download"); boolean result = directDownloadManager.uploadCertificateToHosts(certificate, name, hypervisor); + SuccessResponse response = new SuccessResponse(getCommandName()); response.setSuccess(result); setResponseObject(response); } catch (Exception e) { diff --git a/scripts/util/keystore-cert-import b/scripts/util/keystore-cert-import index 424ab4a718e..459f8366ee4 100755 --- a/scripts/util/keystore-cert-import +++ b/scripts/util/keystore-cert-import @@ -38,9 +38,6 @@ if [ -z "${KS_PASS// }" ]; then exit 1 fi -# Use a new keystore file -NEW_KS_FILE="$KS_FILE.new" - # Import certificate if [ ! -z "${CERT// }" ]; then echo "$CERT" > "$CERT_FILE" @@ -54,8 +51,8 @@ fi # Import cacerts into the keystore awk '/-----BEGIN CERTIFICATE-----?/{n++}{print > "cloudca." n }' "$CACERT_FILE" for caChain in $(ls cloudca.*); do - keytool -delete -noprompt -alias "$caChain" -keystore "$NEW_KS_FILE" -storepass "$KS_PASS" > /dev/null 2>&1 || true - keytool -import -noprompt -storepass "$KS_PASS" -trustcacerts -alias "$caChain" -file "$caChain" -keystore "$NEW_KS_FILE" > /dev/null 2>&1 + keytool -delete -noprompt -alias "$caChain" -keystore "$KS_FILE" -storepass "$KS_PASS" > /dev/null 2>&1 || true + keytool -import -noprompt -storepass "$KS_PASS" -trustcacerts -alias "$caChain" -file "$caChain" -keystore "$KS_FILE" > /dev/null 2>&1 done rm -f cloudca.* @@ -63,21 +60,19 @@ rm -f cloudca.* if [ ! -z "${PRIVKEY// }" ]; then echo "$PRIVKEY" > "$PRIVKEY_FILE" # Re-initialize keystore when private key is provided - keytool -delete -noprompt -alias "$ALIAS" -keystore "$NEW_KS_FILE" -storepass "$KS_PASS" 2>/dev/null || true - openssl pkcs12 -export -name "$ALIAS" -in "$CERT_FILE" -inkey "$PRIVKEY_FILE" -out "$NEW_KS_FILE.p12" -password pass:"$KS_PASS" > /dev/null 2>&1 - keytool -importkeystore -srckeystore "$NEW_KS_FILE.p12" -destkeystore "$NEW_KS_FILE" -srcstoretype PKCS12 -alias "$ALIAS" -deststorepass "$KS_PASS" -destkeypass "$KS_PASS" -srcstorepass "$KS_PASS" -srckeypass "$KS_PASS" > /dev/null 2>&1 + keytool -delete -noprompt -alias "$ALIAS" -keystore "$KS_FILE" -storepass "$KS_PASS" 2>/dev/null || true + openssl pkcs12 -export -name "$ALIAS" -in "$CERT_FILE" -inkey "$PRIVKEY_FILE" -out "$KS_FILE.p12" -password pass:"$KS_PASS" > /dev/null 2>&1 + keytool -importkeystore -srckeystore "$KS_FILE.p12" -destkeystore "$KS_FILE" -srcstoretype PKCS12 -alias "$ALIAS" -deststorepass "$KS_PASS" -destkeypass "$KS_PASS" -srcstorepass "$KS_PASS" -srckeypass "$KS_PASS" > /dev/null 2>&1 else # Import certificate into the keystore - keytool -import -storepass "$KS_PASS" -alias "$ALIAS" -file "$CERT_FILE" -keystore "$NEW_KS_FILE" > /dev/null 2>&1 || true + keytool -import -storepass "$KS_PASS" -alias "$ALIAS" -file "$CERT_FILE" -keystore "$KS_FILE" > /dev/null 2>&1 || true # Export private key from keystore rm -f "$PRIVKEY_FILE" - keytool -importkeystore -srckeystore "$NEW_KS_FILE" -destkeystore "$NEW_KS_FILE.p12" -deststoretype PKCS12 -srcalias "$ALIAS" -deststorepass "$KS_PASS" -destkeypass "$KS_PASS" -srcstorepass "$KS_PASS" -srckeypass "$KS_PASS" > /dev/null 2>&1 - openssl pkcs12 -in "$NEW_KS_FILE.p12" -nodes -nocerts -nomac -password pass:"$KS_PASS" 2>/dev/null | openssl rsa -out "$PRIVKEY_FILE" > /dev/null 2>&1 + keytool -importkeystore -srckeystore "$KS_FILE" -destkeystore "$KS_FILE.p12" -deststoretype PKCS12 -srcalias "$ALIAS" -deststorepass "$KS_PASS" -destkeypass "$KS_PASS" -srcstorepass "$KS_PASS" -srckeypass "$KS_PASS" > /dev/null 2>&1 + openssl pkcs12 -in "$KS_FILE.p12" -nodes -nocerts -nomac -password pass:"$KS_PASS" 2>/dev/null | openssl rsa -out "$PRIVKEY_FILE" > /dev/null 2>&1 fi -# Commit the new keystore -rm -f "$NEW_KS_FILE.p12" -mv -f "$NEW_KS_FILE" "$KS_FILE" +rm -f "$KS_FILE.p12" # Secure libvirtd on cert import if [ -f "$LIBVIRTD_FILE" ]; then diff --git a/scripts/util/keystore-setup b/scripts/util/keystore-setup index ce963363c1d..65f04c48d57 100755 --- a/scripts/util/keystore-setup +++ b/scripts/util/keystore-setup @@ -17,7 +17,7 @@ # under the License. PROPS_FILE="$1" -KS_FILE="$2.new" +KS_FILE="$2" KS_PASS="$3" KS_VALIDITY="$4" CSR_FILE="$5" @@ -35,8 +35,10 @@ if [ -f "$PROPS_FILE" ]; then fi fi -# Generate keystore -rm -f "$KS_FILE" +if [ -f "$KS_FILE" ]; then + keytool -delete -noprompt -alias "$ALIAS" -keystore "$KS_FILE" -storepass "$KS_PASS" > /dev/null 2>&1 || true +fi + CN=$(hostname --fqdn) keytool -genkey -storepass "$KS_PASS" -keypass "$KS_PASS" -alias "$ALIAS" -keyalg RSA -validity "$KS_VALIDITY" -dname cn="$CN",ou="cloudstack",o="cloudstack",c="cloudstack" -keystore "$KS_FILE" > /dev/null 2>&1 diff --git a/server/src/main/java/org/apache/cloudstack/direct/download/DirectDownloadManagerImpl.java b/server/src/main/java/org/apache/cloudstack/direct/download/DirectDownloadManagerImpl.java index d2aa67540f3..99860934cd5 100644 --- a/server/src/main/java/org/apache/cloudstack/direct/download/DirectDownloadManagerImpl.java +++ b/server/src/main/java/org/apache/cloudstack/direct/download/DirectDownloadManagerImpl.java @@ -85,17 +85,17 @@ public class DirectDownloadManagerImpl extends ManagerBase implements DirectDown protected final static String LINE_SEPARATOR = "\n"; @Inject - VMTemplateDao vmTemplateDao; + private VMTemplateDao vmTemplateDao; @Inject - PrimaryDataStoreDao primaryDataStoreDao; + private PrimaryDataStoreDao primaryDataStoreDao; @Inject - HostDao hostDao; + private HostDao hostDao; @Inject - AgentManager agentManager; + private AgentManager agentManager; @Inject - VMTemplatePoolDao vmTemplatePoolDao; + private VMTemplatePoolDao vmTemplatePoolDao; @Inject - DataStoreManager dataStoreManager; + private DataStoreManager dataStoreManager; @Override public List> getCommands() { @@ -366,6 +366,10 @@ public class DirectDownloadManagerImpl extends ManagerBase implements DirectDown @Override public boolean uploadCertificateToHosts(String certificateCer, String alias, String hypervisor) { + if (alias != null && (alias.equalsIgnoreCase("cloud") || alias.startsWith("cloudca"))) { + throw new CloudRuntimeException("Please provide a different alias name for the certificate"); + } + HypervisorType hypervisorType = HypervisorType.getType(hypervisor); List hosts = getRunningHostsToUploadCertificate(hypervisorType); @@ -373,6 +377,7 @@ public class DirectDownloadManagerImpl extends ManagerBase implements DirectDown certificateSanity(certificatePem); s_logger.info("Attempting to upload certificate: " + alias + " to " + hosts.size() + " hosts"); + int hostCount = 0; if (CollectionUtils.isNotEmpty(hosts)) { for (HostVO host : hosts) { if (!uploadCertificate(certificatePem, alias, host.getId())) { @@ -380,8 +385,10 @@ public class DirectDownloadManagerImpl extends ManagerBase implements DirectDown s_logger.error(msg); throw new CloudRuntimeException(msg); } + hostCount++; } } + s_logger.info("Certificate was successfully uploaded to " + hostCount + " hosts"); return true; } @@ -389,6 +396,7 @@ public class DirectDownloadManagerImpl extends ManagerBase implements DirectDown * Upload and import certificate to hostId on keystore */ protected boolean uploadCertificate(String certificate, String certificateName, long hostId) { + s_logger.debug("Uploading certificate: " + certificateName + " to host " + hostId); SetupDirectDownloadCertificateCommand cmd = new SetupDirectDownloadCertificateCommand(certificate, certificateName); Answer answer = agentManager.easySend(hostId, cmd); if (answer == null || !answer.getResult()) {