@@ -22,12 +22,14 @@ function kops_create_cluster() {
2222 CLUSTER_NAME=${2}
2323 BIN=${3}
2424 ZONES=${4}
25- INSTANCE_TYPE=${5}
26- K8S_VERSION=${6}
27- CLUSTER_FILE=${7}
28- KUBECONFIG=${8}
29- KOPS_PATCH_FILE=${9}
30- KOPS_STATE_FILE=${10}
25+ NODE_COUNT=${5}
26+ INSTANCE_TYPE=${6}
27+ K8S_VERSION=${7}
28+ CLUSTER_FILE=${8}
29+ KUBECONFIG=${9}
30+ KOPS_PATCH_FILE=${10}
31+ KOPS_PATCH_NODE_FILE=${11}
32+ KOPS_STATE_FILE=${12}
3133
3234 generate_ssh_key " ${SSH_KEY_PATH} "
3335
@@ -39,15 +41,18 @@ function kops_create_cluster() {
3941 ${BIN} create cluster --state " ${KOPS_STATE_FILE} " \
4042 --ssh-public-key=" ${SSH_KEY_PATH} " .pub \
4143 --zones " ${ZONES} " \
42- --node-count=3 \
44+ --node-count=" ${NODE_COUNT} " \
4345 --node-size=" ${INSTANCE_TYPE} " \
4446 --kubernetes-version=" ${K8S_VERSION} " \
4547 --dry-run \
46- -o json \
48+ -o yaml \
4749 " ${CLUSTER_NAME} " > " ${CLUSTER_FILE} "
4850
4951 if test -f " $KOPS_PATCH_FILE " ; then
50- kops_patch_cluster_file " $CLUSTER_FILE " " $KOPS_PATCH_FILE "
52+ kops_patch_cluster_file " $CLUSTER_FILE " " $KOPS_PATCH_FILE " " Cluster" " "
53+ fi
54+ if test -f " $KOPS_PATCH_NODE_FILE " ; then
55+ kops_patch_cluster_file " $CLUSTER_FILE " " $KOPS_PATCH_NODE_FILE " " InstanceGroup" " Node"
5156 fi
5257
5358 loudecho " Creating cluster $CLUSTER_NAME with $CLUSTER_FILE "
@@ -88,36 +93,63 @@ function kops_delete_cluster() {
8893 ${BIN} delete cluster --name " ${CLUSTER_NAME} " --state " ${KOPS_STATE_FILE} " --yes
8994}
9095
91- # TODO switch this to python or work exclusively with yaml, all this
92- # hacking with jq stinks!
96+ # TODO switch this to python, work exclusively with yaml, use kops toolbox
97+ # template/kops set?, all this hacking with jq stinks!
9398function kops_patch_cluster_file() {
94- CLUSTER_FILE=${1} # input must be json
99+ CLUSTER_FILE=${1} # input must be yaml
95100 KOPS_PATCH_FILE=${2} # input must be yaml
101+ KIND=${3} # must be either Cluster or InstanceGroup
102+ ROLE=${4} # must be either Master or Node
96103
97104 loudecho " Patching cluster $CLUSTER_NAME with $KOPS_PATCH_FILE "
98105
99- # Temporary intermediate files for patching
106+ # Temporary intermediate files for patching, don't mutate CLUSTER_FILE until
107+ # the end
108+ CLUSTER_FILE_JSON=$CLUSTER_FILE .json
100109 CLUSTER_FILE_0=$CLUSTER_FILE .0
101110 CLUSTER_FILE_1=$CLUSTER_FILE .1
102111
103- # Output is an array of Cluster and InstanceGroups
104- jq ' .[] | select(.kind=="Cluster")' " $CLUSTER_FILE " > " $CLUSTER_FILE_0 "
112+ # HACK convert the multiple yaml documents to an array of json objects
113+ yaml_to_json " $CLUSTER_FILE " " $CLUSTER_FILE_JSON "
114+
115+ # Find the json objects to patch
116+ FILTER=" .[] | select(.kind==\" $KIND \" )"
117+ if [ -n " $ROLE " ]; then
118+ FILTER=" $FILTER | select(.spec.role==\" $ROLE \" )"
119+ fi
120+ jq " $FILTER " " $CLUSTER_FILE_JSON " > " $CLUSTER_FILE_0 "
105121
106- # Patch only the Cluster
122+ # Patch only the json objects
107123 kubectl patch -f " $CLUSTER_FILE_0 " --local --type merge --patch " $( cat " $KOPS_PATCH_FILE " ) " -o json > " $CLUSTER_FILE_1 "
108124 mv " $CLUSTER_FILE_1 " " $CLUSTER_FILE_0 "
109125
110- # Write the patched Cluster back to the array
111- jq ' (.[] | select(.kind=="Cluster")) = $cluster[0]' " $CLUSTER_FILE " --slurpfile cluster " $CLUSTER_FILE_0 " > " $CLUSTER_FILE_1 "
126+ # Delete the original json objects, add the patched
127+ # TODO Cluster must always be first?
128+ jq " del($FILTER )" " $CLUSTER_FILE_JSON " | jq " . + \$ patched | sort" --slurpfile patched " $CLUSTER_FILE_0 " > " $CLUSTER_FILE_1 "
112129 mv " $CLUSTER_FILE_1 " " $CLUSTER_FILE_0 "
113130
114- # HACK convert the json array to multiple yaml documents
115- for (( i = 0 ; i < $(jq length "$CLUSTER_FILE_0 "); i++ )) ; do
116- echo " ---" >> " $CLUSTER_FILE_1 "
117- jq " .[$i ]" " $CLUSTER_FILE_0 " | kubectl patch -f - --local -p " {}" --type merge -o yaml >> " $CLUSTER_FILE_1 "
118- done
131+ # HACK convert the array of json objects to multiple yaml documents
132+ json_to_yaml " $CLUSTER_FILE_0 " " $CLUSTER_FILE_1 "
119133 mv " $CLUSTER_FILE_1 " " $CLUSTER_FILE_0 "
120134
121- # Done patching, overwrite original CLUSTER_FILE
135+ # Done patching, overwrite original yaml CLUSTER_FILE
122136 mv " $CLUSTER_FILE_0 " " $CLUSTER_FILE " # output is yaml
137+
138+ # Clean up
139+ rm " $CLUSTER_FILE_JSON "
140+ }
141+
142+ function yaml_to_json() {
143+ IN=${1}
144+ OUT=${2}
145+ kubectl patch -f " $IN " --local -p " {}" --type merge -o json | jq ' .' -s > " $OUT "
146+ }
147+
148+ function json_to_yaml() {
149+ IN=${1}
150+ OUT=${2}
151+ for (( i = 0 ; i < $(jq length "$IN "); i++ )) ; do
152+ echo " ---" >> " $OUT "
153+ jq " .[$i ]" " $IN " | kubectl patch -f - --local -p " {}" --type merge -o yaml >> " $OUT "
154+ done
123155}
0 commit comments