HTTP请求返回码204
[| 2011/10/27 18:49]
今天测试lighttpd是否支持delete请求,发现webdav模块可以实现此功能。不过发现http返回码是204,查了一下,原来此状态码的意思是说请求成功了,但是没有结果返回来。搜到鸟哥一篇文章,讲的很不错,转载一下:
http://www.laruence.com/2011/01/20/1844.html
之前和人讨论过这个问题,,, 今天感冒在家休息, 就回忆了一下, 整理如下.
我们很多的应用在使用Ajax的时候, 大多数情况都是询问型操作, 比如提交数据, 则Ajax只是期待服务器返回:
{status: 0, message:""} //status 0代表成功, 非零的时候, message中包含出错信息.
我们知道HTTP的状态码, 2xx都是表示成功, 而HTTP的204(No Content)响应, 就表示执行成功, 但是没有数据, 浏览器不用刷新页面.也不用导向新的页面.
在HTTP RFC 2616中关于204的描述如下:
类似的还有205 Reset Content, 表示执行成功, 重置页面(Form表单).
于是, 当有一些服务, 只是返回成功与否的时候, 可以尝试使用HTTP的状态码来作为返回信息, 而省掉多余的数据传输, 比如REST中的DELETE和如上所述的查询式Ajax请求.
最后说说205, 205的意思是在接受了浏览器POST请求以后处理成功以后, 告诉浏览器, 执行成功了, 请清空用户填写的Form表单, 方便用户再次填写,
总的来说, 204适合多次对一个Item进行更新, 而205则适合多次提交一个系列的Item.
但, 请注意, 目前还没有一个浏览器支持205, 大部分的浏览器, 都会把205当做204或者200同样对待.
http://www.laruence.com/2011/01/20/1844.html
之前和人讨论过这个问题,,, 今天感冒在家休息, 就回忆了一下, 整理如下.
我们很多的应用在使用Ajax的时候, 大多数情况都是询问型操作, 比如提交数据, 则Ajax只是期待服务器返回:
{status: 0, message:""} //status 0代表成功, 非零的时候, message中包含出错信息.
我们知道HTTP的状态码, 2xx都是表示成功, 而HTTP的204(No Content)响应, 就表示执行成功, 但是没有数据, 浏览器不用刷新页面.也不用导向新的页面.
在HTTP RFC 2616中关于204的描述如下:
引用
If the client is a user agent, it SHOULD NOT change its document view from that which caused the request to be sent. This response is primarily intended to allow input for actions to take place without causing a change to the user agent’s active document view, although any new or updated metainformation SHOULD be applied to the document currently in the user agent’s active view.
类似的还有205 Reset Content, 表示执行成功, 重置页面(Form表单).
引用
The server has fulfilled the request and the user agent SHOULD reset the document view which caused the request to be sent. This response is primarily intended to allow input for actions to take place via user input, followed by a clearing of the form in which the input is given so that the user can easily initiate another input action.
于是, 当有一些服务, 只是返回成功与否的时候, 可以尝试使用HTTP的状态码来作为返回信息, 而省掉多余的数据传输, 比如REST中的DELETE和如上所述的查询式Ajax请求.
最后说说205, 205的意思是在接受了浏览器POST请求以后处理成功以后, 告诉浏览器, 执行成功了, 请清空用户填写的Form表单, 方便用户再次填写,
总的来说, 204适合多次对一个Item进行更新, 而205则适合多次提交一个系列的Item.
但, 请注意, 目前还没有一个浏览器支持205, 大部分的浏览器, 都会把205当做204或者200同样对待.
修改域名DNS服务器
[| 2011/10/27 12:49]
最近几天监控频频爆出dns无法解析问题,群里关注了下,发现godaddy的dns服务器现在开始被和谐了,于是决定换一个。dnspod国人用的比较多,不过在国内总感觉比较扯。还是用he的比较可靠一点。
修改很快,将解析记录都导入he的管理页面后去godaddy切换ns记录,本地nslookup了一下,切换了。
在此期间注意到godaddy有了DNSSec记录功能,看了下,应该是防止dns欺骗的,暂时用不到,没有搞。
修改很快,将解析记录都导入he的管理页面后去godaddy切换ns记录,本地nslookup了一下,切换了。
在此期间注意到godaddy有了DNSSec记录功能,看了下,应该是防止dns欺骗的,暂时用不到,没有搞。
blog迁移
[| 2011/10/27 02:02]
经历了很长时间的准备后,终于把blog迁移了。哈哈,庆祝一下。
考虑了很长时间,最后还是决定还在老服务器上开博客,先不动地方,因为新服务器最近网络变得非常差,失去了信心,而老服务器基本稳定,还能接受,稳妥起见,并且为了避免给搜索引擎带来太大的困扰,所以没有换服务器。
迁移前先升级了下php,之前php还是5.1,实在太老了,加入了centos-test源,yum update提示我几个php依赖错误,卸掉那几个包后重新安装,好了,还有几个包源里没有,比如filter,查了下,原来从5.2起整合进php了,自然也不需要了。还有eaccelerate似乎也找不到,下了源码编译。然后把自己写的模块重新编译一遍,一切正常,restart php。哈哈,升级了。
之前已经修改、测试好了博客,一些配置也配置好了,所以迁移显得非常简单,直接从代码库中拉出代码到指定位置,代码就部署完成。使用昨天编写的数据导入脚本,把数据导入(期间出了个小插曲,php会对同样连接条件的连接请求进行复用,导致数据库use错乱,后来一个用localhost一个用127.0.0.1才好了,这个是始料未及的,因为之前是在两台机器间迁移的)。然后根据之前写的rewrite规则修改nginx配置文件,重启~ok了。
心情不错,写博客又有动力了。
考虑了很长时间,最后还是决定还在老服务器上开博客,先不动地方,因为新服务器最近网络变得非常差,失去了信心,而老服务器基本稳定,还能接受,稳妥起见,并且为了避免给搜索引擎带来太大的困扰,所以没有换服务器。
迁移前先升级了下php,之前php还是5.1,实在太老了,加入了centos-test源,yum update提示我几个php依赖错误,卸掉那几个包后重新安装,好了,还有几个包源里没有,比如filter,查了下,原来从5.2起整合进php了,自然也不需要了。还有eaccelerate似乎也找不到,下了源码编译。然后把自己写的模块重新编译一遍,一切正常,restart php。哈哈,升级了。
之前已经修改、测试好了博客,一些配置也配置好了,所以迁移显得非常简单,直接从代码库中拉出代码到指定位置,代码就部署完成。使用昨天编写的数据导入脚本,把数据导入(期间出了个小插曲,php会对同样连接条件的连接请求进行复用,导致数据库use错乱,后来一个用localhost一个用127.0.0.1才好了,这个是始料未及的,因为之前是在两台机器间迁移的)。然后根据之前写的rewrite规则修改nginx配置文件,重启~ok了。
心情不错,写博客又有动力了。
博客网络优化-静态文件分离
[| 2011/10/22 00:51]
最近又看了几个vps,总感觉为啥相同配置,相同线路,人家跑wp,我跑自制小博客。人家都比我快得多。
之前一直想当然,认为是网络问题之类的。由于今天考虑到了博客迁移,所以这个问题就提上日程了。于是打开chrome调试工具,看了下时间。
一看不要紧,终于找到瓶颈了。。
首先是jquery.js,最早用本机,后来嫌大,用了google提供的,由于最近和谐,google的连接速度非常慢,导致页面一直卡在下载jquery.js上。
由于是静态文件,比较大的体积,且seo无关,这就需要考虑把文件放在一个网络连接比较快的地方,显然放到国内是值得考虑的。
首先试了一下一款云存储产品,发现速度倒是很快,但是无法开启gzip,这个无法忍受。转而考虑比较专业的web托管,一想,sae就是专门干这个的,直接放到sae上最好。于是在sae上申请了个应用,吧jquery.js和几个比较大的图片移过去了。立竿见影,速度提升极大。
再看,发现google的统计代码加载也很慢,反正我也不怎么看google的统计,注释掉。
再访问,飞一般的速度~~~~~~
之前一直想当然,认为是网络问题之类的。由于今天考虑到了博客迁移,所以这个问题就提上日程了。于是打开chrome调试工具,看了下时间。
一看不要紧,终于找到瓶颈了。。
首先是jquery.js,最早用本机,后来嫌大,用了google提供的,由于最近和谐,google的连接速度非常慢,导致页面一直卡在下载jquery.js上。
由于是静态文件,比较大的体积,且seo无关,这就需要考虑把文件放在一个网络连接比较快的地方,显然放到国内是值得考虑的。
首先试了一下一款云存储产品,发现速度倒是很快,但是无法开启gzip,这个无法忍受。转而考虑比较专业的web托管,一想,sae就是专门干这个的,直接放到sae上最好。于是在sae上申请了个应用,吧jquery.js和几个比较大的图片移过去了。立竿见影,速度提升极大。
再看,发现google的统计代码加载也很慢,反正我也不怎么看google的统计,注释掉。
再访问,飞一般的速度~~~~~~
zabbix安装
[| 2011/10/20 23:34]
今天看到一个非常强大的服务器监控程序:zabbix。装了一下。
首先下来源码,最新源码是1.8.8.解压开,configure。缺了一些库,一个一个装上。没啥大问题,唯一一个问题是在打开--enable-static后会报找不到libcurl,应该是libcurl没有提供静态库。时间不多,没有细究,去掉了--enable-static,编译成动态的了。
./configure --prefix=/home/abc/zabbix --enable-server --enable-agent --with-mysql --with-net-snmp=/home/abc/snmpd/bin/net-snmp-config --with-libcurl --with-jabber --enable-ipv6 --with-ssh2
然后make install。这个比较怪,没有单独的make过程,直接make install了。
然后发现只有bin,sbin,share。zabbix是软件免费,服务收费的。怪不得做的这么不自动化,估计想提高门槛好收费。
zabbix依赖webserver、php、mysql。这些软件我之前已经有了,不用再装了。
先在mysql里建表,去源码里找到
create/schema/mysql.sql
create/data/data.sql
create/data/image_mysql.sql
依次导入到mysql里。
然后在zabbix里mkdir etc
将misc/conf/zabbix_*都拷贝到etc里。配置了一下mysql连接信息。
misc/init.d里面有启动用的脚本,我看了一下,感觉还是自己写比较好。
直接启动,告诉我找不到libnetsnmp.so.30。估计是我snmp是自己编译的,zabbix做的有问题,链接路径搞错了,于是先
export LD_LIBRARY_PATH=/*****/snmpd/lib
再启动即可。
然后配置web管理页面。
frontends/php/*里的php文件拷贝到指定位置。开始配置,发现zabbix有个特点,要求php的最大执行时间超长,估计是数据多了处理比较慢。不配好就不能安装,配好后进入管理后台,默认账号和密码是admin和zabbix。进去后配置了下。网页做得比较土,不过功能很强大,很多配置项。
刚开始只启动了zabbix_server,管理后台老是提示无法连接云云,启动了zabbix_agentd后可以监控了。感觉跟文档不符,文档似乎说server也能够监控的。没打算细研究,所以没有细究。
管理页面还支持中文,不错。
现有的小破vps还不至于用这么重量的监控,试试而已。
首先下来源码,最新源码是1.8.8.解压开,configure。缺了一些库,一个一个装上。没啥大问题,唯一一个问题是在打开--enable-static后会报找不到libcurl,应该是libcurl没有提供静态库。时间不多,没有细究,去掉了--enable-static,编译成动态的了。
./configure --prefix=/home/abc/zabbix --enable-server --enable-agent --with-mysql --with-net-snmp=/home/abc/snmpd/bin/net-snmp-config --with-libcurl --with-jabber --enable-ipv6 --with-ssh2
然后make install。这个比较怪,没有单独的make过程,直接make install了。
然后发现只有bin,sbin,share。zabbix是软件免费,服务收费的。怪不得做的这么不自动化,估计想提高门槛好收费。
zabbix依赖webserver、php、mysql。这些软件我之前已经有了,不用再装了。
先在mysql里建表,去源码里找到
create/schema/mysql.sql
create/data/data.sql
create/data/image_mysql.sql
依次导入到mysql里。
然后在zabbix里mkdir etc
将misc/conf/zabbix_*都拷贝到etc里。配置了一下mysql连接信息。
misc/init.d里面有启动用的脚本,我看了一下,感觉还是自己写比较好。
直接启动,告诉我找不到libnetsnmp.so.30。估计是我snmp是自己编译的,zabbix做的有问题,链接路径搞错了,于是先
export LD_LIBRARY_PATH=/*****/snmpd/lib
再启动即可。
然后配置web管理页面。
frontends/php/*里的php文件拷贝到指定位置。开始配置,发现zabbix有个特点,要求php的最大执行时间超长,估计是数据多了处理比较慢。不配好就不能安装,配好后进入管理后台,默认账号和密码是admin和zabbix。进去后配置了下。网页做得比较土,不过功能很强大,很多配置项。
刚开始只启动了zabbix_server,管理后台老是提示无法连接云云,启动了zabbix_agentd后可以监控了。感觉跟文档不符,文档似乎说server也能够监控的。没打算细研究,所以没有细究。
管理页面还支持中文,不错。
现有的小破vps还不至于用这么重量的监控,试试而已。
linux shell脚本信号处理:trap
[| 2011/10/19 01:50]
之前一直以为shell脚本中没法处理信号,所以也没有探究过,突然发现是可以的。
#!/bin/bash
abc(){
echo "signal receive"
}
trap 'abc' INT
sleep 100
这个脚本会在收到ctrl+c的时候打印signal receive。
#!/bin/bash
abc(){
echo "signal receive"
}
trap 'abc' INT
sleep 100
这个脚本会在收到ctrl+c的时候打印signal receive。
linux系统打开core文件设置
[| 2011/10/14 23:30]
默认linux系统是不开启core文件的,不过对于运行较多自己写的程序的服务器,开启core文件还是很有必要的。
首先设置ulimit允许core文件,默认0,不允许。
使用ulimit -c可以设置,但不是永久的。通过编辑/etc/security/limits.conf 文件可以永久改变这一设置。
加入两行:
* soft core unlimited
root soft core unlimited
要对root单独设置,刚开始只设置了*,后来发现没有对root生效。
默认core文件路径和core文件名都不太好,放到固定位置,使用固定规则生成core文件是比较好的选择。
/proc/sys/kernel/core_uses_pid可以控制产生的core文件的文件名中是否添加pid作为扩展,如果添加则文件内容为1,否则为0
echo 1 > /proc/sys/kernel/core_uses_pid
/proc/sys/kernel/core_pattern可以设置格式化的core文件保存位置或文件名,默认文件内容是core
可以这样修改:
echo "/corefile/core-%e-%p-%t" > core_pattern
将会控制所产生的core文件会存放到/corefile目录下,产生的文件名为core-命令名-pid-时间戳
以下是参数列表:
%p - insert pid into filename 添加pid
%u - insert current uid into filename 添加当前uid
%g - insert current gid into filename 添加当前gid
%s - insert signal that caused the coredump into the filename 添加导致产生core的信号
%t - insert UNIX time that the coredump occurred into filename 添加core文件生成时的unix时间
%h - insert hostname where the coredump happened into filename 添加主机名
%e - insert coredumping executable name into filename 添加命令名
首先设置ulimit允许core文件,默认0,不允许。
使用ulimit -c可以设置,但不是永久的。通过编辑/etc/security/limits.conf 文件可以永久改变这一设置。
加入两行:
* soft core unlimited
root soft core unlimited
要对root单独设置,刚开始只设置了*,后来发现没有对root生效。
默认core文件路径和core文件名都不太好,放到固定位置,使用固定规则生成core文件是比较好的选择。
/proc/sys/kernel/core_uses_pid可以控制产生的core文件的文件名中是否添加pid作为扩展,如果添加则文件内容为1,否则为0
echo 1 > /proc/sys/kernel/core_uses_pid
/proc/sys/kernel/core_pattern可以设置格式化的core文件保存位置或文件名,默认文件内容是core
可以这样修改:
echo "/corefile/core-%e-%p-%t" > core_pattern
将会控制所产生的core文件会存放到/corefile目录下,产生的文件名为core-命令名-pid-时间戳
以下是参数列表:
%p - insert pid into filename 添加pid
%u - insert current uid into filename 添加当前uid
%g - insert current gid into filename 添加当前gid
%s - insert signal that caused the coredump into the filename 添加导致产生core的信号
%t - insert UNIX time that the coredump occurred into filename 添加core文件生成时的unix时间
%h - insert hostname where the coredump happened into filename 添加主机名
%e - insert coredumping executable name into filename 添加命令名
ab压力测试时页面动态时被认为错误Failed requests
[| 2011/10/14 10:51]
今天在压力测试一个vps性能时,发现大量Failed requests,非常疑惑,跑脚本curl了很多次,查看结果,发现结果确实有不一致,原来wordpress一个主题上面的主图片是动态变换的,每次请求返回的是随机一个图片地址。ab发现各请求返回内容不一致,所以判断有错误。换成一个普通的主题,正常了。
查看进程所属组(gid)
[| 2011/10/14 00:39]
今天想看某个进程所述的组,发现常用的ps,top等命令都显示不出来。头大,直接去/proc/***/status里面看,有了,Uid,Gid两栏。查到后去passwd和group文件里面对照即可。
supervise启动lighttpd或其他daemon进程问题(linux shell)
[| 2011/10/09 23:27]
今天有同事问到为什么supervise启动lighttpd的时候,lighttpd的pid文件是空的。我试了下,发现果然如此。
首先猜想是不是supervise动了手脚导致程序getpid得到空值,写了个printf getpid的小例子跑了下发现正常。
后来尝试用supervise启动lighttpd,发现supervise每隔1s就尝试启动lighttpd,即使lighttpd已经正常运行了。用刚才的小例子时不会重复尝试,只有被保护程序挂掉后才尝试重启。
后来突然想到lighttpd的两次fork。由于lighttpd进程是以daemon进程形式运行的,在启动过程中有两次fork子进程,然后父进程退出的操作。
supervise中,启动被监控程序的流程是supervise先fork一个自己,子进程调用execvp来启动被监控程序。父进程记录fork时获得的进程号,监控起来。显然,lighttpd第一次fork后,子进程就已经退出了,故supervise以为被监控进程挂了,于是尝试再次启动lighttpd。由于端口被占用的缘故,lighttpd未能启动,由于lighttpd的启动会清空pid文件,而启动失败又没有往里面写入有效进程号,所以pid文件就是空的了。
不使用supervise,通过普通方式两次启动lighttpd,第二次报端口被占用,此时pid文件为空,验证了以上的推论。
首先猜想是不是supervise动了手脚导致程序getpid得到空值,写了个printf getpid的小例子跑了下发现正常。
后来尝试用supervise启动lighttpd,发现supervise每隔1s就尝试启动lighttpd,即使lighttpd已经正常运行了。用刚才的小例子时不会重复尝试,只有被保护程序挂掉后才尝试重启。
后来突然想到lighttpd的两次fork。由于lighttpd进程是以daemon进程形式运行的,在启动过程中有两次fork子进程,然后父进程退出的操作。
supervise中,启动被监控程序的流程是supervise先fork一个自己,子进程调用execvp来启动被监控程序。父进程记录fork时获得的进程号,监控起来。显然,lighttpd第一次fork后,子进程就已经退出了,故supervise以为被监控进程挂了,于是尝试再次启动lighttpd。由于端口被占用的缘故,lighttpd未能启动,由于lighttpd的启动会清空pid文件,而启动失败又没有往里面写入有效进程号,所以pid文件就是空的了。
不使用supervise,通过普通方式两次启动lighttpd,第二次报端口被占用,此时pid文件为空,验证了以上的推论。