Skip to content

Commit ad9e1f0

Browse files
authored
Merge pull request #5184 from magento-honey-badgers/graphql-forwardport
[honey] MC-25215: [Forwardport] [GraphQL] Row_id is used as id for product resolver
2 parents dbb159a + 9444e90 commit ad9e1f0

File tree

12 files changed

+149
-63
lines changed

12 files changed

+149
-63
lines changed

app/code/Magento/CatalogGraphQl/Model/Resolver/Product/EntityIdToId.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ public function resolve(
5353
$product = $value['model'];
5454

5555
$productId = $product->getData(
56-
$this->metadataPool->getMetadata(ProductInterface::class)->getLinkField()
56+
$this->metadataPool->getMetadata(ProductInterface::class)->getIdentifierField()
5757
);
5858

5959
return $productId;

app/code/Magento/CatalogGraphQl/etc/schema.graphqls

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -100,8 +100,8 @@ interface ProductInterface @typeResolver(class: "Magento\\CatalogGraphQl\\Model\
100100
created_at: String @doc(description: "Timestamp indicating when the product was created.")
101101
updated_at: String @doc(description: "Timestamp indicating when the product was updated.")
102102
country_of_manufacture: String @doc(description: "The product's country of origin.")
103-
type_id: String @doc(description: "One of simple, virtual, bundle, downloadable, grouped, or configurable.")
104-
websites: [Website] @doc(description: "An array of websites in which the product is available.") @resolver(class: "Magento\\CatalogGraphQl\\Model\\Resolver\\Product\\Websites")
103+
type_id: String @doc(description: "One of simple, virtual, bundle, downloadable, grouped, or configurable.") @deprecated(reason: "Use __typename instead.")
104+
websites: [Website] @doc(description: "An array of websites in which the product is available.") @deprecated(reason: "The field should not be used on the storefront.") @resolver(class: "Magento\\CatalogGraphQl\\Model\\Resolver\\Product\\Websites")
105105
product_links: [ProductLinksInterface] @doc(description: "An array of ProductLinks objects.") @resolver(class: "Magento\\CatalogGraphQl\\Model\\Resolver\\Product\\BatchProductLinks")
106106
media_gallery_entries: [MediaGalleryEntry] @deprecated(reason: "Use product's `media_gallery` instead") @doc(description: "An array of MediaGalleryEntry objects.") @resolver(class: "Magento\\CatalogGraphQl\\Model\\Resolver\\Product\\MediaGalleryEntries")
107107
price: ProductPrices @deprecated(reason: "Use price_range for product price information.") @doc(description: "A ProductPrices object, indicating the price of an item.") @resolver(class: "Magento\\CatalogGraphQl\\Model\\Resolver\\Product\\Price")

app/code/Magento/StoreGraphQl/Controller/HttpRequestValidator/StoreValidator.php

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -42,16 +42,30 @@ public function validate(HttpRequestInterface $request): void
4242
{
4343
$headerValue = $request->getHeader('Store');
4444
if (!empty($headerValue)) {
45-
$storeCode = ltrim(rtrim($headerValue));
46-
$stores = $this->storeManager->getStores(false, true);
47-
if (!isset($stores[$storeCode])) {
48-
if (strtolower($storeCode) !== 'default') {
49-
$this->storeManager->setCurrentStore(null);
50-
throw new GraphQlInputException(
51-
__("Requested store is not found")
52-
);
53-
}
45+
$storeCode = trim($headerValue);
46+
if (!$this->isStoreActive($storeCode)) {
47+
$this->storeManager->setCurrentStore(null);
48+
throw new GraphQlInputException(__('Requested store is not found'));
5449
}
5550
}
5651
}
52+
53+
/**
54+
* Check if provided store code corresponds to an active store
55+
*
56+
* @param string $storeCode
57+
* @return bool
58+
*/
59+
private function isStoreActive(string $storeCode): bool
60+
{
61+
$stores = $this->storeManager->getStores(false, true);
62+
if (strtolower($storeCode) === 'default') {
63+
return true;
64+
}
65+
if (isset($stores[$storeCode])) {
66+
return (bool)$stores[$storeCode]->getIsActive();
67+
}
68+
69+
return false;
70+
}
5771
}

app/code/Magento/StoreGraphQl/etc/schema.graphqls

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,13 @@ type Query {
44
storeConfig : StoreConfig @resolver(class: "Magento\\StoreGraphQl\\Model\\Resolver\\StoreConfigResolver") @doc(description: "The store config query") @cache(cacheable: false)
55
}
66

7-
type Website @doc(description: "The type contains information about a website") {
8-
id : Int @doc(description: "The ID number assigned to the website")
9-
name : String @doc(description: "The website name. Websites use this name to identify it easier.")
10-
code : String @doc(description: "A code assigned to the website to identify it")
11-
sort_order : Int @doc(description: "The attribute to use for sorting websites")
12-
default_group_id : String @doc(description: "The default group ID that the website has")
13-
is_default : Boolean @doc(description: "Specifies if this is the default website")
7+
type Website @doc(description: "Website is deprecated because it is should not be used on storefront. The type contains information about a website") {
8+
id : Int @deprecated(reason: "The field should not be used on the storefront.") @doc(description: "The ID number assigned to the website")
9+
name : String @deprecated(reason: "The field should not be used on the storefront.") @doc(description: "The website name. Websites use this name to identify it easier.")
10+
code : String @deprecated(reason: "The field should not be used on the storefront.") @doc(description: "A code assigned to the website to identify it")
11+
sort_order : Int @deprecated(reason: "The field should not be used on the storefront.") @doc(description: "The attribute to use for sorting websites")
12+
default_group_id : String @deprecated(reason: "The field should not be used on the storefront.") @doc(description: "The default group ID that the website has")
13+
is_default : Boolean @deprecated(reason: "The field should not be used on the storefront.") @doc(description: "Specifies if this is the default website")
1414
}
1515

1616
type StoreConfig @doc(description: "The type contains information about a store config") {

dev/tests/api-functional/testsuite/Magento/GraphQl/Bundle/BundleProductViewTest.php

Lines changed: 1 addition & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -10,13 +10,12 @@
1010
use Magento\Bundle\Model\Product\OptionList;
1111
use Magento\Catalog\Api\Data\ProductInterface;
1212
use Magento\Catalog\Api\ProductRepositoryInterface;
13-
use Magento\Framework\EntityManager\MetadataPool;
1413
use Magento\Framework\App\Config\ScopeConfigInterface;
1514
use Magento\TestFramework\ObjectManager;
1615
use Magento\TestFramework\TestCase\GraphQlAbstract;
1716

1817
/**
19-
* Bundle product view test
18+
* Test querying Bundle products
2019
*/
2120
class BundleProductViewTest extends GraphQlAbstract
2221
{
@@ -83,12 +82,7 @@ public function testAllFieldsBundleProducts()
8382

8483
/** @var ProductRepositoryInterface $productRepository */
8584
$productRepository = ObjectManager::getInstance()->get(ProductRepositoryInterface::class);
86-
/** @var MetadataPool $metadataPool */
87-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
8885
$bundleProduct = $productRepository->get($productSku, false, null, true);
89-
$bundleProduct->setId(
90-
$bundleProduct->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
91-
);
9286
if ((bool)$bundleProduct->getShipmentType()) {
9387
$this->assertEquals('SEPARATELY', $response['products']['items'][0]['ship_bundle_items']);
9488
} else {
@@ -182,12 +176,7 @@ public function testBundleProductWithNotVisibleChildren()
182176

183177
/** @var ProductRepositoryInterface $productRepository */
184178
$productRepository = ObjectManager::getInstance()->get(ProductRepositoryInterface::class);
185-
/** @var MetadataPool $metadataPool */
186-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
187179
$bundleProduct = $productRepository->get($productSku, false, null, true);
188-
$bundleProduct->setId(
189-
$bundleProduct->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
190-
);
191180
if ((bool)$bundleProduct->getShipmentType()) {
192181
$this->assertEquals('SEPARATELY', $response['products']['items'][0]['ship_bundle_items']);
193182
} else {
@@ -238,7 +227,6 @@ private function assertBundleProductOptions($product, $actualResponse)
238227
$actualResponse['items'],
239228
"Precondition failed: 'bundle product items' must not be empty"
240229
);
241-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
242230
/** @var OptionList $optionList */
243231
$optionList = ObjectManager::getInstance()->get(\Magento\Bundle\Model\Product\OptionList::class);
244232
$options = $optionList->getItems($product);
@@ -249,10 +237,6 @@ private function assertBundleProductOptions($product, $actualResponse)
249237
$childProductSku = $bundleProductLink->getSku();
250238
$productRepository = ObjectManager::getInstance()->get(ProductRepositoryInterface::class);
251239
$childProduct = $productRepository->get($childProductSku);
252-
/** @var MetadataPool $metadataPool */
253-
$childProduct->setId(
254-
$childProduct->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
255-
);
256240
$this->assertEquals(1, count($options));
257241
$this->assertResponseFields(
258242
$actualResponse['items'][0],

dev/tests/api-functional/testsuite/Magento/GraphQl/Catalog/ProductViewTest.php

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313
use Magento\Catalog\Api\ProductRepositoryInterface;
1414
use Magento\Catalog\Model\Category;
1515
use Magento\Framework\DataObject;
16-
use Magento\Framework\EntityManager\MetadataPool;
1716
use Magento\TestFramework\ObjectManager;
1817
use Magento\TestFramework\TestCase\GraphQlAbstract;
1918

@@ -270,11 +269,6 @@ public function testQueryAllFieldsSimpleProduct()
270269
/** @var ProductRepositoryInterface $productRepository */
271270
$productRepository = ObjectManager::getInstance()->get(ProductRepositoryInterface::class);
272271
$product = $productRepository->get($productSku, false, null, true);
273-
/** @var MetadataPool $metadataPool */
274-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
275-
$product->setId(
276-
$product->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
277-
);
278272
$this->assertArrayHasKey('products', $response);
279273
$this->assertArrayHasKey('items', $response['products']);
280274
$this->assertEquals(1, count($response['products']['items']));
@@ -656,15 +650,7 @@ public function testProductPrices()
656650
*/
657651
$productRepository = ObjectManager::getInstance()->get(ProductRepositoryInterface::class);
658652
$firstProduct = $productRepository->get($firstProductSku, false, null, true);
659-
/** @var MetadataPool $metadataPool */
660-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
661-
$firstProduct->setId(
662-
$firstProduct->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
663-
);
664653
$secondProduct = $productRepository->get($secondProductSku, false, null, true);
665-
$secondProduct->setId(
666-
$secondProduct->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
667-
);
668654
self::assertNotNull($response['products']['items'][0]['price'], "price must be not null");
669655
self::assertCount(2, $response['products']['items']);
670656
$this->assertBaseFields($firstProduct, $response['products']['items'][0]);

dev/tests/api-functional/testsuite/Magento/GraphQl/Catalog/VirtualProductViewTest.php

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@
99

1010
use Magento\Catalog\Api\Data\ProductInterface;
1111
use Magento\Catalog\Api\ProductRepositoryInterface;
12-
use Magento\Framework\EntityManager\MetadataPool;
1312
use Magento\TestFramework\ObjectManager;
1413
use Magento\TestFramework\TestCase\GraphQlAbstract;
1514

@@ -57,11 +56,6 @@ public function testQueryAllFieldsVirtualProduct()
5756
/** @var ProductRepositoryInterface $productRepository */
5857
$productRepository = ObjectManager::getInstance()->get(ProductRepositoryInterface::class);
5958
$product = $productRepository->get($productSku, false, null, true);
60-
/** @var MetadataPool $metadataPool */
61-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
62-
$product->setId(
63-
$product->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
64-
);
6559
$this->assertArrayHasKey('products', $response);
6660
$this->assertArrayHasKey('items', $response['products']);
6761
$this->assertEquals(1, count($response['products']['items']));

dev/tests/api-functional/testsuite/Magento/GraphQl/ConfigurableProduct/ConfigurableProductViewTest.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -243,7 +243,7 @@ private function assertBaseFields($product, $actualResponse)
243243
'expected_value' => $product->getData(
244244
$metadataPool->getMetadata(
245245
ProductInterface::class
246-
)->getLinkField()
246+
)->getIdentifierField()
247247
)
248248
],
249249
['response_field' => 'name', 'expected_value' => $product->getName()],
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
<?php
2+
/**
3+
* Copyright © Magento, Inc. All rights reserved.
4+
* See COPYING.txt for license details.
5+
*/
6+
declare(strict_types=1);
7+
8+
namespace Magento\GraphQl\Store;
9+
10+
use Magento\TestFramework\TestCase\GraphQlAbstract;
11+
12+
/**
13+
* Test the GraphQL `Store` header validation
14+
*/
15+
class StoreValidatorTest extends GraphQlAbstract
16+
{
17+
/**
18+
* @param string $storeCode
19+
* @param string $errorMessage
20+
*
21+
* @dataProvider dataProviderInvalidStore
22+
* @magentoApiDataFixture Magento/Store/_files/inactive_store.php
23+
*/
24+
public function testInvalidStoreHeader(string $storeCode, string $errorMessage)
25+
{
26+
$query
27+
= <<<QUERY
28+
{
29+
storeConfig{
30+
code
31+
}
32+
}
33+
QUERY;
34+
$this->expectExceptionMessage($errorMessage);
35+
$this->graphQlMutation($query, [], '', ['Store' => $storeCode]);
36+
}
37+
38+
/**
39+
* Data provider with invalid store codes and expected error messages
40+
*
41+
* @return array
42+
*/
43+
public function dataProviderInvalidStore(): array
44+
{
45+
return [
46+
'non_existing' => [
47+
'non_existing',
48+
'Requested store is not found'
49+
],
50+
'inactive_store' => [
51+
'inactive_store',
52+
'Requested store is not found'
53+
]
54+
];
55+
}
56+
}

dev/tests/api-functional/testsuite/Magento/GraphQl/Tax/ProductViewTest.php

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@
99

1010
use Magento\Catalog\Api\Data\ProductInterface;
1111
use Magento\Catalog\Api\ProductRepositoryInterface;
12-
use Magento\Framework\EntityManager\MetadataPool;
1312
use Magento\TestFramework\ObjectManager;
1413
use Magento\TestFramework\TestCase\GraphQlAbstract;
1514
use Magento\Store\Model\StoreManagerInterface;
@@ -208,11 +207,6 @@ public function testQueryAllFieldsSimpleProduct()
208207

209208
/** @var \Magento\Catalog\Model\Product $product */
210209
$product = $this->productRepository->get($productSku, false, null, true);
211-
/** @var MetadataPool $metadataPool */
212-
$metadataPool = ObjectManager::getInstance()->get(MetadataPool::class);
213-
$product->setId(
214-
$product->getData($metadataPool->getMetadata(ProductInterface::class)->getLinkField())
215-
);
216210
$this->assertArrayHasKey('products', $response);
217211
$this->assertArrayHasKey('items', $response['products']);
218212
$this->assertEquals(1, count($response['products']['items']));

0 commit comments

Comments
 (0)