/usr/share/php/GuzzleHttp/Psr7/MultipartStream.php is in php-guzzlehttp-psr7 1.2.2-1ubuntu1.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
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 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 | <?php
namespace GuzzleHttp\Psr7;
use Psr\Http\Message\StreamInterface;
/**
* Stream that when read returns bytes for a streaming multipart or
* multipart/form-data stream.
*/
class MultipartStream implements StreamInterface
{
use StreamDecoratorTrait;
private $boundary;
/**
* @param array $elements Array of associative arrays, each containing a
* required "name" key mapping to the form field,
* name, a required "contents" key mapping to a
* StreamInterface/resource/string, an optional
* "headers" associative array of custom headers,
* and an optional "filename" key mapping to a
* string to send as the filename in the part.
* @param string $boundary You can optionally provide a specific boundary
*
* @throws \InvalidArgumentException
*/
public function __construct(array $elements = [], $boundary = null)
{
$this->boundary = $boundary ?: uniqid();
$this->stream = $this->createStream($elements);
}
/**
* Get the boundary
*
* @return string
*/
public function getBoundary()
{
return $this->boundary;
}
public function isWritable()
{
return false;
}
/**
* Get the headers needed before transferring the content of a POST file
*/
private function getHeaders(array $headers)
{
$str = '';
foreach ($headers as $key => $value) {
$str .= "{$key}: {$value}\r\n";
}
return "--{$this->boundary}\r\n" . trim($str) . "\r\n\r\n";
}
/**
* Create the aggregate stream that will be used to upload the POST data
*/
protected function createStream(array $elements)
{
$stream = new AppendStream();
foreach ($elements as $element) {
$this->addElement($stream, $element);
}
// Add the trailing boundary with CRLF
$stream->addStream(stream_for("--{$this->boundary}--\r\n"));
return $stream;
}
private function addElement(AppendStream $stream, array $element)
{
foreach (['contents', 'name'] as $key) {
if (!array_key_exists($key, $element)) {
throw new \InvalidArgumentException("A '{$key}' key is required");
}
}
$element['contents'] = stream_for($element['contents']);
if (empty($element['filename'])) {
$uri = $element['contents']->getMetadata('uri');
if (substr($uri, 0, 6) !== 'php://') {
$element['filename'] = $uri;
}
}
list($body, $headers) = $this->createElement(
$element['name'],
$element['contents'],
isset($element['filename']) ? $element['filename'] : null,
isset($element['headers']) ? $element['headers'] : []
);
$stream->addStream(stream_for($this->getHeaders($headers)));
$stream->addStream($body);
$stream->addStream(stream_for("\r\n"));
}
/**
* @return array
*/
private function createElement($name, $stream, $filename, array $headers)
{
// Set a default content-disposition header if one was no provided
$disposition = $this->getHeader($headers, 'content-disposition');
if (!$disposition) {
$headers['Content-Disposition'] = ($filename === '0' || $filename)
? sprintf('form-data; name="%s"; filename="%s"',
$name,
basename($filename))
: "form-data; name=\"{$name}\"";
}
// Set a default content-length header if one was no provided
$length = $this->getHeader($headers, 'content-length');
if (!$length) {
if ($length = $stream->getSize()) {
$headers['Content-Length'] = (string) $length;
}
}
// Set a default Content-Type if one was not supplied
$type = $this->getHeader($headers, 'content-type');
if (!$type && ($filename === '0' || $filename)) {
if ($type = mimetype_from_filename($filename)) {
$headers['Content-Type'] = $type;
}
}
return [$stream, $headers];
}
private function getHeader(array $headers, $key)
{
$lowercaseHeader = strtolower($key);
foreach ($headers as $k => $v) {
if (strtolower($k) === $lowercaseHeader) {
return $v;
}
}
return null;
}
}
|