Skip to content

Commit b08b7ea

Browse files
Merge pull request #8971 from magento-cia/cia-2.4.8-beta1-develop-bugfix-05292024
Cia 2.4.8 beta1 develop bugfix 05292024
2 parents f43c7df + 0c34997 commit b08b7ea

File tree

9 files changed

+142
-48
lines changed

9 files changed

+142
-48
lines changed

app/code/Magento/Config/Model/Config/Backend/File.php

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -278,8 +278,10 @@ protected function _getAllowedExtensions()
278278
*/
279279
private function setValueAfterValidation(string $value): void
280280
{
281-
// avoid intercepting value
282-
if (preg_match('/[^a-z0-9_\/\\-\\.]+/i', $value)) {
281+
if (preg_match('/[^a-z0-9_\/\\-\\.]+/i', $value)
282+
// phpcs:ignore Magento2.Functions.DiscouragedFunction
283+
|| !$this->_mediaDirectory->isFile($this->_getUploadDir() . DIRECTORY_SEPARATOR . basename($value))
284+
) {
283285
throw new LocalizedException(__('Invalid file name'));
284286
}
285287

app/code/Magento/ImportExport/Controller/Adminhtml/Export/File/Download.php

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@
1616
use Magento\Framework\Filesystem;
1717
use Magento\ImportExport\Model\LocalizedFileName;
1818
use Throwable;
19+
use Magento\Framework\Controller\Result\Redirect;
20+
use Magento\Framework\App\ResponseInterface;
1921

2022
/**
2123
* Controller that download file by name.
@@ -25,7 +27,7 @@ class Download extends ExportController implements HttpGetActionInterface
2527
/**
2628
* Url to this controller
2729
*/
28-
const URL = 'adminhtml/export_file/download/';
30+
public const URL = 'adminhtml/export_file/download/';
2931

3032
/**
3133
* @var FileFactory
@@ -64,13 +66,24 @@ public function __construct(
6466
/**
6567
* Controller basic method implementation.
6668
*
67-
* @return \Magento\Framework\Controller\Result\Redirect | \Magento\Framework\App\ResponseInterface
69+
* @return Redirect|ResponseInterface
6870
*/
6971
public function execute()
7072
{
7173
$resultRedirect = $this->resultRedirectFactory->create();
7274
$resultRedirect->setPath('adminhtml/export/index');
75+
7376
$fileName = $this->getRequest()->getParam('filename');
77+
78+
if (empty($fileName)) {
79+
$this->messageManager->addErrorMessage(__('Please provide valid export file name'));
80+
81+
return $resultRedirect;
82+
}
83+
84+
// phpcs:ignore Magento2.Functions.DiscouragedFunction
85+
$fileName = basename($fileName);
86+
7487
$exportDirectory = $this->filesystem->getDirectoryRead(DirectoryList::VAR_IMPORT_EXPORT);
7588

7689
try {

app/code/Magento/ImportExport/Controller/Adminhtml/History/Download.php

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,18 @@
33
* Copyright © Magento, Inc. All rights reserved.
44
* See COPYING.txt for license details.
55
*/
6+
7+
declare(strict_types=1);
8+
69
namespace Magento\ImportExport\Controller\Adminhtml\History;
710

811
use Magento\Framework\App\Action\HttpGetActionInterface;
912
use Magento\Framework\App\Filesystem\DirectoryList;
13+
use Magento\Framework\Controller\ResultInterface;
14+
use Magento\ImportExport\Helper\Report;
1015
use Magento\ImportExport\Model\Import;
16+
use Magento\Framework\Controller\Result\Redirect;
17+
use Magento\Framework\App\ResponseInterface;
1118

1219
/**
1320
* Download history controller
@@ -44,20 +51,27 @@ public function __construct(
4451
/**
4552
* Download backup action
4653
*
47-
* @return void|\Magento\Backend\App\Action
54+
* @return ResponseInterface|Redirect|ResultInterface
55+
* @throws \Exception
4856
*/
4957
public function execute()
5058
{
59+
$resultRedirect = $this->resultRedirectFactory->create();
60+
$resultRedirect->setPath('*/history');
61+
62+
$fileName = $this->getRequest()->getParam('filename');
63+
64+
if (empty($fileName)) {
65+
return $resultRedirect;
66+
}
67+
5168
// phpcs:ignore Magento2.Functions.DiscouragedFunction
52-
$fileName = basename($this->getRequest()->getParam('filename'));
69+
$fileName = basename($fileName);
5370

54-
/** @var \Magento\ImportExport\Helper\Report $reportHelper */
55-
$reportHelper = $this->_objectManager->get(\Magento\ImportExport\Helper\Report::class);
71+
/** @var Report $reportHelper */
72+
$reportHelper = $this->_objectManager->get(Report::class);
5673

5774
if (!$reportHelper->importFileExists($fileName)) {
58-
/** @var \Magento\Backend\Model\View\Result\Redirect $resultRedirect */
59-
$resultRedirect = $this->resultRedirectFactory->create();
60-
$resultRedirect->setPath('*/history');
6175
return $resultRedirect;
6276
}
6377

app/code/Magento/ImportExport/Test/Unit/Controller/Adminhtml/History/DownloadTest.php

Lines changed: 25 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,13 @@
88
namespace Magento\ImportExport\Test\Unit\Controller\Adminhtml\History;
99

1010
use Magento\Backend\App\Action\Context;
11-
use Magento\Backend\Model\View\Result\Redirect;
1211
use Magento\Framework\App\Filesystem\DirectoryList;
1312
use Magento\Framework\App\Request\Http;
1413
use Magento\Framework\App\Response\Http\FileFactory;
1514
use Magento\Framework\App\ResponseInterface;
1615
use Magento\Framework\Controller\Result\Raw;
1716
use Magento\Framework\Controller\Result\RawFactory;
17+
use Magento\Framework\Controller\Result\Redirect;
1818
use Magento\Framework\Controller\Result\RedirectFactory;
1919
use Magento\Framework\TestFramework\Unit\Helper\ObjectManager as ObjectManagerHelper;
2020
use Magento\ImportExport\Controller\Adminhtml\History\Download;
@@ -181,8 +181,7 @@ public function executeDataProvider()
181181
{
182182
return [
183183
'Normal file name' => ['filename.csv', 'filename.csv'],
184-
'Relative file name' => ['../../../../../../../../etc/passwd', 'passwd'],
185-
'Empty file name' => ['', ''],
184+
'Relative file name' => ['../../../../../../../../etc/passwd', 'passwd']
186185
];
187186
}
188187

@@ -196,4 +195,27 @@ public function testExecuteFileNotFound()
196195
$this->resultRaw->expects($this->never())->method('setContents');
197196
$this->downloadController->execute();
198197
}
198+
199+
/**
200+
* Test execute() with return Redirect
201+
* @param string|null $requestFilename
202+
* @dataProvider executeWithRedirectDataProvider
203+
*/
204+
public function testExecuteWithRedirect(?string $requestFilename): void
205+
{
206+
$this->request->method('getParam')->with('filename')->willReturn($requestFilename);
207+
$this->resultRaw->expects($this->never())->method('setContents');
208+
$this->assertSame($this->redirect, $this->downloadController->execute());
209+
}
210+
211+
/**
212+
* @return array
213+
*/
214+
public function executeWithRedirectDataProvider(): array
215+
{
216+
return [
217+
'null file name' => [null],
218+
'empty file name' => [''],
219+
];
220+
}
199221
}

app/code/Magento/Integration/Block/Adminhtml/Integration/Edit/Tab/Info.php

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33
* Copyright © Magento, Inc. All rights reserved.
44
* See COPYING.txt for license details.
55
*/
6+
7+
declare(strict_types=1);
8+
69
namespace Magento\Integration\Block\Adminhtml\Integration\Edit\Tab;
710

811
use Magento\Integration\Controller\Adminhtml\Integration;
@@ -19,23 +22,23 @@ class Info extends \Magento\Backend\Block\Widget\Form\Generic implements \Magent
1922
/**#@+
2023
* Form elements names.
2124
*/
22-
const HTML_ID_PREFIX = 'integration_properties_';
25+
public const HTML_ID_PREFIX = 'integration_properties_';
2326

24-
const DATA_ID = 'integration_id';
27+
public const DATA_ID = 'integration_id';
2528

26-
const DATA_NAME = 'name';
29+
public const DATA_NAME = 'name';
2730

28-
const DATA_EMAIL = 'email';
31+
public const DATA_EMAIL = 'email';
2932

30-
const DATA_ENDPOINT = 'endpoint';
33+
public const DATA_ENDPOINT = 'endpoint';
3134

32-
const DATA_IDENTITY_LINK_URL = 'identity_link_url';
35+
public const DATA_IDENTITY_LINK_URL = 'identity_link_url';
3336

34-
const DATA_SETUP_TYPE = 'setup_type';
37+
public const DATA_SETUP_TYPE = 'setup_type';
3538

36-
const DATA_CONSUMER_ID = 'consumer_id';
39+
public const DATA_CONSUMER_ID = 'consumer_id';
3740

38-
const DATA_CONSUMER_PASSWORD = 'current_password';
41+
public const DATA_CONSUMER_PASSWORD = 'current_password';
3942

4043
/**#@-*/
4144

@@ -161,6 +164,7 @@ protected function _addGeneralFieldset($form, $integrationData)
161164
'label' => __('Identity link URL'),
162165
'name' => self::DATA_IDENTITY_LINK_URL,
163166
'disabled' => $disabled,
167+
'class' => 'validate-url',
164168
'note' => __(
165169
'URL to redirect user to link their 3rd party account with this Magento integration credentials.'
166170
)

app/code/Magento/Integration/Controller/Adminhtml/Integration.php

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,10 +3,14 @@
33
* Copyright © Magento, Inc. All rights reserved.
44
* See COPYING.txt for license details.
55
*/
6+
7+
declare(strict_types=1);
8+
69
namespace Magento\Integration\Controller\Adminhtml;
710

811
use Magento\Backend\App\Action;
9-
use Magento\Integration\Api\OauthServiceInterface as IntegrationOauthService;
12+
use Magento\Framework\App\ObjectManager;
13+
use Magento\Framework\Url\Validator;
1014

1115
/**
1216
* Controller for integrations management.
@@ -20,18 +24,18 @@ abstract class Integration extends Action
2024
*
2125
* @see _isAllowed()
2226
*/
23-
const ADMIN_RESOURCE = 'Magento_Integration::integrations';
27+
public const ADMIN_RESOURCE = 'Magento_Integration::integrations';
2428

2529
/** Param Key for extracting integration id from Request */
26-
const PARAM_INTEGRATION_ID = 'id';
30+
public const PARAM_INTEGRATION_ID = 'id';
2731

2832
/** Reauthorize flag is used to distinguish activation from reauthorization */
29-
const PARAM_REAUTHORIZE = 'reauthorize';
33+
public const PARAM_REAUTHORIZE = 'reauthorize';
3034

31-
const REGISTRY_KEY_CURRENT_INTEGRATION = 'current_integration';
35+
public const REGISTRY_KEY_CURRENT_INTEGRATION = 'current_integration';
3236

3337
/** Saved API form data session key */
34-
const REGISTRY_KEY_CURRENT_RESOURCE = 'current_resource';
38+
public const REGISTRY_KEY_CURRENT_RESOURCE = 'current_resource';
3539

3640
/**
3741
* @var \Magento\Framework\Registry
@@ -73,6 +77,11 @@ abstract class Integration extends Action
7377
*/
7478
protected $escaper;
7579

80+
/**
81+
* @var Validator
82+
*/
83+
protected $urlValidator;
84+
7685
/**
7786
* @param \Magento\Backend\App\Action\Context $context
7887
* @param \Magento\Framework\Registry $registry
@@ -83,6 +92,9 @@ abstract class Integration extends Action
8392
* @param \Magento\Integration\Helper\Data $integrationData
8493
* @param \Magento\Framework\Escaper $escaper
8594
* @param \Magento\Integration\Model\ResourceModel\Integration\Collection $integrationCollection
95+
* @param Validator|null $urlValidator
96+
*
97+
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
8698
*/
8799
public function __construct(
88100
\Magento\Backend\App\Action\Context $context,
@@ -93,7 +105,8 @@ public function __construct(
93105
\Magento\Framework\Json\Helper\Data $jsonHelper,
94106
\Magento\Integration\Helper\Data $integrationData,
95107
\Magento\Framework\Escaper $escaper,
96-
\Magento\Integration\Model\ResourceModel\Integration\Collection $integrationCollection
108+
\Magento\Integration\Model\ResourceModel\Integration\Collection $integrationCollection,
109+
Validator $urlValidator = null
97110
) {
98111
parent::__construct($context);
99112
$this->_registry = $registry;
@@ -104,6 +117,7 @@ public function __construct(
104117
$this->_integrationData = $integrationData;
105118
$this->escaper = $escaper;
106119
$this->_integrationCollection = $integrationCollection;
120+
$this->urlValidator = $urlValidator ?: ObjectManager::getInstance()->get(Validator::class);
107121
parent::__construct($context);
108122
}
109123

app/code/Magento/Integration/Controller/Adminhtml/Integration/Save.php

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33
* Copyright © Magento, Inc. All rights reserved.
44
* See COPYING.txt for license details.
55
*/
6+
7+
declare(strict_types=1);
8+
69
namespace Magento\Integration\Controller\Adminhtml\Integration;
710

811
use Magento\Framework\App\Action\HttpPostActionInterface as HttpPostActionInterface;
@@ -30,6 +33,7 @@ class Save extends \Magento\Integration\Controller\Adminhtml\Integration impleme
3033
*
3134
* @return SecurityCookie
3235
* @deprecated 100.1.0
36+
* @see we don't recommend this approach anymore
3337
*/
3438
private function getSecurityCookie()
3539
{
@@ -76,7 +80,7 @@ public function execute()
7680
$this->messageManager->addErrorMessage($this->escaper->escapeHtml($e->getMessage()));
7781
$this->_getSession()->setIntegrationData($this->getRequest()->getPostValue());
7882
$this->_redirectOnSaveError();
79-
} catch (\Magento\Framework\Exception\LocalizedException $e) {
83+
} catch (LocalizedException $e) {
8084
$this->messageManager->addErrorMessage($this->escaper->escapeHtml($e->getMessage()));
8185
$this->_redirectOnSaveError();
8286
} catch (\Exception $e) {
@@ -148,6 +152,8 @@ protected function _redirectOnSaveError()
148152
*
149153
* @param array $integrationData
150154
* @return void
155+
* @throws IntegrationException
156+
* @throws LocalizedException
151157
*/
152158
private function processData($integrationData)
153159
{
@@ -157,7 +163,15 @@ private function processData($integrationData)
157163
if (!isset($data['resource'])) {
158164
$integrationData['resource'] = [];
159165
}
166+
160167
$integrationData = array_merge($integrationData, $data);
168+
169+
// Check if the Identity Link URL field is not empty and then validate it
170+
$url = $integrationData[Info::DATA_IDENTITY_LINK_URL] ?? null;
171+
if (!empty($url) && !$this->urlValidator->isValid($url)) {
172+
throw new LocalizedException(__('Invalid Identity Link URL'));
173+
}
174+
161175
if (!isset($integrationData[Info::DATA_ID])) {
162176
$integration = $this->_integrationService->create($integrationData);
163177
} else {

app/code/Magento/Integration/i18n/en_US.csv

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -125,3 +125,4 @@ OAuth,OAuth
125125
"Integrations API configuration file","Integrations API configuration file"
126126
"We couldn't find any records.","We couldn't find any records."
127127
Status,Status
128+
"Invalid Identity Link URL", "Invalid Identity Link URL"

0 commit comments

Comments
 (0)