最近和几个朋友一起做用户态协议栈开源项目 NtyTcp ,纯业余爱好,个人情怀。刚刚开始做有好多的Bug,故搭建了一个Bugzilla,用来上传Bug的。

有几个开发朋友想在 bug.ntytcp.com提交bug,不能注册,因为不能发邮件。至于为什么不能发送邮件?因为阿里云把25端口封了,使用smtp不能发送。

使用465端口发送,发现发不出来,又找不到原因。硬着头皮比Bugzilla的源码看了一下。可恨的是自己并没有写过perl代码。

于是用了两天时间连学带看就把bugzilla的源码看了一遍。然后把bugzilla邮件发送的部分重写了一下。先把bugzilla邮件发送部分贴出来。

bugzilla/mailer.pm

sub MessageToMTA {
my ($msg, $send_now) = (@_);
my $method = Bugzilla->params->{'mail_delivery_method'};
return if $method eq 'None';if (Bugzilla->params->{'use_mailer_queue'}
&& ! $send_now
&& ! Bugzilla->dbh->bz_in_transaction()
) {
Bugzilla->job_queue->insert('send_mail', { msg => $msg });
return;
}my $dbh = Bugzilla->dbh;my $email = ref($msg) ? $msg : Bugzilla::MIME->new($msg);# If we're called from within a transaction, we don't want to send the
# email immediately, in case the transaction is rolled back. Instead we
# insert it into the mail_staging table, and bz_commit_transaction calls
# send_staged_mail() after the transaction is committed.
if (! $send_now && $dbh->bz_in_transaction()) {
# The e-mail string may contain tainted values.
my $string = $email->as_string;
trick_taint($string);my $sth = $dbh->prepare("INSERT INTO mail_staging (message) VALUES (?)");
$sth->bind_param(1, $string, $dbh->BLOB_TYPE);
$sth->execute;
return;
}my $from = $email->header('From');my $hostname;
my $transport;
if ($method eq "Sendmail") {
if (ON_WINDOWS) {
$transport = Bugzilla::Sender::Transport::Sendmail->new({ sendmail => SENDMAIL_EXE });
}
else {
$transport = Bugzilla::Sender::Transport::Sendmail->new();
}
}
else {
# Sendmail will automatically append our hostname to the From
# address, but other mailers won't.
my $urlbase = Bugzilla->params->{'urlbase'};
$urlbase =~ m|//([^:/]+)[:/]?|;
$hostname = $1 || 'localhost';
$from .= "\@$hostname" if $from !~ /@/;
$email->header_set('From', $from);
# Sendmail adds a Date: header also, but others may not.
if (!defined $email->header('Date')) {
$email->header_set('Date', time2str("%a, %d %b %Y %T %z", time()));
}
}if ($method eq "SMTP") {
my ($host, $port) = split(/:/, Bugzilla->params->{'smtpserver'}, 2);
$transport = Bugzilla->request_cache->{smtp} //=
Email::Sender::Transport::SMTP::Persistent->new({
host  => $host,
defined($port) ? (port => $port) : (),
sasl_username => Bugzilla->params->{'smtp_username'},
sasl_password => Bugzilla->params->{'smtp_password'},
helo => $hostname,
ssl => Bugzilla->params->{'smtp_ssl'},
debug => Bugzilla->params->{'smtp_debug'} });
}Bugzilla::Hook::process('mailer_before_send', { email => $email });return if $email->header('to') eq '';if ($method eq "Test") {
my $filename = bz_locations()->{'datadir'} . '/mailer.testfile';
open TESTFILE, '>>', $filename;
# From - <date> is required to be a valid mbox file.
print TESTFILE "\n\nFrom - " . $email->header('Date') . "\n" . $email->as_string;
close TESTFILE;
}
else {
# This is useful for Sendmail, so we put it out here.
local $ENV{PATH} = SENDMAIL_PATH;
eval { sendmail($email, { transport => $transport }) };
if ($@) {
ThrowCodeError('mail_send_error', { msg => $@->message, mail => $email });
}
}
}

使用的sendmail($email, {transport=> $transport}), 发送。由于系统的sendmail没有配置好,发送不出来。

自己写了一版单独用perl发送邮件的。

#!/usr/bin/perluse Net::SMTP::SSL;
use MIME::Base64;
use MIME::Lite;my $msg = MIME::Lite->new(
From=>'from@host.com',
To=>'to@host.com',
Subject=>'First Email',
Data=>'nihao',
Type=>'text/html'
);$account="from@host.com";
$password="your password";
$smtp = Net::SMTP::SSL->new(
Host => 'smtp.host.com',
Port => 465,
Timeout => 120,
Debug=>1
); # connect to an SMTP server
die "Couldn't open connection: $!" if (!defined $smtp );
#$smtp->auth($account,$password);$smtp->datasend("AUTH LOGIN\r\n");
$smtp->datasend(encode_base64('from@host.com')); # username
$smtp->datasend(encode_base64('your password')); # password$smtp->mail('from@host.com');
$smtp->to('to@host.com');$smtp->data();$smtp->datasend($msg->as_string());$smtp->datasend("Blah\r\n\r\n");$smtp->dataend();

相信从代码风格来看,就是第一次写perl   。^_^  。 ^_^

这版是可以发送邮件的。

但是跟bugzilla的mailer.pm 发送差别很大。没办法整合。

于是又换了一种写法。

#!/usr/bin/perluse strict;
use warnings;use Email::Sender::Simple qw(sendmail);
use Email::Sender::Transport::SMTP ();
use Email::Simple ();
use Email::Simple::Creator ();
use Email::Sender::Transport::SMTP::TLS;
use Email::Sender::Transport::SMTP::Persistent;
use Email::Sender::Transport::SMTPS;
use Net::SMTP::SSL;
use MIME::Base64;my $smtpserver   = 'smtp.host.com';
my $smtpport     = 465;
my $smtpuser     = 'from@from.com';
my $smtppassword = 'your password';
my $smtpto       = 'to@host.com';
my $hostname     = 'localhost.localdomain';my $transport = Email::Sender::Transport::SMTP::Persistent->new({host  => $smtpserver,defined($smtpport) ? (port => $smtpport) : (),sasl_username => $smtpuser,sasl_password => $smtpuser,helo => $hostname,ssl => 1,debug => 1 });my $email = Email::Simple->create(header => [To      => $smtpto,From    => $smtpuser,Subject => 'Hi!',],body => "This is my message\n",
);#try {
#eval {sendmail($email, { transport => $transport }) };
#}catch {
#die "Error sending email: $_";
my $smtp = Net::SMTP::SSL->new(Host  => $smtpserver,Port => $smtpport,Timeout => 120,Debug => 1);die "Couldn't open connection: $!" if (!defined $smtp );#$smtp->auth(Bugzilla->params->{'smtp_username'}, Bugzilla->params->{'smtp_password'});$smtp->datasend("AUTH LOGIN\n");$smtp->datasend(encode_base64($smtpuser));$smtp->datasend(encode_base64($smtppassword));$smtp->mail($smtpuser);$smtp->to($smtpto);$smtp->data();$smtp->datasend($email->as_string());$smtp->datasend("\r\n\r\n");$smtp->dataend();$smtp->quit();

这个代码的风格就像那么回事了,就写过perl代码的人了 。^_^。^_^

将mailer.pm 的代码整合。

sub MessageToMTA {my ($msg, $send_now) = (@_);my $method = Bugzilla->params->{'mail_delivery_method'};return if $method eq 'None';if (Bugzilla->params->{'use_mailer_queue'}&& ! $send_now&& ! Bugzilla->dbh->bz_in_transaction()) {Bugzilla->job_queue->insert('send_mail', { msg => $msg });return;}my $dbh = Bugzilla->dbh;my $email = ref($msg) ? $msg : Bugzilla::MIME->new($msg);# If we're called from within a transaction, we don't want to send the# email immediately, in case the transaction is rolled back. Instead we# insert it into the mail_staging table, and bz_commit_transaction calls# send_staged_mail() after the transaction is committed.if (! $send_now && $dbh->bz_in_transaction()) {# The e-mail string may contain tainted values.my $string = $email->as_string;trick_taint($string);my $sth = $dbh->prepare("INSERT INTO mail_staging (message) VALUES (?)");$sth->bind_param(1, $string, $dbh->BLOB_TYPE);$sth->execute;return;}my $from = $email->header('From');my $hostname;my $transport;if ($method eq "Sendmail") {if (ON_WINDOWS) {$transport = Bugzilla::Sender::Transport::Sendmail->new({ sendmail => SENDMAIL_EXE });}else {$transport = Bugzilla::Sender::Transport::Sendmail->new();}}else {# Sendmail will automatically append our hostname to the From# address, but other mailers won't.my $urlbase = Bugzilla->params->{'urlbase'};$urlbase =~ m|//([^:/]+)[:/]?|;$hostname = $1 || 'localhost';$from .= "\@$hostname" if $from !~ /@/;$email->header_set('From', $from);# Sendmail adds a Date: header also, but others may not.if (!defined $email->header('Date')) {$email->header_set('Date', time2str("%a, %d %b %Y %T %z", time()));}}my ($host, $port) = split(/:/, Bugzilla->params->{'smtpserver'}, 2);if ($method eq "SMTP") {
#        my ($host, $port) = split(/:/, Bugzilla->params->{'smtpserver'}, 2);$transport = Bugzilla->request_cache->{smtp} //=Email::Sender::Transport::SMTP::Persistent->new({host  => $host,defined($port) ? (port => $port) : (),sasl_username => Bugzilla->params->{'smtp_username'},sasl_password => Bugzilla->params->{'smtp_password'},helo => $hostname,ssl => Bugzilla->params->{'smtp_ssl'},debug => Bugzilla->params->{'smtp_debug'} });}Bugzilla::Hook::process('mailer_before_send', { email => $email });return if $email->header('to') eq '';if ($method eq "Test") {my $filename = bz_locations()->{'datadir'} . '/mailer.testfile';open TESTFILE, '>>', $filename;# From - <date> is required to be a valid mbox file.print TESTFILE "\n\nFrom - " . $email->header('Date') . "\n" . $email->as_string;close TESTFILE;}else {# This is useful for Sendmail, so we put it out here.
#        local $ENV{PATH} = SENDMAIL_PATH;
#        eval { sendmail($email, { transport => $transport }) };
#        if ($@) {
#            ThrowCodeError('mail_send_error', { msg => $@->message, mail => $email });
#        }my $smtp = Net::SMTP::SSL->new(Host  => $host,Port => $port,Timeout => 120,Debug => 1);die "Couldn't open connection: $!" if (!defined $smtp );#$smtp->auth(Bugzilla->params->{'smtp_username'}, Bugzilla->params->{'smtp_password'});$smtp->datasend("AUTH LOGIN\n");$smtp->datasend(encode_base64(Bugzilla->params->{'smtp_username'}));$smtp->datasend(encode_base64(Bugzilla->params->{'smtp_password'}));$smtp->mail(Bugzilla->params->{'smtp_username'});$smtp->to($email->header('to'));$smtp->data();$smtp->datasend($email->as_string());$smtp->datasend("\r\n\r\n");$smtp->dataend();$smtp->quit();}
}

主要是将邮件发送方式修改了。

        local $ENV{PATH} = SENDMAIL_PATH;eval { sendmail($email, { transport => $transport }) };if ($@) {ThrowCodeError('mail_send_error', { msg => $@->message, mail => $email });}

换成了

        my $smtp = Net::SMTP::SSL->new(Host  => $host,Port => $port,Timeout => 120,Debug => 1);die "Couldn't open connection: $!" if (!defined $smtp );#$smtp->auth(Bugzilla->params->{'smtp_username'}, Bugzilla->params->{'smtp_password'});$smtp->datasend("AUTH LOGIN\n");$smtp->datasend(encode_base64(Bugzilla->params->{'smtp_username'}));$smtp->datasend(encode_base64(Bugzilla->params->{'smtp_password'}));$smtp->mail(Bugzilla->params->{'smtp_username'});$smtp->to($email->header('to'));$smtp->data();$smtp->datasend($email->as_string());$smtp->datasend("\r\n\r\n");$smtp->dataend();$smtp->quit();

bugzilla的代码还是写的很人性化的,没有写过perl代码的,一看都能知道个大概。向Bugzilla的作者致敬。

至于邮件发送的流程,大家可以参照rfc822,不要随便相信网上的代码。

转载于:https://blog.51cto.com/wangbojing/2103314

使用Bugzilla,你肯定会遇到的坑。相关推荐

  1. 怎么用爬虫筛选简历_Python爬虫面试简历

    分享之前的爬虫简历,仅供参考,因为技术有限,简历技能点逼格不是很高,但提到的很多爬虫常用技术,都已经写入简历,靠这份简历之前找工作时候2天预约了8家面试,面的第二天,在第4家公司通过拿到offer,后 ...

  2. 【杂谈】您想要的docker环境来了!

    深度学习环境配置一直是大家学习AI的拦路虎,不管你是久经沙场的大佬,还是初出茅庐的小伙,相信你肯定被linux系统环境坑过.快到周末了,咱们就不聊高深莫测的算法了,今天咱们就聊下神器docker的环境 ...

  3. 影视或游戏:中国视效人才的「进与退」

    在<三声>近一年对影视动画从业者的采访中,一个关键问题被不约而同地多次提及:人才的稀缺与流失. 仍未找到长线营收路径的影视动画行业向工业化转型的同时,一场全方位的质量升级竞赛.头部项目比拼 ...

  4. 细说ASP.NET Core与OWIN的关系

    前言 最近这段时间除了工作,所有的时间都是在移植我以前实现的一个Owin框架,相当移植到到Core的话肯定会有很多坑,这个大家都懂,以后几篇文章可能会围绕这个说下,暂时就叫<Dotnet Cor ...

  5. 最近无埋点技术很是流行,抽空研究了下诸葛IO,talkingData以及百分点这些业内知名公司的无埋点SDK,抽取其中重要的信息供大家参考:

    1.首先什么是无埋点呢,其实所谓无埋点就是开发者无需再对追踪点进行埋码,而是脱离代码,只需面对应用界面圈圈点点即可追加随时生效的事件数据点. 无埋点的好处 其实无埋点并不是完全不用写代码,而是尽可能的 ...

  6. 自学前端的误区和痛点解决办法

    网上有很多自学的方案路线,还有一些知道: 但是我感觉他们很多人都是没有真实学习过的,很多人说的那些路线,真的是扯淡: 肯定不是自己通过自学后的感悟,他们所谓的路线可能是结合培训班大纲和知乎的一些答案组 ...

  7. 九度OJ1486 /POJ 1029/2012北京大学研究生复试上机

    wa到死!wa到死!这是一个看着简单,坑及其多的题! 坑一:POJ上是单组输入,九度上是多组输入,妈蛋要是研究生复试遇到这种大坑肯定死掉啊!而且对于codeforces比较习惯的 同学肯定会觉得巨坑无 ...

  8. cesium three性能比较_硬金和千足金都是黄金,哪个比较好?为什么80%人都说硬金不好?...

    黄金是非常稳定的贵金属,自古到今,黄金都是富贵的象征,黄金也是非常稀有.珍贵的金属之一.由于原本黄金首饰是富贵人才干佩戴的首饰,现在生活水平提高了,很多人都购买得起黄金首饰.就在前几年,珠宝市场出现一 ...

  9. 机器学习笔记 增强学习与马尔科夫模型(1)

    本文根据博客以及课堂老师讲授内容整理而来. 吐槽: 继上周介绍了Minimax和Expectimax后,外教这周又给我们介绍了马尔科夫模型,上周兴高采烈的感觉对Optimal Policy有点理解了但 ...

  10. python风格logo_感觉logo不给力? Python十分钟制作属于你自己的个性logo

    欢迎大家订阅公众号:Python从程序猿到程序员 词云的使用相信大家已经不陌生了,使用很简单,直接调用wordcloud包就可以了.它的主要功能是根据文本词汇和词汇频率生成图片,从中可以直观的看出各个 ...

最新文章

  1. 程序员头发失踪之谜 | 每日趣闻
  2. 巴塞尔新资本协议_《巴塞尔公约》修订!进口再生颗粒或对中国产生巨大冲击...
  3. mysql+影响的行数+获取_我们如何获得受MySQL查询影响的总行数?
  4. 亚伦•斯沃茨:提升时间的品质
  5. openshift_OpenShift上具有NetBeans的Java EE
  6. oracle 10g r2 for solaris x86,Oracle10g for Solaris9(x86)安装指南
  7. 信息学奥赛一本通(1176:谁考了第k名)——qsort 函数
  8. @程序员,夏天来了,你该送心仪女生这个啦
  9. ext2文件系统学习(一)
  10. 个人用户可以向运营商申请短信接口吗?
  11. 设计模式:(工厂模式)
  12. 单节2A锂电池充电芯片方案,PD和QC快充充电器5-12V输入
  13. 高质量的博客评论外链有用么?
  14. 深度精简版xp 安装并使用iis【转】
  15. ftp登录成功,无法取得列表
  16. scalac: Token not found: /Users/shengquan.nian/Library/Caches/JetBrains/IntelliJIdea2021.1/compile-s
  17. pycharm使用了ctrl+鼠标回到原来的地方方法
  18. unity-SpriteAtlas图集
  19. ubuntu桌面特效
  20. 从中序与后序遍历构造二叉树

热门文章

  1. 西安工业大学计算机考研分数线,西安工业大学研究生录取分数线
  2. 陕西省计算机分数线,2019陕西省各大学录取分数线最新汇总
  3. 911 S5代理设置
  4. 设计和实现一款轻量级的爬虫框架
  5. 恩智浦智能车主控板分享
  6. html中div背景颜色渐变(透明 对角 附赠颜色查询对照表)
  7. html背景图片大小嵌套,div嵌套div 背景图片 不显示的问题
  8. Flink_网站独立访客数(UV)(Redis+布隆过滤器)
  9. python pillow库画图_Pillow画图
  10. picgo图片上传踩坑