I’m trying to create a cron job that sends an email with a file attachment once a day.
I’m using a simple PHP script to test this and it works fine when I go to the URL and run it. However, when running it via the cron job, the email is sent but not the file attachment.
Here’s my PHP script
Please note I’ve changed info to protect my client, so I use a real email, not test@example.com
just so you don’t think that’s why it’s not working.
<?php // Recipient $to = 'test@example.com'; // Sender $from = 'noreply@example.com'; $fromName = 'Server'; // Email subject $subject = 'Test Subject'; // Attachment file $file = "../test/file.csv"; // Email body content $htmlContent = ' <h3>Test Email</h3> <p>Please find the attached file.</p> '; // Header for sender info $headers = "From: $fromName"." <".$from.">"; // Boundary $semi_rand = md5(time()); $mime_boundary = "==Multipart_Boundary_x{$semi_rand}x"; // Headers for attachment $headers .= "nMIME-Version: 1.0n" . "Content-Type: multipart/mixed;n" . " boundary="{$mime_boundary}""; // Multipart boundary $message = "--{$mime_boundary}n" . "Content-Type: text/html; charset="UTF-8"n" . "Content-Transfer-Encoding: 7bitnn" . $htmlContent . "nn"; // Preparing attachment if(!empty($file) > 0){ if(is_file($file)){ $message .= "--{$mime_boundary}n"; $fp = @fopen($file,"rb"); $data = @fread($fp,filesize($file)); @fclose($fp); $data = chunk_split(base64_encode($data)); $message .= "Content-Type: application/octet-stream; name="".basename($file).""n" . "Content-Description: ".basename($file)."n" . "Content-Disposition: attachment;n" . " filename="".basename($file).""; size=".filesize($file).";n" . "Content-Transfer-Encoding: base64nn" . $data . "nn"; } } $message .= "--{$mime_boundary}--"; $returnpath = "-f" . $from; // Send email $mail = @mail($to, $subject, $message, $headers, $returnpath); ?>
Thanks in advance.
Advertisement
Answer
It would be useful if you posted your CRON command, but I’m going to guess that it begins with something like :
php path/to/your/script.php
If so I think the problem is with this line:
$file = "../test/file.csv";
The path to the file is relative. Likely CRON isn’t operating from the directory that the script exists in so it’s trying to find the file from a directory above it’s current working directory, where it doesn’t exist.
Option 1: change the path to an absolute.
Option 2: If your PHP script exists in the web directory you could change the CRON command to use WGET instead, eg.
wget -O /dev/null -o /dev/null 'https://example.com/yourScript.php'