Skip to content

Commit cd9394c

Browse files
committed
Merge pull request #192
2 parents 3dbbd79 + a916f8f commit cd9394c

23 files changed

+1202
-1454
lines changed

src/GridFS/Bucket.php

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -265,9 +265,14 @@ public function openDownloadStreamByName($filename, array $options = [])
265265
*
266266
* Supported options:
267267
*
268+
* * _id (mixed): File document identifier. Defaults to a new ObjectId.
269+
*
268270
* * chunkSizeBytes (integer): The chunk size in bytes. Defaults to the
269271
* bucket's chunk size.
270272
*
273+
* * metadata (document): User data for the "metadata" field of the files
274+
* collection document.
275+
*
271276
* @param string $filename Filename
272277
* @param array $options Upload options
273278
* @return resource
@@ -322,9 +327,14 @@ public function rename($id, $newFilename)
322327
*
323328
* Supported options:
324329
*
330+
* * _id (mixed): File document identifier. Defaults to a new ObjectId.
331+
*
325332
* * chunkSizeBytes (integer): The chunk size in bytes. Defaults to the
326333
* bucket's chunk size.
327334
*
335+
* * metadata (document): User data for the "metadata" field of the files
336+
* collection document.
337+
*
328338
* @param string $filename Filename
329339
* @param resource $source Readable stream
330340
* @param array $options Stream options

src/GridFS/CollectionWrapper.php

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,9 @@
1717
*/
1818
class CollectionWrapper
1919
{
20+
private $bucketName;
2021
private $chunksCollection;
22+
private $databaseName;
2123
private $checkedIndexes = false;
2224
private $filesCollection;
2325

@@ -33,6 +35,9 @@ class CollectionWrapper
3335
*/
3436
public function __construct(Manager $manager, $databaseName, $bucketName, array $collectionOptions = [])
3537
{
38+
$this->databaseName = (string) $databaseName;
39+
$this->bucketName = (string) $bucketName;
40+
3641
$this->filesCollection = new Collection($manager, $databaseName, sprintf('%s.files', $bucketName), $collectionOptions);
3742
$this->chunksCollection = new Collection($manager, $databaseName, sprintf('%s.chunks', $bucketName), $collectionOptions);
3843
}
@@ -135,10 +140,14 @@ public function findFiles($filter, array $options = [])
135140
return $this->filesCollection->find($filter, $options);
136141
}
137142

138-
// TODO: Remove this
139-
public function getChunksCollection()
143+
/**
144+
* Return the bucket name.
145+
*
146+
* @return string
147+
*/
148+
public function getBucketName()
140149
{
141-
return $this->chunksCollection;
150+
return $this->bucketName;
142151
}
143152

144153
/**
@@ -160,10 +169,14 @@ public function getChunksIteratorByFilesId($id)
160169
return new IteratorIterator($cursor);
161170
}
162171

163-
// TODO: Remove this
164-
public function getFilesCollection()
172+
/**
173+
* Return the database name.
174+
*
175+
* @return string
176+
*/
177+
public function getDatabaseName()
165178
{
166-
return $this->filesCollection;
179+
return $this->databaseName;
167180
}
168181

169182
/**

src/GridFS/ReadableStream.php

Lines changed: 65 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
namespace MongoDB\GridFS;
44

5-
use MongoDB\Driver\Exception\Exception;
5+
use MongoDB\Exception\InvalidArgumentException;
66
use MongoDB\GridFS\Exception\CorruptFileException;
77
use stdClass;
88

@@ -17,11 +17,14 @@ class ReadableStream
1717
private $bufferEmpty;
1818
private $bufferFresh;
1919
private $bytesSeen = 0;
20+
private $chunkSize;
2021
private $chunkOffset = 0;
2122
private $chunksIterator;
22-
private $file;
23+
private $collectionWrapper;
2324
private $firstCheck = true;
25+
private $id;
2426
private $iteratorEmpty = false;
27+
private $length;
2528
private $numChunks;
2629

2730
/**
@@ -33,13 +36,45 @@ class ReadableStream
3336
*/
3437
public function __construct(CollectionWrapper $collectionWrapper, stdClass $file)
3538
{
36-
$this->file = $file;
39+
if ( ! isset($file->chunkSize) || ! is_integer($file->chunkSize) || $file->chunkSize < 1) {
40+
throw new CorruptFileException('file.chunkSize is not an integer >= 1');
41+
}
42+
43+
if ( ! isset($file->length) || ! is_integer($file->length) || $file->length < 0) {
44+
throw new CorruptFileException('file.length is not an integer > 0');
45+
}
3746

38-
$this->chunksIterator = $collectionWrapper->getChunksIteratorByFilesId($this->file->_id);
39-
$this->numChunks = ($file->length >= 0) ? ceil($file->length / $file->chunkSize) : 0;
47+
if ( ! isset($file->_id) && ! array_key_exists('_id', (array) $file)) {
48+
throw new CorruptFileException('file._id does not exist');
49+
}
50+
51+
$this->id = $file->_id;
52+
$this->chunkSize = $file->chunkSize;
53+
$this->length = $file->length;
54+
55+
$this->chunksIterator = $collectionWrapper->getChunksIteratorByFilesId($this->id);
56+
$this->collectionWrapper = $collectionWrapper;
57+
$this->numChunks = ceil($this->length / $this->chunkSize);
4058
$this->initEmptyBuffer();
4159
}
4260

61+
/**
62+
* Return internal properties for debugging purposes.
63+
*
64+
* @see http://php.net/manual/en/language.oop5.magic.php#language.oop5.magic.debuginfo
65+
* @return array
66+
*/
67+
public function __debugInfo()
68+
{
69+
return [
70+
'bucketName' => $this->collectionWrapper->getBucketName(),
71+
'databaseName' => $this->collectionWrapper->getDatabaseName(),
72+
'id' => $this->id,
73+
'chunkSize' => $this->chunkSize,
74+
'length' => $this->length,
75+
];
76+
}
77+
4378
public function close()
4479
{
4580
fclose($this->buffer);
@@ -52,10 +87,19 @@ public function close()
5287
* if data is not available to be read.
5388
*
5489
* @param integer $numBytes Number of bytes to read
55-
* @return string
90+
* @return string
91+
* @throws InvalidArgumentException if $numBytes is negative
5692
*/
5793
public function downloadNumBytes($numBytes)
5894
{
95+
if ($numBytes < 0) {
96+
throw new InvalidArgumentException(sprintf('$numBytes must be >= zero; given: %d', $numBytes));
97+
}
98+
99+
if ($numBytes == 0) {
100+
return '';
101+
}
102+
59103
if ($this->bufferFresh) {
60104
rewind($this->buffer);
61105
$this->bufferFresh = false;
@@ -77,7 +121,7 @@ public function downloadNumBytes($numBytes)
77121
$output .= substr($this->chunksIterator->current()->data->getData(), 0, $bytesLeft);
78122
}
79123

80-
if ( ! $this->iteratorEmpty && $this->file->length > 0 && $bytesLeft < strlen($this->chunksIterator->current()->data->getData())) {
124+
if ( ! $this->iteratorEmpty && $this->length > 0 && $bytesLeft < strlen($this->chunksIterator->current()->data->getData())) {
81125
fwrite($this->buffer, substr($this->chunksIterator->current()->data->getData(), $bytesLeft));
82126
$this->bufferEmpty = false;
83127
}
@@ -103,19 +147,24 @@ public function downloadToStream($destination)
103147
}
104148
}
105149

106-
public function getFile()
107-
{
108-
return $this->file;
109-
}
110-
150+
/**
151+
* Return the stream's ID (i.e. file document identifier).
152+
*
153+
* @return integer
154+
*/
111155
public function getId()
112156
{
113-
return $this->file->_id;
157+
return $this->id;
114158
}
115159

160+
/**
161+
* Return the stream's size in bytes.
162+
*
163+
* @return integer
164+
*/
116165
public function getSize()
117166
{
118-
return $this->file->length;
167+
return $this->length;
119168
}
120169

121170
public function isEOF()
@@ -149,8 +198,8 @@ private function advanceChunks()
149198
$actualChunkSize = strlen($this->chunksIterator->current()->data->getData());
150199

151200
$expectedChunkSize = ($this->chunkOffset == $this->numChunks - 1)
152-
? ($this->file->length - $this->bytesSeen)
153-
: $this->file->chunkSize;
201+
? ($this->length - $this->bytesSeen)
202+
: $this->chunkSize;
154203

155204
if ($actualChunkSize != $expectedChunkSize) {
156205
throw CorruptFileException::unexpectedSize($actualChunkSize, $expectedChunkSize);

src/GridFS/WritableStream.php

Lines changed: 27 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,21 @@ public function __construct(CollectionWrapper $collectionWrapper, $filename, arr
8989
] + array_intersect_key($options, ['aliases' => 1, 'contentType' => 1, 'metadata' => 1]);
9090
}
9191

92+
/**
93+
* Return internal properties for debugging purposes.
94+
*
95+
* @see http://php.net/manual/en/language.oop5.magic.php#language.oop5.magic.debuginfo
96+
* @return array
97+
*/
98+
public function __debugInfo()
99+
{
100+
return [
101+
'bucketName' => $this->collectionWrapper->getBucketName(),
102+
'databaseName' => $this->collectionWrapper->getDatabaseName(),
103+
'file' => $this->file,
104+
];
105+
}
106+
92107
/**
93108
* Closes an active stream and flushes all buffered data to GridFS.
94109
*/
@@ -111,26 +126,23 @@ public function close()
111126
$this->isClosed = true;
112127
}
113128

114-
public function getChunkSize()
115-
{
116-
return $this->chunkSize;
117-
}
118-
119-
public function getFile()
120-
{
121-
return $this->file;
122-
}
123-
129+
/**
130+
* Return the stream's ID (i.e. file document identifier).
131+
*
132+
* @return integer
133+
*/
124134
public function getId()
125135
{
126136
return $this->file['_id'];
127137
}
128138

129-
public function getLength()
130-
{
131-
return $this->length;
132-
}
133-
139+
/**
140+
* Return the stream's size in bytes.
141+
*
142+
* Note: this value will increase as more data is written to the stream.
143+
*
144+
* @return integer
145+
*/
134146
public function getSize()
135147
{
136148
return $this->length;

src/functions.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,9 +77,10 @@ function is_first_key_operator($document)
7777
throw InvalidArgumentException::invalidType('$document', $document, 'array or object');
7878
}
7979

80+
reset($document);
8081
$firstKey = (string) key($document);
8182

82-
return (isset($firstKey[0]) && $firstKey[0] == '$');
83+
return (isset($firstKey[0]) && $firstKey[0] === '$');
8384
}
8485

8586
/**

0 commit comments

Comments
 (0)