Contact

Christopher Bock <christopher@bocki.com>
cb on irc.oftc.net
crpb on irc.libera.chat

some of my shell functions / aliases

  • [get | view] (2025-02-01 11:27:39, 2.1 KB) [[attachment:snapshot.deb822.sh]]
 All files | Selected Files: delete move to page copy to page

   1 alias envi='env -i HOME=$HOME TERM=$TERM PATH=$(getconf PATH)'
   2 alias patterns='man 7 apt-patterns |\grep --colour -E "(~|\?)[a-Z]+"'
   3 alias debian_pin_helper='apt-cache policy| sed "s/o=/\n\tORIGIN=/g;s/a=/\n\tARCHIVE=/g;s/n=/\n\tCODENAME=/g;s/v=/\n\tVERSION=/g;s/l=/\n\tLABEL=/g;s/c=/\n\tCOMPONENT=/g;s/b=/\n\tARCHITECTURE=/g"'
   4 alias debian_release='wget -O- -q http://deb.debian.org/debian/dists/stable/Release |awk "/^(Suite|Codename|Version|Description):/" |paste - - - -'
   5 alias debian_releases='wget -O- -q http://deb.debian.org/debian/dists/{oldoldstable,oldstable,stable,testing,unstable,experimental}/Release |awk "/^(Suite|Codename|Description):/" |paste - - - |expand -t 20'
   6 alias debian_channels='curl -s https://wiki.debian.org/IRC |grep -Po "(?<=>)#.*?(?=<)" |sort |uniq'
   7 alias diff='diff --color --exclude=".git" --exclude="__pycache__"'
   8 alias glog='git log --graph --decorate=full --name-status'
   9 alias glogf='git log --graph --decorate=full --follow -p'
  10 alias gloga='git log --graph --decorate=full --name-status --all ^'
  11 alias trente-ente='t=~/.RHABARBERBARBARA; rm -f $t; ssh-keygen -t ed25519 -P "" -f $t >/dev/null; cat $t.pub |xsel -b ; cat $t |xsel -p ; rm -f $t $t.pub'
  12 alias secbash='systemd-run --pty --property=DynamicUser=yes /bin/bash --norc'
  13 alias seczsh='systemd-run --pty --property=DynamicUser=yes /bin/zsh --no-rcs'
  14 
  15 
  16 # print apt_log w/o so much clutter
  17 apt_hist() {
  18   #test -z $(dpkg --print-foreign-architectures) && DELARCH=":$(dpkg --print-architecture)" || DELARCH="RHABARBER"  # Only show arch on multiarch system
  19   DELARCH=":$(dpkg --print-architecture)"
  20   awk '!/^End|^Error:/ { gsub( /\([^()]*\)/ ,"" );
  21   gsub(/ ,/,""); gsub(/^(Commandline|Start-Date): /,"");
  22   sub(/^Install: /,""); print}' <(zcat -f -- $(find /var/log/apt/history.log* |tac) 2>/dev/null) |sed "s#$DELARCH##g"
  23   #print}' <(zcat -f -- $(find /var/log/apt/history.log* |sort -rV) 2>/dev/null) |sed "s#$DELARCH##g" #alternativ
  24 }
  25 
  26 # get screenshot url's for package*
  27 dscreenshot() {
  28   {
  29     for package in "$@"; do
  30       printf '\thttps://screenshots.debian.net/package/%s\n' "$package"
  31       command psql "postgresql://udd-mirror:udd-mirror@udd-mirror.debian.net/udd" -qAt -F $'\t' --command="select package,version,large_image_url from screenshots where package LIKE '"$package"' ORDER BY version ASC"
  32     done
  33   }
  34 }
  35 compdef '_deb_packages avail' dscreenshot
  36 
  37 apt_show_source() {
  38   {
  39     apt show ${1:-*} |& sed '1,3d' |awk '/^(Package|APT-Sources): / {$1=""; print $NFR}' |sed 'N;s/\n/\t/' |expand -t $(( $COLUMNS / 3 ))
  40   }
  41 }
  42 compdef '_deb_packages avail' apt_show_source
  43 
  44 apt_show_maintainer() {
  45   apt show "${1:-*}" |& sed '1,3d' |awk '/^(Package|Maintainer): / {$1=""; print $NFR}' |sed 'N;s/\n/\t/' |expand -t $(( $COLUMNS / 3 ))
  46 }
  47 compdef '_deb_packages avail' apt_show_maintainer
  48 
  49 # show estimated disk-usage of all installed packages
  50 dpkg_installedsize() {
  51   dpkg-query -Wf '${Installed-Size}\n' | \
  52   awk '{ sum += $1 } END { print sum/1024" MB" }'
  53 }
  54 
  55 # Get latest netinst.iso
  56 debian_download_netinst() {
  57   (
  58   ARCH="${1:-amd64}"
  59   URL="https://cdimage.debian.org/debian-cd/current/$ARCH/iso-cd"
  60   DEBTMP=
  61   DEBTMP="$(command mktemp --suffix=debiancd -d)"
  62   command gpg --keyserver keyring.debian.org --recv-keys 64E6EA7D 6294BE9B 09EA8AC3
  63   cd $DEBTMP || return 1
  64   command wget -P $DEBTMP $URL/SHA512SUMS{,.sign} || return 1
  65   ISO="$(command awk '/debian-[0-9.]*-'$ARCH'-netinst.iso$/ {print $2}' $DEBTMP/SHA512SUMS)"
  66   printf "\n\v\tThe current ISO is %s\n\v\tEnter for yes, Ctrl-c for no\v" $ISO
  67   read accept
  68   command wget -P $DEBTMP $URL/$ISO || return 1
  69   command gpg --with-fingerprint --verify $DEBTMP/SHA512SUMS.sign || return 1
  70   command shasum --ignore-missing --check $DEBTMP/SHA512SUMS || return 1
  71   command printf "Finished download:\n\v\t%s\v\n" $DEBTMP/$ISO
  72 )
  73 }
  74 
  75 # deb822 formated .sources
  76 deb822() {
  77   local list # sources
  78   if [ -t 0 ]; then
  79     list="$(cat ${1:-/usr/share/doc/apt/examples/sources.list})"
  80   else
  81     list="$(cat /dev/stdin)"
  82   fi
  83   # sources="$(dirname $list)/$(basename $list |sed 's/\.list/\.sources/')"
  84   echo $list | sed -e 's/\[.*\]//g' -e 's/^[\t ]*//g' | \
  85   awk '/^deb/ {
  86   printf "Types: "$1"\nURIs: "$2"\nSuites: "$3"\nComponents: "; $1=$2=$3="";
  87   sub(/^[ \t]+/, ""); printf $0"\nEnabled: yes\n#Signed-By: \n\n"}' # | sudo tee -a $sources
  88   # sudo mv $list $list.bak
  89 }
  90 
  91 # deb822 print sources
  92 deb822_list() {
  93   for f in $(echo /etc/apt/sources.list.d/*${1}*.sources); do
  94     printf "${f}\n%80s\n" |tr " " "#"
  95     cat "${f}"
  96   done
  97 }
  98 
  99 
 100 # Size of all Packages Installed
 101 dpkg_installedsize() {
 102   dpkg-query -Wf '${Installed-Size}\n' | \
 103   awk '{ sum += $1 } END { print sum/1024" MB" }'
 104 }
 105 
 106 archive_lookup() {
 107   command -v jq curl >/dev/null || return 1
 108   local URL RET D
 109   URL="$1"
 110   #RET=( $(curl "http://archive.org/wayback/available?url=$(urldecode "$URL")" |jq -r '.archived_snapshots?|.closest.timestamp,.closest.url'))
 111   for timestamp in 19700000000 20991231235959; do
 112     RET=( $(curl "http://archive.org/wayback/available?timestamp=${timestamp}&url=${URL}" |jq -r '.archived_snapshots?|.closest.timestamp,.closest.url'))
 113     D=${RET[1]}
 114     if ! [ $D = null ]; then
 115       D="${D::4}-${D:4:2}-${D:6:2}T${D:8:2}:${D:10:2}+${D:12:2}:00"
 116       printf 'Date: %s URL: %s\n' "$D" "${RET[2]}"
 117     fi
 118   done
 119 }
 120 
 121 pastebin() {
 122   { if [ -t 0 ]; then
 123     cat $1
 124   else
 125     cat /dev/stdin
 126   fi } | command -p pastebinit |sed 's%/hidden/%/plainh/%'| tee >(tr -d "\n"| xclip -i -selection clipboard) |tee -a ~/.pastebinit_history
 127   # local archive...
 128   local URL PASTEID
 129   URL="$(xclip -selection clipboard -o |sed 's/\/$//g')"
 130   PASTEID=${URL##*/}
 131   wget --quiet "$(xclip -selection clipboard -o |sed 's/\/$//g')" --output-document="$HOME/.pastebinit_history.d/$PASTEID"
 132 }
 133 
 134 # PASTE LATEST SCREENSHOT
 135 0x0() {
 136   local file img url ttl=96 histfile=~/.0x0_history res dir=~/snips
 137   if [ "$1" = "-h" ]; then
 138     cat << EOF
 139 Usage:  arg[1] = filename or nothing for newest file in $dir
 140         -h for help
 141         -f for fuzzy thingy
 142         -d for printing curl statements for all tokens
 143 EOF
 144   elif [ "$1" = "-f" ]; then
 145     awk 'NF>2' $histfile |
 146       fzf --disabled \
 147       --bind="p:execute:sensible-browser {2}" \
 148       --bind 'd:preview:command curl -s -Fdelete= -Ftoken="{3}" {2}' \
 149       --preview-window=up \
 150       --header "p: sensible-browser URL; d: delete on 0x0; return: print curl to cli in background" \
 151       --bind 'enter:execute:echo curl -Fdelete= -Ftoken="{3}" {2}'
 152   elif [ "$1" = "-d" ]; then
 153     awk '{printf "curl -Ftoken=%s -Fdelete= %s\n", $3, $2}' $histfile
 154   else
 155     file="$(print "$dir"/*(.om[1]))"
 156     img="${1-$file}"
 157     # '${${img}:a:q}' only works with zsh. you will need an alternative in bash
 158     printf '%s\nfile://%s\nPress Enter to upload! ' ${${img}:a:q} ${${img}:a:q}
 159 #    printf 'file://%s\n' ${${img}:a:q}
 160     read accept
 161     #  curl -s -F"file=@${img}" -Fexpires=96 -Fsecret= https://0x0.st | \
 162     #  tee >(tr -d '\n'| xsel -i -b)
 163     res=( $(curl --write-out '%header{x-token}' -s -F"file=@${img}" -Fexpires=$ttl -Fsecret= https://0x0.st) )
 164     printf '%s' "${res[1]}" | xsel -i -b
 165     printf '%s\t%s\t%s\t%s\n' "$(date -Im)" "${res[1]}" "${res[2]}" "${file}" |tee -a "${histfile}"
 166   fi
 167 }
 168 
 169 # Fluxbox apps helper
 170 fbxprop() {
 171   printf '[app] %s \n[end]\n' "$(
 172   xprop WM_CLASS WM_NAME WM_WINDOW_ROLE |
 173   sed 's/WM_\(.*\)(\(.*\)) = "//g;s/", "/\n/;s/"$//'|
 174   sed '1 s/^/(name=/;2 s/^/(class=/;3 s/^/(title=/;4 s/^/(role=/;s/$/)/g' |
 175   # WM_WINDOW_ROLE might not be found
 176   grep -v WM_WINDOW_ROLE |tr '\n' ' ')"
 177 }
 178 
 179 
 180 tmux_cssh() {
 181   local split match name hosts OPTS
 182   if test $# -ge 3 ; then
 183     if [[ $3 =~ ^[0-9]+$ ]]; then
 184       split="$3"
 185     fi
 186   fi
 187   if test $# -ge 2 ; then
 188     match="$1"
 189     if [[ $2 =~ ^[0-9]+$ ]] && [[ $# = 2 ]]; then
 190       split="$2"
 191       name="$(tr -cd '[:alnum:]' <<< "$1")"
 192     else
 193       name="$2"
 194     fi
 195   fi
 196   if test $# = 1 ; then
 197     if test -z "$(tr -d '[:alnum:]' <<< "$1")"; then
 198       match="$1."
 199       name="$1"
 200     else
 201       match="$1"
 202       name="$(tr -cd '[:alnum:]' <<< "$1")"
 203     fi
 204   fi
 205   if test $# = 0 ; then
 206     return 0
 207   fi
 208   OPTS=(-ts "${name}" -sa -A)
 209   if ! test -z $split ; then OPTS=(${OPTS[@]} -sw "$split"); fi
 210   echo tmux-cssh ${OPTS[@]} $(awk '/^Host .*('$match').*$/ {printf "%s ", $2}' ~/git/ssh_config/*.ssh ~/.ssh/config)
 211   tmux-cssh "${OPTS[@]}" $(awk '/^Host .*('$match').*$/ {printf "%s ", $2}' ~/git/ssh_config/*.ssh ~/.ssh/config)
 212 }
 213 
 214 _cows() {
 215 ( command -v cowsay lolcat faketime || sudo apt install --yes cowsay lolcat faketime ) >/dev/null 2>&1
 216 OPTS=( -b -d -g -n -p -s -t -w -y ); for opt in ${OPTS[@]}; do echo "${1:=MUUUH}" |cowsay $opt |lolcat ; done
 217 for tach in 12-25 08-16 11-07 02-18 04-01; do faketime 2022-$tach apt-get moo| lolcat; done
 218 apt-get -o APT::Moo::Color=true moo moo
 219 }
 220 
 221 # QEMU RUN ISO
 222 qemu_iso() {
 223   iso="$1"
 224   shift
 225   qemu-system-x86_64 --enable-kvm --smp 4 -boot d -m 2G \
 226   -nic user,ipv6=off,model=vmxnet3 --display gtk --serial stdio  \
 227   -cdrom "$iso" $@
 228 }
 229 qemu_serial() {
 230   iso="$1"
 231   shift
 232   qemu-system-x86_64 --enable-kvm --smp 4 -boot d -m 2G \
 233   -nic user,ipv6=off,model=vmxnet3 --display curses --nographic --vga none \
 234   -cdrom "$iso" $@
 235 }
 236 
 237 gdiff() {
 238   local N
 239   test "$1" -eq "$1" && N="$1" || N=1
 240   git diff HEAD~${N} HEAD
 241 }
 242 gdiffs() {
 243   git diff --staged
 244 }
 245 
 246 # clone git repo to e.g. ~/git/$sitename/$usercorpname/$reponame
 247 gclone() {
 248   {
 249     if ((DEBUGTHIS)); then set -x; fi
 250     testuri() { git ls-remote --quiet $1 HEAD >/dev/null 2>&1 ; }
 251     local base url prot link domain subpath usr notld repo rpath
 252     base=~/git/
 253     url="$1"
 254     if ! testuri "$url"; then
 255       echo "Couldn't find a git repository at ${url}!" >/dev/stderr
 256       return 65
 257     fi
 258     if [[ "$url" =~ "https?://" ]]; then
 259       prot="${url%:*}"
 260       link="${url#${prot}://}"
 261       domain="${link%%/*}"
 262       subpath="${link#${domain}}"
 263     elif [[ "$url" =~ "^git@" ]]; then
 264       prot="${url%@*}"
 265       link="${url#${prot}@}"
 266       domain="${link%%:*}"
 267       subpath="${link#${domain}:}"
 268     fi
 269     usr="${subpath%/*}"
 270     notld="${domain%.*}"; notld="${notld#git.}"
 271     repo="${link##*/}"; repo="${repo%*.git}"
 272     rpath="$(realpath -sm "$base/$notld/$usr/$repo"|tr '[:upper:]' '[:lower:]')"
 273     if [ -n "$ZSH_VERSION" ] && type zstyle >/dev/null 2>&1; then
 274       vared -p "Clone $url to: " rpath
 275     elif [ -n "$BASH_VERSION" ] && type caller >/dev/null 2>&1; then
 276       rpath="$(read -e -r -p "Clone "$url" to: " -i "$rpath"; echo "$REPLY")"
 277     fi
 278     if ! test -d "$rpath"; then
 279       mkdir -p "${rpath%/*}"
 280       git clone "$url" "$rpath"
 281       cd $_
 282     else
 283       printf 'Directory %s already exists!\n' "$rpath"
 284       cd $_
 285     fi
 286     set +x
 287   }
 288 }
 289 
 290 
 291 
 292 
 293 
 294 # libvirt shrink all qcow images
 295 libvirt_shrink_qcow() {
 296   VMSR=( $(virsh --quiet --connect=qemu:///session list --state-running --name) )
 297   VMS=( $(virsh --quiet --connect=qemu:///session list --all --name) )
 298   for VM in "${VMSR[@]}"; do
 299     printf "Stopping VM: $VM\n"
 300     virsh --quiet --connect=qemu:///session shutdown --domain $VM
 301     sleep 0.5
 302   done
 303   while true; do
 304     if [[ -z $(virsh --quiet --connect=qemu:///session list --state-running --name) ]]; then
 305       break
 306     else
 307       printf "VMs still running: %s\n" "$(virsh --quiet --connect=qemu:///session list --state-running --name |tr '\n' ' ')"
 308       printf "Waiting 5 seconds to check again\n"
 309       sleep 5
 310     fi
 311   done
 312   printf "\n"
 313   for VM in "${VMS[@]}"; do
 314     printf "VM: $VM\n"
 315     for IMG in $(virsh --quiet --connect=qemu:///session domblklist --details --domain $VM | awk '/disk.*qcow2$/{print $NF}'); do
 316       printf "Compressing $IMG\n"
 317       time qemu-img convert -p -c -O qcow2 $IMG $IMG.tmp
 318       mv -v $IMG{,.bak}
 319       mv -v $IMG{.tmp,}
 320       ls -1sh ${IMG}*
 321       printf "\n"
 322       BAKS="${BAKS} ${IMG}.bak"
 323     done
 324   done
 325   for VM in $VMSR; do
 326     printf "Starting VM: $VM\n"
 327     virsh --quiet --connect=qemu:///session start --domain $VM;
 328   done
 329   printf "\nDon't forget to cleanup the backups:\n rm %s \n" $BAKS
 330 }
 331 
 332 
 333 # libvirt snapshot overview
 334 virsnaps() {
 335   local DOMS DOM SNAPS TREE CURRENT
 336   local SES=${1:-session}
 337   DOMS=( $(virsh --quiet --connect=qemu:///${SES} list --all --name) )
 338   echo -e "\033[1mDomains: ${DOMS[@]}\033[0m"
 339   for DOM in ${DOMS[@]}; do
 340     CURRENT="$(virsh --quiet --connect=qemu:///${SES} snapshot-current --name --domain "$DOM" 2>/dev/null)"
 341     SNAPS="$(virsh --connect=qemu:///${SES} snapshot-list --topological --parent --domain "$DOM")"
 342     TREE="$(virsh --connect=qemu:///${SES} snapshot-list --topological --tree --domain "$DOM")"
 343     if [ "${#CURRENT}" -gt 0 ] ; then
 344       printf '\033[1mDomain: %s\033[0m\n' "$DOM"
 345       printf '%s\n' "$SNAPS"|sed ''/$CURRENT/s//$(printf "\033[1m$CURRENT\033[0m")/''
 346       printf 'Tree:\033[0m\n%s\n' "$TREE"|sed ''/$CURRENT/s//$(printf "\033[1m$CURRENT\033[0m")/''
 347     fi
 348   done
 349 }


CategoryHomepage