Rain-flower Pebble
I was walking along the stream, when I was lucky to meet a beautiful rain-flower pebble.
Although this is not the most beautiful pebble under the sun, I picked it up and went back with happiness.
Because I know this is the best rain-flower pebble that I could find through my lifetime.
I will never go back to this stream any more, but she is the only one in my heart.
…..
我在沙滩上很幸运地捡到块雨花石
我知道她不是最好的
但是我依然很幸运地把她带回去了
因为她是我能找到的最好的所以也是我心里最好的
之后我再也不去那片海滩因为我有我最好的了
。。。。。。
两个宅女逛街
两个宅女逛街
今天芬和琴去徐家汇逛街了,上午她们拍了照片,又有机会看看美女了。哈哈,她们自己说自己是典型的宅女不知道这次逛街会有什么好玩的,会买什么东东。芬还是有点咳,不过好多了。也许是我的冰糖梨水真的有效果,哈哈臭美一下。昨天又给她买了几个梨,听她说吃下去嗓子确实舒服些。
昨天中午吃饭时突然发现芬穿的那件衣服还是蛮漂亮的挺适合她的(标准的美女哦,用红卫的话说就是下得厨房上的厅堂,理想的女友),不知道是不是cc的功劳。我的同学对芬的评价都非常高呢,弄的我好像一坨什么似的。
这周六大家没有看到芬,都蛮想她的,她不在确实冷清很多。虽然她不像花椒师姐那么招人,其实心里面也蛮调皮的可爱的,只是比较喜欢表现的比较乖,下次要好好发掘下她这个方面的潜能。
开朗,开心点好。不过说实话,我第一见她就没有觉得她是个闷的女孩,觉得她是会替人着想的人(有心里咨询师的潜质)。现在发现她有这么多的好友,真是替她开心。
芬你们两个宅女玩开心点哦
芬还是个小女生
芬还是个小女生
哈哈终于发现了,芬还是个小女生,虽然是个比较懂事的小女生。成熟与幼稚并不是看表面说话的,崔表面嘻嘻哈哈的像个小孩,但是他很有理想和抱负的。
知道自己想要什么,是摆脱幼稚的第一步,知道自己怎么去努力,就是成熟的人,和个性无关。芬做的还是不错的,也很努力,可是她有些是来自家人和亲戚的压力,
其实这也很好,只是不要让自己顾虑太多生活是会很累的。要知道一个人的生活是有起伏的,太在乎别人的看法会让自己承受不了失败的,这会让人很脆弱的。
可能是我对芬太好了些吧,这家伙饭吃的好少,这样胃会不好的,而且代谢也会不好的。天冷了,也懒得去换衣服,有种你别生病啊(我妈就是这样说我的,生病还要骂)。
哈哈,以后对要凶一点,让她好好吃饭,否则“叭叭叭叭”。
芬还是个可爱的小女生。
跟芬在一起很开心很甜蜜,sweet!sweet!haha
cc走的日子
今天cc走了,她是芬最好的朋友,但是性格完全不一样,倒是有些像花椒师姐。第一次见她还是满紧张的,因为我这种性格一般不讨这种类型的女孩喜欢的,
而且我也不擅长和这种类型的女孩交往,因为共同点比较少。不过还好,这次看在芬的面子上她没有给我难堪,还对我很热情的。
我们3个人吃了个很愉快的味千拉面,骨头汤还是很好喝的可惜就是小日本的。走的时候她说我是一个贤惠的人,哈哈哈。
芬一点都不喜欢这个称号,其实我也不是,我满讨厌上海小男人这种性格,可惜却被人常常这样认为标准的上海小男人。
我只是觉得亲人之间应该互相体贴照顾啊,特别是生病和难过的时候。要不是芬生病我才不会这么粘呢。
芬的性格真的很好,感觉现在和我们在一起也开朗多了,一点都不闷。
而且还停“坏”的,哈哈。不过我很喜欢这样,我发现她满聪明的很有灵气,只是很内敛。总是说别人怎么怎么好,其实她自己就非常好啦。
不过这几天芬咳嗽还是很利害的,为了照顾cc,自己也没有睡好。我也深有体会,每次崔来我家,我也是有些睡不好的。不过很开心。
You are the best one that I found through my lifetime.
You are the best one that I found through my lifetime.
haha 酸奶竟然成功了而且屡次成功了,其实很简单的。以后去超市买一罐鲜奶,和一小瓶酸奶。留下一点酸奶作为种子发酵就可以了。不过酸奶机真是个好东西。
芬现在睡眠好些了,不知道是我的粥好呢?还是最近感冒了,这几天很冷的,她穿的一直都很少的,所以感冒了,有点咳嗽了。昨天给她买个两个梨不知道有没有效果。
昨晚她做了炒年糕吃,虽然鲜的都点过了头,但是还是很好吃的。最搞笑的是,她说她很闷的,可是我们在一起她话特多,我也是。最后我们一起做菜东西都忘记放了。
师姐今天给她买了一套调羹之类的餐具,还有水果插,和夹子,真是感谢师姐,她真好,不过不知道她看了什么不应该看的,眼睛这几天发炎了,里面张了个小疙瘩,我们给了她
菊花和枸杞,希望可以缓解一下。
c今天过来了,听芬说是美女。其实我也无所谓,她的长相。我只怕她说我很长的猥琐配不上芬,让芬很没有面子。
However ,who cares.好好的做自己,好好的学本领,好好的对待她就可以了。
undefined method `count’ for Array
[1,2,3,4].count you should get an undefined method error
Production:
script/console production
Loading production environment (Rails 2.1.0)
>> User.all.class
=> Array
>> User.find(:all).class
=> Array
>> User.find(:all).count
NoMethodError: undefined method `count’ for #
from (irb):3
Development:
script/console
Loading development environment (Rails 2.1.0)
>> User.all.class
=> Array
>> User.find(:all).class
=> Array
>> User.find(:all).count
=> 2
有时就是会报错,so 可以改成User.find(:all).length
ubuntu下安装配置Postfix邮件系统
1. Introduction(介绍)
Postfix is a Mail Transfer Agent (MTA) which is the default MTA for Ubuntu. It is in Ubuntu’s main repository, which means that it receives security updates. This guide explains how to install and configure postfix and set it up as an SMTP server using a secure connection.
Postfix是一个邮件传输客户端(MTA),它也是ubuntu中默认的邮件传输客户端.它是Ubuntu的main软件库中的一个软件.这意味着它拥有安全更新.这份指南告诉你如何安装及配置postfix并将其设置成一个使用安全连接的SMTP服务器.
2. Installation(安装)
In order to install Postfix with SMTP-AUTH and TLS do the following steps:
安装带SMTP-AUTHT和TLSR的Postfix使用如下的命令:
apt-get install postfix libsasl2 sasl2-bin libsasl2-modules libdb3-util procmail
3. Configuration(配置)
Run:
运行:
dpkg-reconfigure postfix
Insert the following details when asked (replacing server1.example.com with your domain name if you have one):
当要求提供相关信息时输入如下的信息(如果你拥有一个域名的话,将server1.example.com替换成你自己的域名):
* Internet Site
* NONE
* server1.example.com
* server1.example.com, localhost.example.com, localhost
* No
* 127.0.0.0/8
* Yes
* 0
* +
* all
Then run the following commands:
运行下列命令:
### Configure Postfix to do SMTP AUTH using SASL (saslauthd)
postconf -e ’smtpd_sasl_local_domain =’
postconf -e ’smtpd_sasl_auth_enable = yes’
postconf -e ’smtpd_sasl_security_options = noanonymous’
postconf -e ‘broken_sasl_auth_clients = yes’
postconf -e ’smtpd_recipient_restrictions = permit_sasl_authenticated,permit_mynetworks,reject_unauth_destination’
postconf -e ‘inet_interfaces = all’
echo ‘pwcheck_method: saslauthd’ >> /etc/postfix/sasl/smtpd.conf
echo ‘mech_list: plain login’ >> /etc/postfix/sasl/smtpd.conf
### Generate certificates to be used for TLS encryption and/or certificate Authentication
mkdir /etc/postfix/ssl
cd /etc/postfix/ssl/
openssl genrsa -des3 -rand /etc/hosts -out smtpd.key 1024
chmod 600 smtpd.key
openssl req -new -key smtpd.key -out smtpd.csr
openssl x509 -req -days 3650 -in smtpd.csr -signkey smtpd.key -out smtpd.crt
openssl rsa -in smtpd.key -out smtpd.key.unencrypted
mv -f smtpd.key.unencrypted smtpd.key
openssl req -new -x509 -extensions v3_ca -keyout cakey.pem -out cacert.pem -days 3650
### Configure Postfix to do TLS encryption for both incoming and outgoing mail
postconf -e ’smtpd_tls_auth_only = no’
postconf -e ’smtp_use_tls = yes’
postconf -e ’smtpd_use_tls = yes’
postconf -e ’smtp_tls_note_starttls_offer = yes’
postconf -e ’smtpd_tls_key_file = /etc/postfix/ssl/smtpd.key’
postconf -e ’smtpd_tls_cert_file = /etc/postfix/ssl/smtpd.crt’
postconf -e ’smtpd_tls_CAfile = /etc/postfix/ssl/cacert.pem’
postconf -e ’smtpd_tls_loglevel = 1′
postconf -e ’smtpd_tls_received_header = yes’
postconf -e ’smtpd_tls_session_cache_timeout = 3600s’
postconf -e ‘tls_random_source = dev:/dev/urandom’
postconf -e ‘myhostname = server1.example.com’
The file /etc/postfix/main.cf should now look like this: /etc/postfix/main.cf
这个文件应当是如下的内容:
# See /usr/share/postfix/main.cf.dist for a commented, more complete version
smtpd_banner = $myhostname ESMTP $mail_name (Ubuntu)
biff = no
# appending .domain is the MUA’s job.
append_dot_mydomain = no
# Uncomment the next line to generate “delayed mail” warnings
#delay_warning_time = 4h
myhostname = server1.example.com
alias_maps = hash:/etc/aliases
alias_database = hash:/etc/aliases
myorigin = /etc/mailname
mydestination = server1.example.com, localhost.example.com, localhost
relayhost =
mynetworks = 127.0.0.0/8
mailbox_command = procmail -a “$EXTENSION”
mailbox_size_limit = 0
recipient_delimiter = +
inet_interfaces = all
smtpd_sasl_local_domain =
smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
broken_sasl_auth_clients = yes
smtpd_recipient_restrictions = permit_sasl_authenticated,permit_mynetworks,reject _unauth_destination
smtpd_tls_auth_only = no
smtp_use_tls = yes
smtpd_use_tls = yes
smtp_tls_note_starttls_offer = yes
smtpd_tls_key_file = /etc/postfix/ssl/smtpd.key
smtpd_tls_cert_file = /etc/postfix/ssl/smtpd.crt
smtpd_tls_CAfile = /etc/postfix/ssl/cacert.pem
smtpd_tls_loglevel = 1
smtpd_tls_received_header = yes
smtpd_tls_session_cache_timeout = 3600s
tls_random_source = dev:/dev/urandom
Restart the postfix daemon like this:
重启postfix守护进程:
/etc/init.d/postfix restart
4. Authentication(验证)
Authentication will be done by saslauthd.
使用saslauthd来执行验证
We have to change a few things to make it work properly. Because Postfix runs chrooted in /var/spool/postfix we have change a couple paths to live in the false root. (ie. /var/run/saslauthd becomes /var/spool/postfix/var/run/saslauthd):
我们应当修改一些内容来令saslauthd正常工作.因为Postfix需要将根目录更改为/var/spool/postfix ,我们应当将那些使用不正确根目录的目录更改为正确的.(例如:将/var/run/saslauthd 修改为/var/spool/postfix/var/run/saslauthd):
First we edit /etc/default/saslauthd in order to activate saslauthd. Remove # in front of START=yes and add the PWDIR, PARAMS, and PIDFILE lines:
首先,我们需要编辑/etc/default/saslauthd 以激活 saslauthd . 请将 START=yes 之前的 # 号去掉并添加 PWDIR, PARAMS 和 PIDFILE 行:
# This needs to be uncommented before saslauthd will be run automatically
START=yes
PWDIR=”/var/spool/postfix/var/run/saslauthd”
PARAMS=”-m ${PWDIR}”
PIDFILE=”${PWDIR}/saslauthd.pid”
# You must specify the authentication mechanisms you wish to use.
# This defaults to “pam” for PAM support, but may also include
# “shadow” or “sasldb”, like this:
# MECHANISMS=”pam shadow”
MECHANISMS=”pam”
Note: If you prefer, you can use “shadow” instead of “pam”. This will use MD5 hashed password transfer and is perfectly secure. The username and password needed to authenticate will be those of the users on the system you are using on the server.
注 : 如果你喜欢的话,你可以使用”shadow”来替换”pam” .这将使用MD5生成的哈希值来传输以得到更高的安全性. 需要验证的用户名及密码将是那些你服务器上的系统上的.
Next, we update the dpkg “state” of /var/spool/portfix/var/run/saslauthd. The saslauthd init script uses this setting to create the missing directory with the appropriate permissions and ownership:
下一步: 我们更新 dpkg 中 /var/spool/portfix/var/run/saslauthd 的状态. saslauthd 的启动脚本需要一个特定的用户权限来建立一个新的目录.
dpkg-statoverride –force –update –add root sasl 755 /var/spool/postfix/var/run/saslauthd
Finally, start saslauthd:
最后,启动saslauthd:
/etc/init.d/saslauthd start
5. Testing(测试)
To see if SMTP-AUTH and TLS work properly now run the following command:
要查看SMTP-AUTH 及TLS能否正常工作请使用如下命令:
telnet localhost 25
After you have established the connection to your postfix mail server type
在您建立了与您的postfix邮件服务器类型的连接之后
ehlo localhost
If you see the lines
如果你看到如下行
250-STARTTLS
250-AUTH
among others, everything is working.
在其它内容之上,表明一切正常.
Type quit to return to the system’s shell.
输入 quit 以返回系统.
6、安装Postfix
从下面的URL下载Postfix 2.2.8的源代码:http://www.postfix.org
从下面的URL下载Postfix 2.2.8的VDA补丁程序:http://web.onda.com.br/nadal/
chkconfig –level 2345 sendmail off
增加Postfix运行所需要的用户和组,并建立“/home/mail”目录作为存储邮件的地方:
groupadd postfix
groupadd postdrop
useradd postfix -g postfix -c “Postfix user” -d /nonexistent -s /sbin/nologin
mkdir /home/mail
chown postfix:postfix /home/mail
安装Postfix:
gzip -d postfix-2.2.8-vda.patch.gz
tar zvxf postfix-2.2.8.tar.gz
cd postfix-2.2.8
patch -p1 >/etc/postfix/aliases
/usr/bin/newaliases
注:因为Postfix不允许直接发邮件给root用户,所以你需要为root用户建立一个别名。
建立smtpd用户认证的配置文件:
vi /usr/lib/sasl2/smtpd.conf
pwcheck_method: authdaemond
log_level: 3
mech_list: plain login
authdaemond_path:/var/spool/authdaemon/socket
使用postconf -n简化main.cf,这样的好处是main.cf比较短小,不容易造成同一个配置出现两次的问题:
cd /etc/postfix
postconf -n > main2.cf
mv main.cf main.cf.old
mv main2.cf main.cf
修改Postfix的配置文件,#号之后是说明文字:
vi /etc/postfix/main.cf
myhostname = mail.example.com # mail.example.com是安装Postfix软件的主机名
mydomain = example.com # example.com是安装Postfix软件的主机名中的域名部分
myorigin = $mydomain
mydestination =
alias_maps = hash:/etc/aliases
home_mailbox = Maildir/ # 使用Maildir作为邮件的存储格式
# Add following line in file’s finality
virtual_alias_maps = mysql:/etc/postfix/mysql_virtual_alias_maps.cf
virtual_mailbox_base = /home/mail
virtual_mailbox_domains = mysql:/etc/postfix/mysql_virtual_domains_maps.cf
virtual_mailbox_limit = 102400000
virtual_mailbox_maps = mysql:/etc/postfix/mysql_virtual_mailbox_maps.cf
virtual_minimum_uid = 502
virtual_uid_maps = static:502
virtual_gid_maps = static:502
virtual_transport = virtual
# Additional for quota support
virtual_create_maildirsize = yes
virtual_mailbox_extended = yes
virtual_mailbox_limit_maps = mysql:/etc/postfix/mysql_virtual_limit_maps.cf
virtual_mailbox_limit_override = yes
virtual_maildir_limit_message = Sorry, the user’s maildir has overdrawn his diskspace quota, please try again later.
virtual_overquota_bounce = yes
virtual_trash_count=yes
virtual_trash_name=.Trash
broken_sasl_auth_clients = yes
smtpd_recipient_restrictions =
permit_mynetworks,
permit_sasl_authenticated,
reject_non_fqdn_hostname,
reject_non_fqdn_sender,
reject_non_fqdn_recipient,
reject_unauth_destination,
reject_unauth_pipelining,
reject_invalid_hostname,
reject_rbl_client opm.blitzed.org,
reject_rbl_client list.dsbl.org,
reject_rbl_client bl.spamcop.net,
reject_rbl_client sbl-xbl.spamhaus.org
smtpd_sasl_auth_enable = yes
smtpd_sasl_local_domain = $myhostname
smtpd_sasl_security_options = noanonymous
注:①“virtual_gid_maps”和“virtual_uid_maps”是postfix用户的gid和uid, “virtual_minimum_uid”应当≤“virtual_uid_maps”,“virtual_mailbox_limit”是每个邮箱的大小。
②opm.blitzed.org、list.dsbl.org、bl.spamcop.net、sbl-xbl.spamhaus.org是经常使用的几个反垃圾邮件列表,如果你使用上面的设置可能无法收到sina、sohu、163等几个国内主要ISP的邮件。你也可以使用中国反垃圾邮件联盟的反垃圾邮件列表,这样你就能收到国内几个主要ISP的邮件,同时一些垃圾邮件也可能光临你的邮件服务器^_^。
③Postfix使用MySQL存储用户信息的配置文件已经包含在extman的发行包中,等安装extman的时候copy到/etc/postfix目录下即可。
设置Postfix开机自动运行,在/etc/rc.local中增加“/usr/sbin/postfix start&”。
注:①系统已经打开了Postfix的TLS支持,如果你需要这项功能可以参考Postfix发行包中的TLS_README文档进行配置。
②你可以使用一个叫pflogsumm.pl的perl脚本对postfix的日志进行分析,详细的情况见:http://jimsun.linxnet.com/postfix_contrib.html。
7. Installing courier IMAP and POP3
sudo apt-get install courier-pop
sudo apt-get install courier-imap
自已架站就要 DIY 一些比較底層的東西,像是 firewall, dns, mail server… 等等有的沒的。啊!現在想想公司有 MIS 可以依賴真好 (被寵壞啦~)。好,回正題吧。先聲名一下,本文不是架一台 mail server,然後提供用戶 pop3, smtp 等那種偉大的服務。我的需求很簡單,只是讓網站能寄信出去而已,像是寄寄認證信,通知信之類的小事。
OS: Ubuntu
Ubuntu 真是個好用的 Linux distro,以前我是用 redhat 的,但是 fedora 對我的 notebook 支援不好,所以改成最多人使用的 Ubuntu。久而久之就迷上啦!所以 server 也開始改用 Ubuntu。Ubuntu 吸引我的優點是 (1) 不會裝無謂的 service — 從 security 這角度來看是比較好。像 fedora 就 “很好心”,一口氣幫你全裝了,但你不見得用的到,你也不見得都懂那些 service 在幹嘛,留著洞放在那就是徒增無謂的風險。(2) apt-get 比 fedora 的 yum 好用太多了,快速、問題又少 ![]()
Mail Agent: postfix
對我這個 mail 白吃,只能裝人家包好的來用:
sudo apt-get install mutt
上面這個指令自動安裝一個 command-line 的 mail client mutt。mutt 這個程式可以用 command line 指令直接寄帶有 attachment 的 email,功能強大,很適合來做 scripting,推薦大家使用!好了,注意看安裝過程,安裝 mutt 時,apt-get 會順便將 postfix mail agent 也一併安裝了。感覺真爽!緊接著會進入 postfix 的設定畫面:
* General Type of Configuration: 選Internet Site
* Mail name? 設為 mysite.com.tw
* Other dest. to accept mail for? 設為 空白
* Force sync. updates on mail queue? 設 Yes
上面僅列出幾個比較特別要設的,其他的設定都用預設值即可。設完之後 postfix 便會啟動,並且只限本機才能寄 email。(這樣才能避免別人將你的站當垃圾信轉寄站)
安裝完後,查看 /etc/postfix/main.cf 底下應該是長這樣:
myhostname = mysite.com.tw
alias_maps = hash:/etc/aliases
alias_database = hash:/etc/aliases
mydestination =
relayhost =
mynetworks = 127.0.0.0/8
mailbox_size_limit = 0
recipient_delimiter = +
inet_interfaces = all
myorigin = /etc/mailname
inet_protocols = all
如果想要再次修改 postfix 的設定,可以用下面這個指令:
sudo dpkg-reconfigure –priority=low postfix
OK,寄一封信測試一下 postfix 是否正常運作吧:
echo “test content” | mutt -s “test subject” myname@example.com.tw
寄出後,到 /var/log/mail.log 看一下 log 訊息,只要沒看到 refuse talk, reject 之類的字眼,對方的 server 大概已接受了你的來信。OK,現在到你的信箱去(myname@example.com.tw) 應該會收到剛才那一封測試信才是。而且大概會被分類到垃圾信箱…
設定 dns 反查
為了避免寄出去的信被當做垃圾信,首先要設定 dns 反查,讓你的 ip 可以反查回 domain name。這樣別人的 mail server 才比較能相信你的站寄的信件。
#下指令:
nslookup 220.xxx.xxx.xxx
#如果是 hinet ,結果大概是:
Server: 168.95.192.1
Address: 168.95.192.1#53
xxx.xxx.xxx.220.in-addr.arpa name = xxxxxxxxxxxx
最後面的 name= xxxxxxx 如果不是出現你的 domain name,表示還沒設反查。那麼請洽 ISP 幫你設定。我是用 hinet adsl 固定制的,大概說一下流程:首先要到 申請 hinet 領域反解填線上申請表。按照範例填妥後送出,再將畫面上的申請表列印並加蓋個人私章 (個人申請用私章),再 fax 給該單位即可。沒意外的話,下個工作天就會收到已完工的 email。然後 dns 的反查大約需要 12~24 小時才會生效。屆時再用 nslookup 檢查一下即可。
設定 Sender Policy Framework (SPF)
設定 dns 反查只是解決被誤判垃圾信的第一步,接下來還要設定 SPF,一種對付垃圾信的技術,詳細說明請看 Wikipedia SPF。我自個兒呢… 有看沒有懂…. 所幸有高人相助啊!!
首先到你的註冊 domain name 的網站,通常裡面都有 DNS zone file 的設定。請加入下面這一行 spf 相關的設定:
mysite.com.tw. 86400 IN TXT v=spf1 a ip4:220.xxx.xxx.xxx -all
前面是你的 mail 的 full domain name,記得要用 . 結尾。86400 是設定 TTL (Time To Live) 的秒數。86400秒意指這個設定一天內都不需重讀。這個值我亂設的… 也許可以設更長?按理說固定 ip 應該不會常換才是?
好了,設完之後,大概也是等個幾小時才會生效。想確認可以到 邪惡的地方做個測試,只要輸入 doman name 即可。(測完後要記得洗手啊!!)
OK,就設到這邊。gmail 和 yahoo 大致上不會把站寄出去的信當 spam 了,除非你發信的內容太像 spam… 不過 hotmail 還是不大行,也不知還差了啥?這就要請教各位高手了…
ps. 感謝 koji兄 和 tempo兄 指導與協助!
ps2. 如果你是像我一樣,只求本機可以寄信出去,那麼 firewall 不用開 port 25 (smtp)
ps3. 我想先買 Wii 耶。
前 言
在CentOS中,默认的邮件服务器(SMTP方面)是sendmail,但sendmail有若干的缺点,比如,配置复杂、安全漏洞曾被多次发现 –并且依然存在隐患、邮件发送速度慢等等,这里就不再一一叙述。而另一个被广泛应用于邮件服务方面的“Postfix”的缺点就少得多,或者说它就是针对于sendmail的缺点,而被设计的。对应sendmail的短处,它在各方面也比较成熟。所以,无特殊要求,这里不推荐用sendmail来构建邮件服务器。本站介绍的邮件服务器配置方法,也将基于Postfix。
添加MX记录(这里假设使用动态域名)
由于MX记录添加后,可能生效要等待一段时间(通常为数分钟或数十分钟,也可能马上生效),所以在安装配置前,我们首先为动态域名添加MX记录。添加方法也会因域名ISP的不同而不同,但大致信息如下:
mx mail.centospub.com. 10
a mail 服务器的IP地址
mail为别名,10为优先度。这个别名指向服务器的IP地址。(如有疑问或需要帮忙请到 技术论坛 发贴。)
确认MX记录的添加是否生效的方法:
[root@sample ~]# host -t mx centospub.com
centospub.com mail is handled by 10 mail.centospub.com. ← 确认MX记录生效
安装Postfix
然后,安装Postfix。
[root@sample ~]# yum -y install postfix ← 在线安装Postfix
Setting up Install Process
Setting up repositories
dag 100% |=========================| 1.1 kB 00:00
update 100% |=========================| 951 B 00:00
base 100% |=========================| 1.1 kB 00:00
addons 100% |=========================| 951 B 00:00
extras 100% |=========================| 1.1 kB 00:00
Reading repository metadata in from local files
primary.xml.gz 100% |=========================| 28 kB 00:04
update : ################################################## 84/84
Added 84 new packages, deleted 1499 old in 3.44 seconds
primary.xml.gz 100% |=========================| 157 B 00:00
Added 0 new packages, deleted 1499 old in 1.97 seconds
primary.xml.gz 100% |=========================| 26 kB 00:00
extras : ################################################## 102/102
Added 102 new packages, deleted 1499 old in 2.73 seconds
Reducing Dag RPM Repository for Red Hat Enterprise Linux to included packages only
Finished
Parsing package install arguments
Resolving Dependencies
–> Populating transaction set with selected packages. Please wait.
—> Downloading header for postfix to pack into transaction set.
postfix-2.2.10-1.RHEL4.2. 100% |=========================| 40 kB 00:00
—> Package postfix.i386 2:2.2.10-1.RHEL4.2 set to be updated
–> Running transaction check
Dependencies Resolved
=============================================================================
Package Arch Version Repository Size
=============================================================================
Installing:
postfix i386 2:2.2.10-1.RHEL4.2 base 3.0 M
Transaction Summary
=============================================================================
Install 1 Package(s)
Update 0 Package(s)
Remove 0 Package(s)
Total download size: 3.0 M
Downloading Packages:
(1/1): postfix-2.2.10-1.R 100% |=========================| 3.0 MB 00:05
Running Transaction Test
Finished Transaction Test
Transaction Test Succeeded
Running Transaction
Installing: postfix ######################### [1/1]
Installed: postfix.i386 2:2.2.10-1.RHEL4.2
Complete!
配置Postfix及相关组件
[1] 对Postfix进行配置。
[root@sample ~]# vi /etc/postfix/main.cf ← 编辑Postfix的配置文件
#myhostname = host.domain.tld ← 找到此行,将等号后面的部分改写为主机名
↓
myhostname = sample.centospub.com ← 变为此状态,设置系统的主机名
#mydomain = domain.tld ← 找到此行,将等号后面的部分改写为域名
↓
mydomain = centospub.com ← 变为此状态,设置域名(我们将让此处设置将成为E-mail地址“@”后面的部分)
#myorigin = $mydomain ← 找到此行,将行首的#去掉
↓
myorigin = $mydomain ← 变为此状态,将发信地址“@”后面的部分设置为域名(非系统主机名)
inet_interfaces = localhost ← 找到此行,将“localhost”改为“all”
↓
inet_interfaces = all ← 变为此状态,接受来自所有网络的请求
mydestination = $myhostname, localhost.$mydomain, localhost ← 找到此行,在行为添加“$mydomain”
↓
mydestination = $myhostname, localhost.$mydomain, localhost, $mydomain ← 变为此状态,指定发给本地邮件的域名
#relay_domains = $mydestination ← 找到此行,将行首的#去掉
↓
relay_domains = $mydestination ← 变为此状态,定义允许转发的域名
#mynetworks = 168.100.189.0/28, 127.0.0.0/8 ← 找到此行,依照自己的内网情况修改
↓
mynetworks = 168.100.189.0/28, 127.0.0.0/8 ← 变为此状态,指定内网和本地的IP地址范围
#home_mailbox = Maildir/ ← 找到这一行,去掉行首的#
↓
home_mailbox = Maildir/ ← 变为此状态,指定用户邮箱目录
# SHOW SOFTWARE VERSION OR NOT
#
# The smtpd_banner parameter specifies the text that follows the 220
# code in the SMTP server’s greeting banner. Some people like to see
# the mail version advertised. By default, Postfix shows no version.
#
# You MUST specify $myhostname at the start of the text. That is an
# RFC requirement. Postfix itself does not care.
#
#smtpd_banner = $myhostname ESMTP $mail_name
#smtpd_banner = $myhostname ESMTP $mail_name ($mail_version) ← 找到这一行,接此行添加如下行:
smtpd_banner = $myhostname ESMTP unknow ← 添加这一行,不显示SMTP服务器的相关信息
在配置文件的文尾,添加如下行:
smtpd_sasl_auth_enable = yes ← 服务器使用SMTP认证
smtpd_sasl_local_domain = $myhostname ← 指定SMTP认证的本地域名(主机名)
smtpd_sasl_security_options = noanonymous ← 不允许匿名的方式认证
smtpd_recipient_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_unauth_destination
message_size_limit = 15728640 ← 规定邮件最大尺寸为15MB
[2] 配置SMTP认证的相关选项
为了提高安全性,我们不将系统用户的密码作为相应用户SMTP认证的密码,而将在后面为用户建立SMTP认证专用的密码。
[root@sample ~]# vi /usr/lib/sasl2/smtpd.conf ← 编辑SMTP认证的配置文件
pwcheck_method: saslauthd ← 找到此行,将“saslauthd”改为“auxprop”
↓
pwcheck_method: auxprop ← 不使用系统用户密码作为用户的SMTP认证密码
[root@sample ~]# vi /etc/sysconfig/saslauthd
MECH=shadow ← 找到这一行,在前面加#
↓
#MECH=shadow ← 不使用shadow机制
FLAGS= ← 找到此行,在等号后面添加“sasldb”
↓
FLAGS=sasldb ← 定义认证方式为sasldb2
[3] 建立用户的邮箱目录
首先建立用户模板下的邮箱目录,以便于建立新用户时,相应用户的邮箱目录自动被建立。
[root@sample ~]# mkdir /etc/skel/Maildir ← 在用户模板下建立用户邮箱目录
[root@sample ~]# chmod 700 /etc/skel/Maildir ← 设置用户邮箱目录属性为700
然后再为已经存在的用户建立相应邮箱目录。
[root@sample ~]# mkdir /home/centospub/Maildir ← 为用户(这里以centospub用户为例)建立邮箱目录
[root@sample ~]# chmod 700 /home/centospub/Maildir ← 设置该用户邮箱目录属性为700
[root@sample ~]# chown centospub. /home/centospub/Maildir ← 设置该用户邮箱目录为该用户所有
[4] 为用户设置SMTP认证密码
[root@sample ~]# saslpasswd2 -u sample.centospub.com -c centospub ← 为centospub用户设置SMTP认证密码
Password: ← 在这里输入密码(不会显示)
Again (for verification): ← 再次输入密码
[5] 改变SALS的属性及归属
[root@sample ~]# chgrp postfix /etc/sasldb2 ← 将数据库归属改为postfix,
[root@sample ~]# chmod 640 /etc/sasldb2 ← 将数据库属性改为640
[6] 关闭sendmail服务及设置默认MTA
因为在用Postfix作为SMTP服务器的前提下,我们不准备再用sendmail,所以将sendmail服务关掉,以确保安全及节省系统资源。
[root@sample ~]# /etc/rc.d/init.d/sendmail stop ← 关闭sendmail服务
Shutting down sendmail: [ OK ]
Shutting down sm-client: [ OK ]
[root@sample ~]# chkconfig sendmail off ← 关闭sendmail自启动
[root@sample ~]# chkconfig –list sendmail ← 确认sendmail自启动已被关闭(都为off就OK)
sendmail 0:off 1:off 2:off 3:off 4:off 5:off 6:off
然后再将默认的MTA设置为Postfix。
[root@sample ~]# alternatives –config mta ← 设置默认MTA
There are 2 programs which provide ‘mta’.
Selection Command
———————————————–
*+ 1 /usr/sbin/sendmail.sendmail ← 当前状态:sendmail为默认MTA
2 /usr/sbin/sendmail.postfix
Enter to keep the current selection[+], or type selection number: 2 ← 在这里输入2,使Postfix成为默认MTA
启动相应服务
最后,启动SMTP认证及Postfix服务,并设置相应服务为自启动。
[root@sample ~]# chkconfig saslauthd on ← 将SMTP-Auth设置为自启动
[root@sample ~]# chkconfig –list saslauthd ← 确认SMTP-Auth服务状态
saslauthd 0:off 1:off 2:on 3:on 4:on 5:on 6:off ← 确认2~5为on的状态就OK
[root@sample ~]# /etc/rc.d/init.d/saslauthd start ← 启动SMTP-Auth
Starting saslauthd: [ OK ]
[root@sample ~]# chkconfig postfix on ← 将Postfix设置为自启动
[root@sample ~]# chkconfig –list postfix ← 确认Postfix服务状态
postfix 0:off 1:off 2:on 3:on 4:on 5:on 6:off ← 确认2~5为on的状态就OK
[root@sample ~]# /etc/rc.d/init.d/postfix start ← 启动Postfix
Starting postfix: [ OK ]
至此,就完成了SMTP服务器方面的配置,但目前只具从备客户端通过服务器发送邮件的功能。做为完整的邮件服务器,还需具备从客户端通过POP/IMAP协议接受邮件到本地的功能。POP/IMAP服务器的构建请参见下一节 。
优雅的生活
优雅的生活
上次我做的粥效果还不错,感觉莲子还没有煮烂,总的来说不错了。
总结一下:1.小米千万不能放多,一煮就会糊的,可以说是你想想不到的少,一大锅几百粒就足够多了。
2.莲子很难煮的,跑过一晚还是不容易煮好,最好要先煮几个小时。
总之煮这个粥还是满辛苦的,要不停的搅拌。还好芬喜欢喝。
还有银耳也是很容易越煮越多的,2-3棵就可以了。
芬吃饭很少,我满担心她的胃的,不过还好粥她是无限量的。
她上次做酸奶失败了,哈哈,这次我来做。我是学生物,我认为是温度的问题,还有热激下也许效果会更好。
反正我是这么跟她说的,其实这次我偷偷放了瓶酸奶进去的,希望明天能做好,以后告诉她。
跟她在一起很开心,我也没有什么顾虑,觉得生活这样多好啊。她是我见过的最好的女孩,我也不知道我怎么这么幸运啊。
优雅的生活,very good!
biopython NCBIWWW.qblast
http://www.biopython.org/DIST/docs/tutorial/Tutorial.html
6.2 Running BLAST over the Internet
We use the function qblast() in the Bio.Blast.NCBIWWW module call the online version of BLAST. This has three non-optional arguments:
* The first argument is the blast program to use for the search, as a lower case string. The options and descriptions of the programs are available at http://www.ncbi.nlm.nih.gov/BLAST/blast_program.html. Currently qblast only works with blastn, blastp, blastx, tblast and tblastx.
* The second argument specifies the databases to search against. Again, the options for this are available on the NCBI web pages at http://www.ncbi.nlm.nih.gov/BLAST/blast_databases.html.
* The third argument is a string containing your query sequence. This can either be the sequence itself, the sequence in fasta format, or an identifier like a GI number.
The qblast function also take a number of other option arguments which are basically analogous to the different parameters you can set on the BLAST web page. We’ll just highlight a few of them here:
* The qblast function can return the BLAST results in various formats, which you can choose with the optional format_type keyword: “HTML”, “Text”, “ASN.1″, or “XML”. The default is “XML”, as that is the format expected by the parser, described in section 6.4 below.
* The argument expect sets the expectation or e-value threshold.
For more about the optional BLAST arguments, we refer you to the NCBI’s own documentation, or that built into Biopython:
>>> from Bio.Blast import NCBIWWW
>>> help(NCBIWWW.qblast)
For example, if you have a nucleotide sequence you want to search against the non-redundant database using BLASTN, and you know the GI number of your query sequence, you can use:
>>> from Bio.Blast import NCBIWWW
>>> result_handle = NCBIWWW.qblast(”blastn”, “nr”, “8332116″)
Alternatively, if we have our query sequence already in a FASTA formatted file, we just need to open the file and read in this record as a string, and use that as the query argument:
>>> from Bio.Blast import NCBIWWW
>>> fasta_string = open(”m_cold.fasta”).read()
>>> result_handle = NCBIWWW.qblast(”blastn”, “nr”, fasta_string)
We could also have read in the FASTA file as a SeqRecord and then supplied just the sequence itself:
>>> from Bio.Blast import NCBIWWW
>>> from Bio import SeqIO
>>> record = SeqIO.read(open(”m_cold.fasta”), format=”fasta”)
>>> result_handle = NCBIWWW.qblast(”blastn”, “nr”, record.seq)
Supplying just the sequence means that BLAST will assign an identifier for your sequence automatically. You might prefer to use the SeqRecord object’s format method to make a fasta string (which will include the existing identifier):
>>> from Bio.Blast import NCBIWWW
>>> from Bio import SeqIO
>>> record = SeqIO.read(open(”m_cold.fasta”), format=”fasta”)
>>> result_handle = NCBIWWW.qblast(”blastn”, “nr”, record.format(”fasta”))
This approach makes more sense if you have your sequence(s) in a non-FASTA file format which you can extract using Bio.SeqIO (see Chapter 4).
Whatever arguments you give the qblast() function, you should get back your results in a handle object (by default in XML format). The next step would be to parse the XML output into python objects representing the search results (Section 6.4), but you might want to save a local copy of the output file first.
6.3 Saving BLAST output
Before parsing the results, it is often useful to save them into a file so that you can use them later without having to go back and re-blasting everything. I find this especially useful when debugging my code that extracts info from the BLAST files, but it could also be useful just for making backups of things you’ve done.
If you don’t want to save the BLAST output, you can skip to section 6.4. If you do, read on.
We need to be a bit careful since we can use result_handle.read() to read the BLAST output only once – calling result_handle.read() again returns an empty string. First, we use read() and store all of the information from the handle into a string:
>>> blast_results = result_handle.read()
Next, we save this string in a file:
>>> save_file = open(”my_blast.xml”, “w”)
>>> save_file.write(blast_results)
>>> save_file.close()
After doing this, the results are in the file my_blast.xml and the variable blast_results contains the BLAST results in a string form. However, the parse function of the BLAST parser (described in 6.4) takes a file-handle-like object, not a plain string. To get a handle, there are two things you can do:
* Use the Python standard library module cStringIO. The following code will turn the plain string into a handle, which we can feed directly into the BLAST parser:
>>> import cStringIO
>>> result_handle = cStringIO.StringIO(blast_results)
* Open the saved file for reading. Duh.
>>> result_handle = open(”my_blast.xml”)
Now that we’ve got the BLAST results back into a handle again, we are ready to do something with them, so this leads us right into the parsing section.
6.4 Parsing BLAST output
As mentioned above, BLAST can generate output in various formats, such as XML, HTML, and plain text. Originally, Biopython had a parser for BLAST plain text and HTML output, as these were the only output formats supported by BLAST. Unfortunately, the BLAST output in these formats kept changing, each time breaking the Biopython parsers. As keeping up with changes in BLAST became a hopeless endeavor, especially with users running different BLAST versions, we now recommend to parse the output in XML format, which can be generated by recent versions of BLAST. Not only is the XML output more stable than the plain text and HTML output, it is also much easier to parse automatically, making Biopython a whole lot more stable.
Though deprecated, the parsers for BLAST output in plain text or HTML output are still available in Biopython (see Section 6.6). Use them at your own risk: they may or may not work, depending on which BLAST version you’re using.
You can get BLAST output in XML format in various ways. For the parser, it doesn’t matter how the output was generated, as long as it is in the XML format.
* You can use Biopython to run BLAST locally, as described in section 6.1.
* You can use Biopython to run BLAST over the internet, as described in section 6.2.
* You can do the BLAST search yourself on the NCBI site through your web browser, and then save the results. You need to choose XML as the format in which to receive the results, and save the final BLAST page you get (you know, the one with all of the interesting results!) to a file.
* You can also run BLAST locally without using Biopython, and save the output in a file. Again, you need to choose XML as the format in which to receive the results.
The important point is that you do not have to use Biopython scripts to fetch the data in order to be able to parse it.
Doing things in one of these ways, you then need to get a handle to the results. In Python, a handle is just a nice general way of describing input to any info source so that the info can be retrieved using read() and readline() functions. This is the type of input the BLAST parser (and most other Biopython parsers) take.
If you followed the code above for interacting with BLAST through a script, then you already have result_handle, the handle to the BLAST results. For example, using a GI number to do an online search:
>>> from Bio.Blast import NCBIWWW
>>> result_handle = NCBIWWW.qblast(”blastn”, “nr”, “8332116″)
If instead you ran BLAST some other way, and have the BLAST output (in XML format) in the file my_blast.xml, all you need to do is to open the file for reading:
>>> result_handle = open(”my_blast.xml”)
Now that we’ve got a handle, we are ready to parse the output. The code to parse it is really quite small:
>>> from Bio.Blast import NCBIXML
>>> blast_records = NCBIXML.parse(result_handle)
To understand what NCBIXML.parse returns, there are two things that you need to keep in mind:
* The BLAST output may contain the output of more than one BLAST search. This will for example be the case if you ran BLAST locally on a Fasta file containing more than one sequence. For each sequence, the BLAST parser will return one BLAST record.
* The BLAST output may therefore be huge.
To be able to handle these situations, NCBIXML.parse() returns an iterator (like Bio.SeqIO.parse(), see Chapter 4). In plain English, an iterator allows you to step through the BLAST output, retrieving BLAST records one by one for each BLAST search:
>>> blast_record = blast_records.next()
# … do something with blast_record
>>> blast_record = blast_records.next()
# … do something with blast_record
>>> blast_record = blast_records.next()
# … do something with blast_record
>>> blast_record = blast_records.next()
Traceback (most recent call last):
File “”, line 1, in
StopIteration
# No further records
Or, you can use a for-loop:
>>> for blast_record in blast_records:
… # Do something with blast_record
Note though that you can step through the BLAST records only once. Usually, from each BLAST record you would save the information that you are interested in. If you want to save all returned BLAST records, you can convert the iterator into a list:
>>> blast_records = list(blast_records)
Now you can access each BLAST record in the list with an index as usual. If your BLAST file is huge though, you may run into memory problems trying to save them all in a list.
Usually, you’ll be running one BLAST search at a time. Then, all you need to do is to pick up the first (and only) BLAST record in blast_records:
>>> blast_record = blast_records.next()
I guess by now you’re wondering what is in a BLAST record.
6.5 The BLAST record class
A BLAST Record contains everything you might ever want to extract from the BLAST output. Right now we’ll just show an example of how to get some info out of the BLAST report, but if you want something in particular that is not described here, look at the info on the record class in detail, and take a gander into the code or automatically generated documentation – the docstrings have lots of good info about what is stored in each piece of information.
To continue with our example, let’s just print out some summary info about all hits in our blast report greater than a particular threshold. The following code does this:
>>> E_VALUE_THRESH = 0.04
>>> for alignment in blast_record.alignments:
… for hsp in alignment.hsps:
… if hsp.expect gb|AF283004.1|AF283004 Arabidopsis thaliana cold acclimation protein WCOR413-like protein
alpha form mRNA, complete cds
length: 783
e value: 0.034
tacttgttgatattggatcgaacaaactggagaaccaacatgctcacgtcacttttagtcccttacatattcctc…
||||||||| | ||||||||||| || |||| || || |||||||| |||||| | | |||||||| ||| ||…
tacttgttggtgttggatcgaaccaattggaagacgaatatgctcacatcacttctcattccttacatcttcttc…
Basically, you can do anything you want to with the info in the BLAST report once you have parsed it. This will, of course, depend on what you want to use it for, but hopefully this helps you get started on doing what you need to do!
An important consideration for extracting information from a BLAST report is the type of objects that the information is stored in. In Biopython, the parsers return Record objects, either Blast or PSIBlast depending on what you are parsing. These objects are defined in Bio.Blast.Record and are quite complete.
Here are my attempts at UML class diagrams for the Blast and PSIBlast record classes. If you are good at UML and see mistakes/improvements that can be made, please let me know. The Blast class diagram is shown in Figure 6.5.
The PSIBlast record object is similar, but has support for the rounds that are used in the iteration steps of PSIBlast. The class diagram for PSIBlast is shown in Figure 6.5.
6.6 Deprecated BLAST parsers
Older versions of Biopython had parsers for BLAST output in plain text or HTML format. Over the years, we discovered that it is very hard to maintain these parsers in working order. Basically, any small change to the BLAST output in newly released BLAST versions tends to cause the plain text and HTML parsers to break. We therefore recommend parsing BLAST output in XML format, as described in section 6.4.
The HTML parser in Bio.Blast.NCBIWWW has been officially deprecated and will issue warnings if you try and use it. We plan to remove this completely in a few releases time.
Our plain text BLAST parser works a bit better, but use it at your own risk. It may or may not work, depending on which BLAST versions or programs you’re using.
6.6.1 Parsing plain-text BLAST output
The plain text BLAST parser is located in Bio.Blast.NCBIStandalone.
As with the XML parser, we need to have a handle object that we can pass to the parser. The handle must implement the readline() method and do this properly. The common ways to get such a handle are to either use the provided blastall or blastpgp functions to run the local blast, or to run a local blast via the command line, and then do something like the following:
>>> result_handle = open(”my_file_of_blast_output.txt”)
Well, now that we’ve got a handle (which we’ll call result_handle), we are ready to parse it. This can be done with the following code:
>>> from Bio.Blast import NCBIStandalone
>>> blast_parser = NCBIStandalone.BlastParser()
>>> blast_record = blast_parser.parse(result_handle)
This will parse the BLAST report into a Blast Record class (either a Blast or a PSIBlast record, depending on what you are parsing) so that you can extract the information from it. In our case, let’s just use print out a quick summary of all of the alignments greater than some threshold value.
>>> E_VALUE_THRESH = 0.04
>>> for alignment in blast_record.alignments:
… for hsp in alignment.hsps:
… if hsp.expect >> from Bio.Blast import NCBIStandalone
>>> blast_parser = NCBIStandalone.BlastParser()
Then we will assume we have a handle to a bunch of blast records, which we’ll call result_handle. Getting a handle is described in full detail above in the blast parsing sections.
Now that we’ve got a parser and a handle, we are ready to set up the iterator with the following command:
>>> blast_iterator = NCBIStandalone.Iterator(result_handle, blast_parser)
The second option, the parser, is optional. If we don’t supply a parser, then the iterator will just return the raw BLAST reports one at a time.
Now that we’ve got an iterator, we start retrieving blast records (generated by our parser) using next():
>>> blast_record = blast_iterator.next()
Each call to next will return a new record that we can deal with. Now we can iterate through this records and generate our old favorite, a nice little blast report:
>>> for blast_record in blast_iterator :
… E_VALUE_THRESH = 0.04
… for alignment in blast_record.alignments:
… for hsp in alignment.hsps:
… if hsp.expect 75:
… dots = ‘…’
… else:
… dots = ”
… print hsp.query[0:75] + dots
… print hsp.match[0:75] + dots
… print hsp.sbjct[0:75] + dots
The iterator allows you to deal with huge blast records without any memory problems, since things are read in one at a time. I have parsed tremendously huge files without any problems using this.
6.6.3 Finding a bad record somewhere in a huge file
One really ugly problem that happens to me is that I’ll be parsing a huge blast file for a while, and the parser will bomb out with a ValueError. This is a serious problem, since you can’t tell if the ValueError is due to a parser problem, or a problem with the BLAST. To make it even worse, you have no idea where the parse failed, so you can’t just ignore the error, since this could be ignoring an important data point.
We used to have to make a little script to get around this problem, but the Bio.Blast module now includes a BlastErrorParser which really helps make this easier. The BlastErrorParser works very similar to the regular BlastParser, but it adds an extra layer of work by catching ValueErrors that are generated by the parser, and attempting to diagnose the errors.
Let’s take a look at using this parser – first we define the file we are going to parse and the file to write the problem reports to:
>>> import os
>>> blast_file = os.path.join(os.getcwd(), “blast_out”, “big_blast.out”)
>>> error_file = os.path.join(os.getcwd(), “blast_out”, “big_blast.problems”)
Now we want to get a BlastErrorParser:
>>> from Bio.Blast import NCBIStandalone
>>> error_handle = open(error_file, “w”)
>>> blast_error_parser = NCBIStandalone.BlastErrorParser(error_handle)
Notice that the parser take an optional argument of a handle. If a handle is passed, then the parser will write any blast records which generate a ValueError to this handle. Otherwise, these records will not be recorded.
Now we can use the BlastErrorParser just like a regular blast parser. Specifically, we might want to make an iterator that goes through our blast records one at a time and parses them with the error parser:
>>> result_handle = open(blast_file)
>>> iterator = NCBIStandalone.Iterator(result_handle, blast_error_parser)
We can read these records one a time, but now we can catch and deal with errors that are due to problems with Blast (and not with the parser itself):
>>> try:
… next_record = iterator.next()
… except NCBIStandalone.LowQualityBlastError, info:
… print “LowQualityBlastError detected in id %s” % info[1]
The .next() method is normally called indirectly via a for-loop. Right now the BlastErrorParser can generate the following errors:
* ValueError – This is the same error generated by the regular BlastParser, and is due to the parser not being able to parse a specific file. This is normally either due to a bug in the parser, or some kind of discrepancy between the version of BLAST you are using and the versions the parser is able to handle.
* LowQualityBlastError – When BLASTing a sequence that is of really bad quality (for example, a short sequence that is basically a stretch of one nucleotide), it seems that Blast ends up masking out the entire sequence and ending up with nothing to parse. In this case it will produce a truncated report that causes the parser to generate a ValueError. LowQualityBlastError is reported in these cases. This error returns an info item with the following information:
o item[0] – The error message
o item[1] – The id of the input record that caused the error. This is really useful if you want to record all of the records that are causing problems.
As mentioned, with each error generated, the BlastErrorParser will write the offending record to the specified error_handle. You can then go ahead and look and these and deal with them as you see fit. Either you will be able to debug the parser with a single blast report, or will find out problems in your blast runs. Either way, it will definitely be a useful experience!
Hopefully the BlastErrorParser will make it much easier to debug and deal with large Blast files.
6.7 Dealing with PSI-BLAST
You can run the standalone verion of PSI-BLAST (the command line tool blastpgp) using the blastpgp function in the Bio.Blast.NCBIStandalone module. At the time of writing, the NCBI do not appear to support tools running a PSI-BLAST search via the internet.
Note that the Bio.Blast.NCBIXML parser can read the XML output from current versions of PSI-BLAST, but information like which sequences in each iteration is new or reused isn’t present in the XML file. If you care about this information you may have more joy with the plain text output and the PSIBlastParser in Bio.Blast.NCBIStandalone.
6.8 Dealing with RPS-BLAST
You can run the standalone verion of RPS-BLAST (the command line tool rpsblast) using the rpsblast function in the Bio.Blast.NCBIStandalone module. At the time of writing, the NCBI do not appear to support tools running an RPS-BLAST search via the internet.
You can use the Bio.Blast.NCBIXML parser to read the XML output from current versions of RPS-BLAST.
python blast programmer:
from Bio.Blast import NCBIWWW
from Bio import SeqIO
record = SeqIO.read(open("protein.txt"), format="fasta")
result_handle = NCBIWWW.qblast("blastp", "refseq_protein", record.seq, format_type='Text')
blast_results = result_handle.read()
save_file = open("protein1ok.text", "w")
save_file.write(blast_results)
save_file.close()
blastn:
from Bio.Blast import NCBIWWW
from Bio import SeqIO
record = SeqIO.read(open("cdna.txt"), format="fasta")
result_handle = NCBIWWW.qblast("blastn", "nr", record.seq)
blast_results = result_handle.read()
save_file = open("protein1.xml", "w")
save_file.write(blast_results)
save_file.close()
rails 里面设置中文响应
直接这样:
不work:
def searchone
@headers["Content-Type"] = "text/html; charset=gb2312"
@response.headers["Content-Type"] = "text/html; charset=gb2312"
=end
