Skip to content

Instantly share code, notes, and snippets.

@lalyos
Last active December 14, 2023 13:38
Show Gist options
  • Save lalyos/f851fd3273fead83146eeca6822a9604 to your computer and use it in GitHub Desktop.
Save lalyos/f851fd3273fead83146eeca6822a9604 to your computer and use it in GitHub Desktop.
KUBECONFIG helper scripts - magic

Install

Add this to you ~/.bashrc

if [ -f ~/.kube/.kube-config.sh ]; then 
  source ~/.kube/.kube-config.sh
else 
  curl -sLo ~/.kube/.kube-config.sh https://gist.githubusercontent.com/lalyos/f851fd3273fead83146eeca6822a9604/raw/.kube-config.sh
  source ~/.kube/.kube-config.sh
fi

Functions

  • kk: prints the actual KUBECONFIG
  • kselect: select one from files matching $KCPATTERN. All shells sharing this. Be careful: ctx change in one shell has effect to all other shells.
  • kc: sets default KUBECONFIG. combines all matching file: KUBECONFIG=file1:file2:file3
  • kct: new multifile KUBECONFIG, with a temp dumy config in the first place. Usage: the shell get an independent KUBECONFIG, ctx changes don't effect other shells.
  • ksub: creates a subshell with a new KUBECONFIG. The first entry is a temporal dummy kubeconfig.

Configuration

You can use the following env variables

KCPATTERN Your KUBECONFIG naming conventions. Examples:

  • *.yaml: all yaml files [default]
  • config*: all files starting with config

tl;dr

If you have a single file in KUBECONFIG than the actual ctx is stored in the current-context field. But if you have a lot of config files in ~/.kube:

  • ~/.kube/prod (has 1 contex:prod)
  • ~/.kube/dev (has 1 contex:dev)
  • ~/.kube/qa (has 1 contex:qa)

Than imagine you set KUBECONFIG=~/.kube/prod:~/.kube/dev:~/.kube/qa Now you switch betwen contextes easily (k ctx), without changing the KUBECONFIG env var. But let say you switch to qa context: now because the first entry in KUBECONFIG is ~/.kube/prod the current-context field will be set to dev in that file.

Next time you want to use it alone KUBECONFIG=~/.kube/prod it will error out because it references to a nonexisting context.

So the workaround: whenever you use KUBECONFIG=fil1:file2:file3 always insert a dummy file, as the first entry. You can easily create a dummy file:

(KUBECONFIG=~/.kube/dummy kubectl config view)> ~/.kube/dummy

So if you want to have multiple file in KUBECONFIG, the first entry should be a dummy: KUBECONFIG=dummy:fil1:file2:file3

######################################
## KUBECONFIG helpers
######################################
# aliases
alias k='kubectl'
alias kal='kubectl get all'
alias kg='kubectl get'
alias kgs='kubectl get -n kube-system'
alias kgy='kubectl get -o yaml'
alias kke='code ${KUBECONFIG:-$HOME/.kube/config}'
alias kp='[[ "$K8S_PROMPT" ]] && unset K8S_PROMPT || K8S_PROMPT=1'
# prints actual KUBECONFIG
kk() {
echo KUBECONFIG=$KUBECONFIG
}
kunset() {
unset KUBECONFIG
}
kd() {
kubectl "$@" --dry-run -o yaml
}
rspec() {
kubectl get rs ${1:? required} -o yaml | kubectl neat | yq .spec -y | grep -v 'pod-template-hash:\|replicas:'
}
# selects a single yaml from ~/.kube as KUBECONFIG
kselect-old() {
select conf in ~/.kube/${KCPATTERN:-*.yaml}; do
echo selected: ${conf};
break;
done;
export KUBECONFIG=${conf}
}
kctx() {
k config get-contexts
}
kselect() {
find ~/.kube/${KCPATTERN:-config*} \
| fzf -m \
--cycle \
--prompt='KUBECONFIG >' \
--header 'press TAB to select multiple (deselect: shift-TAB) / ENTER to finish' \
| tee .kc
if [[ $(cat .kc | wc -l) -eq 1 ]]; then
echo "===> singli ..."
KUBECONFIG=$(head -1 .kc)
export KUBECONFIG
else
KC=$(mktemp /tmp/config-XXXXX)
KUBECONFIG=$(sed -n 'H;$ {x;s/\n/:/gp;}' < .kc)
kubectl config view --flatten > $KC;
export KUBECONFIG=$KC
fi
echo KUBECONFIG=$KUBECONFIG 1>&2
}
kunsecure() {
cluster=$(kubectl config view --minify -o jsonpath='{.clusters[0].name}')
kubectl config set-cluster $cluster --insecure-skip-tls-verify
}
# sets default KUBECONFIG
kc() {
local FIRST=${1:-$HOME/.kube/dummy}
kcreset ${FIRST}
export KUBECONFIG=$(echo ${FIRST} $HOME/.kube/${KCPATTERN:-*.yaml} |sed "s/ /:/g")
kk
}
# resets ~/.kube/dummy in case it is messed up, or references a wrong context
kcreset() {
local OUT=${1:-~/.kube/dummy}
(KUBECONFIG=${OUT} kubectl config view)> ${OUT}
}
# creates temp KUBECONFIG: ctx changes don't effect other shells
kct-old() {
KC=$(mktemp /tmp/config-XXXXX)
kc $KC
}
kct-old() {
KC=$(mktemp /tmp/config-XXXXX)
KUBECONFIG=$(echo $HOME/.kube/${KCPATTERN:-*.yaml} |sed "s/ /:/g") \
kubectl config view --flatten \
> $KC
export KUBECONFIG=$KC
}
kct() {
KC=$(mktemp /tmp/config-XXXXX)
kubectl config view --flatten > $KC
export KUBECONFIG=$KC
}
kprompt() {
kubectl config view --minify -o go-template='{{ printf "[%v/%v]" (index . "current-context") (index .contexts 0).context.namespace }}'
}
# creates temp KUBECONFIG: in a subshell
ksub() {
OLDVC=$KC
kct
if declare -F kube_ps1 &>/dev/null; then
bash --rcfile <(echo -e "export KUBE_PS1_PREFIX='[${KC#*config-}]('\n. ~/.bashrc")
else
bash --rcfile <(echo -e ". ~/.bashrc \n export PS1='${KC#*config-} \$(kprompt)$ '")
fi
KC=$OLDVC
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment