修正 Vim(Mac) 有时无法正确提交 Git Commit Message 的问题

Jul 15th, 2010 | Filed under Vim
Comments Off

和 Subversion 一样,Git 也可以为 Commit Message 设置一个默认的编辑器,命令如下:

1
$ git config --global core.editor vim

不过我在 Mac OS X 系统使用 Git 的过程中,偶尔会遇到如下的情况:

1
2
3
4
5
6
7
*** Commands ***
  1: status	  2: update	  3: revert	  4: add untracked
  5: patch	  6: diff	  7: quit	  8: help
What now> q
Bye.
error: There was a problem with the editor 'vim'.
Please supply the message using either -m or -F option.

这种情况基本上都是出现在我打错字的时候,开始以为是输入法引起的 Vim 状态异常,不过出现的次数多了才慢慢发现一个规律——如果在 Vim 中编辑文本时因为按键失误出现类似这样:E492: Not an editor command… 的错误信息时,必然无法提交。

查了一下 ProGit 的文档后了解到:如果 Git 的 Commit Hooks 检测到脚本的返回非零状态码的话(Non-Zero Code,表示有错误发生),会阻止本次提交。到这里问题就比较清晰了,显然是 Vim 非正常退出返回了 Non-Zero Code。

为了验证猜测,我作了如下操作,打开终端 Vim,随便输入几个无效指令,造成 Exxx 之类的错误,然后立刻使用 :q 退出,观察返回値,结果:

1
2
3
verdana@phpvim:~ # vim
verdana@phpvim:~ # echo $?
1

:roll: 果然是这样呢!

后来在 Google Group: vim_mac 这个帖子中找到了解决的办法,就是使用完整的 Vim 路径—— /usr/bin/vim :

1
$ git config --global core.editor /usr/bin/vim

不太清楚 Mac OS X 中 Vim 为何会有这种问题,Bram 老大亲自现身作了解释:

Vim 在遇到 Exx Error 时返回 Non-Zero code 是为了兼容 Posix,不过这种情况应该只会出现在使用 Ex Mode 时,Normal/Insert Mode 是不会这样的。

Tags: , ,

Vim color scheme: molokai

Jul 7th, 2010 | Filed under Vim
Comments Off

今天在 vim.org 的脚本库里面闲逛的时候,无意中看到了这个颜色主题。暗色系主题,颜色运用很鲜艳,看起来很养眼,美中不足的是 comment 颜色稍微偏暗了一些,看着不是很清楚,可以打开 molokai.vim 修改一下 hi Comment … 改成亮一点的颜色…

Vim colorscheme - molokai (php)

Vim colorscheme - molokai (vim)

下载地址:
http://www.vim.org/scripts/script.php?script_id=2340

Tags:

Vim 中离开 Insert 模式的快捷键

Jul 7th, 2010 | Filed under Vim
Comments Off

Vim 中码字,在 Insert/Normal 两种模式中频繁切换是无可避免的。那么如何快速在两种模式中切换,显然影响到我们的操作效率。

这里有三个快捷键可以选择: ESC, CTRL+C, CTRL+[

从便捷性上来看,CTRL+C 貌似是最顺手的,CTRL+[ 次之(需要两只手),ESC 最麻烦了,左手需要离开键盘的主要操作区域。

从功能上来看,ESC 等同于 CTRL+[,两者是完全一样的。CTRL+C 则稍稍不同,区别在于它不会自动展开 abbreviations,也不会触发 InsertLeave 事件。在某些些情况下,这可能会造成一点小小的困扰,比如下面的配置。

1
2
3
4
" 当切换 Insert/Normal 模式时,动态修改状态栏颜色
hi StatusLine guifg=#FBFAFB  guibg=#755939  gui=bold
autocmd InsertEnter * hi statusline guifg=#FBFAFB guibg=#44507F gui=bold
autocmd InsertLeave * hi statusline guifg=#FBFAFB guibg=#755939 gui=bold

如果使用 CTRL+C,那么上面最后一行配置就不起作用了。

好在 Vim 可以重新定义按键:

1
2
3
4
inoremap <C-c> <ESC>
 
" 或者作一些小小的改进
inoremap <C-c> <ESC>`^

abbr 依然不会自动展开,实际上这个不是问题,可以使用空格、回车,CTRL+]等等替代,重要的是 InsertLeave Event 回来了。

光标的漂移

默认的情况下,当你按 <ESC> 返回 Normal 模式时,光标会向左边移动一个字符,上面的第二个映射命令中添加了 `^,这样就能让光标保持原来的位置,不再乱跑了。

更多相关的知识请参考(准备好梯子) :x
http://vim.wikia.com/wiki/Avoid_the_escape_key

Tags:

Sweet Home Alabama

Jun 27th, 2010 | Filed under Music
Comments Off

找不到《空中监狱》的版本 How do i live,只好听听原版了~

image

Audio clip: Adobe Flash Player (version 9 or above) is required to play this audio clip. Download the latest version here. You also need to have JavaScript enabled in your browser.

PS: 看来无法引用 Google Music 的地址,隔了一天发现地址变了 :idea:

Tags:

让 Bash 自动完成忽略大小写

Jun 22nd, 2010 | Filed under Mac OS X
Comments Off

大多数人在使用 Bash 时,都会对其进行改造,因为默认的设置真的好难用~

参考以下 ~/.inputrc 设置:

1
2
3
4
5
6
7
8
9
# do not show hidden files in the list
set match-hidden-files off
 
# auto complete ignoring case
set show-all-if-ambiguous on
set completion-ignore-case on
"\ep": history-search-backward
"\e[A": history-search-backward
"\e[B": history-search-forward

默认情况下,按下两次 <tab> 才会出现提示,show-all-if-ambiguous 开启后,只需要一次了。
关掉 match-hidden-files 不显示隐藏文件,特比是当你在 Home 目录时,你会觉得眼前好干净。
开启 completion-ignore-case 忽略大小写,写 PHP 时我估计大约 1/4 的按键都是 shift + 4,该死的美元符号!Shell 命令,我不想再和大写字母纠缠了,让 <tab> 搞定好了。
history-search-*,输入几个字母,按上下箭头,搜索你的历史命令。

更多 Bash 定制请参考:
https://wiki.ubuntu.com/Spec/EnhancedBash

在 Shell 提示符中显示 Git 分支名称

Jun 21st, 2010 | Filed under Mac OS X
Comments Off

Git 的好处之一就是把代码的分支管理变成了一件极其便捷的事情,分支只保留差异,不用复制任何文件,不用连接网络,快速创建,用完即删。Git 分支与项目的复杂程度无关,不管你的项目多么复杂,创建 Git 分支永远都是瞬间的事情。同时,因为保留了父类分支的信息,所以分支的合并也变得异常简单。

当在一个项目中频繁使用多个分支时,可以使用 git status 命令查询自己现在正工作在哪个分支下面,不过难免有脑子发昏的时候,忘记自己在哪个分支下面,因而发生误操作之类的杯具。

那么把分支显示在 Shell 提示符中无疑方便了很多,再也不需要频繁的使用 git status 命令了…

实现原理很简单,大体就是查询当前目录下面的 Git 分支名称,然后嵌入到 PS1 变量中。那么,Git 分支名称可以通过下面的脚本轻松的获得:

git branch --no-color 2> /dev/null | sed -e '/^[^*]/d' -e 's/* \(.*\)/(\1)/'

把上面的脚本封装到函数中,修改 PS1 变量,嵌入函数… 大体是这样。但是这样也意味着一个问题,就是每次 shell 活动(比如切换目录,甚至只是敲下回车)都会执行一次 git … sed 命令,这样每次都启动2个进程,实在是有些不爽。

好在,可以使用另外一种方式来获取 Git 分支名称,在每个 Git 项目中,都有一个 .git 目录,这个目录下面有个叫做 HEAD 的文件,里面包含的当前分支的路径信息:

ref: refs/heads/BRANCH-NAME

我们只要读取这个文件,然后再和对应的路径互相匹配一下就知道正确地分支名称了。不要只是简单的从 HEAD 内容中拆分出最后的 BRANCH-NAME,因为它不一定是正确地。

以下是 Aaron Crane 的实现方式:

## Parses out the branch name from .git/HEAD:
find_git_branch () {
    local dir=. head
    until [ "$dir" -ef / ]; do
        if [ -f "$dir/.git/HEAD" ]; then
            head=$(< "$dir/.git/HEAD")
            if [[ $head = ref:\ refs/heads/* ]]; then
                git_branch=" → ${head#*/*/}"
            elif [[ $head != '' ]]; then
                git_branch=" → (detached)"
            else
                git_branch=" → (unknow)"
            fi
            return
        fi
        dir="../$dir"
    done
    git_branch=''
}

接下来,将这个函数加入到 PROMPT_COMMAND 中,保证 Bash 在创建 prompt 之前调用这个函数取得分支名称:

PROMPT_COMMAND="find_git_branch; $PROMPT_COMMAND"

最后只要重新定义 PS1 变量即可:

# Here is bash color codes you can use
  black=$'\[\e[1;30m\]'
    red=$'\[\e[1;31m\]'
  green=$'\[\e[1;32m\]'
 yellow=$'\[\e[1;33m\]'
   blue=$'\[\e[1;34m\]'
magenta=$'\[\e[1;35m\]'
   cyan=$'\[\e[1;36m\]'
  white=$'\[\e[1;37m\]'
 normal=$'\[\e[m\]'
 
PS1="$white[$magenta\u$white@$green\h$white:$cyan\w$yellow\$git_branch$white]\$ $normal"

以上的代码你可以放在 ~/.profile 或者 ~/.bash_profile 等文件中即可,我的系统是 Snow Leopard,PS1 定义在 /etc/bashrc 中,所以我直接修改的这个文件。

最终效果如下:

image


UPDATE – 2010/06/23:
如果你安装了随 Git 附送的 git-completion.sh 子命令自动完成脚本,也可以使用该脚本提供的方法:

export PS1="[\u@\h \W"'$(__git_ps1 " (%s)")'"]\$ "

Ubuntu 系统,请参考: /etc/bash_completion.d/git

参考文献:
http://www.jonmaddox.com/2008/03/13/show-your-git-branch-name-in-your-prompt/
http://aaroncrane.co.uk/2009/03/git_branch_prompt/

PHP CGI 中 fix_pathinfo 引起的安全隐患

May 22nd, 2010 | Filed under PHP
Comments Off

这两天网上开始疯传一个“nginx文件类型错误解析漏洞”,这个“漏洞”是这样的:

假设有如下的 URL:http://phpvim.net/foo.jpg,当访问 http://phpvim.net/foo.jpg/a.php 时,foo.jpg 将会被执行,如果 foo.jpg 是一个普通文件,那么 foo.jpg 的内容会被直接显示出来,但是如果把一段 php 代码保存为 foo.jpg,那么问题就来了,这段代码就会被直接执行。这对一个 Web 应用来说,所造成的后果无疑是毁灭性的。

关于这个问题,已有高手 laruence 做过详细的分析,这里再多啰嗦几句。

首先不管你是否有用到正则来解析 PATH_INFO,这个漏洞都是存在的。比如下面这个最基本的 nginx 配置:

1
2
3
4
5
6
location ~ \.php$ {
    fastcgi_pass  127.0.0.1:9000;
    fastcgi_index index.php;
    include       fastcgi_params;
    fastcgi_param SCRIPT_FILENAME   $document_root$fastcgi_script_name;
}

漏洞同样会出现,如 laruence 所说,实际上这个漏洞和 nginx 真的没什么关系,nginx 只是个 Proxy,它只负责根据用户的配置文件,通过 fastcgi_param 指令将参数忠实地传递给 FastCGI Server,问题在于 FastCGI Server 如何处理 nginx 提供的参数?

比如访问下面这个 URL:

1
http://phpvim.net/foo.jpg/a.php/b.php/c.php

那么根据上面给出的配置,nginx 传递给 FastCGI 的 SCRIPT_FILENAME 的值为:

1
/home/verdana/public_html/unsafe/foo.jpg/a.php/b.php/c.php

也就是 $_SERVER['ORIG_SCRIPT_FILENAME']。

当 php.ini 中 cgi.fix_pathinfo = 1 时,PHP CGI 以 / 为分隔符号从后向前依次检查如下路径:

1
2
3
4
/home/verdana/public_html/unsafe/foo.jpg/a.php/b.php/c.php
/home/verdana/public_html/unsafe/foo.jpg/a.php/b.php
/home/verdana/public_html/unsafe/foo.jpg/a.php
/home/verdana/public_html/unsafe/foo.jpg

直到找个某个存在的文件,如果这个文件是个非法的文件,so… 悲剧了~

PHP 会把这个文件当成 cgi 脚本执行,并赋值路径给 CGI 环境变量——SCRIPT_FILENAME,也就是 $_SERVER['SCRIPT_FILENAME'] 的值了。

在很多使用 php-fpm (<0.6) 的主机中也会出现这个问题,但新的 php-fpm 的已经关闭了 cgi.fix_pathinfo,如果你查看 phpinfo() 页面会发现这个选项已经不存在了,代码 ini_get(“cgi.fix_pathinfo”) 的返回值也是 “false”。

原因是似乎因为 APC 的一个 bug,当 cgi.fix_pathinfo 开启时,PATH_TRANSLATED 有可能是 NULL,从而引起内存异常,造成 php-fpm crash,所以 php-fpm 关闭这个选项。

Tags: , ,

启动 PHP 内置 FastCGI Server 的脚本

Apr 30th, 2010 | Filed under PHP
Comments Off

前几天把工作平台从 Ubuntu 9.10 Karmic 更新到了 10.04 Lucid,由于 Lucid 官方源自带了 PHP5.3.2,以前使用的 dotdeb 的源就没法用了,一直很喜欢这个源的,不但提供了 PHP5.3 而且还有 php5-fpm 这个很实用的 fcgi 进程管理器,这个在官方源里面是没有的。强行上了 dotdeb 虽然也可以,不过必然有很多包会出现依赖问题,处理这些依赖关系是件很烦心的事情。哥啥都不怕,就怕麻烦~ :!:

对于 PHP 来说,php-fpm 还是最合适的,spawn-fcgi 这类东西就不用考虑了,我宁愿用 PHP5 内置的 FastCGI Server。
Read more…

一切都已改变

Apr 29th, 2010 | Filed under Journal

搬到孵化园已经一个月了,很忙,很烦…

从去年的年底到现在,对我来说有了很大的变化,也有不少的收获。在朋友的帮助下,顺利地组建了自己的 Web 外包团队,落户在了高新孵化园。网站外包,真的是件很没技术含量的事情,也没什么油水可捞,不过倒是一条锻炼团队的途径。

自己也和哥们从东门建设路住了近10年的老房子里面搬到了外双楠,传说中非富即贵的富人区,有多少富贵人家我不知道,我只知道外面吃得东西真他娘的贵!一个人随便找个馆子一顿吃下来就几十块就没了,这也算是刺激自己努力赚钱的动力吧~想想你如果吃了N年的炒饭,面条,而现在还在吃这些的东西,那就太凄凉了!

原来住的老房子在建设路,某半死不活的国企职工宿舍,风水很不好,帮我们看房子的风水师傅说,这里叫做空亡之地。我对命理学一窍不通,不过从字面上看也知道不是什么好地方。大师还帮我们看了八字,给我解释的东西,我都忘光了,只记得关于华盖的一些话。命里有华盖的人通常都是才华横溢、性情恬淡的主,被人说自己聪明当然是件开心的事情,不过后来我发现了其实大师也有很多话没有说,那就是华盖通常也意味着不愿与人交往,常常感到孤独,而且通常与宗教有缘,好吧,我命里不但有华盖,而且还是三个,只能叹一声:马勒戈壁的!

本来还想问问姻缘的,没好意思! :oops:

搬家的时候,带了以前女友的照片,放在电脑桌上,为此还被哥么给嘲笑了一番。笑就笑吧,我忘不了这个女人,和她之间发生的一切,已成昨日黄花。快3年过去了,唯一留下的,就是这张照片还有那永远挥之不去的浓浓情意萦绕在心头。我一直在想,什么时候可以再见到她呢?只是见见也好,怕只怕这辈子再也看不到她了。我为爱烦恼,只因太执着,人常说,男子汉大丈夫,当拿得起放得下,我拿起了这份感情,却再难放下。

父亲常常打电话催我结婚,这样的日子持续了1年多了直到现在依然如此,有段时间几乎是以每天1,2个电话的高频率给我洗脑,灌输男大当婚、女大当嫁的观念,搞的我一听到手机响,就郁闷不堪,很想把手机从窗户扔出去。不过电话还是要接的,于是每次只能信誓旦旦的和父亲保证一定给他找个好儿媳,就这样日子一天天的过去,儿媳还是没着落,父亲也渐渐不再像以前那样紧紧逼迫,只是偶尔还是会提起,而我也懒的再提那些陈词滥调的保证了。呵呵,像我这样的没钱没车没房的头顶三华盖的孤僻三无宅男,想要找个老婆,还真是件极具挑战性的事。在天朝这个环境里,根本是不可能的嘛,哪怕天上真的会掉下个林妹妹,只怕也是脸先着地的,好吧,我宁愿孤独终老,也不愿意委屈自己,寂寞归寂寞,不过反过来想,不也是一生自由自在,不受约束,逍遥快活的么?哎,就当我阿Q好了!笑~ :grin:

Tags:

Vim进阶索引

Mar 15th, 2010 | Filed under Vim
Comments Off

学习使用 Vim 大约已有4、5年了,直到今天仍然有很多不懂的东西,精通自然谈不上,只能说初窥门径。看 best of vim tips 的作者是怎么说的:

David Rayner (zzapper) 15 Years of Vi + 4 years of Vim and still learning

这位大叔,搞了 15 年的 Vi,又搞了 4 年的 Vim,可依旧在学习。看来 Vim 真的是一个可以学到死的文本编辑器。

奇妙的之处就在于,你并不需要完全精通 Vim才能应用到工作中。实际上你只需要了解一些基本的东西,比如模式,光标移动,几个基本的编辑命令就可以让你的编辑效率提高很多,其它的就在实际的工作中根据自己的需要慢慢发掘。

如果你初次接触 Vim,那么建议你运行一下 Vim 安装目录下下面的 vimtutor,了解一下 Vim 的基础知识,花几天时间你就能完全适应它;如果你已经被 manual 中各种眼花缭乱的指令吓傻了,建议你忘掉那些指令,就算暂时记住了,如果用不到你也很快会忘记。

下面是我在网上看到的一个牛人写的教程,涉及到了 Vim 中的很多高级特性,但没有太多让人眼花的指令,读完之后定会有所收获。

:lol:

Tags: