Skip to content

Commit 3cf0949

Browse files
committed
Resolved for conflict in ACP2E-1986
2 parents debc9fd + 78e6653 commit 3cf0949

File tree

5 files changed

+145
-44
lines changed

5 files changed

+145
-44
lines changed

app/code/Magento/Quote/Api/ShipmentEstimationInterface.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,11 @@ interface ShipmentEstimationInterface
1616
{
1717
/**
1818
* Estimate shipping by address and return list of available shipping methods
19+
*
1920
* @param mixed $cartId
2021
* @param AddressInterface $address
2122
* @return \Magento\Quote\Api\Data\ShippingMethodInterface[] An array of shipping methods
23+
* @throws \Magento\Framework\Exception\InputException The specified input is not valid.
2224
* @since 100.0.7
2325
*/
2426
public function estimateByExtendedAddress($cartId, AddressInterface $address);

dev/tests/api-functional/testsuite/Magento/WebapiAsync/Model/AsyncBulkScheduleTest.php

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -33,18 +33,21 @@
3333
*/
3434
class AsyncBulkScheduleTest extends WebapiAbstract
3535
{
36-
const SERVICE_NAME = 'catalogProductRepositoryV1';
37-
const SERVICE_VERSION = 'V1';
38-
const REST_RESOURCE_PATH = '/V1/products';
39-
const ASYNC_BULK_RESOURCE_PATH = '/async/bulk/V1/products';
40-
const ASYNC_CONSUMER_NAME = 'async.operations.all';
36+
public const SERVICE_NAME = 'catalogProductRepositoryV1';
37+
public const SERVICE_VERSION = 'V1';
38+
public const REST_RESOURCE_PATH = '/V1/products';
39+
public const ASYNC_BULK_RESOURCE_PATH = '/async/bulk/V1/products';
40+
public const ASYNC_CONSUMER_NAME = 'async.operations.all';
4141

42-
const KEY_TIER_PRICES = 'tier_prices';
43-
const KEY_SPECIAL_PRICE = 'special_price';
44-
const KEY_CATEGORY_LINKS = 'category_links';
42+
public const KEY_TIER_PRICES = 'tier_prices';
43+
public const KEY_SPECIAL_PRICE = 'special_price';
44+
public const KEY_CATEGORY_LINKS = 'category_links';
4545

46-
const BULK_UUID_KEY = 'bulk_uuid';
46+
public const BULK_UUID_KEY = 'bulk_uuid';
4747

48+
/**
49+
* @var string[]
50+
*/
4851
protected $consumers = [
4952
self::ASYNC_CONSUMER_NAME,
5053
];
@@ -184,7 +187,7 @@ public function testAsyncScheduleBulkWrongEntity($products)
184187
try {
185188
$response = $this->saveProductAsync($products);
186189
} catch (\Exception $e) {
187-
$this->assertEquals(500, $e->getCode());
190+
$this->assertEquals(400, $e->getCode());
188191
}
189192
$this->assertNull($response);
190193
$this->assertEquals(0, $this->checkProductsCreation());

dev/tests/integration/testsuite/Magento/Framework/MessageQueue/MessageEncoderTest.php

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
namespace Magento\Framework\MessageQueue;
88

9+
use Magento\Framework\Exception\LocalizedException;
910
use Magento\Framework\ObjectManagerInterface;
1011
use Magento\Framework\MessageQueue\MessageEncoder;
1112
use Magento\Framework\Communication\Config;
@@ -119,10 +120,9 @@ public function testDecodeInvalidMessageFormat()
119120
*/
120121
public function testDecodeInvalidMessage()
121122
{
122-
$this->expectException(\LogicException::class);
123+
$this->expectException(LocalizedException::class);
123124

124-
$message = 'Property "NotExistingField" does not have accessor method "getNotExistingField" in class '
125-
. '"Magento\Customer\Api\Data\CustomerInterface".';
125+
$message = 'customer.created" must be an instance of "Magento\Customer\Api\Data\CustomerInterface".';
126126
$this->expectExceptionMessage($message);
127127
$this->encoder->decode('customer.created', '{"not_existing_field": "value"}');
128128
}

lib/internal/Magento/Framework/Webapi/ServiceInputProcessor.php

Lines changed: 58 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -296,38 +296,42 @@ protected function _createFromArray($className, $data)
296296
// Converts snake_case to uppercase CamelCase to help form getter/setter method names
297297
// This use case is for REST only. SOAP request data is already camel cased
298298
$camelCaseProperty = SimpleDataObjectConverter::snakeCaseToUpperCamelCase($propertyName);
299-
$methodName = $this->getNameFinder()->getGetterMethodName($class, $camelCaseProperty);
300-
if (!isset($this->methodReflectionStorage[$className . $methodName])) {
301-
$this->methodReflectionStorage[$className . $methodName] = $class->getMethod($methodName);
302-
}
303-
$methodReflection = $this->methodReflectionStorage[$className . $methodName];
304-
if ($methodReflection->isPublic()) {
305-
$returnType = $this->typeProcessor->getGetterReturnType($methodReflection)['type'];
306-
try {
307-
$setterName = $this->getNameFinder()->getSetterMethodName($class, $camelCaseProperty);
308-
} catch (\Exception $e) {
309-
if (empty($value)) {
310-
continue;
311-
} else {
312-
throw $e;
313-
}
299+
try {
300+
$methodName = $this->getNameFinder()->getGetterMethodName($class, $camelCaseProperty);
301+
if (!isset($this->methodReflectionStorage[$className . $methodName])) {
302+
$this->methodReflectionStorage[$className . $methodName] = $class->getMethod($methodName);
314303
}
315-
try {
316-
if ($camelCaseProperty === 'CustomAttributes') {
317-
$setterValue = $this->convertCustomAttributeValue($value, $className);
318-
} else {
319-
$setterValue = $this->convertValue($value, $returnType);
304+
$methodReflection = $this->methodReflectionStorage[$className . $methodName];
305+
if ($methodReflection->isPublic()) {
306+
$returnType = $this->typeProcessor->getGetterReturnType($methodReflection)['type'];
307+
try {
308+
$setterName = $this->getNameFinder()->getSetterMethodName($class, $camelCaseProperty);
309+
} catch (\Exception $e) {
310+
if (empty($value)) {
311+
continue;
312+
} else {
313+
throw $e;
314+
}
320315
}
321-
} catch (SerializationException $e) {
322-
throw new SerializationException(
323-
new Phrase(
324-
'Error occurred during "%field_name" processing. %details',
325-
['field_name' => $propertyName, 'details' => $e->getMessage()]
326-
)
327-
);
316+
try {
317+
if ($camelCaseProperty === 'CustomAttributes') {
318+
$setterValue = $this->convertCustomAttributeValue($value, $className);
319+
} else {
320+
$setterValue = $this->convertValue($value, $returnType);
321+
}
322+
} catch (SerializationException $e) {
323+
throw new SerializationException(
324+
new Phrase(
325+
'Error occurred during "%field_name" processing. %details',
326+
['field_name' => $propertyName, 'details' => $e->getMessage()]
327+
)
328+
);
329+
}
330+
$this->serviceInputValidator->validateEntityValue($object, $propertyName, $setterValue);
331+
$object->{$setterName}($setterValue);
328332
}
329-
$this->serviceInputValidator->validateEntityValue($object, $propertyName, $setterValue);
330-
$object->{$setterName}($setterValue);
333+
} catch (\LogicException $e) {
334+
$this->processInputErrorForNestedSet([$camelCaseProperty]);
331335
}
332336
}
333337

@@ -606,4 +610,29 @@ public function _resetState(): void
606610
{
607611
$this->attributesPreprocessorsMap = [];
608612
}
613+
614+
/**
615+
* Process an input error for child parameters
616+
*
617+
* @param array $inputError
618+
* @return void
619+
* @throws InputException
620+
*/
621+
private function processInputErrorForNestedSet(array $inputError): void
622+
{
623+
if (!empty($inputError)) {
624+
$exception = new InputException();
625+
foreach ($inputError as $errorParamField) {
626+
$exception->addError(
627+
new Phrase(
628+
'"%fieldName" is not supported. Correct the field name and try again.',
629+
['fieldName' => $errorParamField]
630+
)
631+
);
632+
}
633+
if ($exception->wasErrorAdded()) {
634+
throw $exception;
635+
}
636+
}
637+
}
609638
}

lib/internal/Magento/Framework/Webapi/Test/Unit/ServiceInputProcessorTest.php

Lines changed: 69 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
use Magento\Framework\Api\AttributeValueFactory;
1313
use \Magento\Framework\Api\SearchCriteriaInterface;
1414
use Magento\Framework\App\Cache\Type\Reflection;
15+
use Magento\Framework\Exception\InputException;
1516
use Magento\Framework\Exception\InvalidArgumentException;
1617
use Magento\Framework\ObjectManagerInterface;
1718
use Magento\Framework\Reflection\FieldNamer;
@@ -20,6 +21,7 @@
2021
use Magento\Framework\Reflection\TypeProcessor;
2122
use Magento\Framework\Serialize\SerializerInterface;
2223
use Magento\Framework\TestFramework\Unit\Helper\ObjectManager;
24+
use Magento\Framework\Webapi\Exception;
2325
use Magento\Framework\Webapi\Validator\IOLimit\DefaultPageSizeSetter;
2426
use Magento\Framework\Webapi\ServiceInputProcessor;
2527
use Magento\Framework\Webapi\Validator\IOLimit\IOLimitConfigProvider;
@@ -40,6 +42,8 @@
4042
use PHPUnit\Framework\MockObject\MockObject;
4143
use PHPUnit\Framework\TestCase;
4244
use Magento\Framework\Webapi\Validator\EntityArrayValidator\InputArraySizeLimitValue;
45+
use Magento\Quote\Api\ShipmentEstimationInterface;
46+
use Magento\Quote\Api\Data\AddressInterface;
4347

4448
/**
4549
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
@@ -84,16 +88,23 @@ class ServiceInputProcessorTest extends TestCase
8488
*/
8589
private $defaultPageSizeSetter;
8690

91+
/**
92+
* @var AddressInterface|MockObject
93+
*/
94+
protected $addressMock;
95+
8796
/**
8897
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
8998
*/
9099
protected function setUp(): void
91100
{
92101
$this->searchCriteria = self::getMockBuilder(SearchCriteriaInterface::class)
93102
->getMock();
94-
103+
$this->addressMock = self::getMockBuilder(AddressInterface::class)
104+
->getMock();
95105
$objectManagerStatic = [
96-
SearchCriteriaInterface::class => $this->searchCriteria
106+
SearchCriteriaInterface::class => $this->searchCriteria,
107+
AddressInterface::class => $this->addressMock
97108
];
98109
$objectManager = new ObjectManager($this);
99110
$this->objectManagerMock = $this->getMockBuilder(ObjectManagerInterface::class)
@@ -701,4 +712,60 @@ public function invalidCustomAttributesDataProvider()
701712
]
702713
];
703714
}
715+
716+
/**
717+
* @return array
718+
*/
719+
public function payloadDataProvider(): array
720+
{
721+
return [
722+
[
723+
[
724+
'address' => [
725+
"street" => [
726+
"서울 강북구 한천로166길 2 (-서울 강북구 수유동 269-36)"
727+
],
728+
"city." => "pune",
729+
],
730+
'cartId' => "30"
731+
],
732+
1
733+
],
734+
[
735+
[
736+
'address' => [
737+
"street" => [
738+
"서울 강북구 한천로166길 2 (-서울 강북구 수유동 269-36)"
739+
],
740+
"city" => "pune",
741+
],
742+
'cartId' => "30"
743+
],
744+
0
745+
]
746+
];
747+
}
748+
749+
/**
750+
* Validate if payload has correct attributes
751+
*
752+
* @param array $payload
753+
* @param int $exception
754+
* @return void
755+
* @throws Exception
756+
* @dataProvider payloadDataProvider
757+
*/
758+
public function testValidateApiPayload(array $payload, int $exception): void
759+
{
760+
if ($exception) {
761+
$this->expectException(InputException::class);
762+
$this->expectExceptionMessage('"City." is not supported. Correct the field name and try again.');
763+
}
764+
$result = $this->serviceInputProcessor->process(
765+
ShipmentEstimationInterface::class,
766+
'estimateByExtendedAddress',
767+
$payload
768+
);
769+
$this->assertNotEmpty($result);
770+
}
704771
}

0 commit comments

Comments
 (0)