Skip to content

Commit 1d8e3c4

Browse files
committed
Refactor rename and unlink to use the context directly
1 parent fc32d0a commit 1d8e3c4

6 files changed

+61
-83
lines changed

docs/reference/method/MongoDBGridFSBucket-registerGlobalStreamWrapperAlias.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ Supported stream functions:
4949
- :php:`file() <file>`
5050
- :php:`fopen() <fopen>` with "r", "rb", "w", and "wb" modes
5151
- :php:`rename() <rename>` rename all revisions of a file in the same bucket
52-
- :php:`unlink() <unlink>` (remove all revisions of a file)
52+
- :php:`unlink() <unlink>` remove all revisions of a file in the same bucket
5353

5454
In read mode, the stream context can contain the option ``gridfs['revision']``
5555
to specify the revision number of the file to read. If omitted, the most recent

psalm-baseline.xml

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -98,17 +98,26 @@
9898
</file>
9999
<file src="src/GridFS/StreamWrapper.php">
100100
<InvalidArgument>
101-
<code>$context</code>
102-
<code>$context</code>
101+
<code><![CDATA[$this->getContext($path, $mode)]]></code>
102+
<code><![CDATA[$this->getContext($path, $mode)]]></code>
103103
</InvalidArgument>
104-
<MixedAssignment>
104+
<InvalidReturnStatement>
105105
<code>$context</code>
106-
</MixedAssignment>
107-
</file>
108-
<file src="src/GridFS/WritableStream.php">
106+
</InvalidReturnStatement>
107+
<InvalidReturnType>
108+
<code>array{collectionWrapper: CollectionWrapper, file: object}|array{collectionWrapper: CollectionWrapper, filename: string, options: array</code>
109+
</InvalidReturnType>
109110
<MixedArgument>
110-
<code><![CDATA[$this->file['filename']]]></code>
111+
<code><![CDATA[$context['file']->filename]]></code>
112+
<code><![CDATA[$context['file']->filename]]></code>
111113
</MixedArgument>
114+
<MixedAssignment>
115+
<code>$context</code>
116+
</MixedAssignment>
117+
<PossiblyUndefinedArrayOffset>
118+
<code><![CDATA[$context['file']]]></code>
119+
<code><![CDATA[$context['file']]]></code>
120+
</PossiblyUndefinedArrayOffset>
112121
</file>
113122
<file src="src/Model/BSONArray.php">
114123
<MixedAssignment>

src/GridFS/CollectionWrapper.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -87,7 +87,6 @@ public function deleteFileAndChunksByFilename(string $filename): int
8787
{
8888
/** @var iterable<array{_id: mixed}> $files */
8989
$files = $this->findFiles(['filename' => $filename], [
90-
'codec' => null,
9190
'typeMap' => ['root' => 'array'],
9291
'projection' => ['_id' => 1],
9392
]);

src/GridFS/ReadableStream.php

Lines changed: 0 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -22,14 +22,12 @@
2222
use MongoDB\Driver\CursorInterface;
2323
use MongoDB\Exception\InvalidArgumentException;
2424
use MongoDB\GridFS\Exception\CorruptFileException;
25-
use MongoDB\GridFS\Exception\LogicException;
2625

2726
use function assert;
2827
use function ceil;
2928
use function floor;
3029
use function is_integer;
3130
use function is_object;
32-
use function is_string;
3331
use function property_exists;
3432
use function sprintf;
3533
use function strlen;
@@ -178,20 +176,6 @@ public function readBytes(int $length): string
178176
return $data;
179177
}
180178

181-
/**
182-
* Rename all revisions of the file.
183-
*/
184-
public function rename(string $newFilename): bool
185-
{
186-
if (! isset($this->file->filename) || ! is_string($this->file->filename)) {
187-
throw new LogicException('Cannot rename file without a filename');
188-
}
189-
190-
$this->collectionWrapper->updateFilenameForFilename($this->file->filename, $newFilename);
191-
192-
return true;
193-
}
194-
195179
/**
196180
* Seeks the chunk and buffer offsets for the next read operation.
197181
*

src/GridFS/StreamWrapper.php

Lines changed: 44 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -106,15 +106,15 @@ public function rename(string $fromPath, string $toPath): bool
106106
}
107107

108108
try {
109-
$this->stream_open($fromPath, 'r', 0, $openedPath);
109+
$context = $this->getContext($fromPath, 'r');
110110
} catch (FileNotFoundException $e) {
111111
return false;
112112
}
113113

114-
$newName = explode('/', $toPath, 4)[3] ?? '';
115-
assert($this->stream instanceof ReadableStream);
114+
$newFilename = explode('/', $toPath, 4)[3] ?? '';
115+
$context['collectionWrapper']->updateFilenameForFilename($context['file']->filename, $newFilename);
116116

117-
return $this->stream->rename($newName);
117+
return true;
118118
}
119119

120120
/**
@@ -170,41 +170,12 @@ public function stream_eof(): bool
170170
*/
171171
public function stream_open(string $path, string $mode, int $options, ?string &$openedPath): bool
172172
{
173-
$context = [];
174-
175-
/**
176-
* The Bucket methods { @see Bucket::openUploadStream() } and { @see Bucket::openDownloadStreamByFile() }
177-
* always set an internal context. But the context can also be set by the user.
178-
*/
179-
if (is_resource($this->context)) {
180-
$context = stream_context_get_options($this->context)['gridfs'] ?? [];
181-
182-
if (! is_array($context)) {
183-
throw LogicException::invalidContext($context);
184-
}
185-
}
186-
187-
// When the stream is opened using fopen(), the context is not required, it can contain only options.
188-
if (! isset($context['collectionWrapper'])) {
189-
$bucketAlias = explode('/', $path, 4)[2] ?? '';
190-
191-
if (! isset(self::$contextResolvers[$bucketAlias])) {
192-
throw LogicException::bucketAliasNotRegistered($bucketAlias);
193-
}
194-
195-
$context = self::$contextResolvers[$bucketAlias]($path, $mode, $context);
196-
}
197-
198-
if (! $context['collectionWrapper'] instanceof CollectionWrapper) {
199-
throw LogicException::invalidContextCollectionWrapper($context['collectionWrapper']);
200-
}
201-
202173
if ($mode === 'r' || $mode === 'rb') {
203-
return $this->initReadableStream($context);
174+
return $this->initReadableStream($this->getContext($path, $mode));
204175
}
205176

206177
if ($mode === 'w' || $mode === 'wb') {
207-
return $this->initWritableStream($context);
178+
return $this->initWritableStream($this->getContext($path, $mode));
208179
}
209180

210181
throw LogicException::openModeNotSupported($mode);
@@ -326,15 +297,10 @@ public function stream_write(string $data): int
326297

327298
public function unlink(string $path): bool
328299
{
329-
try {
330-
$this->stream_open($path, 'w', 0, $openedPath);
331-
} catch (FileNotFoundException $e) {
332-
return false;
333-
}
300+
$context = $this->getContext($path, 'r');
301+
$count = $context['collectionWrapper']->deleteFileAndChunksByFilename($context['file']->filename);
334302

335-
assert($this->stream instanceof WritableStream);
336-
337-
return $this->stream->delete() > 0;
303+
return $count > 0;
338304
}
339305

340306
/** @return false|array */
@@ -405,4 +371,39 @@ private function initWritableStream(array $contextOptions): bool
405371

406372
return true;
407373
}
374+
375+
/** @return array{collectionWrapper: CollectionWrapper, file: object}|array{collectionWrapper: CollectionWrapper, filename: string, options: array */
376+
private function getContext(string $path, string $mode): array
377+
{
378+
$context = [];
379+
380+
/**
381+
* The Bucket methods { @see Bucket::openUploadStream() } and { @see Bucket::openDownloadStreamByFile() }
382+
* always set an internal context. But the context can also be set by the user.
383+
*/
384+
if (is_resource($this->context)) {
385+
$context = stream_context_get_options($this->context)['gridfs'] ?? [];
386+
387+
if (! is_array($context)) {
388+
throw LogicException::invalidContext($context);
389+
}
390+
}
391+
392+
// When the stream is opened using fopen(), the context is not required, it can contain only options.
393+
if (! isset($context['collectionWrapper'])) {
394+
$bucketAlias = explode('/', $path, 4)[2] ?? '';
395+
396+
if (! isset(self::$contextResolvers[$bucketAlias])) {
397+
throw LogicException::bucketAliasNotRegistered($bucketAlias);
398+
}
399+
400+
$context = self::$contextResolvers[$bucketAlias]($path, $mode, $context);
401+
}
402+
403+
if (! $context['collectionWrapper'] instanceof CollectionWrapper) {
404+
throw LogicException::invalidContextCollectionWrapper($context['collectionWrapper']);
405+
}
406+
407+
return $context;
408+
}
408409
}

src/GridFS/WritableStream.php

Lines changed: 0 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -173,21 +173,6 @@ public function close(): void
173173
$this->isClosed = true;
174174
}
175175

176-
/**
177-
* Delete all files and chunks associated with this stream filename.
178-
*
179-
* @return int The number of deleted files
180-
*/
181-
public function delete(): int
182-
{
183-
try {
184-
return $this->collectionWrapper->deleteFileAndChunksByFilename($this->file['filename']);
185-
} finally {
186-
// Prevent further operations on this stream
187-
$this->abort();
188-
}
189-
}
190-
191176
/**
192177
* Return the stream's file document.
193178
*/

0 commit comments

Comments
 (0)