Skip to content

Commit

Permalink
[Tests] Added test coverage for the new Flysystem v2 integration
Browse files Browse the repository at this point in the history
  • Loading branch information
alongosz committed Dec 12, 2022
1 parent 5bb01b3 commit eaed080
Show file tree
Hide file tree
Showing 7 changed files with 797 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,278 @@
<?php

/**
* @copyright Copyright (C) Ibexa AS. All rights reserved.
* @license For full copyright and license information view LICENSE file distributed with this source code.
*/
declare(strict_types=1);

namespace Ibexa\Tests\Core\IO\Flysystem\Adapter;

use Ibexa\Core\IO\Flysystem\Adapter\LocalSiteAccessAwareFilesystemAdapter;
use Ibexa\Core\IO\Flysystem\PathPrefixer\PathPrefixerInterface;
use League\Flysystem\Config;
use League\Flysystem\FilesystemAdapter;
use League\Flysystem\UnixVisibility\PortableVisibilityConverter;
use League\Flysystem\Visibility;
use League\MimeTypeDetection\MimeTypeDetector;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Filesystem\Filesystem;

/**
* Test proxying of Flysystem's {@see \League\Flysystem\Local\LocalFilesystemAdapter} methods by
* {@see \Ibexa\Core\IO\Flysystem\Adapter\LocalSiteAccessAwareFilesystemAdapter}.
*
* Note: SiteAccess-aware aspect has been tested via PathPrefixer and Visibility converter test cases:
* {@see \Ibexa\Tests\Core\IO\Flysystem\VisibilityConverter\BaseVisibilityConverterTest}
* {@see \Ibexa\Tests\Core\IO\Flysystem\PathPrefixer\DFSSiteAccessAwarePathPrefixerTest}
*/
final class LocalSiteAccessAwareFilesystemAdapterTest extends TestCase
{
private const FLYSYSTEM_TEST_DIR = __DIR__ . '/_flysystem';
private const RELATIVE_FILE_PATH = 'foo/bar.file';
private const RELATIVE_FILE_COPY_PATH = '/bar.copy';
private const ABSOLUTE_FILE_PATH = self::FLYSYSTEM_TEST_DIR . '/' . self::RELATIVE_FILE_PATH;
private const ABSOLUTE_FILE_COPY_PATH = self::FLYSYSTEM_TEST_DIR . self::RELATIVE_FILE_COPY_PATH;
private const PREFIX_PATH_RETURN_MAP = [
[self::RELATIVE_FILE_PATH, self::ABSOLUTE_FILE_PATH],
[self::RELATIVE_FILE_COPY_PATH, self::ABSOLUTE_FILE_COPY_PATH],
['/', self::FLYSYSTEM_TEST_DIR],
['/my_dir', self::FLYSYSTEM_TEST_DIR . '/my_dir'],
];
private const STRIP_PREFIX_RETURN_MAP = [
[self::ABSOLUTE_FILE_PATH, '/' . self::RELATIVE_FILE_PATH],
[self::ABSOLUTE_FILE_COPY_PATH, self::RELATIVE_FILE_COPY_PATH],
[self::FLYSYSTEM_TEST_DIR, '/'],
[self::FLYSYSTEM_TEST_DIR . '/my_dir', '/my_dir'],
];
private const FILE_CONTENTS = 'FOO BAR';

private FilesystemAdapter $adapter;

private Config $config;

public static function setUpBeforeClass(): void
{
if (!is_dir(self::FLYSYSTEM_TEST_DIR)) {
mkdir(self::FLYSYSTEM_TEST_DIR);
}
}

public static function tearDownAfterClass(): void
{
$fileSystem = new Filesystem();
$iterator = new \RecursiveDirectoryIterator(self::FLYSYSTEM_TEST_DIR);
foreach ($iterator as $fileOrDir) {
$fileSystem->remove($fileOrDir);
}
}

protected function setUp(): void
{
$this->adapter = new LocalSiteAccessAwareFilesystemAdapter(
self::FLYSYSTEM_TEST_DIR,
new PortableVisibilityConverter(),
$this->createPathPrefixerMock(),
$this->createMock(MimeTypeDetector::class)
);

$this->config = new Config(
[
Config::OPTION_VISIBILITY => Visibility::PUBLIC,
Config::OPTION_DIRECTORY_VISIBILITY => Visibility::PUBLIC,
]
);
}

/**
* @throws \League\Flysystem\FilesystemException
*/
public function testWrite(): string
{
$this->adapter->write(self::RELATIVE_FILE_PATH, self::FILE_CONTENTS, $this->config);

self::assertFileExists(self::ABSOLUTE_FILE_PATH);

return self::RELATIVE_FILE_PATH;
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testWriteStream(): void
{
// re-use file path for testCopy to copy using writeStream
$this->adapter->writeStream(
self::RELATIVE_FILE_COPY_PATH,
fopen(self::ABSOLUTE_FILE_PATH, 'rb'),
$this->config
);
self::assertFileExists(self::ABSOLUTE_FILE_COPY_PATH);
// unlink to not affect testCopy
unlink(self::ABSOLUTE_FILE_COPY_PATH);
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testFileSize(string $relativeFilePath): void
{
self::assertEquals(
strlen(self::FILE_CONTENTS),
$this->adapter->fileSize($relativeFilePath)->fileSize()
);
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testFileExists(string $relativeFilePath): void
{
self::assertTrue($this->adapter->fileExists($relativeFilePath));
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testLastModified(string $relativeFilePath): void
{
self::assertEquals(
filemtime(self::ABSOLUTE_FILE_PATH),
$this->adapter->lastModified($relativeFilePath)->lastModified()
);
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testCopy(string $relativeFilePath): string
{
$this->adapter->copy($relativeFilePath, self::RELATIVE_FILE_COPY_PATH, $this->config);
self::assertFileExists(self::ABSOLUTE_FILE_COPY_PATH);

return $relativeFilePath;
}

/**
* @depends testCopy
* @depends testRead
* @depends testReadStream
* @depends testVisibility
*
* @throws \League\Flysystem\FilesystemException
*/
public function testMove(string $relativeFilePath): void
{
$this->adapter->move($relativeFilePath, self::RELATIVE_FILE_COPY_PATH, $this->config);
self::assertFileExists(self::ABSOLUTE_FILE_COPY_PATH);
self::assertFileNotExists(self::ABSOLUTE_FILE_PATH);
}

/**
* @depends testCopy
* @depends testWriteStream
*
* @throws \League\Flysystem\FilesystemException
*/
public function testListContents(): void
{
$expectedRootDirectoryContents = [
'/foo',
'/foo/bar.file',
'/bar.copy',
];
$rootDirectoryContents = $this->adapter->listContents('/', true);
foreach ($rootDirectoryContents as $storageAttributes) {
self::assertContains($storageAttributes->path(), $expectedRootDirectoryContents);
}
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testRead(string $relativeFilePath): void
{
self::assertSame(self::FILE_CONTENTS, $this->adapter->read($relativeFilePath));
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testReadStream(string $relativeFilePath): void
{
$fileHandle = $this->adapter->readStream($relativeFilePath);
self::assertIsResource($fileHandle);
// try to read more than expected to make sure there's no trailing data
$contents = fread($fileHandle, strlen(self::FILE_CONTENTS) + 1);
self::assertIsString($contents);
self::assertSame(self::FILE_CONTENTS, $contents);
}

/**
* @throws \League\Flysystem\FilesystemException
*/
public function testCreateDirectory(): string
{
$directoryPathName = '/my_dir';
$this->adapter->createDirectory($directoryPathName, $this->config);
self::assertDirectoryExists(self::FLYSYSTEM_TEST_DIR . $directoryPathName);

return $directoryPathName;
}

/**
* @depends testCreateDirectory
*
* @throws \League\Flysystem\FilesystemException
*/
public function testDeleteDirectory(string $relativeDirectoryPath): void
{
$this->adapter->deleteDirectory($relativeDirectoryPath);
self::assertDirectoryNotExists(self::FLYSYSTEM_TEST_DIR . $relativeDirectoryPath);
}

/**
* @depends testWrite
*
* @throws \League\Flysystem\FilesystemException
*/
public function testVisibility(string $relativeFilePath): void
{
self::assertSame(
Visibility::PUBLIC,
$this->adapter->visibility($relativeFilePath)->visibility()
);
}

private function createPathPrefixerMock(): PathPrefixerInterface
{
$prefixerMock = $this->createMock(PathPrefixerInterface::class);
$prefixerMock
->method('prefixPath')
->willReturnMap(self::PREFIX_PATH_RETURN_MAP);

$stripPrefixReturnMap = self::STRIP_PREFIX_RETURN_MAP;
// add inner directory for iterator purposes
$stripPrefixReturnMap[] = [dirname(self::ABSOLUTE_FILE_PATH), '/foo'];

$prefixerMock
->method('stripPrefix')
->willReturnMap($stripPrefixReturnMap);

return $prefixerMock;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
<?php

/**
* @copyright Copyright (C) Ibexa AS. All rights reserved.
* @license For full copyright and license information view LICENSE file distributed with this source code.
*/
declare(strict_types=1);

namespace Ibexa\Tests\Core\IO\Flysystem\PathPrefixer;

use Ibexa\Core\IO\Flysystem\PathPrefixer\PathPrefixerInterface;
use Ibexa\Tests\Core\Search\TestCase;

/**
* @covers \Ibexa\Core\IO\Flysystem\PathPrefixer\PathPrefixerInterface
*/
abstract class BaseSiteAccessAwarePathPrefixerTest extends TestCase
{
abstract protected function getPrefixer(): PathPrefixerInterface;

abstract public function getDataForTestPrefixPath(): iterable;

abstract public function getDataForTestPrefixDirectoryPath(): iterable;

abstract public function getDataForTestStripPrefixPath(): iterable;

public function getDataForTestStripDirectoryPrefix(): iterable
{
// treat file names as directories
yield from $this->getDataForTestStripPrefixPath();
}

/**
* @dataProvider getDataForTestPrefixPath
*/
public function testPrefixPath(string $expectedPrefixedPath, string $path): void
{
self::assertSame(
$expectedPrefixedPath,
$this->getPrefixer()->prefixPath($path)
);
}

/**
* @dataProvider getDataForTestPrefixDirectoryPath
*/
public function testPrefixDirectoryPath(string $expectedPrefixedPath, string $path): void
{
self::assertSame(
$expectedPrefixedPath,
$this->getPrefixer()->prefixDirectoryPath($path)
);
}

/**
* @dataProvider getDataForTestStripPrefixPath
*/
public function testStripPrefix(string $expectedStrippedPath, string $path): void
{
self::assertSame(
$expectedStrippedPath,
$this->getPrefixer()->stripPrefix($path)
);
}

/**
* @dataProvider getDataForTestStripDirectoryPrefix
*/
public function testStripDirectoryPrefix(string $expectedStrippedPath, string $path): void
{
self::assertSame(
$expectedStrippedPath,
$this->getPrefixer()->stripDirectoryPrefix($path)
);
}
}
Loading

0 comments on commit eaed080

Please sign in to comment.