Update with kubeselect script

Signed-off-by: Manuel Vergara <manuel@vergaracarmona.es>
This commit is contained in:
Manuel Vergara 2023-01-25 15:57:30 +01:00
parent a7d65c08ec
commit ae3b6ebd4e
2 changed files with 349 additions and 2 deletions

View File

@ -1,7 +1,6 @@
<p style="background:#fff; color:red; font-size:2em;font-weight:bold; text-align:center; border: 5px blue solid">NO PUBLICAR</p>
# configuraciones Ubuntu
- Configuración Wifi en HP Pavilion. [WifiES.txt](doc/WifiES.txt)
- Script actualizaciones de paquetes apt y snap. [actualizar.sh](src/actualizar.sh)
- Script de pruebas de red. [pruebaRed.sh](src/pruebaRed.sh)
- Script para seleccionar contextos con kubectl [kubeselect](src/kubeselect)

348
src/kubeselect Executable file
View File

@ -0,0 +1,348 @@
#!/usr/bin/env bash
# This small helper util helps select an available Kubernetes context using the arrow keys
# using one simple command rather than two seperate kubectl commands to first show, then select contexts.
# It uses the mapfile shim found here: https://github.com/dosentmatter/bash-mapfile-shim
# which itself uses upvars by Freddy Vulto: http://fvue.nl/wiki/Bash:_Passing_variables_by_reference
# These are only needed for bash versions < 4, otherwise the native functions are used.
#
# Finally, the small select_option function was found on this Stackoverflow thread:
# https://stackoverflow.com/questions/11426529/reading-output-of-a-command-into-an-array-in-bash
# I included all source code I used as is.
# Bash: Passing variables by reference
# Copyright (C) 2010 Freddy Vulto
# Version: upvars-0.9.dev
# See: http://fvue.nl/wiki/Bash:_Passing_variables_by_reference
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# Assign variable one scope above the caller
# Usage: local "$1" && upvar $1 "value(s)"
# Param: $1 Variable name to assign value to
# Param: $* Value(s) to assign. If multiple values, an array is
# assigned, otherwise a single value is assigned.
# NOTE: For assigning multiple variables, use 'upvars'. Do NOT
# use multiple 'upvar' calls, since one 'upvar' call might
# reassign a variable to be used by another 'upvar' call.
# Example:
#
# f() { local b; g b; echo $b; }
# g() { local "$1" && upvar $1 bar; }
# f # Ok: b=bar
#
upvar() {
if unset -v "$1"; then # Unset & validate varname
if (( $# == 2 )); then
eval $1=\"\$2\" # Return single value
else
eval $1=\(\"\${@:2}\"\) # Return array
fi
fi
}
# Assign variables one scope above the caller
# Usage: local varname [varname ...] &&
# upvars [-v varname value] | [-aN varname [value ...]] ...
# Available OPTIONS:
# -aN Assign next N values to varname as array
# -v Assign single value to varname
# Return: 1 if error occurs
# Example:
#
# f() { local a b; g a b; declare -p a b; }
# g() {
# local c=( foo bar )
# local "$1" "$2" && upvars -v $1 A -a${#c[@]} $2 "${c[@]}"
# }
# f # Ok: a=A, b=(foo bar)
#
upvars() {
if ! (( $# )); then
echo "${FUNCNAME[0]}: usage: ${FUNCNAME[0]} [-v varname"\
"value] | [-aN varname [value ...]] ..." 1>&2
return 2
fi
while (( $# )); do
case $1 in
-a*)
# Error checking
[[ ${1#-a} ]] || { echo "bash: ${FUNCNAME[0]}: \`$1': missing"\
"number specifier" 1>&2; return 1; }
printf %d "${1#-a}" &> /dev/null || { echo "bash:"\
"${FUNCNAME[0]}: \`$1': invalid number specifier" 1>&2
return 1; }
# Assign array of -aN elements
[[ "$2" ]] && unset -v "$2" && eval $2=\(\"\${@:3:${1#-a}}\"\) &&
shift $((${1#-a} + 2)) || { echo "bash: ${FUNCNAME[0]}:"\
"\`$1${2+ }$2': missing argument(s)" 1>&2; return 1; }
;;
-v)
# Assign single value
[[ "$2" ]] && unset -v "$2" && eval $2=\"\$3\" &&
shift 3 || { echo "bash: ${FUNCNAME[0]}: $1: missing"\
"argument(s)" 1>&2; return 1; }
;;
--help) echo "\
Usage: local varname [varname ...] &&
${FUNCNAME[0]} [-v varname value] | [-aN varname [value ...]] ...
Available OPTIONS:
-aN VARNAME [value ...] assign next N values to varname as array
-v VARNAME value assign single value to varname
--help display this help and exit
--version output version information and exit"
return 0 ;;
--version) echo "\
${FUNCNAME[0]}-0.9.dev
Copyright (C) 2010 Freddy Vulto
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law."
return 0 ;;
*)
echo "bash: ${FUNCNAME[0]}: $1: invalid option" 1>&2
return 1 ;;
esac
done
}
# use mapfile_function if mapfile not found
mapfile() {
if type -f mapfile &>/dev/null; then
command mapfile "$@"
else
mapfile_function "$@"
fi
}
# Behaves like bash 4.x mapfile.
mapfile_function() {
local DELIM=$'\n'
local REMOVE_TRAILING_DELIM='false'
local OUTPUT_ARRAY_NAME='MAPFILE'
local OPTIND OPTARG OPTERR
local option
OPTERR=0
while getopts ':d:n:O:s:tu:C:c:' option; do
case "$option" in
d)
DELIM=$OPTARG
;;
t)
REMOVE_TRAILING_DELIM='true'
;;
:)
echo "Option requires an argument: -$OPTARG" >&2
return 1
;;
\?)
echo "Illegal option: -$OPTARG" >&2
return 2
;;
?)
echo "Option unimplemented: -$option" >&2
return 3
;;
esac
done
shift "$((OPTIND - 1))"
if (($# >= 1)); then
OUTPUT_ARRAY_NAME=$1
fi
local output_array=()
local null_end='false'
local REPLY
if [[ -n "$DELIM" ]]; then # stops at first null when DELIM is not null
IFS= read -r -d '' && null_end='true'
fi
while IFS= read -r -d "$DELIM"; do
if [[ "$REMOVE_TRAILING_DELIM" = 'true' ]]; then
output_array+=("$REPLY")
else
output_array+=("$REPLY$DELIM")
fi
done < <(
if [[ -n "$DELIM" ]]; then
echo -n "$REPLY"
[[ "$null_end" = 'true' ]] && printf '%b' '\0'
else
cat
fi
)
if [[ -n "$REPLY" ]] || [[ "$null_end" = 'true' ]]; then
output_array+=("$REPLY")
fi
local "$OUTPUT_ARRAY_NAME" &&
upvars -a"${#output_array[@]}" "$OUTPUT_ARRAY_NAME" "${output_array[@]}"
}
# mapfile according to word splitting rules.
# This isn't used by the shim.
# Empty lines aren't included in array if
# DELIM is whitespace (space, tab, newline) or null.
mapfile_IFS() {
local DELIM=$'\n'
local REMOVE_TRAILING_DELIM='false'
local OUTPUT_ARRAY_NAME='MAPFILE'
local OPTIND OPTARG OPTERR
local option
OPTERR=0
while getopts ':d:n:O:s:tu:C:c:' option; do
case "$option" in
d)
DELIM=$OPTARG
;;
t)
REMOVE_TRAILING_DELIM='true'
;;
:)
echo "Option requires an argument: -$OPTARG" >&2
return 1
;;
\?)
echo "Illegal option: -$OPTARG" >&2
return 2
;;
?)
echo "Option unimplemented: -$option" >&2
return 3
;;
esac
done
shift "$((OPTIND - 1))"
if (($# >= 1)); then
OUTPUT_ARRAY_NAME=$1
fi
local output_array=()
local null_end='false'
local delim_end='false'
local REPLY
local array_front
local array_last
if [[ -n "$DELIM" ]]; then
IFS= read -r -d '' && null_end='true'
[[ "$REPLY" = *"$DELIM" ]] && delim_end='true'
IFS=$DELIM read -r -d '' -a 'output_array' < <(
echo -n "$REPLY"
[[ "$null_end" = 'true' ]] && printf '%b' '\0'
)
if [[ "$REMOVE_TRAILING_DELIM" = 'false' ]]; then
array_front=("${output_array[@]:0:${#output_array[@]} - 1}")
array_last=${output_array[${#output_array[@]} - 1]}
array_front=("${array_front[@]/%/$DELIM}")
if [[ "$delim_end" = 'true' ]]; then
array_last+=$DELIM
fi
output_array=("${array_front[@]}" "$array_last")
fi
else
while IFS=$DELIM read -r -d ''; do
# no need to append null trailing delim because vars can't hold null
[[ -n "$REPLY" ]] && output_array+=("$REPLY")
done
[[ -n "$REPLY" ]] && output_array+=("$REPLY")
fi
local "$OUTPUT_ARRAY_NAME" &&
upvars -a"${#output_array[@]}" "$OUTPUT_ARRAY_NAME" "${output_array[@]}"
}
# Renders a text based list of options that can be selected by the
# user using up, down and enter keys and returns the chosen option.
#
# Arguments : list of options, maximum of 256
# "opt1" "opt2" ...
# Return value: selected index (0 for opt1, 1 for opt2 ...)
function select_option {
# little helpers for terminal print control and key input
ESC=$( printf "\033")
cursor_blink_on() { printf "$ESC[?25h"; }
cursor_blink_off() { printf "$ESC[?25l"; }
cursor_to() { printf "$ESC[$1;${2:-1}H"; }
print_option() { printf " $1 "; }
print_selected() { printf " $ESC[7m $1 $ESC[27m"; }
get_cursor_row() { IFS=';' read -sdR -p $'\E[6n' ROW COL; echo ${ROW#*[}; }
key_input() { read -s -n3 key 2>/dev/null >&2
if [[ $key = $ESC[A ]]; then echo up; fi
if [[ $key = $ESC[B ]]; then echo down; fi
if [[ $key = "" ]]; then echo enter; fi; }
# initially print empty new lines (scroll down if at bottom of screen)
for opt; do printf "\n"; done
# determine current screen position for overwriting the options
local lastrow=`get_cursor_row`
local startrow=$(($lastrow - $#))
# ensure cursor and input echoing back on upon a ctrl+c during read -s
trap "cursor_blink_on; stty echo; printf '\n'; exit" 2
cursor_blink_off
local selected=0
while true; do
# print options by overwriting the last lines
local idx=0
for opt; do
cursor_to $(($startrow + $idx))
if [ $idx -eq $selected ]; then
print_selected "$opt"
else
print_option "$opt"
fi
((idx++))
done
# user key control
case `key_input` in
enter) break;;
up) ((selected--));
if [ $selected -lt 0 ]; then selected=$(($# - 1)); fi;;
down) ((selected++));
if [ $selected -ge $# ]; then selected=0; fi;;
esac
done
# cursor position back to normal
cursor_to $lastrow
printf "\n"
cursor_blink_on
return $selected
}
mapfile -t available_contexts < <( kubectl config get-contexts -oname )
echo "Select context using up/down keys and enter to confirm:"
echo
select_option "${available_contexts[@]}"
choice=$?
kubectl config use-context ${available_contexts[$choice]}