程序员的日常工作
这种更强调 程序员除了写代码之外,还有很多事情要做,比如自动化测试,基础设施的配置和管理,持续集成/持续发布环境,甚至有些团队好需要做一些与运维相关的事情(线上问题监控,环境监控等)。
UNIX编程哲学关于UNIX哲学,其实坊间有多个版本,这里有一个比较详细的清单。虽然有不同的版本,但是有很多一致的地方:
这里列举一些小的例子,我们来看看命令行工具是如何通过应用这些哲学来简化工作,提高效率的。一旦你熟练掌握这些技能,就再也无法摆脱它,也再也忍受不了低效而难用的各种 命令行如何帮助程序员提升效率一个高阶计算器在我的编程生涯的早期,读过的最为振奋的一本书是《UNIX编程环境》,和其他基本UNIX世界的大部头比起来,这本书其实还是比较小众的。我读大二的时候这本书已经出版了差不多22年(中文版也已经有7年了),有一些内容已经过时了,比如没有返回值的 简而言之,这个
另外还有一些自定义的函数等,最后通过 这也是我第一次彻底被UNIX的哲学所折服的体验:
下面是书中的 YFLAGS = -d
OBJS = hoc.o code.o init.o math.o symbol.o
hoc5: $(OBJS)
cc $(OBJS) -lm -o hoc5
hoc.o code.o init.o symbol.o: hoc.h
code.o init.o symbol.o: x.tab.h
x.tab.h: y.tab.h
-cmp -s x.tab.h y.tab.h || cp y.tab.h x.tab.h
pr: hoc.y hoc.h code.c init.c math.c symbol.c
@pr $?
@touch pr
clean:
rm -f $(OBJS) [xy].tab.[ch] 虽然现在来看,这本书的很多内容已经过期(特别是离它第一次出版已经过去了近30年),有兴趣的朋友可以读一读。这里有一个Lex/Yacc的小例子,有情趣的朋友可以看看。 基础设施自动化开发过程中,工程师还需要关注的一个问题是:软件运行的环境。我在上学的时候,刚开始学习Linux的时候,会在Windows机器上装一个虚拟机软件VMWare,然后在VMWare中安装一个 而且这些动作都是在GUI里完成的,每次都要做很多重复的事情:找镜像文件,使用虚拟光驱软件挂载,启动VMWare,安装Linux,配置个人偏好,配置用户名/密码等等。熟练之后,我可以在30分钟 – 60分钟安装和配置好一个新的环境。 Vagrant后来我就发现了Vagrant,它支持开发者通过配置的方式将机器描述出来,然后通过命令行的方式来安装并启动,比如下面这个配置: VAGRANTFILE_API_VERSION = "2"
Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
config.vm.box = "precise64"
config.vm.network "private_network", :ip => "192.168.2.100"
end 它定义了一个虚拟机,使用 $ vagrant up 我的机器就可以在几分钟内装好,因为这个动作是命令行里完成的,我可以在持续集成环境里做同样的事情 – 只需要一条命令。定义好的这个文件可以在团队内共享,可以放入版本管理,团队里的任何一个成员都可以在几分钟内得到一个和我一样的环境。 Ansible一般而言,对于一个软件项目而言,一个全新的操作系统基本上没有任何用处。为了让应用跑起来,我们还需要很多东西。比如Web服务器,Java环境,cgi路径等,除了安装一些软件之外,还有大量的配置工作要做,比如 这些工作做好了,一个环境才算就绪。我记得在上一个项目上,不小心把测试环境的Tomcat目录给删除了,结果害的另外一位同事花了三四个小时才把环境恢复回来(包括重新安装Tomcat,配置一些JAVA_OPTS,应用的部署等)。 不过还在我们有很多工具可以帮助开发者完成环境的自动化准备,比如:Chef, Puppet, Ansible。只需要一些简单的配置,然后结合一个命令行应用,整个过程就可以自动化起来了: - name: setup custom repo
apt: pkg=python-pycurl state=present
- name: enable carbon
copy: dest=/etc/default/graphite-carbon content='CARBON_CACHE_ENABLED=true'
- name: install graphite and deps
apt: name= state=present
with_items: packages
- name: install graphite and deps
pip: name= state=present
with_items: python_packages
- name: setup apache
copy: src=apache2-graphite.conf dest=/etc/apache2/sites-available/default
notify: restart apache
- name: configure wsgi
file: path=/etc/apache2/wsgi state=directory 上边的配置描述了安装 $ ansible 就可以将整个过程自动化起来。现在如果我不小心把 持续集成/持续发布日常开发任务中,除了实际的编码和环境配置之外,另一大部分内容就是持续集成/持续发布了。借助于命令行,这个动作也可以非常高效和自动化。 Jenkins持续集成/持续发布已经是很多企业IT的基本配置了。各个团队通过持续集成环境来编译代码、静态检查、执行单元测试、端到端测试、生成报告、打包、部署到测试环境等等。 比如在 这样的方式,使得自动化变成了可能,要复制一个已有的 node {
def mvnHome
stage('Preparation') { // for display purposes
git 'https://github.com/jglick/simple-maven-project-with-tests.git'
mvnHome = tool 'M3'
}
stage('Build') {
sh "'${mvnHome}/bin/mvn' -Dmaven.test.failure.ignore clean package"
}
stage('Results') {
junit '**/target/surefire-reports/TEST-*.xml'
archive 'target/*.jar'
}
} 上面这段 运维工作自动化监控Graphite是一个功能强大的监控工具,不过其背后的理念倒是很简单:
用户只需要将数据按照一定格式定期发送给 instance.prod.cpu.load 40 1484638635
instance.prod.cpu.load 35 1484638754
instance.prod.cpu.load 23 1484638812 第一个字段表示数据的名称,比如此处 这样, 默认地, echo "instance.prod.cpu.load 23 `date +%s`" | nc -q0 graphite.server 2003
instance.prod.cpu.load 23 1484638812 然后通过管道 定时任务如果我们要自动的将数据每隔几秒就发送给
获取CPU的load在大多数系统中都很容易: ps -A -o %cpu 这里的参数:
这样可以得到每个进程占用CPU负载的数字: %CPU
12.0
8.2
1.2
... 下一步是将这些数字加起来。通过 $ awk '{s+=$1} END {print s}' 比如要计算 $ echo "1\n2\n3" | awk '{s+=$1} END {print s}'
6 通过管道可以讲两者连起来: $ ps -A -o %cpu | awk '{s+=$1} END {print s}' 我们测试一下效果: $ ps -A -o %cpu | awk '{s+=$1} END {print s}'
28.6 看来还不错,有个这个脚本,通过 #!/bin/bash
SERVER=graphite.server
PORT=2003
LOAD=`ps -A -o %cpu | awk '{s+=$1} END {print s}'`
echo "instance.prod.cpu.load ${LOAD} `date +%s`" | nc -q0 ${SERVER} ${PORT} 当然,如果使用Grafana等强调UI的工具,可以很容易的做的更加酷炫: 想想用GUI应用如何做到这些工作。 娱乐命令行的MP3播放器最早的时候,有一个叫做 将我的所有 $ ls /Users/jtqiu/Music/*.mp3 > favorites.list
$ cat favorites.list
...
/Users/jtqiu/Music/Rolling In The Deep-Adele.mp3
/Users/jtqiu/Music/Wavin' Flag-K'Naan.mp3
/Users/jtqiu/Music/蓝莲花-许巍.mp3
... 然后我将这个歌单交给mpg321去在后台播放: $ mpg321 -q --list favorites.list &
[1] 10268 这样我就可以一边写代码一边听音乐,如果听烦了,只需要将这个后台任务切换到前台 $ fg
[1] + 10268 running mpg321 -q --list favorites.list 小结综上,优秀的程序员借助命令行的特性,可以成倍(有时候是跨越数量级的)地提高工作效率,从而有更多的时间进行思考、学习新的技能,或者开发新的工具帮助某项工作的自动化。这也是优秀的程序员之所以优秀的原因。而面向手工的,原始的图形界面会拖慢这一过程,很多原本可以自动化起来的工作被淹没在“简单的GUI”之中。 最后补充一点,本文的关键在于强调 稿源:icodeit |