Gossamer Forum
Home : General : Perl Programming :

Sending file by email blues :(

(Page 1 of 2)
> >
Quote Reply
Sending file by email blues :(
Please can someone tell me why this won't work! I thought at first it must be the location to sendmail, but that didnt work (tried all three different locations possibilities). I then added an error sub to see if the email actually was being sent, but that didn't return anything, so now I am officially stumped! Any ideas you guys? I have never learned how to program the encode stuff, so all of this is new to me Frown

Well, here is the code;

Code:
#!/usr/bin/perl

### User variables - you may change things in this section as indicated ###

# Change this to the correct path to Sendmail for your system #
$mailprog="/usr/lib/sendmail";

# Change this to the LITERAL PATH to the files you wish to mail. Do not forget the ending / #
$filelocation="/home/wwwtempl/public_html/templates/purchase/download/";

# Change this to the email address you want mails to be sent FROM and leave \ behind the @ sign#
$adminmail="webmaster\@wwwtemplates.com";

# Change this to the name you want mails to be sent FROM #
$adminname="Webmaster";

# Change this to reflect the subject line you require for your mails #
$subjectline="Your Template from WWWTemplates.com";

# Change this to show the message you want to include (i.e. the body of the email). #
# A new line is entered by using \n e.g. Hi there\n\nThank-you for your interest in blah blah #
# Note that "Dear Name\n\n" has been inserted for you automatically, Name being the name submitted #

# Change this to the URL of the screen you want to display after the user has submitted the form #
#(i.e. a confirmation screen)#
$returnscreen="http://wwwtemplates.com/templates/purchase/safe/confirmed.cgi?do=sent";

# DO NOT alter anything from here on #

read (STDIN,$temp,$ENV{'CONTENT_LENGTH'});
@pairs=split(/&/,$temp);
foreach $item(@pairs)
{
($key,$content)=split (/=/,$item);
$content=~tr /+/ /;
$content=~s /%(..)/pack("c",hex($1))/ge;
$fields{$key}=$content;
}

require ("mimetypes.pl");

&sendproduct;

$message = qw~First of all, let me congratulate you on your purchase from our quality selection of templates. We hope you enjoy using your purchase, and it saves you a lot of money from time you would have otherwise spent trying to do something like this! Please find attached a copy of the template you just purchased. ~;

sub sendproduct
{

$file=$filelocation.$fields{'attachment'};
($ext) = $file =~ m,\.([^\.]*)$,;
$ext =~ tr,a-z,A-Z,;
$fext=&mimetype($ext);


my @boundaryv = (0..9, 'A'..'F');
srand(time ^ $$);
for (my $i = 0; $i++ < 24;)
{
$boundary .= $boundaryv[rand(@boundaryv)];
}

open MAIL, "| $mailprog -t" || die &error('$!');
print MAIL "To: $fields{'email'}\n";
print MAIL "From: $adminmail\n";
print MAIL "MIME-Version: 1.0\n";
print MAIL "Subject: $subjectline\n";
print MAIL "Content-Type: multipart/mixed; boundary=\"------------$boundary\"\n";
print MAIL "\n";
print MAIL "This is a multi-part message in MIME format.\n";
print MAIL "--------------$boundary\n";
print MAIL "Content-Type: text/plain; charset=us-ascii\n";
print MAIL "Content-Transfer-Encoding: 7bit\n\n";
print MAIL "$message";
print MAIL "\n";
print MAIL "--------------$boundary\n";
print MAIL "Content-Type: $fext; name=\"$fields{'attachment'}\"\n";
print MAIL "Content-Transfer-Encoding: base64\n";
print MAIL "Content-Disposition: inline; filename=\"$fields{'attachment'}\"\n\n";

my $buf;
$/=0;
open INPUT, "$file";
binmode INPUT if ($^O eq 'NT' or $^O eq 'MSWin32');
while(read(INPUT, $buf, 60*57))
{
print MAIL &encode_base64($buf);
}
close INPUT;

print MAIL "\n--------------$boundary--\n";
print MAIL "\n";
close MAIL;
print "Location: $returnscreen\n\n";
exit();
}


sub encode_base64 #($)
{
my ($res, $eol, $padding) = ("", "\n", undef);

while (($_[0] =~ /(.{1,45})/gs))
{
$res .= substr(pack('u', $1), 1);
chop $res;
}

$res =~ tr#` -_#AA-Za-z0-9+/#; # ` help emacs
$padding = (3 - length($_[0]) % 3) % 3; # fix padding at the end

$res =~ s#.{$padding}$#'=' x $padding#e if $padding; # pad eoedv data with ='s
$res =~ s#(.{1,76})#$1$eol#g if (length $eol); # lines of at least 76 characters

return $res;
}

sub error
{

$error = shift;

print "Content-type: text/html \n\n";
print "$error";

}
Thanks to anyone that can help!

Andy

webmaster@ace-installer.com
http://www.ace-installer.com
Quote Reply
Re: Sending file by email blues :( In reply to
Im not surprised it doesn't report anything Wink

&error('$!');

Spot the error?

That encode_base64 sub it yucky too....you should use

use MIME::Base64 qw(encode_base64);

Hmmm also no exit in the error sub

I already posted code in this very forum on how to send a file by email.

Mods:http://wiredon.net/gt/download.shtml
Installations:http://wiredon.net/gt/
Quote Reply
Re: Sending file by email blues :( In reply to
Yeah, I wasn't too keen on the code myself either! Just I don't have time to learn how to do this stuff on my own! Frown

I'll keep trying, and thanks for your help Smile

Andy

webmaster@ace-installer.com
http://www.ace-installer.com
Quote Reply
Re: Sending file by email blues :( In reply to
So why isn't it working?

What happens?

Mods:http://wiredon.net/gt/download.shtml
Installations:http://wiredon.net/gt/
Quote Reply
Re: Sending file by email blues :( In reply to
http://www.gossamer-threads.com/...ew=&sb=&vc=1

Mods:http://wiredon.net/gt/download.shtml
Installations:http://wiredon.net/gt/
Quote Reply
Re: Sending file by email blues :( In reply to
I've changed the line where it accesses sendmail to;

open (MAIL, "| $mailprog -t") || die &error("$!");

This now works when sending to HotMail accounts, but for some reason won't send if I try to send emails to my POP 3 accounts Frown

Oh, and thanks for the link Smile I'll have a look at it later.

Andy

webmaster@ace-installer.com
http://www.ace-installer.com
Quote Reply
Re: Sending file by email blues :( In reply to
Hi,

You do realize that if I pass in:

email=alex@gossamer-threads.com
attachment=/etc/passwd

I can have it send me an email with your password file attached? Also, because file is not checked, I can also run commands on your server quite easily.

Need to always check form input. =)

Cheers,

Alex

--
Gossamer Threads Inc.
Quote Reply
Re: Sending file by email blues :( In reply to
Mmm, thanks for that Alex! I'll remembr that in the future! Wink I think the email thing is something to do with the copy of Sendmail on my hosts server. Would that sound right, as it only seems to send to certain email addresses???

Thanks

Andy

webmaster@ace-installer.com
http://www.ace-installer.com
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
i'm sure you have this working now! i'm able to send attachments and they work fine on my email program. however, the attachments arrive inline and garbled on phones. if yours is working, could you please post the code? thanks!
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

I actually do mine different in my own code. This sends out a 2 part message (plain text and HTML). Its important these days to send out both plain and HTML versions, as it will help you with spam filters.

Code:
sub do_emailing_new {
# Plugins::Emails::do_emailing_new("foo_bar_template","Some subject",$opts)

use MIME::Lite;
use MIME::Base64;
use Encode;
use Links::SiteHTML;

my ($template,$subject,$opts) = @_;

my $to = $opts->{to};

my $from = $opts->{from} || '"Andy" <andy@mysite.com>';

my $html = Links::SiteHTML::display($template, { %$opts } );
my $text = Links::SiteHTML::display("${template}_txt", { %$opts }, { compress => 0 } );

$html = decode( 'utf-8', $html );
$text = decode( 'utf-8', $text );

# print "FOO: $html \n";

use Email::MIME;
use Email::Address::XS;
use Email::Sender::Simple qw(sendmail);
use IO::All;

# multipart message
my @parts = (
Email::MIME->create(
body_str => $text,
attributes => {
encoding => 'quoted-printable',
content_type => "text/plain",
disposition => "inline",
charset => "UTF-8",
}
),
Email::MIME->create(
body_str => $html,
attributes => {
encoding => 'quoted-printable',
charset => "UTF-8",
content_type => "text/html",
disposition => "inline",
}
)
);

if ($opts->{attach_file}) {

my $filename = (reverse split /\//, $opts->{attach_file})[0];

push @parts, Email::MIME->create(
attributes => {
filename => $filename,
content_type => "application/pdf",
encoding => "base64",
name => $filename,
},
body => io( $opts->{attach_file} )->binary->all,
)
}


my $email = Email::MIME->create(
header_str => [
From => $from,
To => [ $to ],
Subject => $subject,
],
parts => \@parts,
attributes => {
encoding => 'base64',
charset => "UTF-8",
content_type => "multipart/alternative",
disposition => "inline",
}
);

#print $email->as_string. "\n\n";

my $bcc = '';
my $bcc = 'andy@ultranerds.co.uk';
if ($bcc) {
sendmail($email,{ to => [$to, $bcc] });
} else {
sendmail($email->as_string);
}

}

Basically you create 2 templates - template_name.html and template_name_txt.html

Call with:

Code:
Plugins::Emails::do_emailing_new("foo_bar_template","Some subject",$opts)
;

$opts contains the following variables:

Code:
from
to (email)

From memory, both of those can be in the format is:

Code:
Some persons name <andy.newby@gmail.com>

I'm sure you can figure out the rest :)

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
you give me too much credit! first, i don't understand templates at all. also, i am able to send attachments fine. the problem only occurs when the recipient opens the mail on iphone or android. instead of showing link to the attachment, the pdf (or whatever) appears as garbled text in the body of the message. i think i'm just doing one little thing wrong, but i've struggled with this off and on (when i have time) for months. after the print MAIL statements for the text part of the message, i have the following:
Code:
### 02/03/2020
print MAIL "\n";
print MAIL "--------------$boundary\n";
print MAIL "Content-Type: pdf; name=\"$attach\"\n";
print MAIL "Content-Transfer-Encoding: base64\n";
print MAIL "Content-Disposition: attachment; filename=\"$attach\"\n\n";
####
$newfile = substr($attach,rindex($attach,"/"));
$newfile =~ s/\///;
open(FILE, "uuencode $attach $newfile|") or die;
while( <FILE>) { print MAIL; };
close(FILE);
### 02/03/2020
print MAIL "\n--------------$boundary--\n";
print MAIL "\n";
#####
i tried replacing
open(FILE, "uuencode $attach $newfile|") or die;
with
open(FILE, "base64 $attach $newfile|") or die;
but it had no effect at all
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

Sorry, I don't send files like that. You have to be so careful to get all the right headers, it much better to send it using existing modules.

Quote:
also, i am able to send attachments fine. the problem only occurs when the recipient opens the mail on iphone or android. instead of showing link to the attachment, the pdf (or whatever) appears as garbled text in the body of the message.

By definition, that's not fine :) haha. It means you are sending data that the phone isn't expecting. The way you are sending emails is very 1990 - you need to update to a better method if you want your emails to come out properly ;)

With regards to the templates - you don't have to use the template bit. You could just as easily do:

Code:
my $html = qq|My html message - you can use <b>etc</b> in here - NO HEADERS - just the email body!|;
my $text = qq|A text version as well (good for mobiles, or low data devices|;

Then the rest of the code basically stands

Cheers

Andy

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
ok, i'm trying to implement your code but i'm getting internal error. ran perl check and it says it cannot find email::MIME. now what??? Gossamer Threads is my host
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

Email GT, and ask them to make sure you have these modules installed:

Code:
use Email::MIME;
use Email::Address::XS;
use Email::Sender::Simple qw(sendmail);
use IO::All;

Also, the best way to play with it would be to make a simple test.cgi script and get the code working like that first (then once you are happy, you can put the code into your main scripts)

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
finally getting back to this! getting following error:

Can't locate Email/MessageID.pm in @INC

it couldn't find Links::SiteHTML, so i commented that line of your code. help?
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

What is the code you are currently using? You won't have access to Links::SiteHTML - so you just need to tweak the code to pass in the html and plain text versions you want. For example:

Code:
<b>Thanks for signing up</b>

<p> some content </p>

Then a plain text version as well:

Code:
Thanks for signing up

some content

So something like:

Code:
my $html = qq|<b>Thanks for signing up</b>

<p> some content </p>|;
my $text = qq|Thanks for signing up

some content|;

The plain text version has 2 reasons:

1) It helps against spam filters (as most spammers don't go to the effort to do it!)
2) On certain devices, it will show better than an HT:ML version (otherwise they try and convert the HTML version into plain text, but this doesn't always come out well)

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Oh, also it looks like you are missing:

Email::MessageID (this will probably install with one of the below modules, so you may not need to do that step)

Double check you have all the required modules:

Email::MIME
Email::Address::XS
mail::Sender::Simple
IO::All;

Most of them should be standard (or already installed)

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
i have the following:
Code:
use Email::MIME;

use Email::Address::XS;
use Email::MessageID;
use Email::Sender::Simple qw(sendmail);
use IO::All;

i just added MessageID line. now i'm getting internal error in dbman. ran perlcheck in gt panel and have following error:
Can't locate Email/MessageID.pm



i had the following message from GT support:
We have installed Email::MIME which should include the installation of Email::Address::XS.
Also, Email::Sender is installed so please check if Email::Sender::Simple is working for you.
Lastly, IO::All is installed.
now what???
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

Maybe you do also need Email::MessageID in that case (I don't remember installing it on my servers, but maybe I did :))

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
finally it's working!!!!!!!! thank you! question: where you have

content_type => "application/pdf",

do i need to test for the type of file (docx,xlsx, etc) and change that line accordingly?
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Cool :)

Yes, you would want to set the correct MIME type. GT::MIMETypes::guess_type() should be able to do that for you if you have a different filetype each time.

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
now it's working find on phone but not on desktop. Crazy when i view source on desktop i can see all the binary stuff for the file, but there is no attachment. the binary stuff doesn't show inline either. here's the attachment section of my send_email
Code:
if ($attach) {

my $filename = (reverse split /\//, $attach)[0]; # also changed in body => below
my $ext = substr($filename,rindex($filename,"."));
my $content;
if ($ext eq '.pdf') { $content = qq|application/pdf|; }
elsif ($ext eq '.docx') { $content = qq|application/vnd.openxmlformats-officedocument.wordprocessingml.document|; }
elsif ($ext eq '.doc') { $content = qq|application/msword|; }
elsif ($ext eq '.xlsx') { $content = qq|application/vnd.openxmlformats-officedocument.spreadsheetml.sheet|; }
elsif ($ext eq '.xls') { $content = qq|application/vnd.ms-excel|; }
elsif (($ext eq '.htm') || ($ext eq '.html')) { $content = qq|text/html|; }
else { $content = qq|application/octet-stream|; }
push @parts, Email::MIME->create(
attributes => {
filename => $filename,
content_type => $content,
encoding => "base64",
name => $filename,
disposition => "attachment",
},
body => io( $attach )->binary->all,
)
}

i added disposition = attachment above hoping that would help, but no effect. i left disposition inline for other sections. do you see any error???
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

Does $ext contain the dot? i.e is it ".xls" or just "xls" ? Personally I don't do:

Code:
disposition => "attachment",

...and it works fine on desktop and mobiles. Not sure if that makes the difference though. What is the full message contents if you look at:

Code:
print $email->as_string. "\n\n";

This is the full email (headers and all). Save that as a .txt/.eml file and upload (as its easier to read)

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
Quote Reply
Re: [Andy] Sending file by email blues :( In reply to
see file yes ext contains the dot

i should mention that roundcube handles the attachment correctly. thunderbird does not. previously (old code) both recognized attachments.

Last edited by:

delicia: Mar 19, 2020, 5:31 AM
Quote Reply
Re: [delicia] Sending file by email blues :( In reply to
Hi,

Can you do a test one to me on andy.newby@gmail.com so I can take a look?

BTW you didn't press "upload" on the attachment, so there wasn't one :)

Cheers

Andy (mod)
andy@ultranerds.co.uk
Want to give me something back for my help? Please see my Amazon Wish List
GLinks ULTRA Package | GLinks ULTRA Package PRO
Links SQL Plugins | Website Design and SEO | UltraNerds | ULTRAGLobals Plugin | Pre-Made Template Sets | FREE GLinks Plugins!
> >