Skip to content

Commit

Permalink
Allow copy without retaining visibility for adapters and implementati…
Browse files Browse the repository at this point in the history
…ons that required fetching visibility for copy and move.
  • Loading branch information
frankdejonge committed Nov 2, 2023
1 parent 015633a commit d15165f
Show file tree
Hide file tree
Showing 7 changed files with 85 additions and 33 deletions.
9 changes: 6 additions & 3 deletions src/AsyncAwsS3/AsyncAwsS3Adapter.php
Original file line number Diff line number Diff line change
Expand Up @@ -315,14 +315,17 @@ public function move(string $source, string $destination, Config $config): void
public function copy(string $source, string $destination, Config $config): void
{
try {
/** @var string $visibility */
$visibility = $config->get(Config::OPTION_VISIBILITY) ?: $this->visibility($source)->visibility();
$visibility = $config->get(Config::OPTION_VISIBILITY);

if ($visibility === null && $config->get('retain_visibility', true)) {
$visibility = $this->visibility($source)->visibility();
}
} catch (Throwable $exception) {
throw UnableToCopyFile::fromLocationTo($source, $destination, $exception);
}

$arguments = [
'ACL' => $this->visibility->visibilityToAcl($visibility),
'ACL' => $this->visibility->visibilityToAcl($visibility ?: 'private'),
'Bucket' => $this->bucket,
'Key' => $this->prefixer->prefixPath($destination),
'CopySource' => $this->bucket . '/' . $this->prefixer->prefixPath($source),
Expand Down
9 changes: 6 additions & 3 deletions src/AwsS3V3/AwsS3V3Adapter.php
Original file line number Diff line number Diff line change
Expand Up @@ -415,8 +415,11 @@ public function move(string $source, string $destination, Config $config): void
public function copy(string $source, string $destination, Config $config): void
{
try {
/** @var string $visibility */
$visibility = $config->get(Config::OPTION_VISIBILITY) ?: $this->visibility($source)->visibility();
$visibility = $config->get(Config::OPTION_VISIBILITY);

if ($visibility === null && $config->get('retain_visibility', true)) {
$visibility = $this->visibility($source)->visibility();
}
} catch (Throwable $exception) {
throw UnableToCopyFile::fromLocationTo(
$source,
Expand All @@ -431,7 +434,7 @@ public function copy(string $source, string $destination, Config $config): void
$this->prefixer->prefixPath($source),
$this->bucket,
$this->prefixer->prefixPath($destination),
$this->visibility->visibilityToAcl($visibility),
$this->visibility->visibilityToAcl($visibility ?: 'private'),
$this->createOptionsFromConfig($config)['params']
);
} catch (Throwable $exception) {
Expand Down
10 changes: 10 additions & 0 deletions src/Config.php
Original file line number Diff line number Diff line change
Expand Up @@ -36,4 +36,14 @@ public function withDefaults(array $defaults): Config
{
return new Config($this->options + $defaults);
}

public function toArray(): array
{
return $this->options;
}

public function withSetting(string $property, mixed $setting): Config
{
return $this->extend([$property => $setting]);
}
}
16 changes: 12 additions & 4 deletions src/Ftp/FtpAdapter.php
Original file line number Diff line number Diff line change
Expand Up @@ -547,16 +547,21 @@ public function move(string $source, string $destination, Config $config): void
$connection = $this->connection();

if ( ! @ftp_rename($connection, $sourceLocation, $destinationLocation)) {
throw UnableToMoveFile::fromLocationTo($source, $destination);
throw UnableToMoveFile::because(error_get_last()['message'] ?? 'reason unknown', $source, $destination);
}
}

public function copy(string $source, string $destination, Config $config): void
{
try {
$readStream = $this->readStream($source);
$visibility = $this->visibility($source)->visibility();
$this->writeStream($destination, $readStream, new Config(compact('visibility')));
$visibility = $config->get(Config::OPTION_VISIBILITY);

if ($visibility === null && $config->get('retain_visibility', true)) {
$config = $config->withSetting(Config::OPTION_VISIBILITY, $this->visibility($source)->visibility());
}

$this->writeStream($destination, $readStream, $config);
} catch (Throwable $exception) {
if (isset($readStream) && is_resource($readStream)) {
@fclose($readStream);
Expand Down Expand Up @@ -604,7 +609,10 @@ private function ensureDirectoryExists(string $dirname, ?string $visibility): vo
}

if ($mode !== false && @ftp_chmod($connection, $mode, $location) === false) {
throw UnableToCreateDirectory::atLocation($dirPath, 'unable to chmod the directory');
throw UnableToCreateDirectory::atLocation(
$dirPath,
'unable to chmod the directory: ' . error_get_last()['message'] ?? 'reason unknown'

Check failure on line 614 in src/Ftp/FtpAdapter.php

View workflow job for this annotation

GitHub Actions / PHPUnit tests on 8.0

Expression on left side of ?? is not nullable.

Check failure on line 614 in src/Ftp/FtpAdapter.php

View workflow job for this annotation

GitHub Actions / PHPUnit tests on 8.1

Expression on left side of ?? is not nullable.
);
}
}
}
Expand Down
12 changes: 9 additions & 3 deletions src/GoogleCloudStorage/GoogleCloudStorageAdapter.php
Original file line number Diff line number Diff line change
Expand Up @@ -348,11 +348,17 @@ public function move(string $source, string $destination, Config $config): void
public function copy(string $source, string $destination, Config $config): void
{
try {
/** @var string $visibility */
$visibility = $this->visibility($source)->visibility();
$visibility = $config->get(Config::OPTION_VISIBILITY);

if ($visibility === null && $config->get('retain_visibility', true)) {
$visibility = $this->visibility($source)->visibility();
}

$prefixedSource = $this->prefixer->prefixPath($source);
$options = ['name' => $this->prefixer->prefixPath($destination)];
$predefinedAcl = $this->visibilityHandler->visibilityToPredefinedAcl($visibility);
$predefinedAcl = $this->visibilityHandler->visibilityToPredefinedAcl(
$visibility ?: PortableVisibilityHandler::NO_PREDEFINED_VISIBILITY
);

if ($predefinedAcl !== PortableVisibilityHandler::NO_PREDEFINED_VISIBILITY) {
$options['predefinedAcl'] = $predefinedAcl;
Expand Down
53 changes: 35 additions & 18 deletions src/MountManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,20 @@ class MountManager implements FilesystemOperator
*/
private $filesystems = [];

/**
* @var Config
*/
private $config;

/**
* MountManager constructor.
*
* @param array<string,FilesystemOperator> $filesystems
*/
public function __construct(array $filesystems = [])
public function __construct(array $filesystems = [], array $config = [])
{
$this->mountFilesystems($filesystems);
$this->config = new Config($config);
}

public function fileExists(string $location): bool
Expand Down Expand Up @@ -156,7 +162,7 @@ public function write(string $location, string $contents, array $config = []): v
[$filesystem, $path] = $this->determineFilesystemAndPath($location);

try {
$filesystem->write($path, $contents, $config);
$filesystem->write($path, $contents, $this->config->extend($config)->toArray());
} catch (UnableToWriteFile $exception) {
throw UnableToWriteFile::atLocation($location, $exception->reason(), $exception);
}
Expand All @@ -166,7 +172,7 @@ public function writeStream(string $location, $contents, array $config = []): vo
{
/** @var FilesystemOperator $filesystem */
[$filesystem, $path] = $this->determineFilesystemAndPath($location);
$filesystem->writeStream($path, $contents, $config);
$filesystem->writeStream($path, $contents, $this->config->extend($config)->toArray());
}

public function setVisibility(string $path, string $visibility): void
Expand Down Expand Up @@ -206,7 +212,7 @@ public function createDirectory(string $location, array $config = []): void
[$filesystem, $path] = $this->determineFilesystemAndPath($location);

try {
$filesystem->createDirectory($path, $config);
$filesystem->createDirectory($path, $this->config->extend($config)->toArray());
} catch (UnableToCreateDirectory $exception) {
throw UnableToCreateDirectory::dueToFailure($location, $exception);
}
Expand All @@ -224,7 +230,8 @@ public function move(string $source, string $destination, array $config = []): v
$sourcePath,
$destinationPath,
$source,
$destination
$destination,
$config,
) : $this->moveAcrossFilesystems($source, $destination, $config);
}

Expand All @@ -240,15 +247,16 @@ public function copy(string $source, string $destination, array $config = []): v
$sourcePath,
$destinationPath,
$source,
$destination
$destination,
$config,
) : $this->copyAcrossFilesystem(
$config['visibility'] ?? null,
$sourceFilesystem,
$sourcePath,
$destinationFilesystem,
$destinationPath,
$source,
$destination
$destination,
$config,
);
}

Expand All @@ -273,7 +281,7 @@ public function temporaryUrl(string $path, DateTimeInterface $expiresAt, array $
throw new UnableToGenerateTemporaryUrl(sprintf('%s does not support generating public urls.', $filesystem::class), $path);
}

return $filesystem->temporaryUrl($path, $expiresAt, $config);
return $filesystem->temporaryUrl($path, $expiresAt, $this->config->extend($config)->toArray());
}

public function checksum(string $path, array $config = []): string
Expand All @@ -285,7 +293,7 @@ public function checksum(string $path, array $config = []): string
throw new UnableToProvideChecksum(sprintf('%s does not support providing checksums.', $filesystem::class), $path);
}

return $filesystem->checksum($path, $config);
return $filesystem->checksum($path, $this->config->extend($config)->toArray());
}

private function mountFilesystems(array $filesystems): void
Expand Down Expand Up @@ -345,28 +353,36 @@ private function copyInSameFilesystem(
string $sourcePath,
string $destinationPath,
string $source,
string $destination
string $destination,
array $config,
): void {
try {
$sourceFilesystem->copy($sourcePath, $destinationPath);
$sourceFilesystem->copy($sourcePath, $destinationPath, $this->config->extend($config)->toArray());
} catch (UnableToCopyFile $exception) {
throw UnableToCopyFile::fromLocationTo($source, $destination, $exception);
}
}

private function copyAcrossFilesystem(
?string $visibility,
FilesystemOperator $sourceFilesystem,
string $sourcePath,
FilesystemOperator $destinationFilesystem,
string $destinationPath,
string $source,
string $destination
string $destination,
array $config,
): void {
$config = $this->config->extend($config);
$retainVisibility = (bool) $config->get('retain_visibility', true);
$visibility = $config->get('visibility');

try {
$visibility = $visibility ?? $sourceFilesystem->visibility($sourcePath);
if ($visibility == null && $retainVisibility) {
$visibility = $sourceFilesystem->visibility($sourcePath);
}

$stream = $sourceFilesystem->readStream($sourcePath);
$destinationFilesystem->writeStream($destinationPath, $stream, compact('visibility'));
$destinationFilesystem->writeStream($destinationPath, $stream, $visibility ? compact('visibility') : []);
} catch (UnableToRetrieveMetadata | UnableToReadFile | UnableToWriteFile $exception) {
throw UnableToCopyFile::fromLocationTo($source, $destination, $exception);
}
Expand All @@ -377,10 +393,11 @@ private function moveInTheSameFilesystem(
string $sourcePath,
string $destinationPath,
string $source,
string $destination
string $destination,
array $config,
): void {
try {
$sourceFilesystem->move($sourcePath, $destinationPath);
$sourceFilesystem->move($sourcePath, $destinationPath, $this->config->extend($config)->toArray());
} catch (UnableToMoveFile $exception) {
throw UnableToMoveFile::fromLocationTo($source, $destination, $exception);
}
Expand Down
9 changes: 7 additions & 2 deletions src/PhpseclibV3/SftpAdapter.php
Original file line number Diff line number Diff line change
Expand Up @@ -327,8 +327,13 @@ public function copy(string $source, string $destination, Config $config): void
{
try {
$readStream = $this->readStream($source);
$visibility = $this->visibility($source)->visibility();
$this->writeStream($destination, $readStream, new Config(compact('visibility')));
$visibility = $config->get(Config::OPTION_VISIBILITY);

if ($visibility === null && $config->get('retain_visibility', true)) {
$config = $config->withSetting(Config::OPTION_VISIBILITY, $this->visibility($source)->visibility());
}

$this->writeStream($destination, $readStream, $config);
} catch (Throwable $exception) {
if (isset($readStream) && is_resource($readStream)) {
@fclose($readStream);
Expand Down

0 comments on commit d15165f

Please sign in to comment.