diff --git a/tests/fixtures/media/october.png b/tests/fixtures/media/october.png new file mode 100644 index 000000000..abf039cf0 Binary files /dev/null and b/tests/fixtures/media/october.png differ diff --git a/tests/fixtures/themes/test/assets/images/october.png b/tests/fixtures/themes/test/assets/images/october.png new file mode 100644 index 000000000..abf039cf0 Binary files /dev/null and b/tests/fixtures/themes/test/assets/images/october.png differ diff --git a/tests/unit/system/classes/ImageResizerTest.php b/tests/unit/system/classes/ImageResizerTest.php index 239d0ac90..2a8187a70 100644 --- a/tests/unit/system/classes/ImageResizerTest.php +++ b/tests/unit/system/classes/ImageResizerTest.php @@ -4,68 +4,187 @@ use System\Classes\ImageResizer; use System\Classes\MediaLibrary; use System\Models\File as FileModel; use Cms\Classes\Controller as CmsController; +use DMS\PHPUnitExtensions\ArraySubset\ArraySubsetAsserts; class ImageResizerTest extends PluginTestCase { - // - // Tests - // + use ArraySubsetAsserts; + + public function tearDown(): void + { + $this->removeMedia(); + parent::tearDown(); + } + + public function testConfiguration() + { + // Resize with default options + $imageResizer = new ImageResizer( + (new CmsController())->themeUrl('assets/images/october.png'), + 100, + 100, + ); + self::assertArraySubset([ + 'width' => 100, + 'height' => 100, + 'options' => [ + 'mode' => 'auto', + 'offset' => [0, 0], + 'sharpen' => 0, + 'interlace' => false, + 'quality' => 90, + 'extension' => 'png', + ], + ], $imageResizer->getConfig()); + + // Resize with customised options + $imageResizer = new ImageResizer( + (new CmsController())->themeUrl('assets/images/october.png'), + 150, + 120, + [ + 'mode' => 'fit', + 'offset' => [2, 2], + 'sharpen' => 23, + 'interlace' => true, + 'quality' => 73, + 'extension' => 'jpg' + ] + ); + self::assertArraySubset([ + 'width' => 150, + 'height' => 120, + 'options' => [ + 'mode' => 'fit', + 'offset' => [2, 2], + 'sharpen' => 23, + 'interlace' => true, + 'quality' => 73, + 'extension' => 'jpg' + ], + ], $imageResizer->getConfig()); + + // Resize with an customised defaults + Event::listen('system.resizer.getDefaultOptions', function (&$options) { + $options = array_merge($options, [ + 'mode' => 'fit', + 'offset' => [2, 2], + 'sharpen' => 23, + 'interlace' => true, + 'quality' => 73, + ]); + }); + + $imageResizer = new ImageResizer( + (new CmsController())->themeUrl('assets/images/october.png'), + 100, + 100, + [], + ); + self::assertArraySubset([ + 'width' => 100, + 'height' => 100, + 'options' => [ + 'mode' => 'fit', + 'offset' => [2, 2], + 'sharpen' => 23, + 'interlace' => true, + 'quality' => 73, + 'extension' => 'png', + ], + ], $imageResizer->getConfig()); + + Event::forget('system.resizer.getDefaultOptions'); + } - /** - * Test the various sources that can be provided - * Need to verify that for each of the sources it's able to - * - identify that the desired image exists - * - identify the correct source for the image - * - and / or identify that the correct resizer URL is generated for the asset - * - * @NOTE: COMPLETELY WIP, ABSOLUTELY DOESN'T WORK RIGHT NOW - * - * Some examples of input to the Twig filter: - * {{ 'assets/images/logo.png' | theme | resize(false, false, {quality: 90}) }} - * {{ record.mediafinder_field | media | resize(200, false) }} - * {{ record.filemodel_property | resize(false, 200, {mode: 'contain'}) }} - * {{ record.filemodel_property.getPath() | resize(600, 202) }} - */ public function testSources() { - $sources = [ - 'themeUrl' => [ - 'source' => (new CmsController())->themeUrl('assets/images/october.png'), - 'target' => '', - ], - 'mediaUrl' => [ - 'source' => MediaLibrary::url('unamed.png'), - 'target' => '', - ], - 'pluginUrl' => [ - 'source' => URL::to('plugins/october/demo/assets/logo.png'), - 'target' => '', - ], - 'absoluteUrl' => [ - 'source' => 'https://example.com/themes/demo/assets/images/october.png', - 'target' => '', - ], - 'relativeUrl' => [ - 'source' => '/plugins/october/demo/assets/logo.png', - 'target' => '', - ], - 'moduleUrl' => [ - 'source' => Backend::skinAsset('assets/images/favicon.png'), - 'target' => '', - ], - 'fileUrl' => [ - 'source' => FileModel::first()->getPath(), - 'target' => '', - ], - 'fileInstance' => [ - 'source' => FileModel::first(), - 'target' => '', - ], - ]; + // Media URL + $this->setUpStorage(); + $this->copyMedia(); + + $imageResizer = new ImageResizer( + MediaLibrary::url('october.png'), + 100, + 100, + ); + $this->assertEquals('png', $imageResizer->getConfig()['options']['extension']); + + // Plugin URL (also tests absolute URLs) + $imageResizer = new ImageResizer( + URL::to('plugins/database/tester/assets/images/avatar.png'), + 100, + 100, + ); + $this->assertEquals('png', $imageResizer->getConfig()['options']['extension']); + + // Relative URL + $imageResizer = new ImageResizer( + '/plugins/database/tester/assets/images/avatar.png', + 100, + 100, + ); + $this->assertEquals('png', $imageResizer->getConfig()['options']['extension']); + + // Module URL + $imageResizer = new ImageResizer( + Backend::skinAsset('assets/images/favicon.png'), + 100, + 100, + ); + $this->assertEquals('png', $imageResizer->getConfig()['options']['extension']); + + // Still to test - FileModel URL and FileModel instance } public function testInvalidInput() { + $this->markTestIncomplete(); + $providedPath = '/plugins/october/demo/assets/NOTPRESENT.png'; } + + protected function setUpStorage() + { + $this->app->useStoragePath(base_path('storage/temp')); + + config(['filesystems.disks.test_local' => [ + 'driver' => 'local', + 'root' => storage_path('app'), + ]]); + + config(['cms.storage.media' => [ + 'disk' => 'test_local', + 'folder' => 'media', + 'path' => '/storage/temp/app/media', + ]]); + } + + protected function copyMedia() + { + $mediaPath = storage_path('app/media'); + + if (!is_dir($mediaPath)) { + mkdir($mediaPath, 0777, true); + } + + foreach (glob(base_path('tests/fixtures/media/*')) as $file) { + $path = pathinfo($file); + copy($file, $mediaPath . DIRECTORY_SEPARATOR . $path['basename']); + } + } + + protected function removeMedia() + { + if ($this->app->storagePath() !== base_path('storage/temp')) { + return; + } + + foreach (glob(storage_path('app/media/*')) as $file) { + unlink($file); + } + + rmdir(storage_path('app/media')); + rmdir(storage_path('app')); + } } diff --git a/tests/unit/system/classes/MediaLibraryTest.php b/tests/unit/system/classes/MediaLibraryTest.php index 6a281eba8..52b70333b 100644 --- a/tests/unit/system/classes/MediaLibraryTest.php +++ b/tests/unit/system/classes/MediaLibraryTest.php @@ -4,7 +4,7 @@ use System\Classes\MediaLibrary; class MediaLibraryTest extends TestCase // @codingStandardsIgnoreLine { - protected function tearDown() : void + public function tearDown(): void { $this->removeMedia(); parent::tearDown(); @@ -76,12 +76,17 @@ class MediaLibraryTest extends TestCase // @codingStandardsIgnoreLine $contents = MediaLibrary::instance()->listFolderContents(); $this->assertNotEmpty($contents, 'Media library item is not discovered'); + $this->assertCount(2, $contents); - $item = reset($contents); - $this->assertEquals('file', $item->type, 'Media library item does not have the right type'); - $this->assertEquals('/text.txt', $item->path, 'Media library item does not have the right path'); - $this->assertNotEmpty($item->lastModified, 'Media library item last modified is empty'); - $this->assertNotEmpty($item->size, 'Media library item size is empty'); + $this->assertEquals('file', $contents[0]->type, 'Media library item does not have the right type'); + $this->assertEquals('/october.png', $contents[0]->path, 'Media library item does not have the right path'); + $this->assertNotEmpty($contents[0]->lastModified, 'Media library item last modified is empty'); + $this->assertNotEmpty($contents[0]->size, 'Media library item size is empty'); + + $this->assertEquals('file', $contents[1]->type, 'Media library item does not have the right type'); + $this->assertEquals('/text.txt', $contents[1]->path, 'Media library item does not have the right path'); + $this->assertNotEmpty($contents[1]->lastModified, 'Media library item last modified is empty'); + $this->assertNotEmpty($contents[1]->size, 'Media library item size is empty'); } protected function setUpStorage()