Skip to content

Commit e83fc73

Browse files
committed
MC-17765: Category A image replaced by uploading to Category B
1 parent c7c66ad commit e83fc73

File tree

4 files changed

+93
-14
lines changed

4 files changed

+93
-14
lines changed

app/code/Magento/Catalog/Model/Category/Attribute/Backend/Image.php

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,9 @@
55
*/
66
namespace Magento\Catalog\Model\Category\Attribute\Backend;
77

8+
use Magento\Catalog\Model\ImageUploader;
89
use Magento\Framework\App\Filesystem\DirectoryList;
10+
use Magento\Framework\File\Uploader;
911

1012
/**
1113
* Catalog category image attribute backend model
@@ -84,6 +86,27 @@ private function getUploadedImageName($value)
8486
return '';
8587
}
8688

89+
/**
90+
* Check that image name exists in catalog/category directory and return new image name if it already exists.
91+
*
92+
* @param string $imageName
93+
* @return string
94+
*/
95+
private function checkUniqueImageName(string $imageName): string
96+
{
97+
$imageUploader = $this->getImageUploader();
98+
$mediaDirectory = $this->_filesystem->getDirectoryWrite(DirectoryList::MEDIA);
99+
$imageAbsolutePath = $mediaDirectory->getAbsolutePath(
100+
$imageUploader->getBasePath() . DIRECTORY_SEPARATOR . $imageName
101+
);
102+
103+
if ($mediaDirectory->isExist($imageAbsolutePath)) {
104+
$imageName = Uploader::getNewFilename($imageAbsolutePath);
105+
}
106+
107+
return $imageName;
108+
}
109+
87110
/**
88111
* Avoiding saving potential upload data to DB
89112
* Will set empty image attribute value if image was not uploaded
@@ -103,6 +126,7 @@ public function beforeSave($object)
103126
}
104127

105128
if ($imageName = $this->getUploadedImageName($value)) {
129+
$imageName = $this->checkUniqueImageName($imageName);
106130
$object->setData($this->additionalData . $attributeName, $value);
107131
$object->setData($attributeName, $imageName);
108132
} elseif (!is_string($value)) {
@@ -113,15 +137,15 @@ public function beforeSave($object)
113137
}
114138

115139
/**
116-
* @return \Magento\Catalog\Model\ImageUploader
140+
* @return ImageUploader
117141
*
118142
* @deprecated 101.0.0
119143
*/
120144
private function getImageUploader()
121145
{
122146
if ($this->imageUploader === null) {
123147
$this->imageUploader = \Magento\Framework\App\ObjectManager::getInstance()
124-
->get(\Magento\Catalog\CategoryImageUpload::class);
148+
->get(ImageUploader::class);
125149
}
126150

127151
return $this->imageUploader;

app/code/Magento/Catalog/Model/ImageUploader.php

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
*/
66
namespace Magento\Catalog\Model;
77

8+
use Magento\Framework\File\Uploader;
9+
810
/**
911
* Catalog image uploader
1012
*/
@@ -202,6 +204,11 @@ public function moveFileFromTmp($imageName)
202204
$baseImagePath = $this->getFilePath($basePath, $imageName);
203205
$baseTmpImagePath = $this->getFilePath($baseTmpPath, $imageName);
204206

207+
if ($this->mediaDirectory->isExist($baseImagePath)) {
208+
$newImageName = Uploader::getNewFileName($this->mediaDirectory->getAbsolutePath($baseImagePath));
209+
$baseImagePath = $this->getFilePath($basePath, $newImageName);
210+
}
211+
205212
try {
206213
$this->coreFileStorageDatabase->copyFile(
207214
$baseTmpImagePath,

app/code/Magento/Catalog/Test/Unit/Model/Category/Attribute/Backend/ImageTest.php

Lines changed: 34 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,9 @@
55
*/
66
namespace Magento\Catalog\Test\Unit\Model\Category\Attribute\Backend;
77

8+
use Magento\Catalog\Model\ImageUploader;
89
use Magento\Framework\App\Filesystem\DirectoryList;
10+
use Magento\Framework\Filesystem\Directory\WriteInterface;
911

1012
class ImageTest extends \PHPUnit\Framework\TestCase
1113
{
@@ -67,7 +69,7 @@ protected function setUp()
6769

6870
$this->imageUploader = $this->createPartialMock(
6971
\Magento\Catalog\Model\ImageUploader::class,
70-
['moveFileFromTmp']
72+
['moveFileFromTmp', 'getBasePath']
7173
);
7274

7375
$this->filesystem = $this->getMockBuilder(\Magento\Framework\Filesystem::class)->disableOriginalConstructor()
@@ -146,8 +148,21 @@ public function testBeforeSaveValueInvalid($value)
146148
*/
147149
public function testBeforeSaveAttributeFileName()
148150
{
149-
$model = $this->objectManager->getObject(\Magento\Catalog\Model\Category\Attribute\Backend\Image::class);
150-
$model->setAttribute($this->attribute);
151+
$model = $this->setUpModelForAfterSave();
152+
$mediaDirectoryMock = $this->createMock(WriteInterface::class);
153+
$this->filesystem->expects($this->once())
154+
->method('getDirectoryWrite')
155+
->with(DirectoryList::MEDIA)
156+
->willReturn($mediaDirectoryMock);
157+
$this->imageUploader->expects($this->once())->method('getBasePath')->willReturn('base/path');
158+
$mediaDirectoryMock->expects($this->once())
159+
->method('getAbsolutePath')
160+
->with('base/path/test123.jpg')
161+
->willReturn('absolute/path/base/path/test123.jpg');
162+
$mediaDirectoryMock->expects($this->once())
163+
->method('isExist')
164+
->with('absolute/path/base/path/test123.jpg')
165+
->willReturn(false);
151166

152167
$object = new \Magento\Framework\DataObject([
153168
'test_attribute' => [
@@ -165,12 +180,14 @@ public function testBeforeSaveAttributeFileName()
165180
*/
166181
public function testBeforeSaveAttributeFileNameOutsideOfCategoryDir()
167182
{
168-
$model = $this->objectManager->getObject(\Magento\Catalog\Model\Category\Attribute\Backend\Image::class, [
169-
'filesystem' => $this->filesystem
170-
]);
171-
183+
$model = $this->setUpModelForAfterSave();
172184
$model->setAttribute($this->attribute);
173185

186+
$mediaDirectoryMock = $this->createMock(WriteInterface::class);
187+
$this->filesystem->expects($this->once())
188+
->method('getDirectoryWrite')
189+
->with(DirectoryList::MEDIA)
190+
->willReturn($mediaDirectoryMock);
174191
$this->filesystem
175192
->expects($this->once())
176193
->method('getUri')
@@ -200,9 +217,15 @@ public function testBeforeSaveAttributeFileNameOutsideOfCategoryDir()
200217
*/
201218
public function testBeforeSaveTemporaryAttribute()
202219
{
203-
$model = $this->objectManager->getObject(\Magento\Catalog\Model\Category\Attribute\Backend\Image::class);
220+
$model = $this->setUpModelForAfterSave();
204221
$model->setAttribute($this->attribute);
205222

223+
$mediaDirectoryMock = $this->createMock(WriteInterface::class);
224+
$this->filesystem->expects($this->once())
225+
->method('getDirectoryWrite')
226+
->with(DirectoryList::MEDIA)
227+
->willReturn($mediaDirectoryMock);
228+
206229
$object = new \Magento\Framework\DataObject([
207230
'test_attribute' => [
208231
['name' => 'test123.jpg', 'tmp_name' => 'abc123', 'url' => 'http://www.example.com/test123.jpg']
@@ -246,7 +269,7 @@ private function setUpModelForAfterSave()
246269
$objectManagerMock->expects($this->any())
247270
->method('get')
248271
->will($this->returnCallback(function ($class, $params = []) use ($imageUploaderMock) {
249-
if ($class == \Magento\Catalog\CategoryImageUpload::class) {
272+
if ($class == ImageUploader::class) {
250273
return $imageUploaderMock;
251274
}
252275

@@ -255,7 +278,8 @@ private function setUpModelForAfterSave()
255278

256279
$model = $this->objectManager->getObject(\Magento\Catalog\Model\Category\Attribute\Backend\Image::class, [
257280
'objectManager' => $objectManagerMock,
258-
'logger' => $this->logger
281+
'logger' => $this->logger,
282+
'filesystem' => $this->filesystem,
259283
]);
260284
$this->objectManager->setBackwardCompatibleProperty($model, 'imageUploader', $this->imageUploader);
261285

dev/tests/integration/testsuite/Magento/Catalog/Model/ImageUploaderTest.php

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,8 +47,8 @@ protected function setUp()
4747
$this->imageUploader = $this->objectManager->create(
4848
\Magento\Catalog\Model\ImageUploader::class,
4949
[
50-
'baseTmpPath' => $this->mediaDirectory->getRelativePath('tmp'),
51-
'basePath' => __DIR__,
50+
'baseTmpPath' => $this->mediaDirectory->getRelativePath('catalog/tmp/category'),
51+
'basePath' => $this->mediaDirectory->getRelativePath('catalog/category'),
5252
'allowedExtensions' => ['jpg', 'jpeg', 'gif', 'png'],
5353
'allowedMimeTypes' => ['image/jpg', 'image/jpeg', 'image/gif', 'image/png']
5454
]
@@ -79,6 +79,29 @@ public function testSaveFileToTmpDir(): void
7979
$this->assertTrue(is_file($this->mediaDirectory->getAbsolutePath($filePath)));
8080
}
8181

82+
public function testMoveFileFromTmp(): void
83+
{
84+
$fileName = 'magento_small_image.jpg';
85+
$expectedFileName = 'magento_small_image_1.jpg';
86+
$fixtureDir = realpath(__DIR__ . '/../_files');
87+
$tmpFilePath = $this->imageUploader->getBaseTmpPath() . DIRECTORY_SEPARATOR. $fileName;
88+
$this->mediaDirectory->create($this->imageUploader->getBaseTmpPath());
89+
90+
copy($fixtureDir . DIRECTORY_SEPARATOR . $fileName, $this->mediaDirectory->getAbsolutePath($tmpFilePath));
91+
92+
$this->imageUploader->moveFileFromTmp($fileName);
93+
94+
$filePath = $this->imageUploader->getBasePath() . DIRECTORY_SEPARATOR . $fileName;
95+
$this->assertTrue(is_file($this->mediaDirectory->getAbsolutePath($filePath)));
96+
97+
copy($fixtureDir . DIRECTORY_SEPARATOR . $fileName, $this->mediaDirectory->getAbsolutePath($tmpFilePath));
98+
99+
$this->imageUploader->moveFileFromTmp($fileName);
100+
101+
$expectedFilePath = $this->imageUploader->getBasePath() . DIRECTORY_SEPARATOR . $expectedFileName;
102+
$this->assertTrue(is_file($this->mediaDirectory->getAbsolutePath($expectedFilePath)));
103+
}
104+
82105
/**
83106
* @expectedException \Magento\Framework\Exception\LocalizedException
84107
* @expectedExceptionMessage File validation failed.
@@ -143,5 +166,6 @@ public static function tearDownAfterClass()
143166
/** @var \Magento\Framework\Filesystem\Directory\WriteInterface $mediaDirectory */
144167
$mediaDirectory = $filesystem->getDirectoryWrite(DirectoryList::MEDIA);
145168
$mediaDirectory->delete('tmp');
169+
$mediaDirectory->delete('catalog');
146170
}
147171
}

0 commit comments

Comments
 (0)