zsh 配置

考虑到我的备份仓库是 Private 的,专门开一篇文章以便复制粘贴。

Oh-My-Zsh Offline Installation

不保证任意环境可用,不保证无 bug

Expand code
main() {
  # Use colors, but only if connected to a terminal, and that terminal
  # supports them.
  if which tput >/dev/null 2>&1; then
      ncolors=$(tput colors)
  fi
  if [ -t 1 ] && [ -n "$ncolors" ] && [ "$ncolors" -ge 8 ]; then
    RED="$(tput setaf 1)"
    GREEN="$(tput setaf 2)"
    YELLOW="$(tput setaf 3)"
    BLUE="$(tput setaf 4)"
    BOLD="$(tput bold)"
    NORMAL="$(tput sgr0)"
  else
    RED=""
    GREEN=""
    YELLOW=""
    BLUE=""
    BOLD=""
    NORMAL=""
  fi

  # Only enable exit-on-error after the non-critical colorization stuff,
  # which may fail on systems lacking tput or terminfo
  set -e

  CHECK_ZSH_INSTALLED=$(grep /zsh$ /etc/shells | wc -l)
  if [ ! $CHECK_ZSH_INSTALLED -ge 1 ]; then
    printf "${YELLOW}Zsh is not installed!${NORMAL} Please install zsh first!\n"
    exit
  fi
  unset CHECK_ZSH_INSTALLED

  if [ ! -n "$ZSH" ]; then
    ZSH=~/.oh-my-zsh
  fi

  # Prevent the cloned repository from having insecure permissions. Failing to do
  # so causes compinit() calls to fail with "command not found: compdef" errors
  # for users with insecure umasks (e.g., "002", allowing group writability). Note
  # that this will be ignored under Cygwin by default, as Windows ACLs take
  # precedence over umasks except for filesystems mounted with option "noacl".
  umask g-w,o-w

  printf "${BLUE}Cloning Oh My Zsh...${NORMAL}\n"
  hash git >/dev/null 2>&1 || {
    echo "Error: git is not installed"
    exit 1
  }
  # The Windows (MSYS) Git is not compatible with normal use on cygwin
  if [ "$OSTYPE" = cygwin ]; then
    if git --version | grep msysgit > /dev/null; then
      echo "Error: Windows/MSYS Git is not supported on Cygwin"
      echo "Error: Make sure the Cygwin git package is installed and is first on the path"
      exit 1
    fi
  fi

  printf "${BLUE}Looking for an existing zsh config...${NORMAL}\n"
  if [ -f ~/.zshrc ] || [ -h ~/.zshrc ]; then
    printf "${YELLOW}Found ~/.zshrc.${NORMAL} ${GREEN}Backing up to ~/.zshrc.pre-oh-my-zsh${NORMAL}\n";
    mv ~/.zshrc ~/.zshrc.pre-oh-my-zsh;
  fi

  printf "${BLUE}Using the Oh My Zsh template file and adding it to ~/.zshrc${NORMAL}\n"
  cp $ZSH/templates/zshrc.zsh-template ~/.zshrc
  sed "/^export ZSH=/ c\\
  export ZSH=$ZSH
  " ~/.zshrc > ~/.zshrc-omztemp
  mv -f ~/.zshrc-omztemp ~/.zshrc

  # If this user's login shell is not already "zsh", attempt to switch.
  TEST_CURRENT_SHELL=$(expr "$SHELL" : '.*/\(.*\)')
  if [ "$TEST_CURRENT_SHELL" != "zsh" ]; then
    # If this platform provides a "chsh" command (not Cygwin), do it, man!
    if hash chsh >/dev/null 2>&1; then
      printf "${BLUE}Time to change your default shell to zsh!${NORMAL}\n"
      chsh -s $(grep /zsh$ /etc/shells | tail -1)
    # Else, suggest the user do so manually.
    else
      printf "I can't change your shell automatically because this system does not have chsh.\n"
      printf "${BLUE}Please manually change your default shell to zsh!${NORMAL}\n"
    fi
  fi

  printf "${GREEN}"
  echo '         __                                     __   '
  echo '  ____  / /_     ____ ___  __  __   ____  _____/ /_  '
  echo ' / __ \/ __ \   / __ `__ \/ / / /  /_  / / ___/ __ \ '
  echo '/ /_/ / / / /  / / / / / / /_/ /    / /_(__  ) / / / '
  echo '\____/_/ /_/  /_/ /_/ /_/\__, /    /___/____/_/ /_/  '
  echo '                        /____/                       ....is now installed!'
  echo ''
  echo ''
  echo 'Please look over the ~/.zshrc file to select plugins, themes, and options.'
  echo ''
  echo 'p.s. Follow us at https://twitter.com/ohmyzsh.'
  echo ''
  echo 'p.p.s. Get stickers and t-shirts at http://shop.planetargon.com.'
  echo ''
  printf "${NORMAL}"
  env zsh
}

main

Powerlevel10k

Follow the official README.

stty Config

stty -a:

speed 38400 baud; rows 24; columns 80; line = 0;
intr = ^C; quit = ^\; erase = ^?; kill = ^U; eof = ^D; eol = <undef>;
eol2 = <undef>; swtch = <undef>; start = ^Q; stop = ^S; susp = ^Z; rprnt = ^R;
werase = ^W; lnext = ^V; discard = ^O; min = 1; time = 0;
-parenb -parodd -cmspar cs8 -hupcl -cstopb cread -clocal -crtscts
-ignbrk -brkint -ignpar -parmrk -inpck -istrip -inlcr -igncr icrnl ixon -ixoff
-iuclc -ixany -imaxbel iutf8
opost -olcuc -ocrnl onlcr -onocr -onlret -ofill -ofdel nl0 cr0 tab0 bs0 vt0 ff0
isig icanon iexten echo echoe echok -echonl -noflsh -xcase -tostop -echoprt
echoctl echoke -flusho -extproc

Aliases & Custom Functions

Expand code
# Keybinding (like a lost technology)
# Mostly you can use command `read` to view the keybinding output
# Except keybindings in `stty` (such as Ctrl+w as word-erase `werase`), it will display the "raw" input
# Another way is press `Ctrl+V`, means `quoted-insert` in zsh/bash.
# Relation: .inputrc, Z Line Editor
bindkey '3~' kill-word # Alt-Delete
bindkey '5~' kill-word # Ctrl-Delete

bindkey '^H' backward-kill-word # Ctrl-Backspacea

bindkey "\e[1;3D" backward-word ### Alt left
bindkey "^[[1;2D" backward-word ### Shift left
bindkey "\e[1;3C" forward-word ### Alt right
bindkey "^[[1;2C" forward-word ### Shift right

# General command shortcut & options aliases
alias svim='sudo vim'
alias vi='vim'
alias ea='vim ~/.zshrc'
alias apply='source ~/.zshrc'
alias tldr="tldr -t base16"
alias diff="diff --strip-trailing-cr"
alias share="python -m http.server "
alias first='awk "{print \$1}"'
alias second='awk "{print \$2}"'

# mkdir && cd
# mc test/deep/folder
mkcdir() {
    mkdir -p -- "$1" &&
    cd -P -- "$1"
}
alias mc=mkcdir # Caution, `mc` is also GNU Midnight Commander

## geoip 8.8.8.8
curl_geoip(){
    echo "Curling https://api.ip.sb/geoip/${1}"
    curl  --noproxy "*" https://api.ip.sb/geoip/${1}
}
alias geoip=curl_geoip

## Commandline Copy & Paste
## echo "text" | cs
## cv
alias cs="xclip"
alias cv="xclip -o"
## Copy to system clipboard
## echo "text" | copy
## <ctrl+v>
alias copy="xclip -selection clipboard"


# Proxy config
setproxy() {
  export SOCKS_PROXY='socks://127.0.0.1:1080'
  export socks_proxy=$SOCKS_PROXY 
  export http_proxy='http://127.0.0.1:1081/' 
  export HTTP_PROXY=$http_proxy 
  export HTTPS_PROXY=$http_proxy 
  export https_proxy=$http_proxy;
}
alias clearproxy="unset HTTP_PROXY; unset http_proxy; unset HTTPS_PROXY; unset https_proxy; unset socks_proxy; unset SOCKS_PROXY;"

# Typo aliases
alias exi=exit
alias eix=exit
alias eixt=exit
alias xit=exit
alias xti=exit
alias ext=exit
alias eit=exit
alias e=exit
alias clera=clear
alias claer=clear
alias c=clear

# manually init nvm (enable it will slow down terminal start time)
nvm_init(){
    source /usr/share/nvm/init-nvm.sh
}

# Helm shortcut
alias hupdate='helm repo update'
alias hls='helm search repo --devel'

alias py='python'
alias py3='python3'
alias py2='python2'

# Hugo new_post
# Sample:
#   new_post "content/post/New Post Title"
#   new_post "content/post/Post Without Date Prefix" -r
new_post() {
  local USAGE=(echo "Usage:
  new_post <path>
Options:
  -r  Generate file name without date
")

  if [[ -z $1 ]] || [[ $1 = "-"* ]]; then
    $USAGE
    return
  fi

  local NO_DATE_FILENAME="false"

  OPTIND=2
  while getopts ":r" opt; do
      case "${opt}" in
      r)
          NO_DATE_FILENAME="true"
          ;;
      *)
          $USAGE
          return
          ;;
      esac
  done
  
  local TITLE=$(basename "$1")
  local DIR_NAME=$(dirname "$1")
  mkdir -p $DIR_NAME
  local FILE_NAME=$(echo "$TITLE" | tr '[:upper:]' '[:lower:]' | tr ' ' '-' )

  if [[ $NO_DATE_FILENAME = "false" ]]; then
    FILE_NAME="$( date +"%Y-%m-%d" )-$FILE_NAME"
  fi

  if [[ ! $FILE_NAME = *".md" ]]; then
    FILE_NAME="$FILE_NAME.md"
  fi
  FILE_NAME="${DIR_NAME}/${FILE_NAME}"
  echo "Generating $FILE_NAME ..."

  if [[ -f $FILE_NAME ]]; then
    echo "File exists!"
    return
  fi

  local DATE_STR=$(date +"%Y-%m-%dT%H:%M:%S%z")
  cat << EOF >> "$FILE_NAME"
---
title: "$TITLE"
subtitle: ""
date: $DATE_STR
categories: []
tags: []
---



<!--more-->

EOF

}

K8s Related 请参考这个。

Paste Performance

Expand code
# This speeds up pasting w/ autosuggest
# https://github.com/zsh-users/zsh-autosuggestions/issues/238
pasteinit() {
  OLD_SELF_INSERT=${${(s.:.)widgets[self-insert]}[2,3]}
  zle -N self-insert url-quote-magic # I wonder if you'd need `.url-quote-magic`?
}

pastefinish() {
  zle -N self-insert $OLD_SELF_INSERT
}
zstyle :bracketed-paste-magic paste-init pasteinit
zstyle :bracketed-paste-magic paste-finish pastefinish

Plugin

plugins=(git colored-man-pages sublime z catimg wakatime zsh-autosuggestions docker docker-compose)

Some plugins need to install manually.

Keybindings (zsh bindkey)

Run bindkey to list all zle keybindings. Here is my config.

Expand code
"^@" set-mark-command
"^A" beginning-of-line
"^B" backward-char
"^D" delete-char-or-list
"^E" end-of-line
"^F" forward-char
"^G" send-break
"^H" backward-kill-word
"^I" expand-or-complete
"^J" accept-line
"^K" kill-line
"^L" clear-screen
"^M" accept-line
"^N" down-line-or-history
"^O" accept-line-and-down-history
"^P" up-line-or-history
"^Q" push-line
"^R" history-incremental-search-backward
"^S" history-incremental-search-forward
"^T" transpose-chars
"^U" kill-whole-line
"^V" quoted-insert
"^W" backward-kill-word
"^X^B" vi-match-bracket
"^X^E" edit-command-line
"^X^F" vi-find-next-char
"^X^J" vi-join
"^X^K" kill-buffer
"^X^N" infer-next-history
"^X^O" overwrite-mode
"^X^R" _read_comp
"^X^U" undo
"^X^V" vi-cmd-mode
"^X^X" exchange-point-and-mark
"^X*" expand-word
"^X=" what-cursor-position
"^X?" _complete_debug
"^XC" _correct_filename
"^XG" list-expand
"^Xa" _expand_alias
"^Xc" _correct_word
"^Xd" _list_expansions
"^Xe" _expand_word
"^Xg" list-expand
"^Xh" _complete_help
"^Xm" _most_recent_file
"^Xn" _next_tags
"^Xr" history-incremental-search-backward
"^Xs" history-incremental-search-forward
"^Xt" _complete_tag
"^Xu" undo
"^X~" _bash_list-choices
"^Y" yank
"^[^D" list-choices
"^[^G" send-break
"^[^H" backward-kill-word
"^[^I" self-insert-unmeta
"^[^J" self-insert-unmeta
"^[^L" clear-screen
"^[^M" self-insert-unmeta
"^[^_" copy-prev-word
"^[ " expand-history
"^[!" expand-history
"^[\"" quote-region
"^[\$" spell-word
"^['" quote-line
"^[," _history-complete-newer
"^[-" neg-argument
"^[." insert-last-word
"^[/" _history-complete-older
"^[0" digit-argument
"^[1" digit-argument
"^[2" digit-argument
"^[3" digit-argument
"^[4" digit-argument
"^[5" digit-argument
"^[6" digit-argument
"^[7" digit-argument
"^[8" digit-argument
"^[9" digit-argument
"^[<" beginning-of-buffer-or-history
"^[>" end-of-buffer-or-history
"^[?" which-command
"^[A" accept-and-hold
"^[B" backward-word
"^[C" capitalize-word
"^[D" kill-word
"^[F" forward-word
"^[G" get-line
"^[H" run-help
"^[L" down-case-word
"^[N" history-search-forward
"^[OA" up-line-or-beginning-search
"^[OB" down-line-or-beginning-search
"^[OC" forward-char
"^[OD" backward-char
"^[OF" end-of-line
"^[OH" beginning-of-line
"^[P" history-search-backward
"^[Q" push-line
"^[S" spell-word
"^[T" transpose-words
"^[U" up-case-word
"^[W" copy-region-as-kill
"^[[1;5C" forward-word
"^[[1;5D" backward-word
"^[[200~" bracketed-paste
"^[[3~" delete-char
"^[[5~" up-line-or-history
"^[[6~" down-line-or-history
"^[[A" up-line-or-history
"^[[B" down-line-or-history
"^[[C" forward-char
"^[[D" backward-char
"^[[Z" reverse-menu-complete
"^[_" insert-last-word
"^[a" accept-and-hold
"^[b" backward-word
"^[c" capitalize-word
"^[d" kill-word
"^[f" forward-word
"^[g" get-line
"^[h" run-help
"^[l" "ls^J"
"^[m" copy-prev-shell-word
"^[n" history-search-forward
"^[p" history-search-backward
"^[q" push-line
"^[s" spell-word
"^[t" transpose-words
"^[u" up-case-word
"^[w" kill-region
"^[x" execute-named-cmd
"^[y" yank-pop
"^[z" execute-last-named-cmd
"^[|" vi-goto-column
"^[~" _bash_complete-word
"^[^?" backward-kill-word
"^_" undo
" " magic-space
"!"-"3" self-insert
"3~" kill-word
"4"-"5" self-insert
"5~" kill-word
"6"-"~" self-insert
"^?" backward-delete-char
"\M-^@"-"\M-^?" self-insert