diff --git a/MediaGalleryRenditionsApi/Model/Config.php b/MediaGalleryRenditions/Model/Config.php similarity index 80% rename from MediaGalleryRenditionsApi/Model/Config.php rename to MediaGalleryRenditions/Model/Config.php index e558f23ab960..f521d85d0687 100644 --- a/MediaGalleryRenditionsApi/Model/Config.php +++ b/MediaGalleryRenditions/Model/Config.php @@ -6,7 +6,7 @@ declare(strict_types=1); -namespace Magento\MediaGalleryRenditionsApi\Model; +namespace Magento\MediaGalleryRenditions\Model; use Magento\Framework\App\Config\ScopeConfigInterface; @@ -31,7 +31,6 @@ class Config private $scopeConfig; /** - * Config constructor. * @param ScopeConfigInterface $scopeConfig */ public function __construct( @@ -47,7 +46,7 @@ public function __construct( */ public function getWidth(): int { - return $this->scopeConfig->getValue(self::XML_PATH_MEDIA_GALLERY_RENDITIONS_WIDTH_PATH); + return (int) $this->scopeConfig->getValue(self::XML_PATH_MEDIA_GALLERY_RENDITIONS_WIDTH_PATH); } /** @@ -57,6 +56,6 @@ public function getWidth(): int */ public function getHeight(): int { - return $this->scopeConfig->getValue(self::XML_PATH_MEDIA_GALLERY_RENDITIONS_HEIGHT_PATH); + return (int) $this->scopeConfig->getValue(self::XML_PATH_MEDIA_GALLERY_RENDITIONS_HEIGHT_PATH); } } diff --git a/MediaGalleryRenditions/Model/GenerateRenditions.php b/MediaGalleryRenditions/Model/GenerateRenditions.php new file mode 100644 index 000000000000..ba82fe2bf293 --- /dev/null +++ b/MediaGalleryRenditions/Model/GenerateRenditions.php @@ -0,0 +1,130 @@ +imageFactory = $imageFactory; + $this->config = $config; + $this->getRenditionPath = $getRenditionPath; + $this->filesystem = $filesystem; + $this->isRenditionRequired = $isRenditionRequired; + $this->driver = $driver; + } + + /** + * @inheritdoc + */ + public function execute(array $paths): void + { + foreach ($paths as $path) { + $mediaDirectory = $this->filesystem->getDirectoryRead(DirectoryList::MEDIA); + $absolutePath = $mediaDirectory->getAbsolutePath($path); + if (!$this->isRenditionRequired->execute($absolutePath)) { + continue; + } + + $renditionPath = $this->getRenditionPath->execute($path); + $this->createDirectory($renditionPath); + + try { + $this->createRendition($absolutePath, $mediaDirectory->getAbsolutePath($renditionPath)); + } catch (\Exception $exception) { + throw new LocalizedException( + __('Cannot create rendition for media asset %path', ['path' => $path]) + ); + } + } + } + + /** + * Create directory for rendition file + * + * @param string $path + * @throws LocalizedException + */ + private function createDirectory(string $path): void + { + try { + $this->filesystem->getDirectoryWrite(DirectoryList::MEDIA) + ->create($this->driver->getParentDirectory($path)); + } catch (\Exception $exception) { + throw new LocalizedException(__('Cannot create directory for rendition %path', ['path' => $path])); + } + } + + /** + * Create rendition file + * + * @param string $absolutePath + * @param string $absoluteRenditionPath + * @throws \Exception + */ + private function createRendition(string $absolutePath, string $absoluteRenditionPath): void + { + $image = $this->imageFactory->create(); + $image->open($absolutePath); + $image->keepAspectRatio(true); + $image->resize($this->config->getWidth(), $this->config->getHeight()); + $image->save($absoluteRenditionPath); + } +} diff --git a/MediaGalleryRenditions/Model/GetRenditionPath.php b/MediaGalleryRenditions/Model/GetRenditionPath.php new file mode 100644 index 000000000000..c0568e4f4593 --- /dev/null +++ b/MediaGalleryRenditions/Model/GetRenditionPath.php @@ -0,0 +1,72 @@ +filesystem = $filesystem; + $this->isRenditionRequired = $isRenditionRequired; + } + + /** + * Returns Rendition image path + * + * @param string $path + * @return string + */ + public function execute(string $path) :string + { + $mediaDirectory = $this->getMediaDirectory(); + + if (!$mediaDirectory->isFile($path)) { + throw new LocalizedException(__('Media asset file %path does not exist!', ['path' => $path])); + } + + if (!$this->isRenditionRequired->execute($mediaDirectory->getAbsolutePath($path))) { + return $path; + } + + return self::RENDITIONS_DIRECTORY_NAME . '/' . ltrim($path, '/'); + } + + /** + * Retrieve media directory instance with read access + * + * @return ReadInterface + */ + private function getMediaDirectory(): ReadInterface + { + return $this->filesystem->getDirectoryRead(DirectoryList::MEDIA); + } +} diff --git a/MediaGalleryRenditions/Model/IsRenditionRequired.php b/MediaGalleryRenditions/Model/IsRenditionRequired.php new file mode 100644 index 000000000000..c46c1da3812c --- /dev/null +++ b/MediaGalleryRenditions/Model/IsRenditionRequired.php @@ -0,0 +1,37 @@ +config = $config; + } + + /** + * Check if image needs to resize or not + * + * @param string $absolutePath + * @return bool + */ + public function execute(string $absolutePath): bool + { + [$width, $height] = getimagesize($absolutePath); + return $width > $this->config->getWidth() || $height > $this->config->getHeight(); + } +} diff --git a/MediaGalleryRenditions/Plugin/CreateRenditions.php b/MediaGalleryRenditions/Plugin/CreateRenditions.php new file mode 100644 index 000000000000..89dfa3813323 --- /dev/null +++ b/MediaGalleryRenditions/Plugin/CreateRenditions.php @@ -0,0 +1,44 @@ +generateRenditions = $generateRenditions; + } + + /** + * Create renditions for synced files. + * + * @param ImportFilesComposite $subject + * @param string[] $paths + * @SuppressWarnings(PHPMD.UnusedFormalParameter) + */ + public function beforeExecute(ImportFilesComposite $subject, array $paths): array + { + $this->generateRenditions->execute($paths); + + return [$paths]; + } +} diff --git a/MediaGalleryRenditions/composer.json b/MediaGalleryRenditions/composer.json index 50b18752fc50..8704effe630a 100644 --- a/MediaGalleryRenditions/composer.json +++ b/MediaGalleryRenditions/composer.json @@ -3,7 +3,9 @@ "description": "Magento module that implements height and width fields for for media gallery items.", "require": { "php": "~7.3.0||~7.4.0", - "magento/framework": "*" + "magento/framework": "*", + "magento/module-media-gallery-renditions-api": "*", + "magento/module-media-gallery-synchronization-api": "*" }, "type": "magento2-module", "license": [ diff --git a/MediaGalleryRenditions/etc/di.xml b/MediaGalleryRenditions/etc/di.xml new file mode 100644 index 000000000000..6b95189efc6c --- /dev/null +++ b/MediaGalleryRenditions/etc/di.xml @@ -0,0 +1,14 @@ + + + + + + + + + diff --git a/MediaGalleryRenditions/etc/module.xml b/MediaGalleryRenditions/etc/module.xml index 792a9e128cc4..93bc9f1c214e 100644 --- a/MediaGalleryRenditions/etc/module.xml +++ b/MediaGalleryRenditions/etc/module.xml @@ -6,5 +6,5 @@ */ --> - + diff --git a/MediaGalleryRenditionsApi/Api/GenerateRenditionsInterface.php b/MediaGalleryRenditionsApi/Api/GenerateRenditionsInterface.php new file mode 100644 index 000000000000..6684fcc47b6c --- /dev/null +++ b/MediaGalleryRenditionsApi/Api/GenerateRenditionsInterface.php @@ -0,0 +1,21 @@ + - +