[php] Mailtje versturen met HTML, plain & bijlages

Pagina: 1
Acties:
  • 126 views sinds 30-01-2008
  • Reageer

Onderwerpen


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Ik heb me echt helemaal lijp gezocht, maar niks lijkt mijn probleem op te lossen. Ondanks dat op Zend.com heel de MIME type wordt uitgelegd, wordt er niet uitgelegd hoe je een mailtje verstuurt met een HTML & plain versie (multipart/alternative) met daarbij één of meerdere bijlages...

Ik doe het momenteel via de functie imap_mail_compose maar het kan ook door zelf een MIME mail te schrijven. Alleen dat gaat me vooralsnog slechter af...

Wie kan mij verder helpen?

Alvast erg bedankt.

Acties:
  • 0 Henk 'm!

  • stekkel
  • Registratie: Augustus 2001
  • Laatst online: 17-09 08:05
structuur is als volgt:
code:
1
2
3
4
5
6
multipart/mixed           (rfc822 header content-type)
    multipart/alternative
         text/plain
         text/html
    application/octet-stream  (attachment 1)
    image/gif                       (plaatje als attachment)

[ Voor 5% gewijzigd door stekkel op 04-03-2004 00:14 . Reden: opmaak ]


Acties:
  • 0 Henk 'm!

Verwijderd

Deze code gebruik ik voor html/plain (attachments heb ik nog niet geprobeerd):
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
$headers  = "MIME-Version: 1.0\r";
$headers .= "Content-Type: text/html; charset=iso-8859-1;\r\n";

$to = "iemand@domein.nl";
$subject = "onderwerp";
$message = "
<html>
<head>
 <title>titel</title>
</head>
<body>
<p>verhaaltje</p>
</body>
</html>
";

mail($to, $subject, $message, $headers);

Acties:
  • 0 Henk 'm!

Verwijderd

Het is niet ingewikkeld. In principe heb je 1 set headers die informatie over de complete body geeft. Eén van die headers geeft inderdaad informatie dat de body van het type multipart/alternative is. En een header geeft aan welke reeks tekens (separator) wordt gebruikt om de gedeelten uit de body te kunnen onderscheiden. Want:

De body bevat allemaal delen, gescheiden door die separator. Elk deel begint met een of meerdere headers, met informatie over het body deel van het onderdeel.

code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
mail headers
mail headers

body
body
body

--separator
part1 headers
part1 headers

part1 body
part1 body
part1 body

--separator
part2 headers
part2 headers

part2 body
part2 body
part2 body

--separator--

De headers van elk part bevatten meestal weer een Content-Type header, encoding header, etc. Zie RFC 2822 en RFC 2045.
Voor binary attachments wil je de body encoden, bijv. met base64.

Genoeg keywords om mee verder te komen denk ik

Acties:
  • 0 Henk 'm!

  • bigtree
  • Registratie: Oktober 2000
  • Laatst online: 16-08 17:16
Is niet zo moeilijk als het lijkt. (zeker als je hem nog naast je toetsenbord op het bureau had liggen) Volgende code is pseudo, dus niet getest.

code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
(header)
MIME-Version: 1.0
Content-Type: multipart/related;
  boundary="boundarya";

(body)
--boundarya
Content-Type: multipart/alternative;
  boundary="boundaryb";

--boundaryb
Content-Type: text-plain;
  charset=...
Content-Transfer-Encoding: ...

Text-only body

--boundaryb
Content-Type: text-plain;
  charset=...
Content-Transfer-Encoding: ...

<html>
Dit is de html-versie.<BR>
Eventueel met [img]"cid:plaatje">

</html[/img]

--boundaryb--

--boundarya

Content-Type: image/gif;
  name="whatever.gif"
Content-Transfer-Encoding: base64
Content-ID: <plaatje>

HJKHJHJKHJKLHDSJFUYEWURIHJKWSHSFKD
DSHFKHSDKJFHDSKHJFKDSHF

--boundarya--
(zag dat er nog meer enthousiastelingen wakker waren, toch maar op 'verstuur' gedrukt)

Lekker woordenboek, als je niet eens weet dat vandalen met een 'n' is.


Acties:
  • 0 Henk 'm!

  • stekkel
  • Registratie: Augustus 2001
  • Laatst online: 17-09 08:05
bigtree schreef op 04 maart 2004 @ 00:07:
Is niet zo moeilijk als het lijkt. (zeker als je hem nog naast je toetsenbord op het bureau had liggen) Volgende code is pseudo, dus niet getest.
een opmerking, indien de attachments niet gerelateerd zijn aan het text/html part dan moet je multipart/mixed in de header gebruiken.

Wanneer de plaatjes onderdeel van het text/html part zijn dan gebruik multipart/related.

een mogelijke combinatie:
code:
1
2
3
4
5
6
7
multipart/mixed           (rfc822 header content-type)
    multipart/alternative
         text/plain
         multipart/related type=text/html
              text/html
              image/jpg    (plaatje in mail)
    application/octet-stream  (attachment 1)

Acties:
  • 0 Henk 'm!

  • SchizoDuckie
  • Registratie: April 2001
  • Laatst online: 18-02 23:12

SchizoDuckie

Kwaak

Why invent the wheel twice :)
Deze functie heb ik eens geschreven voor mass mailings met htm, plain en bijlages :)
Let op!!! deze functie lult rechstreeks tegen je mailserver ipv met mail()


PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
// functie © SchizoDuckie


function SendMail($mailarray)
{
        for ($i=0; $i< sizeof($mailarray); $i++)
        {
                $mailarray[$i]['InnerBoundary'] = "----=_InnerBoundery_001";
                $mailarray[$i]['OuterBoundary'] = "----=_OuterBoundary_000";
                $mailarray[$i]['html']=$mailarray[$i]['html']?$mailarray[$i]['html']:preg_replace("/\n/","<br>",$mailarray[$i]['text'])
                or die("neither text nor html part present.");
                $mailarray[$i]['text']=$mailarray[$i]['text']?$mailarray[$i]['text']:"Sorry, but you need an html mailer to read this mail.";

                //Messages start with text/html alternatives in OB
                $mailarray[$i]['Message'] ="This is a multi-part message in MIME format.\n";
                $mailarray[$i]['Message'].="\n--".$mailarray[$i]['OuterBoundary']."\n";
                $mailarray[$i]['Message'].="Content-Type: multipart/alternative;\n\tboundary=\"".$mailarray[$i]['InnerBoundary']."\"\n\n";

                //plaintext section
                $mailarray[$i]['Message'].="\n--".$mailarray[$i]['InnerBoundary']."\n";
                $mailarray[$i]['Message'].="Content-Type: text/plain;\n\tcharset=\"iso-8859-1\"\n";
                $mailarray[$i]['Message'].="Content-Transfer-Encoding: quoted-printable\n\n";
                // plaintext goes here
                $mailarray[$i]['Message'].=$mailarray[$i]['text']."\n\n";

                // html section
                $mailarray[$i]['Message'].="\n--".$mailarray[$i]['InnerBoundary']."\n";
                $mailarray[$i]['Message'].="Content-Type: text/html;\n\tcharset=\"iso-8859-1\"\n";
                $mailarray[$i]['Message'].="Content-Transfer-Encoding: base64\n\n";
                // html goes here
                $mailarray[$i]['Message'].=chunk_split(base64_encode($mailarray[$i]['html']))."\n\n";

                // end of IB
                $mailarray[$i]['Message'].="\n--".$mailarray[$i]['InnerBoundary']."--\n";

                // attachments
                if(!empty($mailarray[$i]['attachments']))
                {
                        for ($j=0; $j< sizeof($mailarray[$i]['attachments']); $j++)
                        {
                                $mailarray[$i]['Message'].= "\n--".$mailarray[$i]['OuterBoundary']."\n";
                                $mailarray[$i]['Message'].="Content-Type: application/octetstream;\n\tname=\"".$mailarray[$i]['attachments'][$j]['filename']."\"\n";
                                $mailarray[$i]['Message'].="Content-Transfer-Encoding: base64\n";
                                $mailarray[$i]['Message'].="Content-Disposition: attachment;\n\tfilename=\"".$mailarray[$i]['attachments'][$j]['filename']."\"\n\n";
                                $mailarray[$i]['Message'].= chunk_split(base64_encode($mailarray[$i]['attachments'][$j]['content']));
                                $mailarray[$i]['Message'].="\n\n";
                        }
                }
                //message ends
                $mailarray[$i]['Message'].="\n--".$mailarray[$i]['OuterBoundary']."--\n";
        }

        // sending starts here

        $connect = fsockopen(ini_get("SMTP"), ini_get("smtp_port"), $errno, $errstr, 30) or throw_error("Could not talk to the sendmail server!");
        $rcv = fgets($connect, 1024);
        fputs($connect, "HELO {$_SERVER['SERVER_NAME']}\r\n");
        $rcv = fgets($connect, 1024);

        for ($i=0; $i< sizeof($mailarray); $i++)
        {
                fputs($connect, "MAIL FROM:".$mailarray[$i]['fromaddr']."\r\n");
                $rcv = fgets($connect, 1024);
                fputs($connect, "RCPT TO:".$mailarray[$i]['toaddr']."\r\n");
                $rcv = fgets($connect, 1024);
                fputs($connect, "DATA\r\n");
                $rcv = fgets($connect, 1024);
                fputs($connect, "Subject: ".$mailarray[$i]['subject']."\r\n");
                fputs($connect, "From: ".$mailarray[$i]['fromname']." <".$mailarray[$i]['fromaddr'].">\r\n");
                fputs($connect, "To: ".$mailarray[$i]['toname']." <".$mailarray[$i]['toaddr'].">\r\n");
                fputs($connect, "X-Sender: <".$mailarray[$i]['fromaddr'].">\r\n");
                fputs($connect, "MIME-Version: 1.0\r\n");
                fputs($connect, "Return-Path: <".$mailarray[$i]['fromaddr'].">\r\n");
                fputs($connect, "Errors-To: <".$mailarray[$i]['fromaddr'].">\r\n");
                fputs($connect, "X-Mailer: PHP ÜberMailer\r\n");
                fputs($connect, "X-Priority: 1\r\n");
                fputs($connect, "X-MSMail-Priority: High\r\n");
                fputs($connect, "Content-Type: multipart/mixed;\r\n\tboundary=\"".$mailarray[$i]['OuterBoundary']."\"\r\n");
                fputs($connect, "\r\n");
                fputs($connect, stripslashes($mailarray[$i]['Message'])." \r\n");
                fputs($connect, ".\r\n");
                $rcv = fgets($connect, 1024);
                fputs($connect, "RSET\r\n");
                $rcv = fgets($connect, 1024);
                echo("Mail: Message sent to ".$mailarray[$i]['toname']." <".$mailarray[$i]['toaddr']."><br>");
        }
        fputs ($connect, "QUIT\r\n");
        $rcv = fgets ($connect, 1024);
        fclose($connect);
}

for ($i=0; $i< 5; $i++)
{
    $mailarray[$i]['fromname'] = 'Sinterklaas';
    $mailarray[$i]['fromaddr'] = 'info@sinterklaas.nl';
    $mailarray[$i]['toname'] = 'De Kerstman';
    $mailarray[$i]['toaddr'] = 'santa@northpole.orgl';
    $mailarray[$i]['subject'] = 'Testing.. Message #'.$i;
    $mailarray[$i]['text'] = 'Woei! #'.$i.' :D ';
    $mailarray[$i]['html'] = '<b>Woei mekker ende blaat #'.$i.'</b> [img]"http://gathering.tweakers.net/global/smileys/shiny.gif"[/img]';

    $attach['filename'] = 'stoere-factuur.pdf';
    $attach['content'] = file_get_contents('./factuur.pdf');
    $mailarray[$i]['attachments'][] = $attach;
}

sendMail($mailarray);


That should do :)

[ Voor 40% gewijzigd door SchizoDuckie op 04-03-2004 08:11 ]

Stop uploading passwords to Github!


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
stekkel schreef op 04 maart 2004 @ 00:04:
structuur is als volgt:
code:
1
2
3
4
5
6
multipart/mixed           (rfc822 header content-type)
    multipart/alternative
         text/plain
         text/html
    application/octet-stream  (attachment 1)
    image/gif                       (plaatje als attachment)
Zoiets had ik ook in gedachte, maar hoe voer ik dit uit met imap_mail_compose? Ik kom niet verder dan dat ik de text/plain en text/html correct kan versturen... Het is lastig uit te leggen, maar ik snap niet hoe je zeg maar weer uit die "multipart/alternative" komt, zodat je de attachments weer deel laat uitmaken van de multipart/mixed...

Anderen ook bedankt voor hun posts hoor, maar ik wil het eerst eens proberen via imap_mail_compose...

Acties:
  • 0 Henk 'm!

  • stekkel
  • Registratie: Augustus 2001
  • Laatst online: 17-09 08:05
wanneer ik even snel naar die imap_mail_compose functie kijk zie ik dat die erg beperkt is. Dat betekend dat de content van multipart/alternative mee moet geven "contents.data" (ik refereer naar het voorbeeld wat ze daar geven). Daarnaast moet je een boundary mee moeten kunnen geven aan de mimeheader van het multipart/alternative part en ik zie niet zo snel welke structuur de array argumenten van die functie gehanteerd wordt.

M.a.w, de functie zuigt en ik zou het voorbeeld van Papa Eend maar eens goed bekijken.

Zelf heb ik voor dit soort dingen een Deliver class geschreven die een object met de mailstructuur bevat (een tree) zodat ik elke mogelijke mimestructuur kan generen wanneer ik die mailstructuur op de juiste wijze opbouw. Voor dit geval is dat lastig toe te passen omdat het afhankelijk is van heel wat andere classes. Wanneer je toch geinteresseerd ben moet je de SquirrelMail source maar eens downloaden.

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Ik begin er onderhand ook aan te geloven dat die functie niet veel meer kan dan wat het voorbeeld op php.net laat zien. Ik ga me eens storten op het zelf schrijven van de MIME...

Update
Het is me dan uiteindelijk gelukt aan de hand van het voorbeeld van Papa Eend. Heel erg bedankt allemaal!

[ Voor 26% gewijzigd door Verwijderd op 04-03-2004 20:43 ]


Acties:
  • 0 Henk 'm!

Verwijderd

PHPMailer is een zeer volwassen class om mail mee te verzenden.
Zie http://phpmailer.sourceforge.net/

Acties:
  • 0 Henk 'm!

Verwijderd

SchizoDuckie tnx.. goed script!

Acties:
  • 0 Henk 'm!

  • PhoeniX-
  • Registratie: Juni 2000
  • Laatst online: 01-09 10:26
Pagina: 1