Загрузите файл, используя файл получить содержимое


Я понимаю, что могу сделать это с помощью CURL очень легко, но мне было интересно, можно ли использовать file_get_contents() с контекстом потока http для загрузки файла на удаленный веб-сервер, и если да, то как?

Author: halfer, 2010-10-23

2 answers

Прежде всего, первое правило типа содержимого multipart состоит в том, чтобы определить границу , которая будет использоваться в качестве разделителя между каждой частью (потому что, как следует из названия, она может состоять из нескольких частей). Границей может быть любая строка, которая не содержится в теле содержимого. Обычно я буду использовать метку времени:

define('MULTIPART_BOUNDARY', '--------------------------'.microtime(true));

Как только ваша граница определена, вы должны отправить ее с заголовком Content-Type, чтобы сообщить веб-серверу, какой разделитель следует ожидать:

$header = 'Content-Type: multipart/form-data; boundary='.MULTIPART_BOUNDARY;

Как только это произойдет после этого вы должны создать правильный текст содержимого, соответствующий спецификации HTTP и отправленному вами заголовку. Как вы знаете, при отправке файла из формы у вас обычно будет имя поля формы. Мы определим это:

// equivalent to <input type="file" name="uploaded_file"/>
define('FORM_FIELD', 'uploaded_file'); 

Затем мы создаем тело содержимого:

$filename = "/path/to/uploaded/file.zip";
$file_contents = file_get_contents($filename);    

$content =  "--".MULTIPART_BOUNDARY."\r\n".
            "Content-Disposition: form-data; name=\"".FORM_FIELD."\"; filename=\"".basename($filename)."\"\r\n".
            "Content-Type: application/zip\r\n\r\n".
            $file_contents."\r\n";

// add some POST fields to the request too: $_POST['foo'] = 'bar'
$content .= "--".MULTIPART_BOUNDARY."\r\n".
            "Content-Disposition: form-data; name=\"foo\"\r\n\r\n".
            "bar\r\n";

// signal end of request (note the trailing "--")
$content .= "--".MULTIPART_BOUNDARY."--\r\n";

Как вы можете видеть, мы отправляем заголовок Content-Disposition с расположением form-data вместе с параметром name (имя поля формы) и параметром filename (исходное имя файла). Также важно отправить Content-Type заголовок с правильным типом MIME, если вы хотите правильно заполнить $_FILES[]['type'] штуковину.

Если вам нужно было загрузить несколько файлов, вы просто повторяете процесс с битом $content, конечно, с другим FORM_FIELD для каждого файла.

Теперь постройте контекст:

$context = stream_context_create(array(
    'http' => array(
          'method' => 'POST',
          'header' => $header,
          'content' => $content,
    )
));

И выполните:

file_get_contents('http://url/to/upload/handler', false, $context);

ПРИМЕЧАНИЕ: Нет необходимости кодировать ваш двоичный файл перед его отправкой. HTTP отлично справляется с двоичными файлами.

 75
Author: netcoder, 2013-09-12 14:10:46

Вы можете отправить запрос POST с заголовком Content-Type: multipart/form-data и вручную закодировать файл как multipart/form-data.

file_get_contents(URL, false, stream_context_create(array(
    'http' => array(
        'method'  => 'POST',
        'headers' => 'Content-Type: multipart/form-data'
        'content' => MULTIPART_ENCODED_FILE,
    ),
)));
 0
Author: NikiC, 2010-11-19 13:39:00