diff --git a/templates/master/00-master/_base/files/usr-local-bin-etcd-member-recover-sh.yaml b/templates/master/00-master/_base/files/usr-local-bin-etcd-member-recover-sh.yaml new file mode 100644 index 0000000000..ded2adcabc --- /dev/null +++ b/templates/master/00-master/_base/files/usr-local-bin-etcd-member-recover-sh.yaml @@ -0,0 +1,79 @@ +filesystem: "root" +mode: 0755 +path: "/usr/local/bin/etcd-member-recover.sh" +contents: + inline: | + #!/usr/bin/env bash + + # example + # export SETUP_ETCD_ENVIRONMENT=$(oc adm release info --image-for setup-etcd-environment --registry-config=./config.json) + # export KUBE_CLIENT_AGENT=$(oc adm release info --image-for kube-client-agent --registry-config=./config.json) + # sudo -E ./etcd-member-recover.sh 192.168.1.100 + + if [[ $EUID -ne 0 ]]; then + echo "This script must be run as root" + exit 1 + fi + + : ${SETUP_ETCD_ENVIRONMENT:?"Need to set SETUP_ETCD_ENVIRONMENT"} + : ${KUBE_CLIENT_AGENT:?"Need to set KUBE_CLIENT_AGENT"} + + usage () { + echo 'Recovery server IP address required: ./etcd-member-recover.sh 192.168.1.100' + exit + } + + if [ "$1" == "" ]; then + usage + fi + + RECOVERY_SERVER_IP=$1 + + ASSET_DIR=./assets + ASSET_DIR_TMP="$ASSET_DIR/tmp" + CONFIG_FILE_DIR=/etc/kubernetes + MANIFEST_DIR="${CONFIG_FILE_DIR}/manifests" + MANIFEST_STOPPED_DIR=/etc/kubernetes/manifests-stopped + + ETCD_MANIFEST="${MANIFEST_DIR}/etcd-member.yaml" + ETCD_CONFIG=/etc/etcd/etcd.conf + ETCDCTL=$ASSET_DIR/bin/etcdctl + ETCD_VERSION=v3.3.10 + ETCD_DATA_DIR=/var/lib/etcd + ETCD_STATIC_RESOURCES="${CONFIG_FILE_DIR}/static-pod-resources/etcd-member" + + SHARED=/usr/local/share/openshift-recovery + TEMPLATE="$SHARED/template/etcd-generate-certs.yaml.template" + + source "/usr/local/bin/openshift-recovery-tools" + + function run { + init + dl_etcdctl + backup_manifest + backup_etcd_conf + backup_etcd_client_certs + stop_etcd + backup_data_dir + backup_certs + remove_certs + gen_config + download_cert_recover_template + DISCOVERY_DOMAIN=$(grep -oP '(?<=discovery-srv=).*[^"]' $ASSET_DIR/backup/etcd-member.yaml ) + if [ -z "$DISCOVERY_DOMAIN" ]; then + echo "Discovery domain can not be extracted from $ASSET_DIR/backup/etcd-member.yaml" + exit 1 + fi + CLUSTER_NAME=$(echo ${DISCOVERY_DOMAIN} | grep -oP '^.*?(?=\.)') + populate_template '__ETCD_DISCOVERY_DOMAIN__' "$DISCOVERY_DOMAIN" "$TEMPLATE" "$ASSET_DIR/tmp/etcd-generate-certs.stage1" + populate_template '__SETUP_ETCD_ENVIRONMENT__' "$SETUP_ETCD_ENVIRONMENT" "$ASSET_DIR/tmp/etcd-generate-certs.stage1" "$ASSET_DIR/tmp/etcd-generate-certs.stage2" + populate_template '__KUBE_CLIENT_AGENT__' "$KUBE_CLIENT_AGENT" "$ASSET_DIR/tmp/etcd-generate-certs.stage2" "$MANIFEST_STOPPED_DIR/etcd-generate-certs.yaml" + start_cert_recover + verify_certs + stop_cert_recover + patch_manifest + etcd_member_add + start_etcd + } + + run diff --git a/templates/master/00-master/_base/files/usr-local-bin-etcd-snapshot-restore-sh.yaml b/templates/master/00-master/_base/files/usr-local-bin-etcd-snapshot-restore-sh.yaml new file mode 100644 index 0000000000..3c9c4b284f --- /dev/null +++ b/templates/master/00-master/_base/files/usr-local-bin-etcd-snapshot-restore-sh.yaml @@ -0,0 +1,53 @@ +filesystem: "root" +mode: 0755 +path: "/usr/local/bin/etcd-snapshot-restore.sh" +contents: + inline: | + #!/usr/bin/env bash + + set -o errexit + set -o pipefail + + # example + # etcd-snapshot-restore.sh $path-to-snapshot + + if [[ $EUID -ne 0 ]]; then + echo "This script must be run as root" + exit 1 + fi + + ASSET_DIR=./assets + SNAPSHOT_FILE="${ASSET_DIR}/backup/etcd/member/snap/db" + + if [ "$1" != "" ]; then + SNAPSHOT_FILE="$1" + fi + + CONFIG_FILE_DIR=/etc/kubernetes + MANIFEST_DIR="${CONFIG_FILE_DIR}/manifests" + MANIFEST_STOPPED_DIR="${CONFIG_FILE_DIR}/manifests-stopped" + ETCD_VERSION=v3.3.10 + ETCDCTL="${ASSET_DIR}/bin/etcdctl" + ETCD_DATA_DIR=/var/lib/etcd + ETCD_MANIFEST="${MANIFEST_DIR}/etcd-member.yaml" + ETCD_STATIC_RESOURCES="${CONFIG_FILE_DIR}/static-pod-resources/etcd-member" + STOPPED_STATIC_PODS="${ASSET_DIR}/tmp/stopped-static-pods" + + source "/usr/local/bin/openshift-recovery-tools" + + function run { + init + dl_etcdctl + backup_manifest + stop_static_pods + stop_etcd + stop_kubelet + stop_all_containers + backup_data_dir + remove_data_dir + restore_snapshot + start_static_pods + start_kubelet + } + + run diff --git a/templates/master/00-master/_base/files/usr-local-bin-openshift-recovery-tools-sh.yaml b/templates/master/00-master/_base/files/usr-local-bin-openshift-recovery-tools-sh.yaml new file mode 100644 index 0000000000..dc604e80b4 --- /dev/null +++ b/templates/master/00-master/_base/files/usr-local-bin-openshift-recovery-tools-sh.yaml @@ -0,0 +1,313 @@ +filesystem: "root" +mode: 0644 +path: "/usr/local/bin/openshift-recovery-tools" +contents: + inline: | + #!/usr/bin/env bash + + init() { + ASSET_BIN=${ASSET_DIR}/bin + if [ ! -d "$ASSET_BIN" ]; then + echo "Creating asset directory ${ASSET_DIR}" + for dir in {bin,tmp,shared,backup,templates,restore,manifests}; do + /usr/bin/mkdir -p ${ASSET_DIR}/${dir} + done + fi + } + + # download and test etcdctl from upstream release assets + dl_etcdctl() { + GOOGLE_URL=https://storage.googleapis.com/etcd + DOWNLOAD_URL=${GOOGLE_URL} + + echo "Downloading etcdctl binary.." + curl -s -L ${DOWNLOAD_URL}/${ETCD_VERSION}/etcd-${ETCD_VERSION}-linux-amd64.tar.gz -o $ASSET_DIR/tmp/etcd-${ETCD_VERSION}-linux-amd64.tar.gz \ + && tar -xzf $ASSET_DIR/tmp/etcd-${ETCD_VERSION}-linux-amd64.tar.gz -C $ASSET_DIR/shared --strip-components=1 \ + && mv $ASSET_DIR/shared/etcdctl $ASSET_DIR/bin \ + && rm $ASSET_DIR/shared/etcd \ + && ETCDCTL_API=3 $ASSET_DIR/bin/etcdctl version + } + + #backup etcd client certs + backup_etcd_client_certs() { + echo "Trying to backup etcd client certs.." + if [ -f "$ASSET_DIR/backup/etcd-ca-bundle.crt" ] && [ -f "$ASSET_DIR/backup/etcd-client.crt" ] && [ -f "$ASSET_DIR/backup/etcd-client.key" ]; then + echo "etcd client certs already backed up and available $ASSET_DIR/backup/" + else + for i in {1..10}; do + SECRET_DIR="${CONFIG_FILE_DIR}/static-pod-resources/kube-apiserver-pod-${i}/secrets/etcd-client" + CONFIGMAP_DIR="${CONFIG_FILE_DIR}/static-pod-resources/kube-apiserver-pod-${i}/configmaps/etcd-serving-ca" + if [ -f "$CONFIGMAP_DIR/ca-bundle.crt" ] && [ -f "$SECRET_DIR/tls.crt" ] && [ -f "$SECRET_DIR/tls.key" ]; then + cp $CONFIGMAP_DIR/ca-bundle.crt $ASSET_DIR/backup/etcd-ca-bundle.crt + cp $SECRET_DIR/tls.crt $ASSET_DIR/backup/etcd-client.crt + cp $SECRET_DIR/tls.key $ASSET_DIR/backup/etcd-client.key + break + else + echo "$SECRET_DIR does not contain etcd client certs, trying next source .." + fi + done + fi + } + + # backup current etcd-member pod manifest + backup_manifest() { + if [ -e "${ASSET_DIR}/backup/etcd-member.yaml" ]; then + echo "etcd-member.yaml found in ${ASSET_DIR}/backup/" + else + echo "Backing up ${ETCD_MANIFEST} to ${ASSET_DIR}/backup/" + cp ${ETCD_MANIFEST} ${ASSET_DIR}/backup/ + fi + } + + # backup etcd.conf + backup_etcd_conf() { + if [ -e "${ASSET_DIR}/backup/etcd.conf" ]; then + echo "etcd.conf backup upready exists $ASSET_DIR/backup/etcd.conf" + else + echo "Backing up /etc/etcd/etcd.conf to ${ASSET_DIR}/backup/" + cp /etc/etcd/etcd.conf ${ASSET_DIR}/backup/ + fi + } + + backup_data_dir() { + if [ -f "$ASSET_DIR/backup/etcd/member/snap/db" ]; then + echo "etcd data-dir backup found $ASSET_DIR/backup/etcd.." + elif [ ! -f "${ETCD_DATA_DIR}/member/snap/db" ]; then + echo "Local etcd snapshot file not found, backup skipped.." + else + echo "Backing up etcd data-dir.." + cp -rap ${ETCD_DATA_DIR} $ASSET_DIR/backup/ + fi + } + + # backup etcd peer, server and metric certs + backup_certs() { + COUNT=$(ls $ETCD_STATIC_RESOURCES/system\:etcd-* 2>/dev/null | wc -l) + BACKUP_COUNT=$(ls $ASSET_DIR/backup/system\:etcd-* 2>/dev/null | wc -l) + + if [ "$BACKUP_COUNT" -gt 1 ]; then + echo "etcd TLS certificate backups found in $ASSET_DIR/backup.." + elif [ "$COUNT" -eq 0 ]; then + echo "etcd TLS certificates not found, backup skipped.." + else + echo "Backing up etcd certificates.." + cp $ETCD_STATIC_RESOURCES/system\:etcd-* $ASSET_DIR/backup/ + fi + } + + # stop etcd by moving the manifest out of /etcd/kubernetes/manifests + # we wait for all etcd containers to die. + stop_etcd() { + echo "Stopping etcd.." + + if [ ! -d "$MANIFEST_STOPPED_DIR" ]; then + mkdir $MANIFEST_STOPPED_DIR + fi + + if [ -e "$ETCD_MANIFEST" ]; then + mv $ETCD_MANIFEST $MANIFEST_STOPPED_DIR + fi + + for name in {etcd-member,etcd-metric} + do + while [ ! -z "$(crictl pods -name $name --state Ready -q)" ]; do + echo "Waiting for $name to stop" + sleep 10 + done + done + } + + remove_data_dir() { + echo "Removing etcd data-dir ${ETCD_DATA_DIR}" + rm -rf ${ETCD_DATA_DIR} + } + + remove_certs() { + COUNT=$(ls $ETCD_STATIC_RESOURCES/system\:etcd-* 2>/dev/null | wc -l) + if [ "$COUNT" -gt 1 ]; then + echo "Removing etcd certs.." + rm -f $ETCD_STATIC_RESOURCES/system\:etcd-* + fi + } + + restore_snapshot() { + HOSTNAME=$(hostname) + HOSTDOMAIN=$(hostname -d) + ETCD_NAME=etcd-member-${HOSTNAME}.${HOSTDOMAIN} + + source /run/etcd/environment + + if [ ! -f "$SNAPSHOT_FILE" ]; then + echo "Snapshot file not found, restore failed: $SNAPSHOT_FILE." + exit 1 + fi + + sleep 2 + + echo "Restoring etcd member $ETCD_NAME from snapshot.." + + env ETCDCTL_API=3 ${ETCDCTL} snapshot restore $SNAPSHOT_FILE \ + --name $ETCD_NAME \ + --initial-cluster ${ETCD_NAME}=https://${ETCD_DNS_NAME}:2380 \ + --initial-cluster-token etcd-cluster-1 \ + --skip-hash-check=true \ + --initial-advertise-peer-urls https://${ETCD_IPV4_ADDRESS}:2380 \ + --data-dir $ETCD_DATA_DIR + } + + patch_manifest() { + echo "Patching etcd-member manifest.." + cp $ASSET_DIR/backup/etcd-member.yaml $ASSET_DIR/tmp/etcd-member.yaml.template + sed -i /' '--discovery-srv/d $ASSET_DIR/tmp/etcd-member.yaml.template + mv $ASSET_DIR/tmp/etcd-member.yaml.template $MANIFEST_STOPPED_DIR/etcd-member.yaml + } + + # generate a kubeconf like file for the cert agent to consume and contact signer. + gen_config() { + CA=$(base64 $ASSET_DIR/backup/etcd-ca-bundle.crt | tr -d '\n') + CERT=$(base64 $ASSET_DIR/backup/etcd-client.crt | tr -d '\n') + KEY=$(base64 $ASSET_DIR/backup/etcd-client.key | tr -d '\n') + + cat > $ETCD_STATIC_RESOURCES/.recoveryconfig << EOF + clusters: + - cluster: + certificate-authority-data: ${CA} + server: https://${RECOVERY_SERVER_IP}:9943 + name: ${CLUSTER_NAME} + contexts: + - context: + cluster: ${CLUSTER_NAME} + user: kubelet + name: kubelet + current-context: kubelet + preferences: {} + users: + - name: kubelet + user: + client-certificate-data: ${CERT} + client-key-data: ${KEY} + EOF + } + + # add member cluster + etcd_member_add() { + source /run/etcd/environment + HOSTNAME=$(hostname) + HOSTDOMAIN=$(hostname -d) + ETCD_NAME=etcd-member-${HOSTNAME}.${HOSTDOMAIN} + + if [ -d "$ETCD_DATA_DIR" ]; then + rm -rf $ETCD_DATA_DIR + fi + + echo "Updating etcd membership.." + + RESPONSE=$(env ETCDCTL_API=3 $ETCDCTL --cert $ASSET_DIR/backup/etcd-client.crt --key $ASSET_DIR/backup/etcd-client.key --cacert $ASSET_DIR/backup/etcd-ca-bundle.crt \ + --endpoints ${RECOVERY_SERVER_IP}:2379 member add $ETCD_NAME --peer-urls=https://${ETCD_DNS_NAME}:2380) + + if [ $? -eq 0 ]; then + echo "$RESPONSE" + APPEND_CONF=$(echo "$RESPONSE" | sed -e '1,2d') + echo -e "\n\n#[recover]\n$APPEND_CONF" >> $ETCD_CONFIG + else + echo "$RESPONSE" + exit 1 + fi + } + + start_etcd() { + echo "Starting etcd.." + mv ${MANIFEST_STOPPED_DIR}/etcd-member.yaml $MANIFEST_DIR + } + + download_cert_recover_template() { + curl -s https://raw.githubusercontent.com/hexfusion/openshift-recovery/master/manifests/etcd-generate-certs.yaml.template -o $ASSET_DIR/templates/etcd-generate-certs.yaml.template + } + + populate_template() { + FIND="$1" + REPLACE="$2" + TEMPLATE="$3" + OUT="$4" + + echo "Populating template $TEMPLATE" + + if [ -z "$FIND" ] || [ -z "$REPLACE" ] || [ -z "$TEMPLATE" ] || [ -z "$OUT" ]; then + echo "populate_template requires 4 arguments FIND, REPLACE, TEMPLATE and OUT" + exit 1 + elif [ ! -f "$TEMPLATE" ]; then + echo "template $TEMPLATE does not exist" + exit 1 + fi + + TMP_FILE=$(date +"%m-%d-%Y-%H%M") + cp $TEMPLATE "$ASSET_DIR/tmp/${TMP_FILE}" + + sed -i "s|${FIND}|${REPLACE}|" "$ASSET_DIR/tmp/${TMP_FILE}" + mv "$ASSET_DIR/tmp/${TMP_FILE}" "$OUT" + } + + start_cert_recover() { + echo "Starting etcd client cert recovery agent.." + mv ${MANIFEST_STOPPED_DIR}/etcd-generate-certs.yaml $MANIFEST_DIR + } + + verify_certs() { + while [ "$(ls $ETCD_STATIC_RESOURCES | wc -l)" -lt 9 ]; do + echo "Waiting for certs to generate.." + sleep 10 + done + } + + stop_cert_recover() { + echo "Stopping cert recover.." + + if [ -f "${CONFIG_FILE_DIR}/manifests/etcd-generate-certs.yaml" ]; then + mv ${CONFIG_FILE_DIR}/manifests/etcd-generate-certs.yaml $MANIFEST_STOPPED_DIR + fi + + for name in {generate-env,generate-certs}; do + while [ ! -z "$(crictl pods -name $name --state Ready -q)" ]; do + echo "Waiting for $name to stop" + sleep 10 + done + done + } + + stop_static_pods() { + echo "Stopping all static pods.." + + if [ ! -d "$MANIFEST_STOPPED_DIR" ]; then + mkdir $MANIFEST_STOPPED_DIR + fi + + find ${MANIFEST_DIR} -maxdepth 1 -type f -printf "%f\n" > $STOPPED_STATIC_PODS + + while read STATIC_POD; do + echo "..stopping $STATIC_POD" + mv ${MANIFEST_DIR}/${STATIC_POD} $MANIFEST_STOPPED_DIR + done <$STOPPED_STATIC_PODS + } + + start_static_pods() { + echo "Starting static pods.." + while read STATIC_POD; do + echo "..starting $STATIC_POD" + mv ${MANIFEST_STOPPED_DIR}/${STATIC_POD} $MANIFEST_DIR + done <$STOPPED_STATIC_PODS + } + + stop_kubelet() { + echo "Stopping kubelet.." + systemctl stop kubelet.service + } + + start_kubelet() { + echo "Starting kubelet.." + systemctl start kubelet.service + } + + stop_all_containers() { + echo "Stopping all containers.." + crictl ps -q | xargs -r crictl stop + } diff --git a/templates/master/00-master/_base/files/usr-local-bin-tokenize-signer-sh.yaml b/templates/master/00-master/_base/files/usr-local-bin-tokenize-signer-sh.yaml new file mode 100644 index 0000000000..12132b86a6 --- /dev/null +++ b/templates/master/00-master/_base/files/usr-local-bin-tokenize-signer-sh.yaml @@ -0,0 +1,42 @@ +filesystem: "root" +mode: 0755 +path: "/usr/local/bin/tokenize-signer.sh" +contents: + inline: | + #!/usr/bin/env bash + + set -o errexit + set -o pipefail + + # example + # export KUBE_ETCD_SIGNER_SERVER=$(oc adm release info --image-for kube-etcd-signer-server --registry-config=./config.json) + # sudo -E ./tokenize-signer.sh ip-10-0-134-97 + + : ${KUBE_ETCD_SIGNER_SERVER:?"Need to set KUBE_ETCD_SIGNER_SERVER"} + + usage () { + echo 'Hostname required: ./tokenize-signer.sh ip-10-0-134-97' + exit + } + + if [ "$1" == "" ]; then + usage + fi + + MASTER_HOSTNAME=$1 + + ASSET_DIR=./assets + SHARED=/usr/local/share/openshift-recovery + TEMPLATE=$SHARED/template/kube-etcd-cert-signer.yaml.template + TEMPLATE_TMP=$ASSET_DIR/tmp/kube-etcd-cert-signer.yaml.stage1 + + source "/usr/local/bin/openshift-recovery-tools" + + function run { + init + populate_template '__MASTER_HOSTNAME__' "$MASTER_HOSTNAME" "$TEMPLATE" "$TEMPLATE_TMP" + populate_template '__KUBE_ETCD_SIGNER_SERVER__' "$KUBE_ETCD_SIGNER_SERVER" "$TEMPLATE_TMP" "$ASSET_DIR/manifests/kube-etcd-cert-signer.yaml" + echo "Tokenized template now ready: $ASSET_DIR/manifests/kube-etcd-cert-signer.yaml" + } + + run diff --git a/templates/master/00-master/_base/files/usr-local-share-openshift-recovery-template-etcd-generate-certs-yaml-template.yaml b/templates/master/00-master/_base/files/usr-local-share-openshift-recovery-template-etcd-generate-certs-yaml-template.yaml new file mode 100644 index 0000000000..37749dfa46 --- /dev/null +++ b/templates/master/00-master/_base/files/usr-local-share-openshift-recovery-template-etcd-generate-certs-yaml-template.yaml @@ -0,0 +1,86 @@ +filesystem: "root" +mode: 0644 +path: "/usr/local/share/openshift-recovery/template/etcd-generate-certs.yaml.template" +contents: + inline: | + apiVersion: v1 + kind: Pod + metadata: + name: etcd-generate-certs + namespace: openshift-etcd + labels: + k8s-app: etcd + spec: + containers: + - name: generate-env + image: "__SETUP_ETCD_ENVIRONMENT__" + args: + - "run" + - "--discovery-srv=__ETCD_DISCOVERY_DOMAIN__" + - "--output-file=/run/etcd/environment" + - "--v=4" + volumeMounts: + - name: discovery + mountPath: /run/etcd/ + - name: generate-certs + image: "__KUBE_CLIENT_AGENT__" + command: + - /bin/sh + - -c + - | + #!/bin/sh + set -euxo pipefail + + source /run/etcd/environment + + [ -e /etc/ssl/etcd/system:etcd-server:${ETCD_DNS_NAME}.crt -a \ + -e /etc/ssl/etcd/system:etcd-server:${ETCD_DNS_NAME}.key ] || \ + kube-client-agent \ + request \ + --kubeconfig=/etc/ssl/etcd/.recoveryconfig \ + --orgname=system:etcd-servers \ + --assetsdir=/etc/ssl/etcd \ + --dnsnames=localhost,etcd.kube-system.svc,etcd.kube-system.svc.cluster.local,etcd.openshift-etcd.svc,etcd.openshift-etcd.svc.cluster.local,"${ETCD_WILDCARD_DNS_NAME}" \ + --commonname=system:etcd-server:${ETCD_DNS_NAME} \ + --ipaddrs=${ETCD_IPV4_ADDRESS},127.0.0.1 \ + + [ -e /etc/ssl/etcd/system:etcd-peer:${ETCD_DNS_NAME}.crt -a \ + -e /etc/ssl/etcd/system:etcd-peer:${ETCD_DNS_NAME}.key ] || \ + kube-client-agent \ + request \ + --kubeconfig=/etc/ssl/etcd/.recoveryconfig \ + --orgname=system:etcd-peers \ + --assetsdir=/etc/ssl/etcd \ + --dnsnames=${ETCD_DNS_NAME},__ETCD_DISCOVERY_DOMAIN__ \ + --commonname=system:etcd-peer:${ETCD_DNS_NAME} \ + --ipaddrs=${ETCD_IPV4_ADDRESS} \ + + [ -e /etc/ssl/etcd/system:etcd-metric:${ETCD_DNS_NAME}.crt -a \ + -e /etc/ssl/etcd/system:etcd-metric:${ETCD_DNS_NAME}.key ] || \ + kube-client-agent \ + request \ + --kubeconfig=/etc/ssl/etcd/.recoveryconfig \ + --orgname=system:etcd-metrics \ + --assetsdir=/etc/ssl/etcd \ + --dnsnames=localhost,etcd.kube-system.svc,etcd.kube-system.svc.cluster.local,etcd.openshift-etcd.svc,etcd.openshift-etcd.svc.cluster.local,${ETCD_DNS_NAME} \ + --commonname=system:etcd-metric:${ETCD_DNS_NAME} \ + --ipaddrs=${ETCD_IPV4_ADDRESS} \ + + terminationMessagePolicy: FallbackToLogsOnError + volumeMounts: + - name: discovery + mountPath: /run/etcd/ + - name: certs + mountPath: /etc/ssl/etcd/ + hostNetwork: true + priorityClassName: system-node-critical + tolerations: + - operator: "Exists" + restartPolicy: Always + volumes: + - name: certs + hostPath: + path: /etc/kubernetes/static-pod-resources/etcd-member + - name: discovery + hostPath: + path: /run/etcd diff --git a/templates/master/00-master/_base/files/usr-local-share-openshift-recovery-template-kube-etcd-cert-signer-yaml-template.yaml b/templates/master/00-master/_base/files/usr-local-share-openshift-recovery-template-kube-etcd-cert-signer-yaml-template.yaml new file mode 100644 index 0000000000..1837cb9159 --- /dev/null +++ b/templates/master/00-master/_base/files/usr-local-share-openshift-recovery-template-kube-etcd-cert-signer-yaml-template.yaml @@ -0,0 +1,77 @@ +filesystem: "root" +mode: 0644 +path: "/usr/local/share/openshift-recovery/template/kube-etcd-cert-signer.yaml.template" +contents: + inline: | + apiVersion: v1 + kind: Pod + metadata: + name: etcd-signer + namespace: openshift-config + labels: + k8s-app: etcd + spec: + containers: + - name: etcd-signer + image: "__KUBE_ETCD_SIGNER_SERVER__" + command: + - /bin/sh + - -c + - | + #!/bin/sh + set -euox pipefail + + source /run/etcd/environment + + exec kube-etcd-signer-server serve \ + --cacrt=/etc/ssl/etcd/signer/tls.crt \ + --cakey=/etc/ssl/etcd/signer/tls.key \ + --metric-cacrt=/etc/ssl/etcd/metric-signer/tls.crt \ + --metric-cakey=/etc/ssl/etcd/metric-signer/tls.key \ + --servcrt=/etc/ssl/etcd/system:etcd-server:${ETCD_DNS_NAME}.crt \ + --servkey=/etc/ssl/etcd/system:etcd-server:${ETCD_DNS_NAME}.key \ + --address=0.0.0.0:9943 \ + --csrdir=/tmp \ + --peercertdur=26280h \ + --servercertdur=26280h \ + --metriccertdur=26280h + resources: + requests: + memory: 600Mi + cpu: 300m + terminationMessagePolicy: FallbackToLogsOnError + volumeMounts: + - name: discovery + mountPath: /run/etcd/ + - name: etcd-certs + mountPath: /etc/ssl/etcd/ + - name: etcd-signer + mountPath: /etc/ssl/etcd/signer + - name: etcd-metric-signer + mountPath: /etc/ssl/etcd/metric-signer + ports: + - name: server + containerPort: 9943 + protocol: TCP + securityContext: + privileged: true + hostNetwork: true + nodeSelector: + kubernetes.io/hostname: "__MASTER_HOSTNAME__" + priorityClassName: system-node-critical + tolerations: + - operator: "Exists" + restartPolicy: Always + volumes: + - name: etcd-certs + hostPath: + path: /etc/kubernetes/static-pod-resources/etcd-member + - name: discovery + hostPath: + path: /run/etcd + - name: etcd-signer + secret: + secretName: etcd-signer + - name: etcd-metric-signer + secret: + secretName: etcd-metric-signer