From 0d4545b5d0d0fd0d25afb87d6a5d83eb6b18e03b Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Wed, 7 Dec 2022 11:03:35 +0800 Subject: [PATCH 01/19] QA-4212 kafka ssl ca generate scripts --- .../generate_ssl_CA/ssl_one_way.sh | 67 +++++++++++++++++ .../generate_ssl_CA/ssl_two_way.sh | 73 +++++++++++++++++++ 2 files changed, 140 insertions(+) create mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh create mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh new file mode 100644 index 00000000..cb72d181 --- /dev/null +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh @@ -0,0 +1,67 @@ +#!/bin/bash +# The example: bash ssl_one_way.sh kafka-0.tigergraph.com ~/SSL_one_way tiger123 +# The example password: tiger123 +# The example server host name: kafka-0.tigergraph.com +# The certificate generation path: ~/SSL_one_way + +if [ $# -eq 3 ]; then + server_hostname=$1 + generate_root=$2 + pass=$3 +else + echo "Error in parameter. Please check." + echo "e.g. bash ssl_one_way.sh server_hostname generate_root password" + exit 1 +fi + +env_prepare(){ + # install java + if ! which java > /dev/null 2>&1; then + echo "start install openjdk." + sudo yum update -y > /dev/null 2>&1 + sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + echo "install openjdk-1.8.0 successfully." + else + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + if [[ $java_version != "1.8.0" ]];then + echo "start upgrade java." + rpm -qa | grep java | sudo xargs rpm -e --nodeps + sudo yum update -y > /dev/null 2>&1 + sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + echo "install openjdk-1.8.0 successfully." + else + echo "The java version is openjdk-1.8.0 now." + fi + fi + + # install openssl + if ! openssl version > /dev/null 2>&1;then + sudo yum -y install openssl > /dev/null 2>&1 + fi +} + +ssl_oneway_ca_generate(){ + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + echo "start create certificates..." + sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} + sudo openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Confluent/CN=Confluent" + echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr + sudo openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial + echo ${pass} | sudo keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt + echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt + echo -e "${pass}\n${pass}\ny" | sudo keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt + + if [ $? != 0 ]; then + echo "failed to generate certificates." + exit 1 + else + echo "certificates generated successfully." + fi +} + +env_prepare +ssl_oneway_ca_generate ${server_hostname} ${generate_root} ${pass} \ No newline at end of file diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh new file mode 100644 index 00000000..f9560ff7 --- /dev/null +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh @@ -0,0 +1,73 @@ +#!/bin/bash +# The example: bash ssl_two_way.sh kafka-0.tigergraph.com tigergraph ~/SSL_two_way tiger123 +# The example password: tiger123 +# The example server host name: kafka-0.tigergraph.com +# The example client host name: tigergraph +# The certificate generation path: ~/SSL_two_way + +if [ $# -eq 4 ]; then + server_hostname=$1 + client_hostname=$2 + generate_root=$3 + pass=$4 +else + echo "Error in parameter. Please check." + echo "e.g. bash ssl_two_way.sh server_hostname client_hostname generate_root password" + exit 1 +fi + +env_prepare(){ + # install java + if ! which java > /dev/null 2>&1; then + echo "start install openjdk." + sudo yum update -y > /dev/null 2>&1 + sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + echo "install openjdk-1.8.0 successfully." + else + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + if [[ $java_version != "1.8.0" ]];then + echo "start upgrade java." + rpm -qa | grep java | sudo xargs rpm -e --nodeps + sudo yum update -y > /dev/null 2>&1 + sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + echo "install openjdk-1.8.0 successfully." + else + echo "The java version is openjdk-1.8.0 now." + fi + fi + + # install openssl + if ! openssl version > /dev/null 2>&1;then + sudo yum -y install openssl > /dev/null 2>&1 + fi +} + +ssl_twoway_ca_generate(){ + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + echo "start create certificates for kafka broker..." + sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} + sudo openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Confluent/CN=Confluent" + echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr + sudo openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial + echo ${pass} | sudo keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt + echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt + + echo "start generate private key / public key certificate pair for the client..." + sudo openssl req -newkey rsa:2048 -nodes -keyout ${client_hostname}_client.key -out ${client_hostname}_client.csr -subj "/C=US/ST=CA/L=Palo Alto/O=Confluent/CN=Confluent" + sudo openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${client_hostname}_client.csr -out ${client_hostname}_client.crt -days 365 -CAcreateserial + echo -e "${pass}\n${pass}\ny" | sudo keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt + + if [ $? != 0 ]; then + echo "failed to generate certificates." + exit 1 + else + echo "certificates generated successfully." + fi +} + +env_prepare +ssl_twoway_ca_generate ${server_hostname} ${generate_root} ${pass} \ No newline at end of file From 60dcd447741223783d52c197400f985c85fb8590 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Tue, 27 Dec 2022 15:12:00 +0800 Subject: [PATCH 02/19] QA-4212 new version --- tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh | 102 +++++++++ .../generate_ssl_CA/ssl_one_way.sh | 67 ------ .../generate_ssl_CA/ssl_two_way.sh | 73 ------ .../generate_ssl_CA/utils/env_utils | 215 ++++++++++++++++++ .../generate_ssl_CA/utils/pretty_print | 52 +++++ 5 files changed, 369 insertions(+), 140 deletions(-) create mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh delete mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh delete mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh create mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils create mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/utils/pretty_print diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh new file mode 100644 index 00000000..4cd6ddd2 --- /dev/null +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh @@ -0,0 +1,102 @@ +#!/bin/bash +# ssl_one_way ca files generation +# ssl_two_way ca files generation + +cd $(dirname $0) +BASE_DIR=$(pwd) + +source_file() { + file=$1 + msg="$2" + src_flag=$3 + if [ -f "$file" ]; then + if [ "$src_flag" != "false" ]; then + source $file + fi + else + echo $(tput setaf 1) "[ERROR ]: $msg" $(tput sgr0) + exit 1 + fi +} + +# source all functions +source_file utils/pretty_print "No miss tools found, utils/pretty_print NOT exist, exit" true +source_file utils/env_utils "No miss tools found, utils/env_utils NOT exist, exit" true + +OSG=$(get_os) +OS=$(echo "$OSG" | cut -d' ' -f1) +version=$(echo "$OSG" | cut -d' ' -f2) +OSV="$OS$(echo "$version" | cut -d'.' -f1)" + +# this script only support rhel/centos +prog "Checking operation system (OS) version ..." +check_os $OS $version + +prog "Checking root/sudo ..." +check_root + +server_hostname=kafka-0.tigergraph.com +generate_root=~/SSL_files +pass=tiger123 +ssl_type=ssl_one_way +client_hostname= + +opt_string=":ho:s:t:p:ic:" +incompatible_opt="" +while getopts $opt_string opt; do + case $opt in + h) + help + ;; + s) + server_hostname=$OPTARG + ;; + o) + if [[ "$OPTARG" == "ssl_two_way" ]]; then + ssl_type=$OPTARG + two_way=true + elif [[ "$OPTARG" == "ssl_one_way" ]]; then + ssl_type=$OPTARG + two_way=false + else + error "\"-o\" only supports \"ssl_one_way\" or \"ssl_two_way\"" + exit 1 + fi + ;; + t) + generate_root=$OPTARG + ;; + c) + client_hostname=$OPTARG + incompatible_opt+=" -c" + ;; + p) + pass=$OPTARG + ;; + i) + SETUP_JDK=true + ;; + *) + error "${bldred}Invalid option, the correct usage is described below: $txtrst" + help + ;; + esac +done + +if [[ "$two_way" == "true" ]] && [[ -z $incompatible_opt ]]; then + echo "${bldred}Option '-o ssl_two_way' needs to be used together with option '-c', the correct usage is described below: $txtrst" + help +fi + +# install openJDK +# Using option '-i' will install openjdk-1.8.0, otherwise openjdk-1.8.0 will not be installed +install_openJDK +# install openssl +install_openssl +# ca generation +rm -rf $generate_root +if [[ "$ssl_type" == "ssl_one_way" ]]; then + ssl_oneway_ca_generate +else + ssl_twoway_ca_generate +fi \ No newline at end of file diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh deleted file mode 100644 index cb72d181..00000000 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_one_way.sh +++ /dev/null @@ -1,67 +0,0 @@ -#!/bin/bash -# The example: bash ssl_one_way.sh kafka-0.tigergraph.com ~/SSL_one_way tiger123 -# The example password: tiger123 -# The example server host name: kafka-0.tigergraph.com -# The certificate generation path: ~/SSL_one_way - -if [ $# -eq 3 ]; then - server_hostname=$1 - generate_root=$2 - pass=$3 -else - echo "Error in parameter. Please check." - echo "e.g. bash ssl_one_way.sh server_hostname generate_root password" - exit 1 -fi - -env_prepare(){ - # install java - if ! which java > /dev/null 2>&1; then - echo "start install openjdk." - sudo yum update -y > /dev/null 2>&1 - sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - echo "install openjdk-1.8.0 successfully." - else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) - if [[ $java_version != "1.8.0" ]];then - echo "start upgrade java." - rpm -qa | grep java | sudo xargs rpm -e --nodeps - sudo yum update -y > /dev/null 2>&1 - sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - echo "install openjdk-1.8.0 successfully." - else - echo "The java version is openjdk-1.8.0 now." - fi - fi - - # install openssl - if ! openssl version > /dev/null 2>&1;then - sudo yum -y install openssl > /dev/null 2>&1 - fi -} - -ssl_oneway_ca_generate(){ - if [ ! -d ${generate_root} ]; then - mkdir -p ${generate_root} - fi - - cd $generate_root - echo "start create certificates..." - sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} - sudo openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Confluent/CN=Confluent" - echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr - sudo openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial - echo ${pass} | sudo keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt - echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt - echo -e "${pass}\n${pass}\ny" | sudo keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt - - if [ $? != 0 ]; then - echo "failed to generate certificates." - exit 1 - else - echo "certificates generated successfully." - fi -} - -env_prepare -ssl_oneway_ca_generate ${server_hostname} ${generate_root} ${pass} \ No newline at end of file diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh deleted file mode 100644 index f9560ff7..00000000 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl_two_way.sh +++ /dev/null @@ -1,73 +0,0 @@ -#!/bin/bash -# The example: bash ssl_two_way.sh kafka-0.tigergraph.com tigergraph ~/SSL_two_way tiger123 -# The example password: tiger123 -# The example server host name: kafka-0.tigergraph.com -# The example client host name: tigergraph -# The certificate generation path: ~/SSL_two_way - -if [ $# -eq 4 ]; then - server_hostname=$1 - client_hostname=$2 - generate_root=$3 - pass=$4 -else - echo "Error in parameter. Please check." - echo "e.g. bash ssl_two_way.sh server_hostname client_hostname generate_root password" - exit 1 -fi - -env_prepare(){ - # install java - if ! which java > /dev/null 2>&1; then - echo "start install openjdk." - sudo yum update -y > /dev/null 2>&1 - sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - echo "install openjdk-1.8.0 successfully." - else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) - if [[ $java_version != "1.8.0" ]];then - echo "start upgrade java." - rpm -qa | grep java | sudo xargs rpm -e --nodeps - sudo yum update -y > /dev/null 2>&1 - sudo yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - echo "install openjdk-1.8.0 successfully." - else - echo "The java version is openjdk-1.8.0 now." - fi - fi - - # install openssl - if ! openssl version > /dev/null 2>&1;then - sudo yum -y install openssl > /dev/null 2>&1 - fi -} - -ssl_twoway_ca_generate(){ - if [ ! -d ${generate_root} ]; then - mkdir -p ${generate_root} - fi - - cd $generate_root - echo "start create certificates for kafka broker..." - sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} - sudo openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Confluent/CN=Confluent" - echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr - sudo openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial - echo ${pass} | sudo keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt - echo ${pass} | sudo keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt - - echo "start generate private key / public key certificate pair for the client..." - sudo openssl req -newkey rsa:2048 -nodes -keyout ${client_hostname}_client.key -out ${client_hostname}_client.csr -subj "/C=US/ST=CA/L=Palo Alto/O=Confluent/CN=Confluent" - sudo openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${client_hostname}_client.csr -out ${client_hostname}_client.crt -days 365 -CAcreateserial - echo -e "${pass}\n${pass}\ny" | sudo keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt - - if [ $? != 0 ]; then - echo "failed to generate certificates." - exit 1 - else - echo "certificates generated successfully." - fi -} - -env_prepare -ssl_twoway_ca_generate ${server_hostname} ${generate_root} ${pass} \ No newline at end of file diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils new file mode 100644 index 00000000..b9df9878 --- /dev/null +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils @@ -0,0 +1,215 @@ +#!/bin/bash + +get_os(){ + if [ -f "/etc/apt/sources.list" ]; then + if [ -f "/etc/linx-release" ]; then + os_version=$(cat /etc/linx-release | grep -o '[0-9]\.[0-9]\.[0-9]\{1,3\}' ) + echo "ROCKY $os_version" + elif [ -f "/etc/lsb-release" ]; then + os_version=$(cat /etc/lsb-release | grep "DISTRIB_RELEASE" | cut -d= -f2) + echo "UBUNTU $os_version" + elif [ -f "/etc/os-release" ]; then + os_version=$(cat /etc/os-release | grep "VERSION_ID" | cut -d= -f2) + os_version=${os_version//\"} # remove all double quotes + echo "DEBIAN $os_version" + fi + elif [ -d "/etc/yum.repos.d" ]; then + # Centos and RedHat are treated equally + if grep "Amazon Linux" /etc/system-release &>/dev/null; then + os_version=" 7.0" + else + variant="$(cat /etc/system-release | cut -d ' ' -f2)" + if [ "$variant" = "Stream" ]; then + os_version=" $(cat /etc/os-release | grep 'VERSION_ID=' | cut -d'"' -f 2)" + else + os_version="$(cat /etc/system-release | grep -o ' [0-9]\.[0-9]\{1,3\}')" + fi + fi + echo "RHEL$os_version" + elif [ -d "/etc/zypp/repos.d" ]; then + os_version=$(cat /etc/os-release | grep "VERSION_ID" | cut -d= -f2) + os_version=${os_version//\"} # remove all double quotes + echo "SUSE $os_version" + else + echo "UNKOWN OS" + fi +} + +check_os(){ + OS=$1 + version=$2 + note "OS obtained: $OS $version" + local error_msg="Unsupported OS. Current support CentOS 6.5 to 8.0; RedHat 6.5 to 9.0;" + if [ -z "$version" ]; then + error "Unknown OS version. $error_msg" + exit 1 + fi + + if [ "$OS" = "RHEL" ]; then + # the following one will end with one item array on docker centos 7.3, i.e. "${ver_arr[0]}" is "7 3" + # local ver_arr=(${version//./ }) + IFS='.' read -r -a ver_arr <<< "$version" + if [[ "${ver_arr[0]}" -lt "6" || "${ver_arr[0]}" -eq "6" && "${ver_arr[1]}" -lt "5" ]]; then + error "$error_msg" + exit 1 + else + note "OS check passed [OK]" + fi + else + error "$error_msg" + exit 1 + fi +} + +check_root(){ + if [[ $EUID -ne 0 ]]; then + error "Sudo or root rights are required." + exit 1 + fi +} + +install_openJDK(){ + if [[ "${SETUP_JDK}" == "true" ]]; then + if ! which java > /dev/null 2>&1; then + prog "start install openjdk-1.8.0." + yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + else + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + if [[ $java_version != "1.8.0" ]];then + prog "start update to openjdk-1.8.0." + rpm -qa | grep java | xargs rpm -e --nodeps + yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + else + prog "The java version is openjdk-1.8.0 now." + fi + fi + # check install + if command -v java &> /dev/null;then + prog "JDK Install Success..." + else + error "JDK Install Fail..." && exit 1 + fi + + else + if ! which java > /dev/null 2>&1; then + error "Java environment not detected. You can choose option \"-i\" to install openjdk-1.8.0." + exit 1 + else + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + if [[ $java_version != "1.8.0" ]];then + error "This script currently only supports openjdk-1.8.0." + exit 1 + else + prog "The java version is openjdk-1.8.0 now." + fi + fi + fi +} + +install_openssl(){ + if ! openssl version > /dev/null 2>&1;then + prog "start install openssl..." + yum -y install openssl > /dev/null 2>&1 + fi + + if [ $? != 0 ]; then + error "Failed to install openssl." + exit 1 + fi +} + +ssl_oneway_ca_generate(){ + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + prog "start create certificates..." + keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} + openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" + echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr + openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial + echo ${pass} | keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt + echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt + echo -e "${pass}\n${pass}\ny" | keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt + + if [ $? != 0 ]; then + error "Failed to generate certificates." + exit 1 + else + prog "Certificates generated successfully." + fi +} + +ssl_oneway_ca_generate(){ + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + prog "start create ssl_one_way certificates..." + keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} + openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" + echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr + openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial + echo ${pass} | keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt + echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt + echo -e "${pass}\n${pass}\ny" | keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt + + if [ $? != 0 ]; then + error "Failed to generate certificates." + exit 1 + else + prog "Certificates generated successfully." + fi +} + +ssl_twoway_ca_generate(){ + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + prog "start create ssl_two_way certificates for kafka broker..." + keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} + openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" + echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr + openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial + echo ${pass} | keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt + echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt + + prog "start generate private key, public key certificate pair for the client..." + openssl req -newkey rsa:2048 -nodes -keyout ${client_hostname}_client.key -out ${client_hostname}_client.csr -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" + openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${client_hostname}_client.csr -out ${client_hostname}_client.crt -days 365 -CAcreateserial + echo -e "${pass}\n${pass}\ny" | keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt + + if [ $? != 0 ]; then + error "Failed to generate certificates." + exit 1 + else + prog "Certificates generated successfully." + fi +} + +help(){ + echo + echo "Usage:" + mesg_green "./`basename $0` [-o ssl_two_way] [-c ] [-s ] [-t ] [-p ] [-i]" + mesg_green "./`basename $0` [-o ssl_two_way] [-c ] [-s ] [-t ] [-p ]" + mesg_green "./`basename $0` [-o ssl_one_way] [-s ] [-t ] [-p ] [-i]" + mesg_green "./`basename $0` [-o ssl_one_way] [-s ] [-t ] [-p ]" + mesg_green "./`basename $0` -h" + echo "Options:" + echo " -h -- Show the help" + echo " -o -- SSL certificate type: ssl_one_way or ssl_two_way [default: ssl_one_way]" + echo " -s -- Kafka broker host name [default: kafka-0.tigergraph.com]" + echo " -t -- Certificate Generation Path [default: ~/SSL_files]" + echo " -c -- Tigergraph Client host name" + echo " -p -- Password [default: tiger123]" + echo " -i -- Install openjdk-1.8.0" + echo + warn "Using option '-i' will install openjdk-1.8.0, otherwise openjdk-1.8.0 will not be installed. +Please note that if the local machine does not have a java environment, some certificates generation will fail." + warn "If the option '-o' value is 'ssl_two_way', we should use the '-c' option at the same time." + exit 0 +} \ No newline at end of file diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/pretty_print b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/pretty_print new file mode 100644 index 00000000..972e689c --- /dev/null +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/pretty_print @@ -0,0 +1,52 @@ +#!/bin/bash + +txtbld=$(tput bold) +bldblk=${txtbld}$(tput setaf 0) # black +bldred=${txtbld}$(tput setaf 1) # red +bldgre=${txtbld}$(tput setaf 2) # green +bldyel=${txtbld}$(tput setaf 3) # yellow +bldblu=${txtbld}$(tput setaf 4) # blue +bldmag=${txtbld}$(tput setaf 5) # magenta +bldcya=${txtbld}$(tput setaf 6) # cyan +bldwhi=${txtbld}$(tput setaf 7) # white +txtrst=$(tput sgr0) # Reset + +error(){ + echo "${bldred}[ERROR ]: $* $txtrst" +} + +warn(){ + echo "${bldyel}[WARNING ]: $* $txtrst" +} + +note(){ + echo "${bldcya}[NOTE ]: $* $txtrst" +} + +prog(){ + echo "${bldgre}[PROGRESS]: $(date +"%T") $* $txtrst" +} + +mesg_red(){ + echo "${bldred}$* $txtrst" +} + +mesg_green(){ + echo "${bldgre}$* $txtrst" +} + +mesg_yellow(){ + echo "${bldyel}$* $txtrst" +} + +mesg_blue(){ + echo "${bldblu}$* $txtrst" +} + +mesg_cyan(){ + echo "${bldcya}$* $txtrst" +} + +mesg_mag(){ + echo "${bldmag}$* $txtrst" +} From 201e074aa1f36841034db749538a680c2f4dd3e3 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Tue, 27 Dec 2022 15:58:45 +0800 Subject: [PATCH 03/19] QA-4212 modify file path --- tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh index 4cd6ddd2..1c74d9db 100644 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh @@ -94,9 +94,12 @@ install_openJDK # install openssl install_openssl # ca generation -rm -rf $generate_root if [[ "$ssl_type" == "ssl_one_way" ]]; then + generate_root=$generate_root/ssl_one_way + rm -rf $generate_root ssl_oneway_ca_generate else + generate_root=$generate_root/ssl_two_way + rm -rf $generate_root ssl_twoway_ca_generate fi \ No newline at end of file From 8b37efa22b2555bdecf406dcb3631f2ec140dae2 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Tue, 3 Jan 2023 16:46:42 +0800 Subject: [PATCH 04/19] QA-4212 modify help message --- tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh | 13 ++-- .../generate_ssl_CA/utils/env_utils | 66 ++++++++----------- 2 files changed, 34 insertions(+), 45 deletions(-) diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh index 1c74d9db..9809147c 100644 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh @@ -41,7 +41,7 @@ pass=tiger123 ssl_type=ssl_one_way client_hostname= -opt_string=":ho:s:t:p:ic:" +opt_string=":ht:s:d:p:ic:" incompatible_opt="" while getopts $opt_string opt; do case $opt in @@ -51,7 +51,7 @@ while getopts $opt_string opt; do s) server_hostname=$OPTARG ;; - o) + t) if [[ "$OPTARG" == "ssl_two_way" ]]; then ssl_type=$OPTARG two_way=true @@ -59,11 +59,11 @@ while getopts $opt_string opt; do ssl_type=$OPTARG two_way=false else - error "\"-o\" only supports \"ssl_one_way\" or \"ssl_two_way\"" + error "\"-t\" only supports \"ssl_one_way\" or \"ssl_two_way\"" exit 1 fi ;; - t) + d) generate_root=$OPTARG ;; c) @@ -75,6 +75,7 @@ while getopts $opt_string opt; do ;; i) SETUP_JDK=true + SETUP_OPENSSL=true ;; *) error "${bldred}Invalid option, the correct usage is described below: $txtrst" @@ -84,12 +85,12 @@ while getopts $opt_string opt; do done if [[ "$two_way" == "true" ]] && [[ -z $incompatible_opt ]]; then - echo "${bldred}Option '-o ssl_two_way' needs to be used together with option '-c', the correct usage is described below: $txtrst" + echo "${bldred}Option '-t ssl_two_way' needs to be used together with option '-c', the correct usage is described below: $txtrst" help fi +# Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed # install openJDK -# Using option '-i' will install openjdk-1.8.0, otherwise openjdk-1.8.0 will not be installed install_openJDK # install openssl install_openssl diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils index b9df9878..490e376f 100644 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils @@ -107,37 +107,25 @@ install_openJDK(){ } install_openssl(){ - if ! openssl version > /dev/null 2>&1;then - prog "start install openssl..." - yum -y install openssl > /dev/null 2>&1 - fi - - if [ $? != 0 ]; then - error "Failed to install openssl." - exit 1 - fi -} - -ssl_oneway_ca_generate(){ - if [ ! -d ${generate_root} ]; then - mkdir -p ${generate_root} - fi - - cd $generate_root - prog "start create certificates..." - keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} - openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" - echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr - openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial - echo ${pass} | keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt - echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt - echo -e "${pass}\n${pass}\ny" | keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt + if [[ "${SETUP_OPENSSL}" == "true" ]]; then + if ! openssl version > /dev/null 2>&1;then + prog "start install openssl..." + yum -y install openssl > /dev/null 2>&1 + else + prog "Openssl is installed, skip installation." + fi - if [ $? != 0 ]; then - error "Failed to generate certificates." - exit 1 + if [ $? != 0 ]; then + error "Failed to install openssl." + exit 1 + fi else - prog "Certificates generated successfully." + if ! openssl version > /dev/null 2>&1;then + error "Openssl is not installed. You can choose option \"-i\" to install openssl." + exit 1 + else + prog "Openssl is installed." + fi fi } @@ -194,22 +182,22 @@ ssl_twoway_ca_generate(){ help(){ echo echo "Usage:" - mesg_green "./`basename $0` [-o ssl_two_way] [-c ] [-s ] [-t ] [-p ] [-i]" - mesg_green "./`basename $0` [-o ssl_two_way] [-c ] [-s ] [-t ] [-p ]" - mesg_green "./`basename $0` [-o ssl_one_way] [-s ] [-t ] [-p ] [-i]" - mesg_green "./`basename $0` [-o ssl_one_way] [-s ] [-t ] [-p ]" + mesg_green "./`basename $0` [-t ssl_two_way] [-c ] [-s ] [-d ] [-p ] [-i]" + mesg_green "./`basename $0` [-t ssl_two_way] [-c ] [-s ] [-d ] [-p ]" + mesg_green "./`basename $0` [-t ssl_one_way] [-s ] [-d ] [-p ] [-i]" + mesg_green "./`basename $0` [-t ssl_one_way] [-s ] [-d ] [-p ]" mesg_green "./`basename $0` -h" echo "Options:" echo " -h -- Show the help" - echo " -o -- SSL certificate type: ssl_one_way or ssl_two_way [default: ssl_one_way]" + echo " -t -- SSL certificate type: ssl_one_way or ssl_two_way [default: ssl_one_way]" echo " -s -- Kafka broker host name [default: kafka-0.tigergraph.com]" - echo " -t -- Certificate Generation Path [default: ~/SSL_files]" - echo " -c -- Tigergraph Client host name" + echo " -d -- Certificate Generation Path [default: ~/SSL_files]" + echo " -c -- TigerGraph Client host name" echo " -p -- Password [default: tiger123]" - echo " -i -- Install openjdk-1.8.0" + echo " -i -- Install openjdk-1.8.0 and openssl" echo - warn "Using option '-i' will install openjdk-1.8.0, otherwise openjdk-1.8.0 will not be installed. + warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. Please note that if the local machine does not have a java environment, some certificates generation will fail." - warn "If the option '-o' value is 'ssl_two_way', we should use the '-c' option at the same time." + warn "If the option '-t' value is 'ssl_two_way', we should use the '-c' option at the same time." exit 0 } \ No newline at end of file From 17b2323de1c10d59e2d5c0f07f7013da987612cf Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Tue, 3 Jan 2023 17:11:17 +0800 Subject: [PATCH 05/19] QA-4212 password check --- tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh index 9809147c..fadc9f2e 100644 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh +++ b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh @@ -71,7 +71,12 @@ while getopts $opt_string opt; do incompatible_opt+=" -c" ;; p) - pass=$OPTARG + if [ ${#OPTARG} -lt 6 ];then + error "Password is too short - must be at least 6 characters." + exit 1 + else + pass=$OPTARG + fi ;; i) SETUP_JDK=true From ec6ca7adfad0d77b1fafadffbdc3644cf34f1fa0 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Fri, 10 Feb 2023 17:32:49 +0800 Subject: [PATCH 06/19] new version --- tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh | 111 ------- .../generate_ssl_CA/utils/env_utils | 203 ------------ .../generate_ssl_CA/general_ssl_script.sh | 255 +++++++++++++++ .../generate_ssl_CA/generate_new_ssl.sh | 135 ++++++++ .../kafka_ssl/generate_ssl_CA/utils/env_utils | 306 ++++++++++++++++++ .../generate_ssl_CA/utils/pretty_print | 0 .../kafka_ssl/generate_ssl_CA/utils/ssl_utils | 164 ++++++++++ 7 files changed, 860 insertions(+), 314 deletions(-) delete mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh delete mode 100644 tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils create mode 100644 tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh create mode 100644 tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh create mode 100644 tools/kafka_ssl/generate_ssl_CA/utils/env_utils rename tools/{kafka_sasl_ssl => kafka_ssl}/generate_ssl_CA/utils/pretty_print (100%) create mode 100644 tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh b/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh deleted file mode 100644 index fadc9f2e..00000000 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/ssl.sh +++ /dev/null @@ -1,111 +0,0 @@ -#!/bin/bash -# ssl_one_way ca files generation -# ssl_two_way ca files generation - -cd $(dirname $0) -BASE_DIR=$(pwd) - -source_file() { - file=$1 - msg="$2" - src_flag=$3 - if [ -f "$file" ]; then - if [ "$src_flag" != "false" ]; then - source $file - fi - else - echo $(tput setaf 1) "[ERROR ]: $msg" $(tput sgr0) - exit 1 - fi -} - -# source all functions -source_file utils/pretty_print "No miss tools found, utils/pretty_print NOT exist, exit" true -source_file utils/env_utils "No miss tools found, utils/env_utils NOT exist, exit" true - -OSG=$(get_os) -OS=$(echo "$OSG" | cut -d' ' -f1) -version=$(echo "$OSG" | cut -d' ' -f2) -OSV="$OS$(echo "$version" | cut -d'.' -f1)" - -# this script only support rhel/centos -prog "Checking operation system (OS) version ..." -check_os $OS $version - -prog "Checking root/sudo ..." -check_root - -server_hostname=kafka-0.tigergraph.com -generate_root=~/SSL_files -pass=tiger123 -ssl_type=ssl_one_way -client_hostname= - -opt_string=":ht:s:d:p:ic:" -incompatible_opt="" -while getopts $opt_string opt; do - case $opt in - h) - help - ;; - s) - server_hostname=$OPTARG - ;; - t) - if [[ "$OPTARG" == "ssl_two_way" ]]; then - ssl_type=$OPTARG - two_way=true - elif [[ "$OPTARG" == "ssl_one_way" ]]; then - ssl_type=$OPTARG - two_way=false - else - error "\"-t\" only supports \"ssl_one_way\" or \"ssl_two_way\"" - exit 1 - fi - ;; - d) - generate_root=$OPTARG - ;; - c) - client_hostname=$OPTARG - incompatible_opt+=" -c" - ;; - p) - if [ ${#OPTARG} -lt 6 ];then - error "Password is too short - must be at least 6 characters." - exit 1 - else - pass=$OPTARG - fi - ;; - i) - SETUP_JDK=true - SETUP_OPENSSL=true - ;; - *) - error "${bldred}Invalid option, the correct usage is described below: $txtrst" - help - ;; - esac -done - -if [[ "$two_way" == "true" ]] && [[ -z $incompatible_opt ]]; then - echo "${bldred}Option '-t ssl_two_way' needs to be used together with option '-c', the correct usage is described below: $txtrst" - help -fi - -# Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed -# install openJDK -install_openJDK -# install openssl -install_openssl -# ca generation -if [[ "$ssl_type" == "ssl_one_way" ]]; then - generate_root=$generate_root/ssl_one_way - rm -rf $generate_root - ssl_oneway_ca_generate -else - generate_root=$generate_root/ssl_two_way - rm -rf $generate_root - ssl_twoway_ca_generate -fi \ No newline at end of file diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils deleted file mode 100644 index 490e376f..00000000 --- a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/env_utils +++ /dev/null @@ -1,203 +0,0 @@ -#!/bin/bash - -get_os(){ - if [ -f "/etc/apt/sources.list" ]; then - if [ -f "/etc/linx-release" ]; then - os_version=$(cat /etc/linx-release | grep -o '[0-9]\.[0-9]\.[0-9]\{1,3\}' ) - echo "ROCKY $os_version" - elif [ -f "/etc/lsb-release" ]; then - os_version=$(cat /etc/lsb-release | grep "DISTRIB_RELEASE" | cut -d= -f2) - echo "UBUNTU $os_version" - elif [ -f "/etc/os-release" ]; then - os_version=$(cat /etc/os-release | grep "VERSION_ID" | cut -d= -f2) - os_version=${os_version//\"} # remove all double quotes - echo "DEBIAN $os_version" - fi - elif [ -d "/etc/yum.repos.d" ]; then - # Centos and RedHat are treated equally - if grep "Amazon Linux" /etc/system-release &>/dev/null; then - os_version=" 7.0" - else - variant="$(cat /etc/system-release | cut -d ' ' -f2)" - if [ "$variant" = "Stream" ]; then - os_version=" $(cat /etc/os-release | grep 'VERSION_ID=' | cut -d'"' -f 2)" - else - os_version="$(cat /etc/system-release | grep -o ' [0-9]\.[0-9]\{1,3\}')" - fi - fi - echo "RHEL$os_version" - elif [ -d "/etc/zypp/repos.d" ]; then - os_version=$(cat /etc/os-release | grep "VERSION_ID" | cut -d= -f2) - os_version=${os_version//\"} # remove all double quotes - echo "SUSE $os_version" - else - echo "UNKOWN OS" - fi -} - -check_os(){ - OS=$1 - version=$2 - note "OS obtained: $OS $version" - local error_msg="Unsupported OS. Current support CentOS 6.5 to 8.0; RedHat 6.5 to 9.0;" - if [ -z "$version" ]; then - error "Unknown OS version. $error_msg" - exit 1 - fi - - if [ "$OS" = "RHEL" ]; then - # the following one will end with one item array on docker centos 7.3, i.e. "${ver_arr[0]}" is "7 3" - # local ver_arr=(${version//./ }) - IFS='.' read -r -a ver_arr <<< "$version" - if [[ "${ver_arr[0]}" -lt "6" || "${ver_arr[0]}" -eq "6" && "${ver_arr[1]}" -lt "5" ]]; then - error "$error_msg" - exit 1 - else - note "OS check passed [OK]" - fi - else - error "$error_msg" - exit 1 - fi -} - -check_root(){ - if [[ $EUID -ne 0 ]]; then - error "Sudo or root rights are required." - exit 1 - fi -} - -install_openJDK(){ - if [[ "${SETUP_JDK}" == "true" ]]; then - if ! which java > /dev/null 2>&1; then - prog "start install openjdk-1.8.0." - yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) - if [[ $java_version != "1.8.0" ]];then - prog "start update to openjdk-1.8.0." - rpm -qa | grep java | xargs rpm -e --nodeps - yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - else - prog "The java version is openjdk-1.8.0 now." - fi - fi - # check install - if command -v java &> /dev/null;then - prog "JDK Install Success..." - else - error "JDK Install Fail..." && exit 1 - fi - - else - if ! which java > /dev/null 2>&1; then - error "Java environment not detected. You can choose option \"-i\" to install openjdk-1.8.0." - exit 1 - else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) - if [[ $java_version != "1.8.0" ]];then - error "This script currently only supports openjdk-1.8.0." - exit 1 - else - prog "The java version is openjdk-1.8.0 now." - fi - fi - fi -} - -install_openssl(){ - if [[ "${SETUP_OPENSSL}" == "true" ]]; then - if ! openssl version > /dev/null 2>&1;then - prog "start install openssl..." - yum -y install openssl > /dev/null 2>&1 - else - prog "Openssl is installed, skip installation." - fi - - if [ $? != 0 ]; then - error "Failed to install openssl." - exit 1 - fi - else - if ! openssl version > /dev/null 2>&1;then - error "Openssl is not installed. You can choose option \"-i\" to install openssl." - exit 1 - else - prog "Openssl is installed." - fi - fi -} - -ssl_oneway_ca_generate(){ - if [ ! -d ${generate_root} ]; then - mkdir -p ${generate_root} - fi - - cd $generate_root - prog "start create ssl_one_way certificates..." - keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} - openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" - echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr - openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial - echo ${pass} | keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt - echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt - echo -e "${pass}\n${pass}\ny" | keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt - - if [ $? != 0 ]; then - error "Failed to generate certificates." - exit 1 - else - prog "Certificates generated successfully." - fi -} - -ssl_twoway_ca_generate(){ - if [ ! -d ${generate_root} ]; then - mkdir -p ${generate_root} - fi - - cd $generate_root - prog "start create ssl_two_way certificates for kafka broker..." - keytool -keystore server.keystore.jks -alias ${server_hostname} -validity 365 -genkey -keyalg RSA -dname "cn=${server_hostname}" -storepass ${pass} -keypass ${pass} - openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" - echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -certreq -file ${server_hostname}_server.csr - openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${server_hostname}_server.csr -out ${server_hostname}_server.crt -days 365 -CAcreateserial - echo ${pass} | keytool -keystore server.keystore.jks -alias CARoot -import -noprompt -file ca-root.crt - echo ${pass} | keytool -keystore server.keystore.jks -alias ${server_hostname} -import -file ${server_hostname}_server.crt - - prog "start generate private key, public key certificate pair for the client..." - openssl req -newkey rsa:2048 -nodes -keyout ${client_hostname}_client.key -out ${client_hostname}_client.csr -subj "/C=US/ST=CA/L=Palo Alto/O=Tigergraph/CN=Tigergraph" - openssl x509 -req -CA ca-root.crt -CAkey ca-root.key -in ${client_hostname}_client.csr -out ${client_hostname}_client.crt -days 365 -CAcreateserial - echo -e "${pass}\n${pass}\ny" | keytool -keystore server.truststore.jks -alias CARoot -import -file ca-root.crt - - if [ $? != 0 ]; then - error "Failed to generate certificates." - exit 1 - else - prog "Certificates generated successfully." - fi -} - -help(){ - echo - echo "Usage:" - mesg_green "./`basename $0` [-t ssl_two_way] [-c ] [-s ] [-d ] [-p ] [-i]" - mesg_green "./`basename $0` [-t ssl_two_way] [-c ] [-s ] [-d ] [-p ]" - mesg_green "./`basename $0` [-t ssl_one_way] [-s ] [-d ] [-p ] [-i]" - mesg_green "./`basename $0` [-t ssl_one_way] [-s ] [-d ] [-p ]" - mesg_green "./`basename $0` -h" - echo "Options:" - echo " -h -- Show the help" - echo " -t -- SSL certificate type: ssl_one_way or ssl_two_way [default: ssl_one_way]" - echo " -s -- Kafka broker host name [default: kafka-0.tigergraph.com]" - echo " -d -- Certificate Generation Path [default: ~/SSL_files]" - echo " -c -- TigerGraph Client host name" - echo " -p -- Password [default: tiger123]" - echo " -i -- Install openjdk-1.8.0 and openssl" - echo - warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. -Please note that if the local machine does not have a java environment, some certificates generation will fail." - warn "If the option '-t' value is 'ssl_two_way', we should use the '-c' option at the same time." - exit 0 -} \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh b/tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh new file mode 100644 index 00000000..33f4fac0 --- /dev/null +++ b/tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh @@ -0,0 +1,255 @@ +#!/bin/bash + +cd $(dirname $0) +BASE_DIR=$(pwd) + +source_file() { + file=$1 + msg="$2" + src_flag=$3 + if [ -f "$file" ]; then + if [ "$src_flag" != "false" ]; then + source $file + fi + else + echo $(tput setaf 1) "[ERROR ]: $msg" $(tput sgr0) + exit 1 + fi +} + +# source all functions +source_file utils/pretty_print "No miss tools found, utils/pretty_print NOT exist, exit" true +source_file utils/env_utils "No miss tools found, utils/env_utils NOT exist, exit" true +source_file utils/ssl_utils "No miss tools found, utils/ssl_utils NOT exist, exit" true + +OSG=$(get_os) +OS=$(echo "$OSG" | cut -d' ' -f1) +version=$(echo "$OSG" | cut -d' ' -f2) +OSV="$OS$(echo "$version" | cut -d'.' -f1)" + +generate_root=${BASE_DIR}/SSL_files +CN=kafka-0.tigergraph.com +storetype=jks +pass=tiger123 +CARoot="" +CA_key="" +keystore="" +truststore="" +importCA="" + +CARoot_flag="" +subCA_flag="" +genKeystore_flag="" +genTruststore_flag="" +importToKeystore_flag="" +importToTruststore_flag="" +help_flag="" + +opt_string="hip:c:s:" +opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,import:,import_to_keystore,import_to_truststore,storetype:,keystore:,truststore:,cer:,cerKey:,CN:" +ARGS=`getopt -a -o $opt_string --long $opt_long_string -- "$@"` + +if [ $? != 0 ] ; then exit 1 ; fi +eval set -- "${ARGS}" +while : +do + case $1 in + -h|--help) + help_flag=true + ;; + --gen_CARoot) + CARoot_flag=true + ;; + --gen_subCA) + subCA_flag=true + ;; + --gen_keystore) + genKeystore_flag=true + ;; + --gen_truststore) + genTruststore_flag=true + ;; + --import_to_keystore) + importToKeystore_flag=true + ;; + --import_to_truststore) + importToTruststore_flag=true + ;; + --cer) + CARoot=`path_conver $2` + shift + ;; + --cerKey) + CA_key=`path_conver $2` + shift + ;; + --keystore) + keystore=`path_conver $2` + shift + ;; + --truststore) + truststore=`path_conver $2` + shift + ;; + --import) + importCA=`path_conver $2` + shift + ;; + -d|--directory) + generate_root=$2 + if [ ! -d ${generate_root} ]; then + error "The path '$generate_root' does not exist" + exit 1 + else + generate_root=`path_conver $generate_root`/SSL_files + fi + shift + ;; + -p|--passphrase) + pass=$2 + if [ ${#pass} -lt 6 ];then + error "Password is too short - must be at least 6 characters." + exit 1 + fi + shift + ;; + -c|--CN) + CN=$2 + shift + ;; + -s|--storetype) + storetype=$2 + shift + ;; + -i|--install) + SETUP_JDK=true + SETUP_OPENSSL=true + ;; + --) + shift + break + ;; + *) + error "${bldred}Invalid option, the correct usage is described below: $txtrst" + general_help + ;; + esac +shift +done + +if [[ ! -z $help_flag ]]; then + if [[ ! -z $CARoot_flag ]]; then + general_usage gen_CARoot + elif [[ ! -z $subCA_flag ]]; then + general_usage gen_subCA + elif [[ ! -z $genKeystore_flag ]]; then + general_usage gen_keystore + elif [[ ! -z $genTruststore_flag ]]; then + general_usage gen_truststore + elif [[ ! -z $importToKeystore_flag ]]; then + general_usage import_to_keystore + elif [[ ! -z $importToTruststore_flag ]]; then + general_usage import_to_truststore + else + general_help + fi + exit 0 +else + # this script only support rhel/centos + prog "Checking operation system (OS) version ..." + check_os $OS $version + + prog "Checking root/sudo ..." + check_root + + # Using option '-i/--install' will install openjdk-1.8.0 and openssl, + # otherwise openjdk-1.8.0 and openssl will not be installed + # install openJDK + install_openJDK + # install openssl + install_openssl + + if [[ ! -z $CARoot_flag ]]; then + prog "root-CA generate directory: $generate_root" + prog "root-CA subject CN: $CN" + CARoot=${generate_root}/ca-root.crt + CA_key=${generate_root}/ca-root.key + + check_file ${CARoot} 0 + check_file ${CA_key} 0 + generate_CARoot ${generate_root} $CN + fi + + if [[ ! -z $genKeystore_flag ]]; then + prog "keystore generate directory: $generate_root" + prog "keystore -Dname CN: $CN" + + generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server" + keystore=`ls -rt $(find ${generate_root} -type f -name "server.keystore*") | head -1` + prog "generate keystore: $keystore" + fi + + if [[ ! -z $subCA_flag ]]; then + prog "subordinate-CA generate directory: $generate_root" + if [ -z "${CARoot}" -o -z "${CA_key}" ]; then + error "Missing options: '-cer' or '-cerKey', exiting..." + general_usage gen_CARoot + exit 1 + else + check_CARoot ${CARoot} ${CA_key} + fi + + if [ -z "${keystore}" ]; then + generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server" + keystore=`find ${generate_root} -type f -name "server.keystore*" | head -1` + fi + + # generate sub-certificate + generate_subCA ${generate_root} ${keystore} ${CARoot} ${CA_key} ${CN} ${pass} + subCA=${CN}.crt + + prog "generate subordinate-CA: $subCA successfully" + fi + + if [[ ! -z $genTruststore_flag ]]; then + prog "truststore generate directory: $generate_root" + generate_truststore ${generate_root} "server" ${pass} ${storetype} + truststore=`ls -rt $(find ${generate_root} -type f -name "server.truststore*") | head -1` + prog "generate truststore: $truststore" + fi + + if [[ ! -z $importToKeystore_flag ]]; then + if [ -z "${keystore}" -o -z "${importCA}" ]; then + error "'-keystore' and '-import' are required options" + general_usage import_to_keystore + exit 1 + fi + alias=${importCA##*/} + alias=${alias%.*} + prog "import alias is ${alias}" + check_file ${keystore} 1 + check_file ${importCA} 1 + import_to_keystore ${keystore} ${importCA} ${alias} ${pass} + fi + + if [[ ! -z $importToTruststore_flag ]]; then + if [ -z "${truststore}" -o -z "${importCA}" ]; then + error "'-truststore' and '-import' are required options" + general_usage import_to_truststore + exit 1 + fi + alias=${importCA##*/} + alias=${alias%.*} + prog "import alias is ${alias}" + check_file ${truststore} 1 + check_file ${importCA} 1 + import_to_truststore ${truststore} ${importCA} ${alias} ${pass} + fi + + total_flag=($CARoot_flag $genKeystore_flag $subCA_flag $genTruststore_flag $importToKeystore_flag $importToTruststore_flag) + if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then + error "Please enter at least one Command" + general_help + exit 1 + fi +fi diff --git a/tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh b/tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh new file mode 100644 index 00000000..97a7e5d5 --- /dev/null +++ b/tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh @@ -0,0 +1,135 @@ +#!/bin/bash + +cd $(dirname $0) +BASE_DIR=$(pwd) + +source_file() { + file=$1 + msg="$2" + src_flag=$3 + if [ -f "$file" ]; then + if [ "$src_flag" != "false" ]; then + source $file + fi + else + echo $(tput setaf 1) "[ERROR ]: $msg" $(tput sgr0) + exit 1 + fi +} + +# source all functions +source_file utils/pretty_print "No miss tools found, utils/pretty_print NOT exist, exit" true +source_file utils/env_utils "No miss tools found, utils/env_utils NOT exist, exit" true +source_file utils/ssl_utils "No miss tools found, utils/ssl_utils NOT exist, exit" true + +OSG=$(get_os) +OS=$(echo "$OSG" | cut -d' ' -f1) +version=$(echo "$OSG" | cut -d' ' -f2) +OSV="$OS$(echo "$version" | cut -d'.' -f1)" + +generate_root=${BASE_DIR}/SSL_files +CN=kafka-0.tigergraph.com +storetype=jks +pass=tiger123 + +opt_string="hud:p:c:is:" +opt_long_string="help,usage,directory:,passphrase:,CN:,storetype:,install" +ARGS=`getopt -a -o $opt_string --long $opt_long_string -- "$@"` +if [ $? != 0 ] ; then exit 1 ; fi +eval set -- "${ARGS}" +while : +do + case $1 in + -h|--help) + help + exit 0 + ;; + -u|--usage) + usage + exit 0 + ;; + -d|--directory) + generate_root=$2 + if [ ! -d ${generate_root} ]; then + error "The path '$generate_root' does not exist" + exit 1 + else + generate_root=`path_conver $generate_root`/SSL_files + fi + shift + ;; + -p|--passphrase) + pass=$2 + if [ ${#pass} -lt 6 ];then + error "Password is too short - must be at least 6 characters." + exit 1 + fi + shift + ;; + -c|--CN) + CN=$2 + shift + ;; + -s|--storetype) + storetype=$2 + shift + ;; + -i|--install) + SETUP_JDK=true + SETUP_OPENSSL=true + ;; + --) + shift + break + ;; + *) + error "${bldred}Invalid option, the correct usage is described below: $txtrst" + help + ;; + esac +shift +done + +# this script only support rhel/centos +prog "Checking operation system (OS) version ..." +check_os $OS $version + +prog "Checking root/sudo ..." +check_root + +# Using option '-i/--install' will install openjdk-1.8.0 and openssl, +# otherwise openjdk-1.8.0 and openssl will not be installed +# install openJDK +install_openJDK +# install openssl +install_openssl + +# 1. generate CARoot and CA_key +rm -rf $generate_root +generate_CARoot ${generate_root} $CN +CARoot=${generate_root}/ca-root.crt +CA_key=${generate_root}/ca-root.key + +# 2. check CARoot and CA_key +check_CARoot ${CARoot} ${CA_key} + +# 3. generate keystore +generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server" +keystore=`find ${generate_root} -type f -name "server.keystore*" | head -1` + +# 4. generate sub-certificate +generate_subCA ${generate_root} ${keystore} ${CARoot} ${CA_key} ${CN} ${pass} +subCA=${CN}.crt + +# 5. import CARoot to keystore +import_to_keystore ${keystore} ${CARoot} "CARoot" ${pass} + +# 6. import sub-certificate to keystore +import_to_keystore ${keystore} ${subCA} ${CN} ${pass} + +# 7. generate truststore +generate_truststore ${generate_root} "server" ${pass} ${storetype} +truststore=`find ${generate_root} -type f -name "server.truststore*" | head -1` + +# 8. import CARoot to truststore +import_to_truststore ${truststore} ${CARoot} "CARoot" ${pass} \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils new file mode 100644 index 00000000..42088676 --- /dev/null +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -0,0 +1,306 @@ +#!/bin/bash + +get_os(){ + if [ -f "/etc/apt/sources.list" ]; then + if [ -f "/etc/linx-release" ]; then + os_version=$(cat /etc/linx-release | grep -o '[0-9]\.[0-9]\.[0-9]\{1,3\}' ) + echo "ROCKY $os_version" + elif [ -f "/etc/lsb-release" ]; then + os_version=$(cat /etc/lsb-release | grep "DISTRIB_RELEASE" | cut -d= -f2) + echo "UBUNTU $os_version" + elif [ -f "/etc/os-release" ]; then + os_version=$(cat /etc/os-release | grep "VERSION_ID" | cut -d= -f2) + os_version=${os_version//\"} # remove all double quotes + echo "DEBIAN $os_version" + fi + elif [ -d "/etc/yum.repos.d" ]; then + # Centos and RedHat are treated equally + if grep "Amazon Linux" /etc/system-release &>/dev/null; then + os_version=" 7.0" + else + variant="$(cat /etc/system-release | cut -d ' ' -f2)" + if [ "$variant" = "Stream" ]; then + os_version=" $(cat /etc/os-release | grep 'VERSION_ID=' | cut -d'"' -f 2)" + else + os_version="$(cat /etc/system-release | grep -o ' [0-9]\.[0-9]\{1,3\}')" + fi + fi + echo "RHEL$os_version" + elif [ -d "/etc/zypp/repos.d" ]; then + os_version=$(cat /etc/os-release | grep "VERSION_ID" | cut -d= -f2) + os_version=${os_version//\"} # remove all double quotes + echo "SUSE $os_version" + else + echo "UNKOWN OS" + fi +} + +check_os(){ + OS=$1 + version=$2 + note "OS obtained: $OS $version" + local error_msg="Unsupported OS. Current support CentOS 6.5 to 8.0; RedHat 6.5 to 9.0;" + if [ -z "$version" ]; then + error "Unknown OS version. $error_msg" + exit 1 + fi + + if [ "$OS" = "RHEL" ]; then + # the following one will end with one item array on docker centos 7.3, i.e. "${ver_arr[0]}" is "7 3" + # local ver_arr=(${version//./ }) + IFS='.' read -r -a ver_arr <<< "$version" + if [[ "${ver_arr[0]}" -lt "6" || "${ver_arr[0]}" -eq "6" && "${ver_arr[1]}" -lt "5" ]]; then + error "$error_msg" + exit 1 + else + note "OS check passed [OK]" + fi + else + error "$error_msg" + exit 1 + fi +} + +check_root(){ + if [[ $EUID -ne 0 ]]; then + error "Sudo or root rights are required." + exit 1 + fi +} + +install_openJDK(){ + if [[ "${SETUP_JDK}" == "true" ]]; then + if ! which java > /dev/null 2>&1; then + prog "start install openjdk-1.8.0." + yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + else + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + if [[ $java_version != "1.8.0" ]];then + prog "start update to openjdk-1.8.0." + rpm -qa | grep java | xargs rpm -e --nodeps + yum install -y java-1.8.0-openjdk > /dev/null 2>&1 + else + prog "The java version is openjdk-1.8.0 now." + fi + fi + # check install + if command -v java &> /dev/null;then + prog "JDK Install Success..." + else + error "JDK Install Fail..." && exit 1 + fi + + else + if ! which java > /dev/null 2>&1; then + error "Java environment not detected. You can choose option \"-i\" to install openjdk-1.8.0." + exit 1 + else + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + if [[ $java_version != "1.8.0" ]];then + error "This script currently only supports openjdk-1.8.0." + exit 1 + else + prog "The java version is openjdk-1.8.0 now." + fi + fi + fi +} + +install_openssl(){ + if [[ "${SETUP_OPENSSL}" == "true" ]]; then + if ! openssl version > /dev/null 2>&1;then + prog "start install openssl..." + yum -y install openssl > /dev/null 2>&1 + else + prog "Openssl is installed, skip installation." + fi + + if [ $? != 0 ]; then + error "Failed to install openssl." + exit 1 + fi + else + if ! openssl version > /dev/null 2>&1;then + error "Openssl is not installed. You can choose option \"-i\" to install openssl." + exit 1 + else + prog "Openssl is installed." + fi + fi +} + +path_conver(){ + relativePath=$1 + firstChar=${relativePath: 0: 1} + + if [[ "$firstChar" == "" ]]; then + echo "relative-path(\$1) is null" + exit 1 + elif [[ "$firstChar" == "/" ]]; then + echo $relativePath + exit 0 + fi + + tmpPath1=`dirname $relativePath` + tmpFullpath1=`cd $tmpPath1 && pwd` + tmpPath2=`basename $relativePath` + + echo ${tmpFullpath1}/${tmpPath2} +} + +check_file(){ + file=$1 + type=$2 + if [ -f "$file" ];then + if [[ "${type}" == "0" ]]; then + error "$file already exists, exit." + exit 1 + fi + elif [[ "${type}" == "1" || "${type}" == "" ]]; then + error "$file not exist, exit." + exit 1 + fi +} + +help(){ + echo + echo "Usage:" + mesg_green "./`basename $0` [-d ] [-c ][-p ] [-s ] [-i]" + mesg_green "./`basename $0` [-d ] [-c ][-p ] [-s ]" + mesg_green "./`basename $0` -h" + mesg_green "./`basename $0` -u" + echo "Options:" + echo " -h,-help -- Show the help" + echo " -u,-usage -- Usage example" + echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" + echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo " -s,-storetype -- Keystore/Truststore storetype, e.g. jks, pkcs12 [default: jks]" + echo " -i,-install -- Install openjdk-1.8.0 and openssl" + echo + warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. +Please note that if the local machine does not have a java environment, some certificates generation will fail." + exit 0 +} + +usage(){ + echo "${bldblu}./`basename $0` -d ./SSL_files -p tiger123 -c kafka-0.tigergraph.com -s pkcs12 -i $txtrst" + echo "${bldblu}./`basename $0` -d ./SSL_files -p tiger123 -c kafka-0.tigergraph.com -s jks $txtrst" + echo "${bldblu}./`basename $0` -directory ./SSL_files -passphrase tiger123 -CN kafka-0.tigergraph.com -storetype pkcs12 -install $txtrst" + echo "${bldblu}./`basename $0` -i" + echo "${bldblu}./`basename $0` $txtrst" +} + +general_help(){ + echo + echo "Commands:" + echo " -h,-help -- Show the help" + echo " -gen_CARoot -- Generate root CA and private_key" + echo " -gen_keystore -- Generate an empty keystore" + echo " -gen_truststore -- Generate truststore" + echo " -gen_subCA -- Generate subordinate CA through root CA" + echo " -import_to_keystore -- Import CA to keystore" + echo " -import_to_truststore -- Import CA to truststore" + echo + warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. + Please note that if the local machine does not have a java environment, some certificates generation will fail." + echo + warn "Use './`basename $0` -command_name -help' for usage of command_name" + exit 0 +} + +general_usage(){ + usage_flag=$1 + case $usage_flag in + gen_CARoot) + echo + echo "Usage:" + mesg_green "./`basename $0` [--gen_CARoot] [-d ] [-c ]" + mesg_green "./`basename $0` --gen_CARoot -d ./SSL_file -c kafka-0.tigergraph.com" + mesg_green "./`basename $0` --gen_CARoot -c kafka-0.tigergraph.com" + echo "Options:" + echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" + echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + exit 0 + ;; + gen_keystore) + echo + echo "Usage:" + mesg_green "./`basename $0` [--gen_keystore] [-d ] [-p ] [-s ]" + echo "Example:" + mesg_green "./`basename $0` --gen_keystore -d ./SSL_files -p tiger123 -s pkcs12" + mesg_green "./`basename $0` --gen_keystore -p tiger123" + mesg_green "./`basename $0` --gen_keystore -s jks" + mesg_green "./`basename $0` --gen_keystore" + echo + echo "Options:" + echo " -d,-directory -- Generation Path [default: ./SSL_files]" + echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo " -s,-storetype -- Keystore storetype, e.g. jks, pkcs12 [default: jks]" + echo + exit 0 + ;; + gen_subCA) + echo + echo "Usage:" + mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-keystore ] [-c ] [-p ]" + mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-c ] [-p ]" + mesg_green "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-key.pem -keystore ./SSL_files/server.keystore.jks -c kafka-0.tigergraph.com -p tiger123" + mesg_green "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-key.pem -c kafka-0.tigergraph.com -p tiger123" + echo "Options:" + echo " -d,-directory -- Generation Path [default: ./SSL_files]" + echo " -cer,--cer -- Root-CA used to sign subordinate certificate" + echo " -cerKey -- Root-CA key file" + echo " -keystore -- Keystore path, if you have a keystore, you can ignore this option" + echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + exit 0 + ;; + gen_truststore) + echo + echo "Usage:" + mesg_green "./`basename $0` [--gen_truststore] [-d ] [-c ] [-p ] [-s ]" + mesg_green "./`basename $0` --gen_truststore -d ./SSL_file -c kafka-0.tigergraph.com -p tiger123 -s pkcs12" + mesg_green "./`basename $0` --gen_truststore -c kafka-0.tigergraph.com -p tiger123" + echo "Options:" + echo " -d,-directory -- Generation Path [default: ./SSL_files]" + echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo " -s,-storetype -- Truststore storetype, e.g. jks, pkcs12 [default: jks]" + exit 0 + ;; + import_to_keystore) + echo + echo "Usage:" + mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" + mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" + echo "Example:" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore.jks -import ca-root.crt -p tiger123" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore.jks -import kafka-0.tigergraph.com.crt -passphrase tiger123" + echo + echo "Options:" + echo " -keystore -- Keystore path" + echo " -import -- Certificate to import" + echo " -p,-passphrase -- Keystore storepass and keypass [default: tiger123]" + echo + exit 0 + ;; + import_to_truststore) + echo + echo "Usage:" + mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" + mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" + echo "Example:" + mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore.jks -import ca-root.crt -p tiger123" + mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore.jks -import client.crt -passphrase tiger123" + echo + echo "Options:" + echo " -truststore -- Truststore path" + echo " -import -- Certificate to import" + echo " -p,-passphrase -- Truststore storepass and keypass [default: tiger123]" + echo + exit 0 + ;; + esac + +} diff --git a/tools/kafka_sasl_ssl/generate_ssl_CA/utils/pretty_print b/tools/kafka_ssl/generate_ssl_CA/utils/pretty_print similarity index 100% rename from tools/kafka_sasl_ssl/generate_ssl_CA/utils/pretty_print rename to tools/kafka_ssl/generate_ssl_CA/utils/pretty_print diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils new file mode 100644 index 00000000..f268e100 --- /dev/null +++ b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils @@ -0,0 +1,164 @@ +#!/bin/bash + +generate_CARoot(){ + local generate_root=$1 + local CN=$2 + + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + if [ -z "$CN" ]; then + error "subject CN is empty" + exit 1 + fi + + prog "start creating certificate authority(CA) for signing..." + prog "CARoot path: ${generate_root}/ca-root.crt" + prog "private_key path: ${generate_root}/ca-root.key" + openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/CN=$CN" +} + +check_CARoot(){ + local CA_Crt=$1 + local privateKey=$2 + + if [ ! -f $CA_Crt ];then + error "CA certificate does not exist." + exit 1 + elif [ ! -f $privateKey ];then + error "CA key file does not exist." + exit 1 + fi + + prog "Start checking certificate validity..." + if openssl verify -CApath CApath $CA_Crt | grep "OK" > /dev/null;then + prog "CA certificate validation passed." + else + error "Non-valid CA certificate:$CA_Crt" + exit 1 + fi + + # Verify whether the CARoot matches the private_key file + # Calculate the md5 value + crtMD5=$(openssl x509 -noout -modulus -in $CA_Crt | openssl md5 | awk -F"=" '{print $NF}') + privateKeyMD5=$(openssl rsa -noout -modulus -in $privateKey | openssl md5 | awk -F"=" '{print $NF}') + + if [ "$crtMD5" = "$privateKeyMD5" ]; then + prog "CA certificate and private key match successfully." + else + error "CA certificate($CA_Crt) and private key($privateKey) do not match." + exit 1 + fi +} + +### generate an empty keystore +# 1. default storetype is JKS +# 2. validity is 365 +generate_keystore(){ + local genRoot=$1 + local pass=$2 + local CN=$3 + local storetype=$4 + local keystoreName=$5 + + if [ ! -d ${genRoot} ]; then + mkdir -p ${genRoot} + fi + + cd $genRoot + prog "start creating keystore..." + case $storetype in + pkcs12|PKCS12|pk12|PK12|p12|P12) + prog "The storetype of keystore is pkcs12." + keytool -genkey -keystore ${keystoreName}.keystore.p12 -validity 365 -storepass $pass -keypass $pass -dname "CN=$CN" -storetype pkcs12 + # delete default Key-pair, the alias is 'mykey' + keytool -delete -alias mykey -keystore ${keystoreName}.keystore.p12 -storepass ${pass} + ;; + JKS|jks) + prog "The storetype of keystore is JKS." + keytool -keystore ${keystoreName}.keystore.jks -validity 365 -genkey -keyalg RSA -dname "CN=$CN" -storepass ${pass} -keypass ${pass} -storetype jks + keytool -delete -alias mykey -keystore ${keystoreName}.keystore.jks -storepass ${pass} + ;; + *) + prog "The default storetype of keystore is JKS." + keytool -keystore ${keystoreName}.keystore.jks -validity 365 -genkey -keyalg RSA -dname "CN=$CN" -storepass ${pass} -keypass ${pass} + keytool -delete -alias mykey -keystore ${keystoreName}.keystore.jks -storepass ${pass} + ;; + esac +} + +generate_subCA(){ + local generate_root=$1 + local keystore=$2 + local CA_root=$3 + local CA_key=$4 + local subCA_name=$5 + local pass=$6 + + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + prog "start creating certificate signing request (CSR)..." + keytool -keystore ${keystore} -certreq -file ${subCA_name}.csr -storepass ${pass} -keypass ${pass} + + prog "sign sub-certificate through ca-root..." + openssl x509 -req -CA ${CA_root} -CAkey ${CA_key} -in ${subCA_name}.csr -out ${subCA_name}.crt -days 365 -CAcreateserial +} + +import_to_keystore(){ + local keystore=$1 + local import_file=$2 + local alias=$3 + local pass=$4 + + prog "import ${import_file} to keystore: ${keystore}" + keytool -keystore ${keystore} -alias ${alias} -import -file ${import_file} -storepass ${pass} -keypass ${pass} -noprompt +} + +# at least one CA file is required to generate truststore +generate_truststore(){ + local generate_root=$1 + local truststoreName=$2 + local pass=$3 + local storetype=$4 + local firstFile=${generate_root}/firstCA.crt + + if [ ! -d ${generate_root} ]; then + mkdir -p ${generate_root} + fi + + cd $generate_root + if [ ! -f "$firstFile" ]; then + openssl req -nodes -new -x509 -keyout firstCA.key -out firstCA.crt -days 365 -subj "/CN=myFirstCA" + fi + + prog "start creating truststore and import one CA..." + case $storetype in + pkcs12|PKCS12|pk12|PK12|p12|P12) + prog "The storetype of keystore is pkcs12." + prog "import ${firstFile} to truststore ${generate_root}/${truststoreName}.truststore.p12" + keytool -keystore ${truststoreName}.truststore.p12 -alias myfirstCA -import -file ${firstFile} -storepass ${pass} -keypass ${pass} -storetype pkcs12 -noprompt + ;; + *) + prog "The default storetype of keystore is JKS." + prog "import ${firstFile} to truststore ${generate_root}/${truststoreName}.truststore.jks" + keytool -keystore ${truststoreName}.truststore.jks -alias myfirstCA -import -file ${firstFile} -storepass ${pass} -keypass ${pass} -storetype jks -noprompt + ;; + esac + + rm -rf firstCA* +} + +import_to_truststore(){ + local truststore=$1 + local import_file=$2 + local alias=$3 + local pass=$4 + + prog "import ${import_file} to truststore: ${truststore}" + keytool -keystore ${truststore} -alias ${alias} -import -file ${import_file} -storepass ${pass} -keypass ${pass} -noprompt +} \ No newline at end of file From 00f30e03e673b151d712aa87cdec83768bc80cea Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Thu, 16 Feb 2023 16:18:33 +0800 Subject: [PATCH 07/19] QA-4212 add universal script for ssl --- .../{generate_new_ssl.sh => ssl_generate.sh} | 8 +- .../{general_ssl_script.sh => ssl_renewal.sh} | 116 ++++++++++-------- .../kafka_ssl/generate_ssl_CA/utils/env_utils | 49 +++++--- .../kafka_ssl/generate_ssl_CA/utils/ssl_utils | 57 ++++++--- 4 files changed, 136 insertions(+), 94 deletions(-) rename tools/kafka_ssl/generate_ssl_CA/{generate_new_ssl.sh => ssl_generate.sh} (93%) rename tools/kafka_ssl/generate_ssl_CA/{general_ssl_script.sh => ssl_renewal.sh} (62%) diff --git a/tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh similarity index 93% rename from tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh rename to tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh index 97a7e5d5..256ad774 100644 --- a/tools/kafka_ssl/generate_ssl_CA/generate_new_ssl.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh @@ -114,8 +114,8 @@ CA_key=${generate_root}/ca-root.key check_CARoot ${CARoot} ${CA_key} # 3. generate keystore -generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server" -keystore=`find ${generate_root} -type f -name "server.keystore*" | head -1` +generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server.keystore" +keystore=server.keystore # 4. generate sub-certificate generate_subCA ${generate_root} ${keystore} ${CARoot} ${CA_key} ${CN} ${pass} @@ -128,8 +128,8 @@ import_to_keystore ${keystore} ${CARoot} "CARoot" ${pass} import_to_keystore ${keystore} ${subCA} ${CN} ${pass} # 7. generate truststore -generate_truststore ${generate_root} "server" ${pass} ${storetype} -truststore=`find ${generate_root} -type f -name "server.truststore*" | head -1` +generate_truststore ${generate_root} "server.truststore" ${pass} ${storetype} +truststore=server.truststore # 8. import CARoot to truststore import_to_truststore ${truststore} ${CARoot} "CARoot" ${pass} \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh similarity index 62% rename from tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh rename to tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh index 33f4fac0..e9f071c9 100644 --- a/tools/kafka_ssl/generate_ssl_CA/general_ssl_script.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh @@ -45,8 +45,8 @@ importToKeystore_flag="" importToTruststore_flag="" help_flag="" -opt_string="hip:c:s:" -opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,import:,import_to_keystore,import_to_truststore,storetype:,keystore:,truststore:,cer:,cerKey:,CN:" +opt_string="hip:c:s:d:" +opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,directory:,import:,import_to_keystore,import_to_truststore,storetype:,keystore:,truststore:,cer:,cerKey:,CN:" ARGS=`getopt -a -o $opt_string --long $opt_long_string -- "$@"` if [ $? != 0 ] ; then exit 1 ; fi @@ -169,6 +169,7 @@ else # install openssl install_openssl + # generate root CA if [[ ! -z $CARoot_flag ]]; then prog "root-CA generate directory: $generate_root" prog "root-CA subject CN: $CN" @@ -180,76 +181,89 @@ else generate_CARoot ${generate_root} $CN fi + # generate keystore if [[ ! -z $genKeystore_flag ]]; then prog "keystore generate directory: $generate_root" - prog "keystore -Dname CN: $CN" - - generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server" - keystore=`ls -rt $(find ${generate_root} -type f -name "server.keystore*") | head -1` - prog "generate keystore: $keystore" + prog "Keystore -Dname CN: $CN" + generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server.keystore" + keystore=${generate_root}/server.keystore + prog "Generate keystore: $keystore" + note "View keystore: keytool -list -v -keystore $keystore -storepass $pass" fi + # generate a sub-certificate using the keytool if [[ ! -z $subCA_flag ]]; then - prog "subordinate-CA generate directory: $generate_root" - if [ -z "${CARoot}" -o -z "${CA_key}" ]; then - error "Missing options: '-cer' or '-cerKey', exiting..." - general_usage gen_CARoot - exit 1 - else - check_CARoot ${CARoot} ${CA_key} - fi - - if [ -z "${keystore}" ]; then - generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server" - keystore=`find ${generate_root} -type f -name "server.keystore*" | head -1` + prog "Subordinate-CA generate directory: $generate_root" + if [[ -z "$CARoot" || -z "$CA_key" ]]; then + error "Missing options: '-cer' or '-cerKey', exiting..." + general_usage gen_subCA + exit 1 fi - # generate sub-certificate - generate_subCA ${generate_root} ${keystore} ${CARoot} ${CA_key} ${CN} ${pass} - subCA=${CN}.crt + check_CARoot $CARoot $CA_key - prog "generate subordinate-CA: $subCA successfully" + # Generate keystore + if [[ -z "$keystore" ]]; then + keystore=${generate_root}/server.keystore + note "Use keytool to generate CRS: If no keystore is provided, a new keystore will be created, CN=${CN}" + note "Default keystore: $keystore" + if [ -f "$keystore" ];then + check_keystore $keystore $pass + keystoreType=$(keytool -list -v -keystore $keystore -storepass $pass |& awk '/Keystore type/{print $NF}') + else + keystoreType=$storetype + fi + generate_keystore $generate_root $pass $CN $keystoreType "server.keystore" + else + check_keystore $keystore $pass + keystoreType=$(keytool -list -v -keystore $keystore -storepass $pass |& awk '/Keystore type/{print $NF}') + keystoreName=${keystore##*/} + generate_keystore $generate_root $pass $CN $keystoreType $keystoreName + fi + generate_subCA $generate_root $keystore $CARoot $CA_key $CN $pass + prog "Generate subordinate-CA: ${CN}.crt successfully" fi - if [[ ! -z $genTruststore_flag ]]; then - prog "truststore generate directory: $generate_root" - generate_truststore ${generate_root} "server" ${pass} ${storetype} - truststore=`ls -rt $(find ${generate_root} -type f -name "server.truststore*") | head -1` - prog "generate truststore: $truststore" + # generate truststore + if [[ ! -z ${genTruststore_flag:-} ]]; then + local truststore="${generate_root}/server.truststore" + if [ ! -f "${truststore}" ]; then + prog "truststore generate directory: ${generate_root}" + generate_truststore "${generate_root}" "server.truststore" "${pass}" "${storetype}" + fi + prog "generate truststore: ${truststore}" + note "View truststore: keytool -list -v -keystore ${truststore} -storepass ${pass}" fi + # import CA to keystore if [[ ! -z $importToKeystore_flag ]]; then - if [ -z "${keystore}" -o -z "${importCA}" ]; then - error "'-keystore' and '-import' are required options" - general_usage import_to_keystore - exit 1 - fi - alias=${importCA##*/} - alias=${alias%.*} - prog "import alias is ${alias}" - check_file ${keystore} 1 - check_file ${importCA} 1 - import_to_keystore ${keystore} ${importCA} ${alias} ${pass} + [ -z "${keystore}${importCA}" ] \ + && { error "'-keystore' and '-import' are required options"; general_usage import_to_keystore; exit 1; } + alias=${importCA##*/} + alias=${alias%.*} + prog "Import alias is ${alias}" + check_file ${keystore} 1 + check_file ${importCA} 1 + import_to_keystore ${keystore} ${importCA} ${alias} ${pass} fi + # import CA to truststore if [[ ! -z $importToTruststore_flag ]]; then - if [ -z "${truststore}" -o -z "${importCA}" ]; then - error "'-truststore' and '-import' are required options" - general_usage import_to_truststore - exit 1 - fi - alias=${importCA##*/} - alias=${alias%.*} - prog "import alias is ${alias}" - check_file ${truststore} 1 - check_file ${importCA} 1 - import_to_truststore ${truststore} ${importCA} ${alias} ${pass} + [ -z "${truststore}${importCA}" ] \ + && { error "'-truststore' and '-import' are required options"; general_usage import_to_truststore; exit 1; } + alias=${importCA##*/} + alias=${alias%.*} + prog "Import alias is ${alias}" + check_file ${truststore} 1 + check_file ${importCA} 1 + import_to_truststore ${truststore} ${importCA} ${alias} ${pass} fi + # enter at least one command total_flag=($CARoot_flag $genKeystore_flag $subCA_flag $genTruststore_flag $importToKeystore_flag $importToTruststore_flag) if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then error "Please enter at least one Command" general_help exit 1 fi -fi +fi \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 42088676..2cc47fb1 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -205,7 +205,7 @@ general_help(){ warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. Please note that if the local machine does not have a java environment, some certificates generation will fail." echo - warn "Use './`basename $0` -command_name -help' for usage of command_name" + note "Use './`basename $0` -command_name -help' for usage of command_name" exit 0 } @@ -216,27 +216,31 @@ general_usage(){ echo echo "Usage:" mesg_green "./`basename $0` [--gen_CARoot] [-d ] [-c ]" - mesg_green "./`basename $0` --gen_CARoot -d ./SSL_file -c kafka-0.tigergraph.com" - mesg_green "./`basename $0` --gen_CARoot -c kafka-0.tigergraph.com" + echo "Example:" + mesg_blue "./`basename $0` --gen_CARoot -d ./SSL_files -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_CARoot -c kafka-0.tigergraph.com" + echo echo "Options:" echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + echo exit 0 ;; gen_keystore) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_keystore] [-d ] [-p ] [-s ]" + mesg_green "./`basename $0` [--gen_keystore] [-d ] [-p ] [-s ] [-c ]" echo "Example:" - mesg_green "./`basename $0` --gen_keystore -d ./SSL_files -p tiger123 -s pkcs12" - mesg_green "./`basename $0` --gen_keystore -p tiger123" - mesg_green "./`basename $0` --gen_keystore -s jks" - mesg_green "./`basename $0` --gen_keystore" + mesg_blue "./`basename $0` --gen_keystore -d ./SSL_files -p tiger123 -s pkcs12 -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_keystore -p tiger123 -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_keystore -s jks" + mesg_blue "./`basename $0` --gen_keystore" echo echo "Options:" echo " -d,-directory -- Generation Path [default: ./SSL_files]" echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" echo " -s,-storetype -- Keystore storetype, e.g. jks, pkcs12 [default: jks]" + echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" echo exit 0 ;; @@ -245,28 +249,34 @@ general_usage(){ echo "Usage:" mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-keystore ] [-c ] [-p ]" mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-c ] [-p ]" - mesg_green "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-key.pem -keystore ./SSL_files/server.keystore.jks -c kafka-0.tigergraph.com -p tiger123" - mesg_green "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-key.pem -c kafka-0.tigergraph.com -p tiger123" + echo "Example:" + mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.key -keystore ./SSL_files/server.keystore.jks -c kafka-0.tigergraph.com -p tiger123" + mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.pem -c kafka-0.tigergraph.com -p tiger123" + echo echo "Options:" echo " -d,-directory -- Generation Path [default: ./SSL_files]" echo " -cer,--cer -- Root-CA used to sign subordinate certificate" echo " -cerKey -- Root-CA key file" - echo " -keystore -- Keystore path, if you have a keystore, you can ignore this option" + echo " -keystore -- Keystore path, if not provided, a default keystore will be generated" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo exit 0 ;; gen_truststore) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_truststore] [-d ] [-c ] [-p ] [-s ]" - mesg_green "./`basename $0` --gen_truststore -d ./SSL_file -c kafka-0.tigergraph.com -p tiger123 -s pkcs12" - mesg_green "./`basename $0` --gen_truststore -c kafka-0.tigergraph.com -p tiger123" + mesg_green "./`basename $0` [--gen_truststore] [-d ] [-p ] [-s ]" + echo "Example:" + mesg_blue "./`basename $0` --gen_truststore -d ./SSL_file -p tiger123 -s pkcs12" + mesg_blue "./`basename $0` --gen_truststore -c kafka-0.tigergraph.com -p tiger123" + mesg_blue "./`basename $0` --gen_truststore" + echo echo "Options:" echo " -d,-directory -- Generation Path [default: ./SSL_files]" - echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" echo " -s,-storetype -- Truststore storetype, e.g. jks, pkcs12 [default: jks]" + echo exit 0 ;; import_to_keystore) @@ -275,8 +285,8 @@ general_usage(){ mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" echo "Example:" - mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore.jks -import ca-root.crt -p tiger123" - mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore.jks -import kafka-0.tigergraph.com.crt -passphrase tiger123" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -import ./SSL_files/ca-root.crt -p tiger123" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -import ./SSL_files/kafka-0.tigergraph.com.crt -passphrase tiger123" echo echo "Options:" echo " -keystore -- Keystore path" @@ -291,8 +301,8 @@ general_usage(){ mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" echo "Example:" - mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore.jks -import ca-root.crt -p tiger123" - mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore.jks -import client.crt -passphrase tiger123" + mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -import ./SSL_files/ca-root.crt -p tiger123" + mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -import ./SSL_files/client.crt -passphrase tiger123" echo echo "Options:" echo " -truststore -- Truststore path" @@ -302,5 +312,4 @@ general_usage(){ exit 0 ;; esac - } diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils index f268e100..74251f3f 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils @@ -14,7 +14,7 @@ generate_CARoot(){ exit 1 fi - prog "start creating certificate authority(CA) for signing..." + prog "Start creating certificate authority(CA) for signing..." prog "CARoot path: ${generate_root}/ca-root.crt" prog "private_key path: ${generate_root}/ca-root.key" openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/CN=$CN" @@ -68,25 +68,39 @@ generate_keystore(){ fi cd $genRoot - prog "start creating keystore..." + prog "Start creating keystore..." case $storetype in pkcs12|PKCS12|pk12|PK12|p12|P12) prog "The storetype of keystore is pkcs12." - keytool -genkey -keystore ${keystoreName}.keystore.p12 -validity 365 -storepass $pass -keypass $pass -dname "CN=$CN" -storetype pkcs12 - # delete default Key-pair, the alias is 'mykey' - keytool -delete -alias mykey -keystore ${keystoreName}.keystore.p12 -storepass ${pass} - ;; - JKS|jks) - prog "The storetype of keystore is JKS." - keytool -keystore ${keystoreName}.keystore.jks -validity 365 -genkey -keyalg RSA -dname "CN=$CN" -storepass ${pass} -keypass ${pass} -storetype jks - keytool -delete -alias mykey -keystore ${keystoreName}.keystore.jks -storepass ${pass} + keytool -genkey -keystore ${keystoreName} -validity 365 -storepass $pass -keypass $pass -dname "CN=$CN" -alias $CN -storetype pkcs12 ;; *) prog "The default storetype of keystore is JKS." - keytool -keystore ${keystoreName}.keystore.jks -validity 365 -genkey -keyalg RSA -dname "CN=$CN" -storepass ${pass} -keypass ${pass} - keytool -delete -alias mykey -keystore ${keystoreName}.keystore.jks -storepass ${pass} + keytool -keystore ${keystoreName} -validity 365 -genkey -keyalg RSA -dname "CN=$CN" -alias $CN -storepass ${pass} -keypass ${pass} -storetype jks ;; esac + + if [ $? -ne 0 ]; then + exit 1 + fi +} + +check_keystore(){ + local keystore=$1 + local pass=$2 + local keystoreType="" + + if [ -f "$keystore" ]; then + keystoreType=$(keytool -list -v -keystore $keystore -storepass $pass |& awk '/Keystore type/{print $NF}') + else + error "$keystore does not exist" + exit 1 + fi + + if [[ $keystoreType != "jks" && $keystoreType != "PKCS12" ]]; then + error "$keystore is not a supported keystore type (JKS or PKCS12)" + exit 1 + fi } generate_subCA(){ @@ -102,8 +116,8 @@ generate_subCA(){ fi cd $generate_root - prog "start creating certificate signing request (CSR)..." - keytool -keystore ${keystore} -certreq -file ${subCA_name}.csr -storepass ${pass} -keypass ${pass} + prog "Start creating certificate signing request (CSR)..." + keytool -keystore ${keystore} -alias ${subCA_name} -certreq -file ${subCA_name}.csr -storepass ${pass} -keypass ${pass} prog "sign sub-certificate through ca-root..." openssl x509 -req -CA ${CA_root} -CAkey ${CA_key} -in ${subCA_name}.csr -out ${subCA_name}.crt -days 365 -CAcreateserial @@ -116,6 +130,7 @@ import_to_keystore(){ local pass=$4 prog "import ${import_file} to keystore: ${keystore}" + note "How to check whether the certificate already exists: keytool -list -v -keystore ${keystore} -storepass ${pass}" keytool -keystore ${keystore} -alias ${alias} -import -file ${import_file} -storepass ${pass} -keypass ${pass} -noprompt } @@ -136,20 +151,23 @@ generate_truststore(){ openssl req -nodes -new -x509 -keyout firstCA.key -out firstCA.crt -days 365 -subj "/CN=myFirstCA" fi - prog "start creating truststore and import one CA..." + prog "Start creating truststore and import one CA..." case $storetype in pkcs12|PKCS12|pk12|PK12|p12|P12) prog "The storetype of keystore is pkcs12." - prog "import ${firstFile} to truststore ${generate_root}/${truststoreName}.truststore.p12" - keytool -keystore ${truststoreName}.truststore.p12 -alias myfirstCA -import -file ${firstFile} -storepass ${pass} -keypass ${pass} -storetype pkcs12 -noprompt + keytool -keystore ${truststoreName} -alias myfirstCA -import -file ${firstFile} -storepass ${pass} -keypass ${pass} -storetype pkcs12 -noprompt ;; *) prog "The default storetype of keystore is JKS." - prog "import ${firstFile} to truststore ${generate_root}/${truststoreName}.truststore.jks" - keytool -keystore ${truststoreName}.truststore.jks -alias myfirstCA -import -file ${firstFile} -storepass ${pass} -keypass ${pass} -storetype jks -noprompt + keytool -keystore ${truststoreName} -alias myfirstCA -import -file ${firstFile} -storepass ${pass} -keypass ${pass} -storetype jks -noprompt ;; esac + if [ $? -ne 0 ]; then + rm -rf firstCA* + exit 1 + fi + rm -rf firstCA* } @@ -160,5 +178,6 @@ import_to_truststore(){ local pass=$4 prog "import ${import_file} to truststore: ${truststore}" + note "How to check whether the certificate already exists: keytool -list -v -keystore ${truststore} -storepass ${pass}" keytool -keystore ${truststore} -alias ${alias} -import -file ${import_file} -storepass ${pass} -keypass ${pass} -noprompt } \ No newline at end of file From 7ce1ff30ef0681c39e741b7cd43830b317ee83b2 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Thu, 16 Feb 2023 16:38:14 +0800 Subject: [PATCH 08/19] QA-4212 modify example --- tools/kafka_ssl/generate_ssl_CA/utils/env_utils | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 2cc47fb1..37f800f7 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -269,7 +269,7 @@ general_usage(){ mesg_green "./`basename $0` [--gen_truststore] [-d ] [-p ] [-s ]" echo "Example:" mesg_blue "./`basename $0` --gen_truststore -d ./SSL_file -p tiger123 -s pkcs12" - mesg_blue "./`basename $0` --gen_truststore -c kafka-0.tigergraph.com -p tiger123" + mesg_blue "./`basename $0` --gen_truststore -p tiger123" mesg_blue "./`basename $0` --gen_truststore" echo echo "Options:" From 835f6bf833e9156cfb926b28e17e1c03f9ce86fe Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Thu, 16 Feb 2023 16:47:05 +0800 Subject: [PATCH 09/19] QA-4212 update usage --- tools/kafka_ssl/generate_ssl_CA/utils/env_utils | 2 -- 1 file changed, 2 deletions(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 37f800f7..7cbcedc0 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -283,7 +283,6 @@ general_usage(){ echo echo "Usage:" mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" - mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" echo "Example:" mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -import ./SSL_files/ca-root.crt -p tiger123" mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -import ./SSL_files/kafka-0.tigergraph.com.crt -passphrase tiger123" @@ -299,7 +298,6 @@ general_usage(){ echo echo "Usage:" mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" - mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" echo "Example:" mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -import ./SSL_files/ca-root.crt -p tiger123" mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -import ./SSL_files/client.crt -passphrase tiger123" From d09ad14582016f99f6ce933209c5d4ed2cf9a088 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Thu, 16 Feb 2023 17:20:52 +0800 Subject: [PATCH 10/19] QA-4212 delete the firstCA in truststore --- tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh index e9f071c9..8a91c031 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh @@ -226,13 +226,13 @@ else # generate truststore if [[ ! -z ${genTruststore_flag:-} ]]; then - local truststore="${generate_root}/server.truststore" + truststore="${generate_root}/server.truststore" if [ ! -f "${truststore}" ]; then - prog "truststore generate directory: ${generate_root}" + prog "generate truststore: ${truststore}" generate_truststore "${generate_root}" "server.truststore" "${pass}" "${storetype}" fi - prog "generate truststore: ${truststore}" - note "View truststore: keytool -list -v -keystore ${truststore} -storepass ${pass}" + warn "${truststore} already exists, skipping generation!" + note "View truststore: keytool -list -v -keystore ${truststore} -storepass ''" fi # import CA to keystore From 3785cad81913ff568a03a404c37deea6fe4240d6 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Thu, 16 Feb 2023 17:22:06 +0800 Subject: [PATCH 11/19] add warning in gen_truststore --- tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils | 1 + 1 file changed, 1 insertion(+) diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils index 74251f3f..6f1b30c3 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils @@ -168,6 +168,7 @@ generate_truststore(){ exit 1 fi + keytool -delete -alias myfirstCA -keystore ${truststoreName} -storepass ${pass} rm -rf firstCA* } From ea287f1d03c8a838f808a536533d94dc687d8462 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Mon, 20 Feb 2023 17:36:11 +0800 Subject: [PATCH 12/19] QA-4212 update import_to_keystore --- .../kafka_ssl/generate_ssl_CA/ssl_generate.sh | 4 +- .../kafka_ssl/generate_ssl_CA/ssl_renewal.sh | 85 ++++----- .../kafka_ssl/generate_ssl_CA/utils/env_utils | 68 +++---- .../kafka_ssl/generate_ssl_CA/utils/ssl_utils | 167 ++++++++++++++---- 4 files changed, 209 insertions(+), 115 deletions(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh index 256ad774..1ffe9365 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh @@ -106,7 +106,7 @@ install_openssl # 1. generate CARoot and CA_key rm -rf $generate_root -generate_CARoot ${generate_root} $CN +generate_CARoot $generate_root $CN $pass CARoot=${generate_root}/ca-root.crt CA_key=${generate_root}/ca-root.key @@ -122,7 +122,7 @@ generate_subCA ${generate_root} ${keystore} ${CARoot} ${CA_key} ${CN} ${pass} subCA=${CN}.crt # 5. import CARoot to keystore -import_to_keystore ${keystore} ${CARoot} "CARoot" ${pass} +import_to_keystore ${keystore} "CARoot" ${CARoot} ${CA_key} ${pass} # 6. import sub-certificate to keystore import_to_keystore ${keystore} ${subCA} ${CN} ${pass} diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh index 8a91c031..8642e1cc 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh @@ -31,11 +31,11 @@ generate_root=${BASE_DIR}/SSL_files CN=kafka-0.tigergraph.com storetype=jks pass=tiger123 -CARoot="" -CA_key="" +storepass=tiger123 +CA="" +CAkey="" keystore="" truststore="" -importCA="" CARoot_flag="" subCA_flag="" @@ -46,7 +46,7 @@ importToTruststore_flag="" help_flag="" opt_string="hip:c:s:d:" -opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,directory:,import:,import_to_keystore,import_to_truststore,storetype:,keystore:,truststore:,cer:,cerKey:,CN:" +opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,directory:,import_to_keystore,storepass:,import_to_truststore,storetype:,keystore:,truststore:,cer:,cerKey:,CN:" ARGS=`getopt -a -o $opt_string --long $opt_long_string -- "$@"` if [ $? != 0 ] ; then exit 1 ; fi @@ -76,11 +76,11 @@ do importToTruststore_flag=true ;; --cer) - CARoot=`path_conver $2` + CA=`path_conver $2` shift ;; --cerKey) - CA_key=`path_conver $2` + CAkey=`path_conver $2` shift ;; --keystore) @@ -91,10 +91,6 @@ do truststore=`path_conver $2` shift ;; - --import) - importCA=`path_conver $2` - shift - ;; -d|--directory) generate_root=$2 if [ ! -d ${generate_root} ]; then @@ -113,6 +109,10 @@ do fi shift ;; + --storepass) + storepass=$2 + shift + ;; -c|--CN) CN=$2 shift @@ -173,12 +173,12 @@ else if [[ ! -z $CARoot_flag ]]; then prog "root-CA generate directory: $generate_root" prog "root-CA subject CN: $CN" - CARoot=${generate_root}/ca-root.crt - CA_key=${generate_root}/ca-root.key + CA=${generate_root}/ca-root.crt + CAkey=${generate_root}/ca-root.key - check_file ${CARoot} 0 - check_file ${CA_key} 0 - generate_CARoot ${generate_root} $CN + check_file ${CA} 0 + check_file ${CAkey} 0 + generate_CARoot $generate_root $CN $pass fi # generate keystore @@ -194,33 +194,14 @@ else # generate a sub-certificate using the keytool if [[ ! -z $subCA_flag ]]; then prog "Subordinate-CA generate directory: $generate_root" - if [[ -z "$CARoot" || -z "$CA_key" ]]; then + if [[ -z "$CA" || -z "$CAkey" ]]; then error "Missing options: '-cer' or '-cerKey', exiting..." general_usage gen_subCA exit 1 fi - check_CARoot $CARoot $CA_key - - # Generate keystore - if [[ -z "$keystore" ]]; then - keystore=${generate_root}/server.keystore - note "Use keytool to generate CRS: If no keystore is provided, a new keystore will be created, CN=${CN}" - note "Default keystore: $keystore" - if [ -f "$keystore" ];then - check_keystore $keystore $pass - keystoreType=$(keytool -list -v -keystore $keystore -storepass $pass |& awk '/Keystore type/{print $NF}') - else - keystoreType=$storetype - fi - generate_keystore $generate_root $pass $CN $keystoreType "server.keystore" - else - check_keystore $keystore $pass - keystoreType=$(keytool -list -v -keystore $keystore -storepass $pass |& awk '/Keystore type/{print $NF}') - keystoreName=${keystore##*/} - generate_keystore $generate_root $pass $CN $keystoreType $keystoreName - fi - generate_subCA $generate_root $keystore $CARoot $CA_key $CN $pass + check_cert $CA $CAkey $pass + generate_sub_cert $generate_root $CA $CAkey $pass $CN prog "Generate subordinate-CA: ${CN}.crt successfully" fi @@ -229,34 +210,36 @@ else truststore="${generate_root}/server.truststore" if [ ! -f "${truststore}" ]; then prog "generate truststore: ${truststore}" - generate_truststore "${generate_root}" "server.truststore" "${pass}" "${storetype}" + generate_truststore "${generate_root}" "server.truststore" "${storepass}" "${storetype}" + else + warn "${truststore} already exists, skipping generation!" fi - warn "${truststore} already exists, skipping generation!" - note "View truststore: keytool -list -v -keystore ${truststore} -storepass ''" + note "View truststore: keytool -list -v -keystore ${truststore} -storepass ${storepass}" fi - # import CA to keystore + # import keycert pair to keystore if [[ ! -z $importToKeystore_flag ]]; then - [ -z "${keystore}${importCA}" ] \ - && { error "'-keystore' and '-import' are required options"; general_usage import_to_keystore; exit 1; } - alias=${importCA##*/} + [[ -z "$CA" || -z "$CAkey" || -z "$keystore" ]] \ + && { error "'-keystore', '-cer' and '-cerKey' are required options"; general_usage import_to_keystore; exit 1; } + alias=${CA##*/} alias=${alias%.*} prog "Import alias is ${alias}" check_file ${keystore} 1 - check_file ${importCA} 1 - import_to_keystore ${keystore} ${importCA} ${alias} ${pass} + check_file ${CA} 1 + check_file ${CAkey} 1 + import_to_keystore ${keystore} ${alias} ${CAkey} ${CA} ${storepass} ${pass} fi # import CA to truststore if [[ ! -z $importToTruststore_flag ]]; then - [ -z "${truststore}${importCA}" ] \ - && { error "'-truststore' and '-import' are required options"; general_usage import_to_truststore; exit 1; } - alias=${importCA##*/} + [[ -z "$CA" || -z "$truststore" ]] \ + && { error "'-truststore' and '-cer' are required options"; general_usage import_to_truststore; exit 1; } + alias=${CA##*/} alias=${alias%.*} prog "Import alias is ${alias}" check_file ${truststore} 1 - check_file ${importCA} 1 - import_to_truststore ${truststore} ${importCA} ${alias} ${pass} + check_file ${CA} 1 + import_to_truststore ${truststore} ${CA} ${alias} ${storepass} fi # enter at least one command diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 7cbcedc0..bfb7e03d 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -196,16 +196,17 @@ general_help(){ echo "Commands:" echo " -h,-help -- Show the help" echo " -gen_CARoot -- Generate root CA and private_key" - echo " -gen_keystore -- Generate an empty keystore" - echo " -gen_truststore -- Generate truststore" - echo " -gen_subCA -- Generate subordinate CA through root CA" - echo " -import_to_keystore -- Import CA to keystore" - echo " -import_to_truststore -- Import CA to truststore" + echo " -gen_keystore -- Generate keystore" + echo " -gen_truststore -- Generate an empty truststore" + echo " -gen_subCA -- Generate subordinate CA through parent CA" + echo " -import_to_keystore -- import certificate and certificate_private_key pair to keystore" + echo " -import_to_truststore -- Import certificate to truststore" echo warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. Please note that if the local machine does not have a java environment, some certificates generation will fail." echo note "Use './`basename $0` -command_name -help' for usage of command_name" + echo exit 0 } @@ -215,14 +216,15 @@ general_usage(){ gen_CARoot) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_CARoot] [-d ] [-c ]" + mesg_green "./`basename $0` [--gen_CARoot] [-d ] [-c ] [-p ]" echo "Example:" - mesg_blue "./`basename $0` --gen_CARoot -d ./SSL_files -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_CARoot -d ./SSL_files -c kafka-0.tigergraph.com -p tiger123" mesg_blue "./`basename $0` --gen_CARoot -c kafka-0.tigergraph.com" echo echo "Options:" echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + echo " -p,-passphrase -- PASSPHRASE of CA private key (optional) [default: tiger123]" echo exit 0 ;; @@ -238,43 +240,44 @@ general_usage(){ echo echo "Options:" echo " -d,-directory -- Generation Path [default: ./SSL_files]" - echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo " -p,-passphrase -- The 'keypass' and 'storepass' of keystore [default: tiger123]" echo " -s,-storetype -- Keystore storetype, e.g. jks, pkcs12 [default: jks]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" echo + note "'keypass' is the password used to secure the private key that is associated with a particular entry in the keystore." + note "'storepass' is the password used to secure the keystore as a whole. " + warn "When the keystore is generated for the first time in this script, both use the same password '-p'." + echo exit 0 ;; gen_subCA) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-keystore ] [-c ] [-p ]" - mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-c ] [-p ]" + mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-p ] [-c ]" echo "Example:" - mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.key -keystore ./SSL_files/server.keystore.jks -c kafka-0.tigergraph.com -p tiger123" - mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.pem -c kafka-0.tigergraph.com -p tiger123" + mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_files/tigergraph.com.crt -cerKey ./SSL_files/tigergraph.com.key -p tiger123 -c kafka-0.tigergraph.com" echo echo "Options:" echo " -d,-directory -- Generation Path [default: ./SSL_files]" - echo " -cer,--cer -- Root-CA used to sign subordinate certificate" - echo " -cerKey -- Root-CA key file" - echo " -keystore -- Keystore path, if not provided, a default keystore will be generated" + echo " -cer,--cer -- Parent certificate used to sign subordinate certificate" + echo " -cerKey -- Parent certificate private key file" + echo " -p,-passphrase -- Passphrase of parent certificate private key [default: tiger123]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" - echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" echo exit 0 ;; gen_truststore) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_truststore] [-d ] [-p ] [-s ]" + mesg_green "./`basename $0` [--gen_truststore] [-d ] [-storepass ] [-s ]" echo "Example:" - mesg_blue "./`basename $0` --gen_truststore -d ./SSL_file -p tiger123 -s pkcs12" - mesg_blue "./`basename $0` --gen_truststore -p tiger123" + mesg_blue "./`basename $0` --gen_truststore -d ./SSL_file -storepass tiger123 -s pkcs12" + mesg_blue "./`basename $0` --gen_truststore -storepass tiger123" mesg_blue "./`basename $0` --gen_truststore" echo echo "Options:" echo " -d,-directory -- Generation Path [default: ./SSL_files]" - echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo " -storepass -- Truststore password [default: tiger123]" echo " -s,-storetype -- Truststore storetype, e.g. jks, pkcs12 [default: jks]" echo exit 0 @@ -282,32 +285,33 @@ general_usage(){ import_to_keystore) echo echo "Usage:" - mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-import ] [-p ]" + mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-cer ] [-cerKey ] [-storepass ] [-p ]" echo "Example:" - mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -import ./SSL_files/ca-root.crt -p tiger123" - mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -import ./SSL_files/kafka-0.tigergraph.com.crt -passphrase tiger123" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.key -storepass 123456 -p tiger123" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.key -storepass 123456" echo echo "Options:" - echo " -keystore -- Keystore path" - echo " -import -- Certificate to import" - echo " -p,-passphrase -- Keystore storepass and keypass [default: tiger123]" + echo " -keystore -- Keystore path" + echo " -cer,--cer -- Certificate file path" + echo " -cerKey -- Certificate private key file path" + echo " -storepass -- keystore password [default: tiger123]" + echo " -p,-passphrase -- Passphrase for the certificate private key [default: tiger123]" echo exit 0 ;; import_to_truststore) echo echo "Usage:" - mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-import ] [-p ]" + mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-cer ] [-storepass ]" echo "Example:" - mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -import ./SSL_files/ca-root.crt -p tiger123" - mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -import ./SSL_files/client.crt -passphrase tiger123" + mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -cer ./SSL_files/ca-root.crt -storepass tiger123" echo echo "Options:" echo " -truststore -- Truststore path" - echo " -import -- Certificate to import" - echo " -p,-passphrase -- Truststore storepass and keypass [default: tiger123]" + echo " -cer -- Certificate to import" + echo " -storepass -- Truststore password [default: tiger123]" echo exit 0 ;; esac -} +} \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils index 6f1b30c3..3b4245f0 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils @@ -1,8 +1,12 @@ #!/bin/bash -generate_CARoot(){ +generate_CARoot() { local generate_root=$1 local CN=$2 + local ca_passphrase=$3 + local ca_key=${generate_root}/ca-root.key + local ca_cert=${generate_root}/ca-root.crt + local ca_days=365 if [ ! -d ${generate_root} ]; then mkdir -p ${generate_root} @@ -14,10 +18,12 @@ generate_CARoot(){ exit 1 fi - prog "Start creating certificate authority(CA) for signing..." + # Generate the private key + openssl genrsa -aes256 -passout pass:"$ca_passphrase" -out "$ca_key" 4096 + # Generate the self-signed certificate + openssl req -x509 -new -nodes -key "$ca_key" -sha256 -days "$ca_days" -subj "/CN=$CN" -passin pass:"$ca_passphrase" -out "$ca_cert" prog "CARoot path: ${generate_root}/ca-root.crt" prog "private_key path: ${generate_root}/ca-root.key" - openssl req -nodes -new -x509 -keyout ca-root.key -out ca-root.crt -days 365 -subj "/CN=$CN" } check_CARoot(){ @@ -53,6 +59,45 @@ check_CARoot(){ fi } +check_cert() { + local cert_path=$1 + local key_path=$2 + local key_pass=$3 + + if [ ! -f $cert_path ];then + error "Certificate file does not exist." + exit 1 + elif [ ! -f $key_path ];then + error "Certificate private-key file does not exist." + exit 1 + fi + + prog "Start checking if the private key can be decrypted with the given password..." + if ! openssl rsa -in "${key_path}" -passin "pass:${key_pass}" -check > /dev/null 2>&1; then + error "The private key password is incorrect." >&2 + exit 1 + fi + + prog "Start checking if the certificate matches the private key..." + if ! openssl x509 -noout -modulus -in "${cert_path}" | openssl md5 > /tmp/cert.md5; then + error "Failed to compute the certificate md5." >&2 + exit 1 + fi + + if ! openssl rsa -noout -modulus -in "${key_path}" -passin "pass:${key_pass}" | openssl md5 > /tmp/key.md5; then + error "Failed to compute the private key md5." >&2 + exit 1 + fi + + if ! diff /tmp/cert.md5 /tmp/key.md5 > /dev/null; then + error "The certificate and private key do not match." >&2 + exit 1 + fi + + prog "The certificate, private key, and password are all correct." + rm /tmp/cert.md5 /tmp/key.md5 +} + ### generate an empty keystore # 1. default storetype is JKS # 2. validity is 365 @@ -69,6 +114,7 @@ generate_keystore(){ cd $genRoot prog "Start creating keystore..." + note "keypass and storepass will use the same password: $pass" case $storetype in pkcs12|PKCS12|pk12|PK12|p12|P12) prog "The storetype of keystore is pkcs12." @@ -103,38 +149,86 @@ check_keystore(){ fi } -generate_subCA(){ +generate_sub_cert() { local generate_root=$1 - local keystore=$2 - local CA_root=$3 - local CA_key=$4 - local subCA_name=$5 - local pass=$6 + local parent_cert=$2 # path to the parent certificate file + local parent_key=$3 # path to the parent private key file + local parent_key_pass=$4 # password for the parent private key file + local sub_name=$5 # name for the sub-certificate + + local sub_key=${sub_name}.key + local sub_cert=${sub_name}.crt if [ ! -d ${generate_root} ]; then mkdir -p ${generate_root} fi - cd $generate_root - prog "Start creating certificate signing request (CSR)..." - keytool -keystore ${keystore} -alias ${subCA_name} -certreq -file ${subCA_name}.csr -storepass ${pass} -keypass ${pass} + cd ${generate_root} + # Create a new RSA private key for the sub-certificate + openssl genrsa -out $sub_key 2048 + + # Create a certificate signing request (CSR) for the sub-certificate + openssl req -new -key $sub_key -out /tmp/sub.csr -subj "/CN=${sub_name}" + + # Sign the CSR with the parent certificate and private key to generate the sub-certificate + prog "sign sub-certificate through $parent_cert..." + openssl x509 -req -in /tmp/sub.csr -CA $parent_cert -CAkey $parent_key -passin pass:$parent_key_pass -out $sub_cert -days 365 -sha256 -CAcreateserial - prog "sign sub-certificate through ca-root..." - openssl x509 -req -CA ${CA_root} -CAkey ${CA_key} -in ${subCA_name}.csr -out ${subCA_name}.crt -days 365 -CAcreateserial + # Remove the temporary files + rm /tmp/sub.csr } -import_to_keystore(){ +# import keycert pair to keystore +import_to_keystore() { local keystore=$1 - local import_file=$2 - local alias=$3 - local pass=$4 + local alias=$2 + local keyfile=$3 + local certfile=$4 + local keystorepass=$5 + local keypass=$6 + local password_file="/tmp/password" - prog "import ${import_file} to keystore: ${keystore}" - note "How to check whether the certificate already exists: keytool -list -v -keystore ${keystore} -storepass ${pass}" - keytool -keystore ${keystore} -alias ${alias} -import -file ${import_file} -storepass ${pass} -keypass ${pass} -noprompt + # Check if the keystore exists and the keystore password is correct + if ! keytool -list -keystore "$keystore" -storepass "$keystorepass" >/dev/null 2>&1; then + error "Keystore not found or incorrect keystore password" + exit 1 + fi + + # Check that the key password matches the private key file + if [ -n "$keypass" ]; then + if ! openssl rsa -in "$keyfile" -passin pass:"$keypass" -noout >/dev/null 2>&1; then + error "Incorrect key password" + exit 1 + fi + fi + + # Export the key/certificate pair to a PKCS12 file + printf "%s" "$keypass" > "$password_file" + if openssl pkcs12 -export -in "$certfile" -inkey "$keyfile" -out /tmp/keycert.p12 -name "$alias" -passin file:"$password_file" -passout pass:"$keypass"; then + prog "Successfully exported key/certificate pair to PKCS12 file" + else + error "Error exporting key/certificate pair to PKCS12 file" + exit 1 + fi + rm -f "$password_file" + + # Import the key/certificate pair into the keystore + printf "%s\n%s\n" "$keypass" "$keystorepass" | keytool -importkeystore -srckeystore /tmp/keycert.p12 -srcstoretype PKCS12 -srcalias "$alias" \ + -destalias "$alias" -destkeystore "$keystore" -deststoretype JKS -deststorepass "$keystorepass" \ + -destkeypass "$keypass" -storepass "$keystorepass" -keypass "$keypass" -noprompt + + if [ $? -eq 0 ]; then + prog "Successfully imported key/certificate pair to keystore" + else + error "Error importing key/certificate pair to keystore" + exit 1 + fi + + note "To check whether the certificate already exists, run:" + note "keytool -list -v -keystore $keystore -storepass $keystorepass" } -# at least one CA file is required to generate truststore +# generate an empty truststore generate_truststore(){ local generate_root=$1 local truststoreName=$2 @@ -172,13 +266,26 @@ generate_truststore(){ rm -rf firstCA* } -import_to_truststore(){ - local truststore=$1 - local import_file=$2 - local alias=$3 - local pass=$4 +import_to_truststore() { + local truststore=$1 # path to the truststore file + local import_file=$2 # path to the certificate file to be imported + local alias=$3 # alias for the certificate entry + local storepass=$4 # truststore password + + # Check if the truststore password is correct + keytool -list -keystore "$truststore" -storepass "$storepass" >/dev/null 2>&1 + if [ $? -ne 0 ]; then + error "Incorrect truststore password" + exit 1 + fi + + # Import the certificate into the truststore + keytool -import -noprompt -trustcacerts -alias "$alias" -file "$import_file" -keystore "$truststore" -storepass "$storepass" + if [ $? -ne 0 ]; then + error "Error importing certificate to truststore" + exit 1 + fi - prog "import ${import_file} to truststore: ${truststore}" - note "How to check whether the certificate already exists: keytool -list -v -keystore ${truststore} -storepass ${pass}" - keytool -keystore ${truststore} -alias ${alias} -import -file ${import_file} -storepass ${pass} -keypass ${pass} -noprompt + prog "Certificate successfully imported to truststore" + note "How to check whether the certificate already exists: keytool -list -v -keystore ${truststore} -storepass ${storepass}" } \ No newline at end of file From c021311281ee1b8b1aed4358376f0a8f4e827f92 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Mon, 20 Feb 2023 18:15:12 +0800 Subject: [PATCH 13/19] QA-4212 update ssl_generate script --- .../kafka_ssl/generate_ssl_CA/ssl_generate.sh | 24 ++++++++++--------- .../kafka_ssl/generate_ssl_CA/ssl_renewal.sh | 6 ++--- .../kafka_ssl/generate_ssl_CA/utils/env_utils | 4 ++-- 3 files changed, 18 insertions(+), 16 deletions(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh index 1ffe9365..06c87542 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh @@ -18,9 +18,9 @@ source_file() { } # source all functions -source_file utils/pretty_print "No miss tools found, utils/pretty_print NOT exist, exit" true -source_file utils/env_utils "No miss tools found, utils/env_utils NOT exist, exit" true -source_file utils/ssl_utils "No miss tools found, utils/ssl_utils NOT exist, exit" true +source_file utils/pretty_print "File utils/pretty_print NOT found, exit" true +source_file utils/env_utils "File utils/env_utils NOT found, exit" true +source_file utils/ssl_utils "File utils/ssl_utils NOT found, exit" true OSG=$(get_os) OS=$(echo "$OSG" | cut -d' ' -f1) @@ -107,29 +107,31 @@ install_openssl # 1. generate CARoot and CA_key rm -rf $generate_root generate_CARoot $generate_root $CN $pass -CARoot=${generate_root}/ca-root.crt -CA_key=${generate_root}/ca-root.key +CA=${generate_root}/ca-root.crt +CAkey=${generate_root}/ca-root.key # 2. check CARoot and CA_key -check_CARoot ${CARoot} ${CA_key} +check_cert $CA $CAkey $pass # 3. generate keystore generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server.keystore" keystore=server.keystore # 4. generate sub-certificate -generate_subCA ${generate_root} ${keystore} ${CARoot} ${CA_key} ${CN} ${pass} +generate_sub_cert $generate_root $CA $CAkey $pass $CN subCA=${CN}.crt +subCA_key=${CN}.key # 5. import CARoot to keystore -import_to_keystore ${keystore} "CARoot" ${CARoot} ${CA_key} ${pass} +import_to_keystore ${keystore} "CARoot" ${CAkey} ${CA} ${pass} ${pass} # 6. import sub-certificate to keystore -import_to_keystore ${keystore} ${subCA} ${CN} ${pass} +import_to_keystore ${keystore} "CARoot" ${CAkey} ${CA} ${pass} ${pass} +import_to_keystore ${keystore} ${CN} ${subCA_key} ${subCA} ${pass} ${pass} # 7. generate truststore -generate_truststore ${generate_root} "server.truststore" ${pass} ${storetype} +generate_truststore ${generate_root} "server.truststore" "${pass}" "${storetype}" truststore=server.truststore # 8. import CARoot to truststore -import_to_truststore ${truststore} ${CARoot} "CARoot" ${pass} \ No newline at end of file +import_to_truststore ${truststore} ${CA} "CARoot" ${pass} \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh index 8642e1cc..580c53bc 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh @@ -18,9 +18,9 @@ source_file() { } # source all functions -source_file utils/pretty_print "No miss tools found, utils/pretty_print NOT exist, exit" true -source_file utils/env_utils "No miss tools found, utils/env_utils NOT exist, exit" true -source_file utils/ssl_utils "No miss tools found, utils/ssl_utils NOT exist, exit" true +source_file utils/pretty_print "File utils/pretty_print NOT found, exit" true +source_file utils/env_utils "File utils/env_utils NOT found, exit" true +source_file utils/ssl_utils "File utils/ssl_utils NOT found, exit" true OSG=$(get_os) OS=$(echo "$OSG" | cut -d' ' -f1) diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index bfb7e03d..59b676b1 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -74,7 +74,7 @@ install_openJDK(){ prog "start install openjdk-1.8.0." yum install -y java-1.8.0-openjdk > /dev/null 2>&1 else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) + java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) if [[ $java_version != "1.8.0" ]];then prog "start update to openjdk-1.8.0." rpm -qa | grep java | xargs rpm -e --nodeps @@ -89,7 +89,6 @@ install_openJDK(){ else error "JDK Install Fail..." && exit 1 fi - else if ! which java > /dev/null 2>&1; then error "Java environment not detected. You can choose option \"-i\" to install openjdk-1.8.0." @@ -180,6 +179,7 @@ help(){ echo warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. Please note that if the local machine does not have a java environment, some certificates generation will fail." + echo exit 0 } From f4bf23c186855f7cb58e2a58bca485c838fad600 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Tue, 21 Feb 2023 10:50:03 +0800 Subject: [PATCH 14/19] QA-4212 support openJDK1.8.0 and later --- .../kafka_ssl/generate_ssl_CA/utils/env_utils | 25 ++++++++++--------- 1 file changed, 13 insertions(+), 12 deletions(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 59b676b1..03e4c01e 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -68,23 +68,23 @@ check_root(){ fi } -install_openJDK(){ +install_openJDK() { if [[ "${SETUP_JDK}" == "true" ]]; then if ! which java > /dev/null 2>&1; then prog "start install openjdk-1.8.0." yum install -y java-1.8.0-openjdk > /dev/null 2>&1 else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) - if [[ $java_version != "1.8.0" ]];then + java_version=$(java -version 2>&1 | awk -F '"' '/version/ {print $2}') + if [[ ("$(echo "$java_version" | cut -d'.' -f1)" -ge 1 && "$(echo "$java_version" | cut -d'.' -f2)" -ge 8) || "$(echo "$java_version" | cut -d'.' -f1)" -ge 11 ]]; then + prog "The installed Java version is greater than 1.8.0. No update necessary." + else prog "start update to openjdk-1.8.0." rpm -qa | grep java | xargs rpm -e --nodeps yum install -y java-1.8.0-openjdk > /dev/null 2>&1 - else - prog "The java version is openjdk-1.8.0 now." fi fi # check install - if command -v java &> /dev/null;then + if command -v java &> /dev/null; then prog "JDK Install Success..." else error "JDK Install Fail..." && exit 1 @@ -94,12 +94,12 @@ install_openJDK(){ error "Java environment not detected. You can choose option \"-i\" to install openjdk-1.8.0." exit 1 else - java_version=$(java -version 2>&1 | sed '1!d' | sed -e 's/"//g' | awk '{print $3}'| cut -d_ -f1) - if [[ $java_version != "1.8.0" ]];then - error "This script currently only supports openjdk-1.8.0." - exit 1 + java_version=$(java -version 2>&1 | awk -F '"' '/version/ {print $2}') + if [[ ("$(echo "$java_version" | cut -d'.' -f1)" -ge 1 && "$(echo "$java_version" | cut -d'.' -f2)" -ge 8) || "$(echo "$java_version" | cut -d'.' -f1)" -ge 11 ]]; then + prog "The java version is openjdk-1.8.0 or later now." else - prog "The java version is openjdk-1.8.0 now." + error "This script currently only supports openjdk-1.8.0 or later." + exit 1 fi fi fi @@ -173,12 +173,13 @@ help(){ echo " -u,-usage -- Usage example" echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" - echo " -p,-passphrase -- PASSPHRASE [default: tiger123]" + echo " -p,-passphrase -- Keystore/Truststore password or certificate private key passphrase [default: tiger123]" echo " -s,-storetype -- Keystore/Truststore storetype, e.g. jks, pkcs12 [default: jks]" echo " -i,-install -- Install openjdk-1.8.0 and openssl" echo warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. Please note that if the local machine does not have a java environment, some certificates generation will fail." + warn "" echo exit 0 } From a15679324cfc0e9ca3f5337e29c7c38ffe7c4979 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Mon, 27 Feb 2023 16:15:43 +0800 Subject: [PATCH 15/19] QA-4212 ssl_generate.sh and ssl_import.sh --- .../kafka_ssl/generate_ssl_CA/ssl_generate.sh | 190 +++++++++++++----- .../{ssl_renewal.sh => ssl_import.sh} | 125 +++--------- .../kafka_ssl/generate_ssl_CA/utils/env_utils | 137 ++++++------- .../kafka_ssl/generate_ssl_CA/utils/ssl_utils | 53 ++--- 4 files changed, 236 insertions(+), 269 deletions(-) rename tools/kafka_ssl/generate_ssl_CA/{ssl_renewal.sh => ssl_import.sh} (53%) diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh index 06c87542..89323e9a 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh @@ -27,35 +27,61 @@ OS=$(echo "$OSG" | cut -d' ' -f1) version=$(echo "$OSG" | cut -d' ' -f2) OSV="$OS$(echo "$version" | cut -d'.' -f1)" -generate_root=${BASE_DIR}/SSL_files +generate_root=${BASE_DIR}/SSL_OUTPUT CN=kafka-0.tigergraph.com storetype=jks pass=tiger123 - -opt_string="hud:p:c:is:" -opt_long_string="help,usage,directory:,passphrase:,CN:,storetype:,install" +storepass=tiger123 +storeName="" +CA="" +CAkey="" + +CARoot_flag="" +subCA_flag="" +genKeystore_flag="" +genTruststore_flag="" +help_flag="" + +opt_string="hip:c:s:o:n:" +opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,output:,storepass:,storetype:,cer:,cerKey:,CN:,name:" ARGS=`getopt -a -o $opt_string --long $opt_long_string -- "$@"` + if [ $? != 0 ] ; then exit 1 ; fi eval set -- "${ARGS}" while : do case $1 in -h|--help) - help - exit 0 + help_flag=true + ;; + --gen_CARoot) + CARoot_flag=true + ;; + --gen_subCA) + subCA_flag=true + ;; + --gen_keystore) + genKeystore_flag=true + ;; + --gen_truststore) + genTruststore_flag=true + ;; + --cer) + CA=`path_conver $2` + shift ;; - -u|--usage) - usage - exit 0 + --cerKey) + CAkey=`path_conver $2` + shift ;; - -d|--directory) + -o|--output) generate_root=$2 if [ ! -d ${generate_root} ]; then - error "The path '$generate_root' does not exist" - exit 1 - else - generate_root=`path_conver $generate_root`/SSL_files + warn "The path '$generate_root' does not exist" + prog "start creating output directory..." + mkdir -p $generate_root fi + generate_root=`path_conver $generate_root` shift ;; -p|--passphrase) @@ -66,6 +92,10 @@ do fi shift ;; + --storepass) + storepass=$2 + shift + ;; -c|--CN) CN=$2 shift @@ -74,6 +104,10 @@ do storetype=$2 shift ;; + -n|--name) + storeName=$2 + shift + ;; -i|--install) SETUP_JDK=true SETUP_OPENSSL=true @@ -84,54 +118,100 @@ do ;; *) error "${bldred}Invalid option, the correct usage is described below: $txtrst" - help + generate_help ;; esac shift done -# this script only support rhel/centos -prog "Checking operation system (OS) version ..." -check_os $OS $version - -prog "Checking root/sudo ..." -check_root - -# Using option '-i/--install' will install openjdk-1.8.0 and openssl, -# otherwise openjdk-1.8.0 and openssl will not be installed -# install openJDK -install_openJDK -# install openssl -install_openssl - -# 1. generate CARoot and CA_key -rm -rf $generate_root -generate_CARoot $generate_root $CN $pass -CA=${generate_root}/ca-root.crt -CAkey=${generate_root}/ca-root.key - -# 2. check CARoot and CA_key -check_cert $CA $CAkey $pass - -# 3. generate keystore -generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server.keystore" -keystore=server.keystore +if [[ ! -z $help_flag ]]; then + if [[ ! -z $CARoot_flag ]]; then + general_usage gen_CARoot + elif [[ ! -z $subCA_flag ]]; then + general_usage gen_subCA + elif [[ ! -z $genKeystore_flag ]]; then + general_usage gen_keystore + elif [[ ! -z $genTruststore_flag ]]; then + general_usage gen_truststore + else + generate_help + fi + exit 0 +else + # this script only support rhel/centos + prog "Checking operation system (OS) version ..." + check_os $OS $version + + prog "Checking root/sudo ..." + check_root + + # Using option '-i/--install' will install openjdk-1.8.0 and openssl, + # otherwise openjdk-1.8.0 and openssl will not be installed + # install openJDK + install_openJDK + # install openssl + install_openssl + + # generate root CA + if [[ ! -z $CARoot_flag ]]; then + prog "root-CA output directory: $generate_root" + prog "root-CA CN: $CN" + CA=${generate_root}/ca-root.crt + CAkey=${generate_root}/ca-root.key + + check_file ${CA} 0 + check_file ${CAkey} 0 + generate_CARoot $generate_root $CN $pass + fi -# 4. generate sub-certificate -generate_sub_cert $generate_root $CA $CAkey $pass $CN -subCA=${CN}.crt -subCA_key=${CN}.key + # generate keystore + if [[ ! -z $genKeystore_flag ]]; then + if [[ -z $storeName ]]; then + storeName=server.keystore + fi + prog "keystore output directory: $generate_root" + prog "Keystore -Dname CN: $CN" + prog "keystore name: $storeName" + generate_keystore ${generate_root} ${pass} ${CN} ${storetype} ${storeName} + keystore=${generate_root}/${storeName} + prog "Generate keystore: $keystore" + note "View keystore: keytool -list -v -keystore $keystore -storepass $pass" + fi -# 5. import CARoot to keystore -import_to_keystore ${keystore} "CARoot" ${CAkey} ${CA} ${pass} ${pass} + # generate a sub-certificate using the keytool + if [[ ! -z $subCA_flag ]]; then + prog "Subordinate-CA output directory: $generate_root" + if [[ -z "$CA" || -z "$CAkey" ]]; then + error "Missing options: '-cer' or '-cerKey', exiting..." + general_usage gen_subCA + exit 1 + fi -# 6. import sub-certificate to keystore -import_to_keystore ${keystore} "CARoot" ${CAkey} ${CA} ${pass} ${pass} -import_to_keystore ${keystore} ${CN} ${subCA_key} ${subCA} ${pass} ${pass} + check_cert $CA $CAkey $pass + generate_sub_cert $generate_root $CA $CAkey $pass $CN + prog "Generate subordinate-CA: ${CN}.crt successfully" + fi -# 7. generate truststore -generate_truststore ${generate_root} "server.truststore" "${pass}" "${storetype}" -truststore=server.truststore + # generate truststore + if [[ ! -z ${genTruststore_flag:-} ]]; then + if [[ -z $storeName ]]; then + storeName=server.truststore + fi + truststore="${generate_root}/${storeName}" + if [ ! -f "${truststore}" ]; then + prog "Generate truststore: ${truststore}" + generate_truststore "${generate_root}" "${storeName}" "${storepass}" "${storetype}" + else + warn "${truststore} already exists, skipping generation!" + fi + note "View truststore: keytool -list -v -keystore ${truststore} -storepass ${storepass}" + fi -# 8. import CARoot to truststore -import_to_truststore ${truststore} ${CA} "CARoot" ${pass} \ No newline at end of file + # enter at least one command + total_flag=($CARoot_flag $genKeystore_flag $subCA_flag $genTruststore_flag) + if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then + error "Please enter at least one Command" + generate_help + exit 1 + fi +fi \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_import.sh similarity index 53% rename from tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh rename to tools/kafka_ssl/generate_ssl_CA/ssl_import.sh index 580c53bc..1297fd55 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_renewal.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_import.sh @@ -27,26 +27,19 @@ OS=$(echo "$OSG" | cut -d' ' -f1) version=$(echo "$OSG" | cut -d' ' -f2) OSV="$OS$(echo "$version" | cut -d'.' -f1)" -generate_root=${BASE_DIR}/SSL_files -CN=kafka-0.tigergraph.com -storetype=jks -pass=tiger123 storepass=tiger123 CA="" CAkey="" +pass=tiger123 keystore="" truststore="" -CARoot_flag="" -subCA_flag="" -genKeystore_flag="" -genTruststore_flag="" importToKeystore_flag="" importToTruststore_flag="" help_flag="" -opt_string="hip:c:s:d:" -opt_long_string="help,gen_CARoot,gen_subCA,gen_keystore,gen_truststore,passphrase:,directory:,import_to_keystore,storepass:,import_to_truststore,storetype:,keystore:,truststore:,cer:,cerKey:,CN:" +opt_string="hip:" +opt_long_string="help,passphrase:,import_to_keystore,storepass:,import_to_truststore,keystore:,truststore:,cer:,cerKey:" ARGS=`getopt -a -o $opt_string --long $opt_long_string -- "$@"` if [ $? != 0 ] ; then exit 1 ; fi @@ -57,18 +50,6 @@ do -h|--help) help_flag=true ;; - --gen_CARoot) - CARoot_flag=true - ;; - --gen_subCA) - subCA_flag=true - ;; - --gen_keystore) - genKeystore_flag=true - ;; - --gen_truststore) - genTruststore_flag=true - ;; --import_to_keystore) importToKeystore_flag=true ;; @@ -77,27 +58,33 @@ do ;; --cer) CA=`path_conver $2` + if [ $? -ne 0 ]; then + error "$CA" + exit 1 + fi shift ;; --cerKey) CAkey=`path_conver $2` + if [ $? -ne 0 ]; then + error "$CAkey" + exit 1 + fi shift ;; --keystore) keystore=`path_conver $2` + if [ $? -ne 0 ]; then + error "$keystore" + exit 1 + fi shift ;; --truststore) truststore=`path_conver $2` - shift - ;; - -d|--directory) - generate_root=$2 - if [ ! -d ${generate_root} ]; then - error "The path '$generate_root' does not exist" + if [ $? -ne 0 ]; then + error "$truststore" exit 1 - else - generate_root=`path_conver $generate_root`/SSL_files fi shift ;; @@ -113,14 +100,6 @@ do storepass=$2 shift ;; - -c|--CN) - CN=$2 - shift - ;; - -s|--storetype) - storetype=$2 - shift - ;; -i|--install) SETUP_JDK=true SETUP_OPENSSL=true @@ -131,27 +110,19 @@ do ;; *) error "${bldred}Invalid option, the correct usage is described below: $txtrst" - general_help + import_help ;; esac shift done if [[ ! -z $help_flag ]]; then - if [[ ! -z $CARoot_flag ]]; then - general_usage gen_CARoot - elif [[ ! -z $subCA_flag ]]; then - general_usage gen_subCA - elif [[ ! -z $genKeystore_flag ]]; then - general_usage gen_keystore - elif [[ ! -z $genTruststore_flag ]]; then - general_usage gen_truststore - elif [[ ! -z $importToKeystore_flag ]]; then + if [[ ! -z $importToKeystore_flag ]]; then general_usage import_to_keystore elif [[ ! -z $importToTruststore_flag ]]; then general_usage import_to_truststore else - general_help + import_help fi exit 0 else @@ -169,55 +140,7 @@ else # install openssl install_openssl - # generate root CA - if [[ ! -z $CARoot_flag ]]; then - prog "root-CA generate directory: $generate_root" - prog "root-CA subject CN: $CN" - CA=${generate_root}/ca-root.crt - CAkey=${generate_root}/ca-root.key - - check_file ${CA} 0 - check_file ${CAkey} 0 - generate_CARoot $generate_root $CN $pass - fi - - # generate keystore - if [[ ! -z $genKeystore_flag ]]; then - prog "keystore generate directory: $generate_root" - prog "Keystore -Dname CN: $CN" - generate_keystore ${generate_root} ${pass} ${CN} ${storetype} "server.keystore" - keystore=${generate_root}/server.keystore - prog "Generate keystore: $keystore" - note "View keystore: keytool -list -v -keystore $keystore -storepass $pass" - fi - - # generate a sub-certificate using the keytool - if [[ ! -z $subCA_flag ]]; then - prog "Subordinate-CA generate directory: $generate_root" - if [[ -z "$CA" || -z "$CAkey" ]]; then - error "Missing options: '-cer' or '-cerKey', exiting..." - general_usage gen_subCA - exit 1 - fi - - check_cert $CA $CAkey $pass - generate_sub_cert $generate_root $CA $CAkey $pass $CN - prog "Generate subordinate-CA: ${CN}.crt successfully" - fi - - # generate truststore - if [[ ! -z ${genTruststore_flag:-} ]]; then - truststore="${generate_root}/server.truststore" - if [ ! -f "${truststore}" ]; then - prog "generate truststore: ${truststore}" - generate_truststore "${generate_root}" "server.truststore" "${storepass}" "${storetype}" - else - warn "${truststore} already exists, skipping generation!" - fi - note "View truststore: keytool -list -v -keystore ${truststore} -storepass ${storepass}" - fi - - # import keycert pair to keystore + # import key-cert pair to keystore if [[ ! -z $importToKeystore_flag ]]; then [[ -z "$CA" || -z "$CAkey" || -z "$keystore" ]] \ && { error "'-keystore', '-cer' and '-cerKey' are required options"; general_usage import_to_keystore; exit 1; } @@ -230,7 +153,7 @@ else import_to_keystore ${keystore} ${alias} ${CAkey} ${CA} ${storepass} ${pass} fi - # import CA to truststore + # import certificate to truststore if [[ ! -z $importToTruststore_flag ]]; then [[ -z "$CA" || -z "$truststore" ]] \ && { error "'-truststore' and '-cer' are required options"; general_usage import_to_truststore; exit 1; } @@ -243,10 +166,10 @@ else fi # enter at least one command - total_flag=($CARoot_flag $genKeystore_flag $subCA_flag $genTruststore_flag $importToKeystore_flag $importToTruststore_flag) + total_flag=($importToKeystore_flag $importToTruststore_flag) if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then error "Please enter at least one Command" - general_help + import_help exit 1 fi fi \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 03e4c01e..b23202ca 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -129,22 +129,26 @@ install_openssl(){ } path_conver(){ - relativePath=$1 - firstChar=${relativePath: 0: 1} + local rel_path="$1" + local abs_path - if [[ "$firstChar" == "" ]]; then - echo "relative-path(\$1) is null" - exit 1 - elif [[ "$firstChar" == "/" ]]; then - echo $relativePath - exit 0 + # If the path is already absolute, return it as-is + if [[ "$rel_path" == /* ]]; then + abs_path="$rel_path" + else + abs_path="$(pwd)/$rel_path" + fi + + # Check if the path exists before calling realpath + if [[ ! -e "$abs_path" ]]; then + echo "Path $abs_path does not exist" + return 1 fi - tmpPath1=`dirname $relativePath` - tmpFullpath1=`cd $tmpPath1 && pwd` - tmpPath2=`basename $relativePath` + # Canonicalize the path to remove any redundant elements + abs_path="$(realpath "$abs_path")" - echo ${tmpFullpath1}/${tmpPath2} + echo "$abs_path" } check_file(){ @@ -161,50 +165,32 @@ check_file(){ fi } -help(){ - echo - echo "Usage:" - mesg_green "./`basename $0` [-d ] [-c ][-p ] [-s ] [-i]" - mesg_green "./`basename $0` [-d ] [-c ][-p ] [-s ]" - mesg_green "./`basename $0` -h" - mesg_green "./`basename $0` -u" - echo "Options:" - echo " -h,-help -- Show the help" - echo " -u,-usage -- Usage example" - echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" - echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" - echo " -p,-passphrase -- Keystore/Truststore password or certificate private key passphrase [default: tiger123]" - echo " -s,-storetype -- Keystore/Truststore storetype, e.g. jks, pkcs12 [default: jks]" - echo " -i,-install -- Install openjdk-1.8.0 and openssl" - echo - warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. -Please note that if the local machine does not have a java environment, some certificates generation will fail." - warn "" - echo - exit 0 -} - -usage(){ - echo "${bldblu}./`basename $0` -d ./SSL_files -p tiger123 -c kafka-0.tigergraph.com -s pkcs12 -i $txtrst" - echo "${bldblu}./`basename $0` -d ./SSL_files -p tiger123 -c kafka-0.tigergraph.com -s jks $txtrst" - echo "${bldblu}./`basename $0` -directory ./SSL_files -passphrase tiger123 -CN kafka-0.tigergraph.com -storetype pkcs12 -install $txtrst" - echo "${bldblu}./`basename $0` -i" - echo "${bldblu}./`basename $0` $txtrst" -} - -general_help(){ +generate_help(){ echo echo "Commands:" echo " -h,-help -- Show the help" - echo " -gen_CARoot -- Generate root CA and private_key" + echo " -gen_CARoot -- Generate root-CA and private_key" echo " -gen_keystore -- Generate keystore" echo " -gen_truststore -- Generate an empty truststore" - echo " -gen_subCA -- Generate subordinate CA through parent CA" - echo " -import_to_keystore -- import certificate and certificate_private_key pair to keystore" + echo " -gen_subCA -- Generate subordinate CA through superior certificate" + echo + warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. + Please note that if the local machine does not have a java environment, some operations will fail." + echo + note "Use './`basename $0` -command_name -help' for usage of command_name" + echo + exit 0 +} + +import_help(){ + echo + echo "Commands:" + echo " -h,-help -- Show the help" + echo " -import_to_keystore -- Import certificate and certificate_private_key pair to keystore" echo " -import_to_truststore -- Import certificate to truststore" echo warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. - Please note that if the local machine does not have a java environment, some certificates generation will fail." + Please note that if the local machine does not have a java environment, some operations will fail." echo note "Use './`basename $0` -command_name -help' for usage of command_name" echo @@ -217,13 +203,13 @@ general_usage(){ gen_CARoot) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_CARoot] [-d ] [-c ] [-p ]" + mesg_green "./`basename $0` [--gen_CARoot] [-o ] [-c ] [-p ]" echo "Example:" - mesg_blue "./`basename $0` --gen_CARoot -d ./SSL_files -c kafka-0.tigergraph.com -p tiger123" + mesg_blue "./`basename $0` --gen_CARoot -o ./SSL_OUTPUT -c kafka-0.tigergraph.com -p tiger123" mesg_blue "./`basename $0` --gen_CARoot -c kafka-0.tigergraph.com" echo echo "Options:" - echo " -d,-directory -- Certificate Generation Path [default: ./SSL_files]" + echo " -o,-output -- Certificate file output Path [default: ./SSL_OUTPUT]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" echo " -p,-passphrase -- PASSPHRASE of CA private key (optional) [default: tiger123]" echo @@ -232,37 +218,37 @@ general_usage(){ gen_keystore) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_keystore] [-d ] [-p ] [-s ] [-c ]" + mesg_green "./`basename $0` [--gen_keystore] [-o ] [-s ] [-storepass ] [-c ] [-n ]" echo "Example:" - mesg_blue "./`basename $0` --gen_keystore -d ./SSL_files -p tiger123 -s pkcs12 -c kafka-0.tigergraph.com" - mesg_blue "./`basename $0` --gen_keystore -p tiger123 -c kafka-0.tigergraph.com" - mesg_blue "./`basename $0` --gen_keystore -s jks" + mesg_blue "./`basename $0` --gen_keystore -o ./SSL_OUTPUT -s pkcs12 -storepass tiger123 -c kafka-0.tigergraph.com -n server.keystore.pk12" + mesg_blue "./`basename $0` --gen_keystore -storepass tiger123 -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_keystore -s jks -n server.keystore.jks" mesg_blue "./`basename $0` --gen_keystore" echo echo "Options:" - echo " -d,-directory -- Generation Path [default: ./SSL_files]" - echo " -p,-passphrase -- The 'keypass' and 'storepass' of keystore [default: tiger123]" + echo " -o,-output -- Output directory [default: ./SSL_OUTPUT]" echo " -s,-storetype -- Keystore storetype, e.g. jks, pkcs12 [default: jks]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" + echo " -storepass -- Keystore password [default: tiger123]" + echo " -n,-name -- Keystore file name, e.g. server.keystore.jks [default: server.keystore]" echo - note "'keypass' is the password used to secure the private key that is associated with a particular entry in the keystore." note "'storepass' is the password used to secure the keystore as a whole. " - warn "When the keystore is generated for the first time in this script, both use the same password '-p'." echo exit 0 ;; gen_subCA) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_subCA] [-d ] [-cer ] [-cerKey ] [-p ] [-c ]" + mesg_green "./`basename $0` [--gen_subCA] [-o ] [-cer ] [-cerKey ] [-p ] [-c ]" echo "Example:" - mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_files/tigergraph.com.crt -cerKey ./SSL_files/tigergraph.com.key -p tiger123 -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_subCA -o ./SSL_OUTPUT -cer ./SSL_OUTPUT/tigergraph.com.crt -cerKey ./SSL_OUTPUT/tigergraph.com.key -p tiger123 -c kafka-0.tigergraph.com" + mesg_blue "./`basename $0` --gen_subCA -cer ./SSL_OUTPUT/tigergraph.com.crt -cerKey ./SSL_OUTPUT/tigergraph.com.key -c kafka-0.tigergraph.com" echo echo "Options:" - echo " -d,-directory -- Generation Path [default: ./SSL_files]" - echo " -cer,--cer -- Parent certificate used to sign subordinate certificate" - echo " -cerKey -- Parent certificate private key file" - echo " -p,-passphrase -- Passphrase of parent certificate private key [default: tiger123]" + echo " -o,-output -- Output directory [default: ./SSL_OUTPUT]" + echo " -cer,--cer -- Superior certificate used to sign subordinate certificate" + echo " -cerKey -- Superior certificate private key file" + echo " -p,-passphrase -- Passphrase of superior certificate private key [default: tiger123]" echo " -c,-CN -- Subject CN, accept wildcard domain name [default: kafka-0.tigergraph.com]" echo exit 0 @@ -270,32 +256,33 @@ general_usage(){ gen_truststore) echo echo "Usage:" - mesg_green "./`basename $0` [--gen_truststore] [-d ] [-storepass ] [-s ]" + mesg_green "./`basename $0` [--gen_truststore] [-o ] [-storepass ] [-s ] [-n ]" echo "Example:" - mesg_blue "./`basename $0` --gen_truststore -d ./SSL_file -storepass tiger123 -s pkcs12" + mesg_blue "./`basename $0` --gen_truststore -o ./SSL_OUTPUT -storepass tiger123 -s pkcs12 -n server.truststore.pk12" mesg_blue "./`basename $0` --gen_truststore -storepass tiger123" mesg_blue "./`basename $0` --gen_truststore" echo echo "Options:" - echo " -d,-directory -- Generation Path [default: ./SSL_files]" + echo " -o,-output -- Output directory [default: ./SSL_OUTPUT]" echo " -storepass -- Truststore password [default: tiger123]" echo " -s,-storetype -- Truststore storetype, e.g. jks, pkcs12 [default: jks]" + echo " -n,-name -- Truststore file name, e.g. server.truststore.jks [default: server.truststore]" echo exit 0 ;; import_to_keystore) echo echo "Usage:" - mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-cer ] [-cerKey ] [-storepass ] [-p ]" + mesg_green "./`basename $0` [--import_to_keystore] [-keystore ] [-cer ] [-cerKey ] [-storepass ] [-p ]" echo "Example:" - mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.key -storepass 123456 -p tiger123" - mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_files/server.keystore -cer ./SSL_files/ca-root.crt -cerKey ./SSL_files/ca-root.key -storepass 123456" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_OUTPUT/server.keystore -cer ./SSL_OUTPUT/ca-root.crt -cerKey ./SSL_OUTPUT/ca-root.key -storepass 123456 -p tiger123" + mesg_blue "./`basename $0` --import_to_keystore -keystore ./SSL_OUTPUT/server.keystore -cer ./SSL_OUTPUT/ca-root.crt -cerKey ./SSL_OUTPUT/ca-root.key -storepass 123456" echo echo "Options:" echo " -keystore -- Keystore path" echo " -cer,--cer -- Certificate file path" echo " -cerKey -- Certificate private key file path" - echo " -storepass -- keystore password [default: tiger123]" + echo " -storepass -- Keystore password [default: tiger123]" echo " -p,-passphrase -- Passphrase for the certificate private key [default: tiger123]" echo exit 0 @@ -303,13 +290,13 @@ general_usage(){ import_to_truststore) echo echo "Usage:" - mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-cer ] [-storepass ]" + mesg_green "./`basename $0` [--import_to_truststore] [-truststore ] [-cer ] [-storepass ]" echo "Example:" - mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_files/server.truststore -cer ./SSL_files/ca-root.crt -storepass tiger123" + mesg_blue "./`basename $0` --import_to_truststore -truststore ./SSL_OUTPUT/server.truststore -cer ./SSL_OUTPUT/ca-root.crt -storepass tiger123" echo echo "Options:" echo " -truststore -- Truststore path" - echo " -cer -- Certificate to import" + echo " -cer -- Certificate file path" echo " -storepass -- Truststore password [default: tiger123]" echo exit 0 diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils index 3b4245f0..1a7dbfd0 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/ssl_utils @@ -24,39 +24,7 @@ generate_CARoot() { openssl req -x509 -new -nodes -key "$ca_key" -sha256 -days "$ca_days" -subj "/CN=$CN" -passin pass:"$ca_passphrase" -out "$ca_cert" prog "CARoot path: ${generate_root}/ca-root.crt" prog "private_key path: ${generate_root}/ca-root.key" -} - -check_CARoot(){ - local CA_Crt=$1 - local privateKey=$2 - - if [ ! -f $CA_Crt ];then - error "CA certificate does not exist." - exit 1 - elif [ ! -f $privateKey ];then - error "CA key file does not exist." - exit 1 - fi - - prog "Start checking certificate validity..." - if openssl verify -CApath CApath $CA_Crt | grep "OK" > /dev/null;then - prog "CA certificate validation passed." - else - error "Non-valid CA certificate:$CA_Crt" - exit 1 - fi - - # Verify whether the CARoot matches the private_key file - # Calculate the md5 value - crtMD5=$(openssl x509 -noout -modulus -in $CA_Crt | openssl md5 | awk -F"=" '{print $NF}') - privateKeyMD5=$(openssl rsa -noout -modulus -in $privateKey | openssl md5 | awk -F"=" '{print $NF}') - - if [ "$crtMD5" = "$privateKeyMD5" ]; then - prog "CA certificate and private key match successfully." - else - error "CA certificate($CA_Crt) and private key($privateKey) do not match." - exit 1 - fi + prog "passphrase for private_key: ${ca_passphrase}" } check_cert() { @@ -65,16 +33,18 @@ check_cert() { local key_pass=$3 if [ ! -f $cert_path ];then - error "Certificate file does not exist." + error "Certificate file $cert_path does not exist." exit 1 elif [ ! -f $key_path ];then - error "Certificate private-key file does not exist." + error "Certificate private-key file $key_path does not exist." exit 1 fi prog "Start checking if the private key can be decrypted with the given password..." if ! openssl rsa -in "${key_path}" -passin "pass:${key_pass}" -check > /dev/null 2>&1; then - error "The private key password is incorrect." >&2 + error "The private key is incorrect." + error "Certificate private-key file: $key_path" + error "private-key passphrase: ${key_pass}" exit 1 fi @@ -90,7 +60,9 @@ check_cert() { fi if ! diff /tmp/cert.md5 /tmp/key.md5 > /dev/null; then - error "The certificate and private key do not match." >&2 + error "The certificate and private key do not match." + error "Certificate file: ${cert_path}" + error "Certificate private-key file: ${key_path}" exit 1 fi @@ -114,7 +86,6 @@ generate_keystore(){ cd $genRoot prog "Start creating keystore..." - note "keypass and storepass will use the same password: $pass" case $storetype in pkcs12|PKCS12|pk12|PK12|p12|P12) prog "The storetype of keystore is pkcs12." @@ -164,6 +135,11 @@ generate_sub_cert() { fi cd ${generate_root} + if [ -f ${sub_cert} -o -f ${sub_key} ]; then + error "${sub_cert} or ${sub_key} already exists" + exit 1 + fi + # Create a new RSA private key for the sub-certificate openssl genrsa -out $sub_key 2048 @@ -283,6 +259,7 @@ import_to_truststore() { keytool -import -noprompt -trustcacerts -alias "$alias" -file "$import_file" -keystore "$truststore" -storepass "$storepass" if [ $? -ne 0 ]; then error "Error importing certificate to truststore" + warn "If alias already exists, you can rename the import-certificate name and import it again." exit 1 fi From 14b586d8bcc13f0f80179d017abad48b35281847 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Mon, 27 Feb 2023 16:32:13 +0800 Subject: [PATCH 16/19] QA-4212 change private_key to root-CA private_key --- tools/kafka_ssl/generate_ssl_CA/utils/env_utils | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index b23202ca..9edb854e 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -169,7 +169,7 @@ generate_help(){ echo echo "Commands:" echo " -h,-help -- Show the help" - echo " -gen_CARoot -- Generate root-CA and private_key" + echo " -gen_CARoot -- Generate root-CA and root-CA private_key" echo " -gen_keystore -- Generate keystore" echo " -gen_truststore -- Generate an empty truststore" echo " -gen_subCA -- Generate subordinate CA through superior certificate" From 8cc0ed8fff41f7b1baa3053351e96192ae595e43 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Mon, 6 Mar 2023 11:40:49 +0800 Subject: [PATCH 17/19] QA-4212 add ssl_example --- tools/kafka_ssl/README.md | 58 +++++++++++++++++++ .../kafka_ssl/generate_ssl_CA/ssl_example.sh | 35 +++++++++++ .../kafka_ssl/generate_ssl_CA/ssl_generate.sh | 36 +++++++----- tools/kafka_ssl/generate_ssl_CA/ssl_import.sh | 17 +++--- .../kafka_ssl/generate_ssl_CA/utils/env_utils | 2 + 5 files changed, 125 insertions(+), 23 deletions(-) create mode 100644 tools/kafka_ssl/README.md create mode 100644 tools/kafka_ssl/generate_ssl_CA/ssl_example.sh diff --git a/tools/kafka_ssl/README.md b/tools/kafka_ssl/README.md new file mode 100644 index 00000000..53b3aba0 --- /dev/null +++ b/tools/kafka_ssl/README.md @@ -0,0 +1,58 @@ +# SSL - certificates/keystore/truststore generate +# SSL - import key/certificate pairs into an existing keystore +# SSL - import certificate into an existing truststore + +# help commands +1. bash ssl_generate.sh -h +2. bash ssl_import.sh -h + +# help options +1. bash ssl_generate.sh -gen_keystore -h +2. bash ssl_import.sh -import_to_keystore -h + +# Example +1. Only generate a Certificate Authority (CA) key and certificate + - `bash ssl_generate.sh -gen_CARoot -c kafka-0.tigergraph.com -p 123456` + - 'kafka-0.tigergraph.com' is the CN of Certificate Authority (CA) + - '123456' is the passphrase of CA private_key + + +2. Only generate a keystore + - `bash ssl_generate.sh -gen_keystore -c kafka-0.tigergraph.com -storepass 123456` + - 'kafka-0.tigergraph.com' is the Subject CN of keystore + - '123456' is the storepass of keystore + + +3. Only generate an empty truststore + - `bash ssl_generate.sh -gen_truststore -storepass 123456` + - '123456' is the storepass of truststore + + +4. At the same time, generate CARoot/CARoot private_key, keystore, and an empty truststore + - `bash ssl_generate.sh -c kafka-0.tigergraph.com` + - 'kafka-0.tigergraph.com' is the CN + - The default passphrase of CA private_key is 'tiger123' + - The default storepass of keystore and truststore is 'tiger123' + + +5. Sign sub-certificates with an existing certificate (CARoot or other Superior certificate) + - `bash ssl_generate.sh -gen_subCA -cer ./SSL_OUTPUT/ca-root.crt -cerKey ./SSL_OUTPUT/ca-root.key -p 123456` + - './SSL_OUTPUT/ca-root.crt' is the path of higher-level CA + - './SSL_OUTPUT/ca-root.key' is the path of higher-level CA private_key + - '123456' is the passphrase of higher-level CA private_key + + +6. Import key/certificate pairs into an existing keystore + - `bash ssl_import.sh -import_to_keystore -keystore ./SSL_OUTPUT/server.keystore -cer ./SSL_OUTPUT/ca-root.crt -cerKey ./SSL_OUTPUT/ca-root.key -storepass 123456 -p tiger123` + - './SSL_OUTPUT/server.keystore' is the path of your keystore + - './SSL_OUTPUT/ca-root.crt' is the certificate path to be imported + - './SSL_OUTPUT/ca-root.key' is the certificate private_key path to be imported + - '123456' is the storepass of keystore + - 'tiger123' is the passphrase of the certificate private_key + + +7. Import certificate into an existing truststore + - `bash ssl_import.sh -import_to_truststore -truststore ./SSL_OUTPUT/server.truststore -cer ./SSL_OUTPUT/ca-root.crt -storepass 123456` + - './SSL_OUTPUT/server.truststore' is the path of your truststore + - './SSL_OUTPUT/ca-root.crt' is the certificate path to be imported + - '123456' is the storepass of the truststore \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh new file mode 100644 index 00000000..d97cd7de --- /dev/null +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh @@ -0,0 +1,35 @@ +#! /bin/bash + +cd $(dirname $0) +BASE_DIR=$(pwd) + +broker_hostname=kafka-0.tigergraph.com +client_hostname=tigergraph +output_path=./SSL_OUTPUT + +cleanup() { +if [ ! -z "${output_path}" -a -d ${output_path} ]; then + rm -fr ${output_path} +fi +} + +# cleanup +cleanup + +## step1: Generate a Certificate Authority (CA) private_key/certificate, keystore and truststore +bash ssl_generate.sh + +## step2: generate and sign Kafka broker private_key/certificate +bash ssl_generate.sh -gen_subCA -cer ${output_path}/ca-root.crt -cerKey ${output_path}/ca-root.key -c ${broker_hostname} + +## step3: import CA key/certificate pairs to keystore +bash ssl_import.sh -import_to_keystore -keystore ${output_path}/server.keystore -cer ${output_path}/ca-root.crt -cerKey ${output_path}/ca-root.key + +## step4: import Kafka broker private_key/certificate in keystore +bash ssl_import.sh -import_to_keystore -keystore ${output_path}/server.keystore -cer ${output_path}/${broker_hostname}.crt -cerKey ${output_path}/${broker_hostname}.key + +## step5: generate and sign client private_key/certificate +bash ssl_generate.sh -gen_subCA -cer ${output_path}/ca-root.crt -cerKey ${output_path}/ca-root.key -c ${client_hostname} + +## step6: import CA certificate in trustStore +bash ssl_import.sh -import_to_truststore -truststore ${output_path}/server.truststore -cer ${output_path}/ca-root.crt \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh index 89323e9a..6e64bf12 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_generate.sh @@ -152,6 +152,16 @@ else # install openssl install_openssl + # If the command is empty, --gen_CARoot, --gen_keystore, and --gen_truststore are executed by default + total_flag=($CARoot_flag $genKeystore_flag $subCA_flag $genTruststore_flag) + if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then + CARoot_flag=true + genKeystore_flag=true + genTruststore_flag=true + note "The input command is empty." + note "'--gen_CARoot', '--gen_keystore', and '--gen_truststore' are executed by default." + fi + # generate root CA if [[ ! -z $CARoot_flag ]]; then prog "root-CA output directory: $generate_root" @@ -167,13 +177,15 @@ else # generate keystore if [[ ! -z $genKeystore_flag ]]; then if [[ -z $storeName ]]; then - storeName=server.keystore + keystoreName=server.keystore + else + keystoreName=${storeName}.keystore fi prog "keystore output directory: $generate_root" prog "Keystore -Dname CN: $CN" - prog "keystore name: $storeName" - generate_keystore ${generate_root} ${pass} ${CN} ${storetype} ${storeName} - keystore=${generate_root}/${storeName} + prog "keystore name: $keystoreName" + generate_keystore ${generate_root} ${storepass} ${CN} ${storetype} ${keystoreName} + keystore=${generate_root}/${keystoreName} prog "Generate keystore: $keystore" note "View keystore: keytool -list -v -keystore $keystore -storepass $pass" fi @@ -195,23 +207,17 @@ else # generate truststore if [[ ! -z ${genTruststore_flag:-} ]]; then if [[ -z $storeName ]]; then - storeName=server.truststore + truststoreName=server.truststore + else + truststoreName=${storeName}.truststore fi - truststore="${generate_root}/${storeName}" + truststore="${generate_root}/${truststoreName}" if [ ! -f "${truststore}" ]; then prog "Generate truststore: ${truststore}" - generate_truststore "${generate_root}" "${storeName}" "${storepass}" "${storetype}" + generate_truststore "${generate_root}" "${truststoreName}" "${storepass}" "${storetype}" else warn "${truststore} already exists, skipping generation!" fi note "View truststore: keytool -list -v -keystore ${truststore} -storepass ${storepass}" fi - - # enter at least one command - total_flag=($CARoot_flag $genKeystore_flag $subCA_flag $genTruststore_flag) - if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then - error "Please enter at least one Command" - generate_help - exit 1 - fi fi \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_import.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_import.sh index 1297fd55..c546eec7 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_import.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_import.sh @@ -140,6 +140,15 @@ else # install openssl install_openssl + # enter at least one command + total_flag=($importToKeystore_flag $importToTruststore_flag) + if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then + importToKeystore_flag=true + importToTruststore_flag=true + note "The input command is empty." + note "'--import_to_keystore' and '--import_to_truststore' are executed by default." + fi + # import key-cert pair to keystore if [[ ! -z $importToKeystore_flag ]]; then [[ -z "$CA" || -z "$CAkey" || -z "$keystore" ]] \ @@ -164,12 +173,4 @@ else check_file ${CA} 1 import_to_truststore ${truststore} ${CA} ${alias} ${storepass} fi - - # enter at least one command - total_flag=($importToKeystore_flag $importToTruststore_flag) - if [[ -z $(IFS=,; echo "${total_flag[*]}") ]]; then - error "Please enter at least one Command" - import_help - exit 1 - fi fi \ No newline at end of file diff --git a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils index 9edb854e..9bda44f4 100644 --- a/tools/kafka_ssl/generate_ssl_CA/utils/env_utils +++ b/tools/kafka_ssl/generate_ssl_CA/utils/env_utils @@ -176,6 +176,8 @@ generate_help(){ echo warn "Using option '-i' will install openjdk-1.8.0 and openssl, otherwise openjdk-1.8.0 and openssl will not be installed. Please note that if the local machine does not have a java environment, some operations will fail." + echo + warn "If the command is empty, '--gen_CARoot', '--gen_keystore', and '--gen_truststore' are executed by default." echo note "Use './`basename $0` -command_name -help' for usage of command_name" echo From acf0d5a4296d4432fa07d7522d2c523e5cd2c999 Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Mon, 6 Mar 2023 11:46:09 +0800 Subject: [PATCH 18/19] QA-4212 modify README --- tools/kafka_ssl/README.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tools/kafka_ssl/README.md b/tools/kafka_ssl/README.md index 53b3aba0..3615a674 100644 --- a/tools/kafka_ssl/README.md +++ b/tools/kafka_ssl/README.md @@ -36,10 +36,11 @@ 5. Sign sub-certificates with an existing certificate (CARoot or other Superior certificate) - - `bash ssl_generate.sh -gen_subCA -cer ./SSL_OUTPUT/ca-root.crt -cerKey ./SSL_OUTPUT/ca-root.key -p 123456` + - `bash ssl_generate.sh -gen_subCA -cer ./SSL_OUTPUT/ca-root.crt -cerKey ./SSL_OUTPUT/ca-root.key -p 123456` -c tigergraph - './SSL_OUTPUT/ca-root.crt' is the path of higher-level CA - './SSL_OUTPUT/ca-root.key' is the path of higher-level CA private_key - '123456' is the passphrase of higher-level CA private_key + - 'tigergraph' is the CN of your sub-certificate 6. Import key/certificate pairs into an existing keystore From f08eb4777dac61baff91ddd4a6e41852ef647f5f Mon Sep 17 00:00:00 2001 From: xiongyiping123 Date: Wed, 8 Mar 2023 11:28:52 +0800 Subject: [PATCH 19/19] QA-4212 add default value --- tools/kafka_ssl/generate_ssl_CA/ssl_example.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh b/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh index d97cd7de..a16466aa 100644 --- a/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh +++ b/tools/kafka_ssl/generate_ssl_CA/ssl_example.sh @@ -3,8 +3,8 @@ cd $(dirname $0) BASE_DIR=$(pwd) -broker_hostname=kafka-0.tigergraph.com -client_hostname=tigergraph +broker_hostname=${1:-kafka-0.tigergraph.com} +client_hostname=${2:-tigergraph} output_path=./SSL_OUTPUT cleanup() {