perl script sendMail



我需要写一个perl脚本发送电子邮件。脚本应该读取包含电子邮件地址作为其第一个参数的.txt文档(可以有多个地址,并且它们都用";"分隔)和作为电子邮件正文的.html文档作为其第二个参数。

#!/usr/bin/perl -w
use Net::SMTP::SSL;
sub send_mail {
    my $to = $ARGV[0];
    open(MYFILE, $to) || die("Could not open file!");
    @recepients=<MYFILE>;
    close(MYFILE);
    my $body = $ARGV[1];
    open (TXTFILE, $body);
    @lines = <TXTFILE>;
    close(TXTFILE);
    $body = join("",@lines);
    my $from = 'theAddress@gmail.com';
    my $password = 'thePassword';
    my $smtp;
    if (not $smtp = Net::SMTP::SSL->new('smtp.gmail.com',
                            Port => 465,
                            Debug => 1)) {
        die "Could not connect to servern";
    }
    $smtp->auth($from, $password) || die "Authentication failed!n";
    $smtp->mail($from . "n");
    my @recepients = split(/;/, $to);
    foreach my $recp (@recepients) {
        $smtp->to($recp . "n");
    }
    $smtp->data();
    $smtp->datasend("From: " . $from . "n");
    $smtp->datasend("To: " . $to . "n");
    $smtp->datasend("Subject: " . $subject . "n");
    $smtp->datasend("n");
    $smtp->datasend($body . "n");
    $smtp->dataend();
    $smtp->quit;
}
&send_mail()

所以我试着解决一些问题,但是我有一个问题,从。txt和。html文档中提取信息。因此,错误应该在分割收件人的某个地方。

您的脚本中有几个问题。我建议您使用Perl::Critic,因为它可以分析您的代码,并且通常会给出有用的提示。

以下作品:

#!/usr/bin/env perl

始终使用strictwarnings

use strict;
use warnings;
use Net::SMTP::SSL;

English将给出错误消息的文本表示

use English qw(-no_match_vars);

Carp从调用者的角度发出警告和错误

use Carp;
our $VERSION = '1.0.0';
sub send_mail {
    my ( $to, $body ) = @_;

最好也将文件句柄作为变量

    my $to_handle;
    my $text_handle;

总是声明变量

    my @recipients;
    my @lines;

总是检查系统调用(open, close,…)的返回值

    # print the error message in case of errors
    open $to_handle, '<', $to
      or croak "Error opening $to: $OS_ERROR";
    @recipients = <$to_handle>;
    close $to_handle
      or croak "Error closing $to: $OS_ERROR";
    open $text_handle, '<', $body
      or croak "Error opening $body: $OS_ERROR";
    @lines = <$text_handle>;
    close $text_handle
      or croak "Error closing $body: $OS_ERROR";
    $body = join '', @lines;
    my $from     = '.....@gmail.com';

我会避免在脚本源

中放置密码
    my $password = '*****';
    my $smtp;

不要在die/warn/…因为它将删除发生错误的行号

    $smtp = Net::SMTP::SSL->new(
        'smtp.gmail.com',
        Port  => 465,
        Debug => 1
    ) or croak 'Could not connect to server';
    $smtp->auth( $from, $password )
      or croak 'Authentication failed!';
    $smtp->mail( $from . "n" );
    # removed trailing n
    chomp $recipients[0];

;分隔列表位于第一行(数组的第一个元素):您必须拆分第一行。

    foreach my $recp ( split /;/mxs, $recipients[0] ) {
        $smtp->to( $recp . "n" );
    }
    $smtp->data();
    $smtp->datasend( "From: $fromn" );
    $smtp->datasend( "To: $ton" );

$subject没有定义,您可以通过strictwarnings来检测它

    $smtp->datasend("Subject: Testn");
    $smtp->datasend("n");
    $smtp->datasend("$bodyn" );
    $smtp->dataend();
    $smtp->quit;

如果没有指定return, perl将使用最后一次求值的结果作为结果,因此以return结束子例程是一个很好的做法。

    return;
}

计算主体中的ARGV。如果您将处理分散在一个或几个子例程中,您将失去清晰度

if ( !$ARGV[0] || !$ARGV[1] ) {
    print STDERR "usage: send to contentn";
    exit 1;
}

缺少一个分号。你不需要使用&调用子程序

send_mail($ARGV[0], $ARGV1);

1;

最新更新