我输入bash --version
后,可以得到:
GNU bash, version 3.2.57(1)-release (x86_64-apple-darwin14)
Copyright (C) 2007 Free Software Foundation, Inc.
在默认的MacBook Air上,会自带一个bash。可是,它的版本却偏老。
这不仅带来许多使用上的不便,例如命令参数补全(bash-completion
不支持bash3.2),也有很多隐患。
我唯一值得欣慰的是,这个版本足以抵御Shellshock漏洞。
升级,方法就是下载最新的bash源码、编译、替换当前的bash,这三步。
当然,这还有个前提,你必须已经安装Xcode(关键是配套的Command line tools)了。
如果你连git
和gcc
都没有,那就没必要搞什么bash了。
此外,HomeBrew
也是要有的,为了方便。
下载并解压:
curl https://ftp.gnu.org/gnu/bash/bash-4.3.tar.gz -o ~/Downloads/bash-4.3.gz
tar xzf ~/Downloads/bash-4.3.gz -C ~/Downloads/
我当前最新的bash版本是4.3。可以在这里查看最新的版本。
cd ~/Downloads/bash-4.3
./configure && make && sudo make install
安装到这里就结束了。直接输入bash --version
的结果,和刚才一样。但是重启、新建终端窗口、新建终端TAB页中,都可以得到新的结果。
此时,终端用的用的bash,是在/usr/local/bin/bash
的新安装bash。
如果要完全替代原bash,还需要更改/bin/bash
。
sudo mv /bin/bash /bin/bash3.2
sudo ln -s /usr/local/bin/bash /bin/bash
这一步,如果你只是在控制台敲命令,或者是使用bash bash_script
的方式来执行脚本,那么可有可无。
但是,如果你需要用./bash_script
或其它更复杂的使用方式,那么全局配置是必须的。
因为,你打开大多数bash脚本都可以在第一行看到:
#!/bin/bash
#!
这个操作符,会把脚本解释器设置为/bin/bash
。所以你将一会儿用旧的,一会儿用新的。
因此,更改链接是必须的。
(本节内容,受教于zrong’s Blog。)
brew install bash
sudo mv /bin/bash /bin/bash3.2
sudo ln -s /usr/local/Library/LinkedKegs/bash /bin/bash
和前面的区别,就是不用编译,直接安装,bash实体的放置位置有差异而已。
但是,我的水平虽然说不上什么不对,却不太喜欢这种太“方便”的做法。
brew本来就是依赖bash的命令行工具,如今反过来管理bash。总觉得不太稳妥。
如果你因为什么原因怒删brew,及其全部文件(包括/usr/local/Cellar
下的bash实体)。那么/bin/bash
这个死链,能否支撑你的terminal?
Mac上的bash,如果不配置,不仅丑,而且难用。
即使换上最新的版本,也是如此。
如果按TAB键,不能自动补全,那么bash和Windows下被人唾弃的CMD,还能有多大差距?
安装bash-completion
brew install bash-completion
然后在.bash_profile
里,添加其相关配置:
if [ -f $(brew --prefix)/etc/bash_completion ]; then
. $(brew --prefix)/etc/bash_completion
fi
在我的机器上,brew --prefix
就是/usr/local
。
这样,bash的很多自带命令、大多brew安装的命令,就可以完美补全了。
遗憾的是,此时Git仍然不能补全。
单独配置Git的补全:
curl https://raw.githubusercontent.com/git/git/master/contrib/completion/git-completion.bash > ~/.git-completion.bash
echo "source ~/.git-completion.bash" >> .bash_profile
.git-completion.bash
文件从Git在GitHub上的Git库里(嘿嘿)扒拉下来。或者,你也愿意把整个git库拉下来,然后执行cp
?source
配置写到.bash_profile
里去。重启、新开、或执行
source ~/.git-completion.bash
后,Git就可以补全啦!
对ls
,可以在.bash_profile
里,加入
export CLICOLOR=1
export CLICOLOR_FORCE=1
export LSCOLORS=gxfxaxdxcxegedabagacad
ls
命令的颜色。这句的作用,和alias ls='ls -G'
类似。ls
的结果作为输出,提供给类似grep
这样的命令时,也保持原先的颜色。字母 | 颜色 | 字母 | 带色粗体 |
---|---|---|---|
a | 黑色 | A | 黑色粗体 |
b | 红色 | B | 红色粗体 |
c | 绿色 | C | 绿色粗体 |
d | 棕色 | D | 棕色粗体 |
e | 蓝色 | E | 蓝色粗体 |
f | 洋红色 | F | 洋红色粗体 |
g | 青色 | G | 青色粗体 |
h | 浅灰色 | H | 浅灰色粗体 |
第N个字母 | 代表的文件类型 |
---|---|
1 | directory |
2 | symbolic link |
3 | socket |
4 | pipe |
5 | executable |
6 | block special |
7 | character special |
8 | executable with setuid bit set |
9 | executable with setgid bit set |
10 | directory writable to others, with sticky bit |
11 | directory writable to others, without sticky bit |
文件类型应该不需要翻译吧。(你确定翻译了你还认识?)
详见man ls
,搜索color。
对grep
,可以在.bash_profile
里,加入
export GREP_OPTIONS='--color=always'
或
alias grep='grep --color'
能用环境变量配置的,不建议用alias
。
默认为高亮红色,可以通过修改
export GREP_COLOR='a;b'
来改变默认颜色。其中a
填入数字,效果如下:
a | 效果 |
---|---|
0 | 关闭所有属性 |
1 | 设置高亮度 |
4 | 下划线 |
5 | 闪烁 |
7 | 反显 |
8 | 消隐 |
b
填入数字,效果如下:
前景 | 后景 | 颜色 |
---|---|---|
30 | 40 | 黑色 |
31 | 41 | 红色 |
32 | 42 | 绿色 |
33 | 43 | 黄色 |
34 | 44 | 蓝色 |
35 | 45 | 紫色 |
36 | 46 | 青色 |
37 | 47 | 白色 |
默认为1;31
,即红色高亮 。
我喜欢
export GREP_COLOR='5;40'
黑底闪烁。
(话说,谁知道Markdown怎么设置“黑底闪烁”?)
如果还有其它需要对显示结果配色的CMD,只需要查看man CMD
并搜索color或option,按照以上方法,应该都能配置。
如果命令本身不支持配色,那就没办法了。
alias如果过多,一般都会单独用一个文件来管理。
这里用.alias.bash
,下面的alias
都加入这个文件。
别忘了在.bash_profile
里,要加一行
source .alias.bash
ls
的alias ll='ls -hlF'
alias l.='ls -d .*'
alias lsf='ls -hl | grep -v ^d'
alias lsd='ls -hl | grep ^d'
alias lr='ls -R | grep ":$" | sed -e '\''s/:$//'\'' -e '\''s/[^-][^\/]*\//--/g'\'' -e '\''s/^/ /'\'' -e '\''s/-/|/'\'''
ll
是加强版ls
,显示目录、文件的详细信息l.
仅显示隐藏文件、目录lsf
仅显示文件,不显示目录lsd
仅显示目录,不显示文件lr
以tree
的形式显示当前目录下的所有文件夹,不显示文件以下是关于返回上级目录的:
alias ..='cd ..'
alias ...='cd ../../'
alias ....='cd ../../../'
alias .....='cd ../../../../'
alias ......='cd ../../../../../'
git
的alias gl="git log --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit"
alias glg='git log --graph --full-history --all --color --pretty=format:"%x1b[31m%h%x09%x1b[32m%d%x1b[0m%x20%s"'
gl
是不错的单行log展示形式glg
是有commit关系图形的形式,类似gitkalias df='df -h'
alias rm='rm -i'
alias freq='cut -f1 -d" " ~/.bash_history | sort | uniq -c | sort -nr | head -n 30'
alias tm='ps -ef | grep'
df
为总是显示M或G等单位符号,提高可读性。类似的还有du
,不过一般du
都是要带参数的,我常用du -hd1
和du -hs
,既然都要带参数,这个h就不用偷懒了。rm -i
会总是再提醒一次“是否删除”,安全一些。alias
后,输入-f
可以忽略提示。freq
会列出你最常用的30个命令。这个命令我也不常用,只是列在这里,随时学习这个多重管道。tm
后面加进程名称,例如tm firefox
,可以找出其PID(第二列),以便kill
。还有mcd
和多功能解压extract
。它俩只能用function
来实现了。
function mcd() {
mkdir -p "$1" && cd "$1";
}
extract () {
if [ -f $1 ] ; then
case $1 in
*.tar.bz2) tar xjf $1 ;;
*.tar.gz) tar xzf $1 ;;
*.bz2) bunzip2 $1 ;;
*.rar) unrar e $1 ;;
*.gz) gunzip $1 ;;
*.tar) tar xf $1 ;;
*.tbz2) tar xjf $1 ;;
*.tgz) tar xzf $1 ;;
*.zip) unzip $1 ;;
*.Z) uncompress $1 ;;
*.7z) 7z x $1 ;;
*) echo "'$1' cannot be extracted via extract()" ;;
esac
else
echo "'$1' is not a valid file"
fi
}
(更多详细信息,请参考《是时候展示真正的alias技术了》。)
我的MacBook Air 11,默认的字体是Menlo 11pt
。
显然,对这么小的屏幕来说,这个字体太小了!
在很长的一段时间内,我用的都是Menlo 14pt
。字形的辨识度很高,在VIM里能显示40行。
现在,在欣赏了Mac OS X 10.10自带的所有字体后,我还是更喜欢Monaco 13pt
。
13pt的它,和14pt的Menlo大小差不多,而且在我的视觉里,更可爱一些。
更改字体,在终端的【偏好设置】【描述文件】【文本】【字体】。
我没有尝试非自带字体,留待以后吧。
(更多字体信息,请参考10大最适合编程的字体或收听内核恐慌5·编程字体。)
上面的东西,如果你不想花时间看,那么把以下这段直接贴到Terminal就行了。
不过,需要注意的是:
sudo
两句,务必要确保前面都OK再执行因此,在echo
以上的这些命令,建议一行一行地贴。
两个echo
不用担心,"
和$
等符号都被转义了,可以正常写入.bash_profile
和.alias.bash
。
(嘿嘿,如果你是直接跳到这来看的,是不是心中一虚,又跳回去从头看?哇哈哈哈哈哈……^_^……)
一个完整带判断带异常处理的shell,只能等以后更新了。
shell如下:
这块建议逐行拷贝到Terminal。
bash --version
curl https://ftp.gnu.org/gnu/bash/bash-4.3.tar.gz -o ~/Downloads/bash-4.3.gz
tar xzf ~/Downloads/bash-4.3.gz -C ~/Downloads/
cd ~/Downloads/bash-4.3
./configure && make && sudo make install
sudo mv /bin/bash /bin/bash3.2
sudo ln -s /usr/local/bin/bash /bin/bash
brew install bash-completion
curl https://raw.githubusercontent.com/git/git/master/contrib/completion/git-completion.bash > ~/.git-completion.bash
如果上面执行都OK的话,可以配置文件了。
这块建议全部拷贝到Terminal中。切忌直接拷贝到文件,因为内含转义字符\"
等。
echo "
# Setting bash-completion
if [ -f \$(brew --prefix)/etc/bash_completion ]; then
. \$(brew --prefix)/etc/bash_completion;
fi
# Setting git completion
source ~/.git-completion.bash
# Persinal bash profile #
# ls
export CLICOLOR=1 #ls color
export CLICOLOR_FORCE=1
export LSCOLORS=gxfxaxdxcxegedabagacad #ls color specific
# grep
export GREP_OPTIONS='--color=always'
export GREP_COLOR='5;40'
# alias
source ~/.alias.bash
" \
>> ~/.bash_profile
echo "\
#!/bin/bash
# alias
# ls
# List files and directories with human readable detailed infomation
alias ll='ls -hlF'
# Show hidden files only
alias l.='ls -d .*'
# Show files only
alias lsf='ls -hl | grep -v ^d'
# Show directories only
alias lsd='ls -hl | grep ^d'
# Recursive directory listing
alias lr='ls -R | grep \":\$\" | sed -e '\''s/:\$//'\'' -e '\''s/[^-][^\/]*\//--/g'\'' -e '\''s/^/ /'\'' -e '\''s/-/|/'\'''
# Jump back n directories at a time
alias ..='cd ..'
alias ...='cd ../../'
alias ....='cd ../../../'
alias .....='cd ../../../../'
alias ......='cd ../../../../../'
# git
# Compact, colorized git log
alias gl=\"git log --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit\"
# Visualise git log (like gitk, in the terminal)
alias glg='git log --graph --full-history --all --color --pretty=format:\"%x1b[31m%h%x09%x1b[32m%d%x1b[0m%x20%s\"'
# Human readable df
alias df='df -h'
# rm will be more safe by reminding you if without -f behind
alias rm='rm -i'
# Show which commands you use the most
alias freq='cut -f1 -d\" \" ~/.bash_history | sort | uniq -c | sort -nr | head -n 30'
# Search for process
alias tm='ps -ef | grep'
# function
# mkdir and cd into
function mcd() {
mkdir -p \"\$1\" && cd \"\$1\";
}
# extract files
extract () {
if [ -f \$1 ] ; then
case \$1 in
*.tar.bz2) tar xjf \$1 ;;
*.tar.gz) tar xzf \$1 ;;
*.bz2) bunzip2 \$1 ;;
*.rar) unrar e \$1 ;;
*.gz) gunzip \$1 ;;
*.tar) tar xf \$1 ;;
*.tbz2) tar xjf \$1 ;;
*.tgz) tar xzf \$1 ;;
*.zip) unzip \$1 ;;
*.Z) uncompress \$1 ;;
*.7z) 7z x \$1 ;;
*) echo \"'\$1' cannot be extracted via extract()\" ;;
esac
else
echo \"'\$1' is not a valid file\"
fi
}
" \
> ~/.alias.bash
重启终端。
什么?你说iTem2+Zsh?
连这你都知道了,还看我这篇破文干什么?
o(╯□╰)o
稍微介绍下吧。
iTerm2是MacOS自带终端Terminal的替代品,也是iTerm的后继者。它要在 MacOS 10.5 (Leopard) 或以上的版本运行。iTerm2带着一堆你从不知道而又一直渴求的功能,把终端这种工具,推向新的时代!
——[iTem 2 官网](http://iterm2.com)
以上是我的翻译,将就着看吧。
iTerm2是Terminal的一个加强版高级替代品,打开【偏好设置】看一眼就明白了——这种Windows设置般的恐怖功能迷阵,蕴含着数量庞大的功能和巨大的可定制空间。
不过我暂时是不会用的,因为在我的列表里,还有一堆更高优先级的东西要去学zhe习teng。
此外还有一个巨大的痛点——全屏快捷键不能全屏!开发者根本不理解我这个买得起MacBook Air 11买不起Magic Mouse的艹民之心!
Z Shell(Zsh) 是一种Unix shell,它可以用作为交互式的登录shell,也是一种强大的shell脚本命令解释器。Zsh可以认为是一种Bourne shell的扩展,带有数量庞大的改进,包括一些bash、ksh、tcsh的功能。
——[Z shell - 维基百科](https://zh.wikipedia.org/wiki/Z_shell)
除了前面提过的学zhe习teng优先级以外,Zsh作为一个bash的替代品,是否值得学习,还有待商榷。
如果你时间宽裕,我建议二者都学;如果你和我一样日程很满,我建议你只学一种。
而如果只学一种,学习一个主流的bash,比一个非主流的Zsh,在大多数情况下减少很多麻烦。至少,你不用每遇到一个新的工作环境(公司工作站、网络服务器、虚拟机等),就要替换一次bash。
而且,很多情况下别无选择。
(你以为你能拿到root权限吗?)
(OK,你是管理员,你敢擅自把公用的Linux系统里的shell配置成Zsh吗?)
╮(╯_╰)╭
O(∩_∩)O~