15

As a "look under the covers" tutorial for myself I am building a PHP script to gather emails from a POP3 mailbox. While attempting to make use of binary attachments I am stuck trying to figure out what to do with the attachment information.

Given a string that would be gathered from an email:

------=_Part_16735_17392833.1229653992102 Content-Type: image/jpeg; name=trans2.jpg Content-Transfer-Encoding: base64 X-Attachment-Id: f_fow87t5j0 Content-Disposition: attachment; filename=trans2.jpg

/9j/4AAQSkZJRgABAgEASABIAAD/4QxrRXhpZgAATU0AKgAAAAgABwESAAMAAAABAAEAAAEaAAUA AAABAAAAYgEbAAUAAAABAAAAagEoAAMAAAABAAIAAAExAAIAAAAUAAAAcgEyAAIAAAAUAAAAhodp

(...)

EAgEAgEAgEAgEAg8IBQRL/Lbe/tJrScHqZ2lkmE4XUP2XcSDZZ2VvZ28dtbsDIYmhkbRxAIJCAQC AQCAQf/ScyAQCAQCAQCAQCAQCAQCAQCAQCAQCAQf/9k= ------=_Part_16735_17392833.1229653992102--

Is there a way to save off the data to disk so that it would be in a usable format?

8 Answers 8

31

Pass the data to base64_decode() to get the binary data, write it out to a file with file_put_contents()

Sign up to request clarification or add additional context in comments.

Comments

9

If you have a lot of data to write out that needs to be decoded before writing I would suggest using stream filters so decode the data as you write it...

$fh = fopen('where_you_are_writing', 'wb');
stream_filter_append($fh, 'convert.base64-decode');

// Do a lot of writing here. It will be automatically decoded from base64.

fclose($h);

Comments

2

I tried the below but did not work for me, was generating an empty image file.

file_put_contents('img.png', base64_decode($base64string));

this is how it worked for me:

$data = 'data:image/png;base64,AAAFBfj42Pj4';

list($type, $data) = explode(';', $data);
list(, $data)      = explode(',', $data);
$data = base64_decode($data);

file_put_contents('/tmp/image.png', $data);

I took the code from : How to save a PNG image server-side, from a base64 data string

1 Comment

just the list($type, $data) = explode(';', $data); list(, $data) = explode(',', $data); fixed my code. Many thanks!
2
function base64_decode_file($data)
{
    if(preg_match('/^data\:([a-zA-Z]+\/[a-zA-Z]+);base64\,([a-zA-Z0-9\+\/]+\=*)$/', $data, $matches)) {
        return [
                'mime' => $matches[1],
                'data' => base64_decode($matches[2]),
        ];
    }
    return false;
}

2 Comments

I guess this was down voted because it doesn't specifically answer the question but its a very useful little helper so I'm tossing you an upvote.
BTW, you had a few redundant escape characters in your regex: if(preg_match('/^data:([a-zA-Z]+\/[a-zA-Z]+);base64,([a-zA-Z0-9+\/]+=*)$/', $data, $matches)) {
0

While reinventing the wheel has some entertainment and educational value, I would try to resist the temptation: Mailparse, Mail_mimeDecode

Comments

0

I had a similar situation, and this is what I did. As noted earlier, make sure to remove the extraneous lines before and after the base64 string.

<?php
$INPUT = "inputfile_base64_encoded.txt";
$OUTPUT = "output_decoded.zip";
$contents = file_get_contents($INPUT);
$bin = base64_decode($contents);
file_put_contents($OUTPUT, $bin);
?>

Comments

0

Chop off first and last line, base64decode and save under given filename.

done.

Comments

-1

For big base64 strings from a DB you need use load()

$imgdata = $FromDB['BASE64']->load();
$imgdata =  base64_decode($imgdata);
file_put_contents($fileName, $imgdata);

2 Comments

What type of object is $FromDB['BASE64']? plain string data is not an object in php
@Mohammed Farag A varchar field from the database is an object, using the load method you can load a big amount of characters.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.