Inviare un'email con allegato con PHP

Un'emal di questo tipo presenta delle caratteristiche molto diverse da un'email standard di tipo testuale

Pubblicato da ,
Ultima modifica

In questo articolo vedremo quali sono i passi da seguire per poter inviare un allegato direttamente da una pagina web, usando la funzione mail() di PHP.

La prima cosa da fare è di predisporre di un modulo web particolare <form> che permetta all'utente di cercare tra i file del suo computer, quando l'utente avrà compilato i campi del modulo web e cliccato sul bottone invia allora dobbiamo recuperare questi dati e successivamente creare il messaggio email con allegato.

Esempio: modulo web in cui l'utente inserisce il Nome, Cognome, Email e un allegato:

Codice HTML

 <form enctype="multipart/form-data" action="mailallegato.php" method="post">
<label>Nome: </label>
<input type="text" name="nome" required>
<label>Cognome: </label>
<input type="text" name="cognome" required>
<label>E_mail: </label>
<input type="email" name="email" required>
<label>Allegato: </label>
<input type="file" name="allegato" required>
<input type="submit" value="invia">
</form>

il form per poter inviare un'email con allegato deve avere un attributo enctype uguale a multipart/form-data, questo attributo indica che i dati che verranno inviati non sono soltanto di tipo testuale ma sono anche dati relativi ad un file, l'attributo action è uguale a mailallegato.php che è lo script PHP che riceve i dati dal modulo, il campo input tipo file consente all'utente di cercare all'interno del proprio computer il file da allegare.

Adesso che abbiamo il modulo web, possiamo incominciare a scrivere il file mailallegato.php:

Codice PHP

 <?php 

// mailallegato.php 

$nomefile = $_FILES['allegato']['name'];
$tipofile = $_FILES['allegato']['type'];
$posizionefile = $_FILES['allegato']['tmp_name'];
$nome = $_POST['nome'];
$cname = $_POST['cognome'];
$email= $_POST['email'];

$texfile = fopen($posizionefile,"rb");
$dati_allegato = fread( $texfile , filesize($posizionefile) ) ;
fclose($texfile);

$dati_allegato = chunk_split(base64_encode($dati_allegato));

$numero_casuale = md5(time());
$cod_delimitatore = "--=NextPart_$numero_casuale";

$nomefile, $tipofile e $posizionefile sono rispettivamente il nome del file, il tipo (Content-Type) cioè se è un file .jpg, .txt, .pdf, ect, e la posizione, infatti quando clicchiamo sul pulsante invia del modulo, il file viene caricato in una cartella temporanea sul server e gli viene anche assegnato un nome, abbiamo bisogno di questi valori per poter recuperare i dati dell'allegato, infatti tramite il metodo fread() andiamo a recuperarli, in particolare il metodo fread() viene utilizzato per leggere il contenuto di un file precedentemente aperto mediante la funzione fopen(), richiede due parametri il puntatore del file ($texfile) e la dimensione (in bytes) del file (filesize($posizionefile)), la variabile $dati_allegato viene poi codificata su base64 usando il metodo base64_encode(), e il risultato così codificato viene poi passato al metodo chunk_split() che lo suddivide in righe tutte della stessa lunghezza (76 caratteri valore di default), infine il codice delimitatore $cod_delimitatore generato con i metodi md5() e time() che ci servirà per comporre il messaggio.

Adesso che abbiamo il necessario possiamo iniziare a comporre il messaggio, in particolare il messaggio dovrà essere così composto:

MIME-Version: 1.0
Content-type: multipart/mixed;boundary="$cod_delimitatore"
Tipo di messaggio
This is a multi-part message in MINE format.
--$cod_delimitatore
Content-Type: text/plain;charset="iso-8859-1"
Content-Transfer-Encoding: 7bit
>> qui il testo della  email
Testo del messaggio
--$cod_delimitatore
Content-Type: $tipofile;name="$nomefile"
Content-Disposition:attachment; filename="$nomefile"
Content-Transfer-Encoding: base64

$dati_allegato << codifica contenuto allegato
Corpo dell'allegato
--$cod_delimitatore--Fine messaggio

quindi questo è il codice del messaggio:

Codice PHP

 <?php 

// mailallegato.php 

$tipo_email="MIME-Version: 1.0\nContent-type: multipart/mixed;\n boundary=\"$cod_delimitatore\"\n\n";
$mittente="From: $nome <$email>\n$tipo_email";
$destinatario="< email destinatario >";
$oggetto="Messaggio dal Web con Allegato";
$test_mail="Messaggio inviato da $nome, email: $email";

$messaggio_a="This is a multi-part message in MINE format.\n\n"."--$cod_delimitatore\n"."Content-Type:text/plain;charset=\"iso-8859-1\"\n"."Content-Transfer-Encoding:7bit\n\n"."$test_mail\n\n";

$messaggio_b="--$cod_delimitatore\n"."Content-Type:$tipofile;name=\"$nomefile\"\n"."Content-Disposition:attachment;filename=\"$nomefile\"\n"."Content-Transfer-Encoding:base64\n\n"."$dati_allegato\n\n"."--$cod_delimitatore--\n";

$messaggio="$messaggio_a$messaggio_b";


if ( mail($destinatario,$oggetto,$messaggio,$mittente) )
  echo "Messaggio inviato con successo";
else
  echo "Errore. Nessun messaggio inviato.";