Skip to content

Commit 679cd33

Browse files
authored
Merge pull request #5831 from magento-honey-badgers/MC-20636
[honey] MC-20636: MyAccount :: Order Details :: Order Details by Order Number
2 parents ac1ea0b + c3d2dac commit 679cd33

File tree

50 files changed

+5176
-20
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

50 files changed

+5176
-20
lines changed

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

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,12 @@ input FilterMatchTypeInput @doc(description: "Defines a filter that performs a f
7979
match: String @doc(description: "One or more words to filter on")
8080
}
8181

82+
input FilterStringTypeInput @doc(description: "Defines a filter for an input string.") {
83+
in: [String] @doc(description: "Filters items that are exactly the same as entries specified in an array of strings.")
84+
eq: String @doc(description: "Filters items that are exactly the same as the specified string.")
85+
match: String @doc(description: "Defines a filter that performs a fuzzy search using the specified string.")
86+
}
87+
8288
type SearchResultPageInfo @doc(description: "SearchResultPageInfo provides navigation for the query response") {
8389
page_size: Int @doc(description: "Specifies the maximum number of items to return")
8490
current_page: Int @doc(description: "Specifies which page of results to return")
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
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\SalesGraphQl\Model;
9+
10+
use Magento\Framework\GraphQl\Exception\GraphQlInputException;
11+
use Magento\Framework\GraphQl\Query\Resolver\TypeResolverInterface;
12+
13+
/**
14+
* Composite class to resolve invoice item type
15+
*/
16+
class InvoiceItemInterfaceTypeResolverComposite implements TypeResolverInterface
17+
{
18+
/**
19+
* @var TypeResolverInterface[]
20+
*/
21+
private $invoiceItemTypeResolvers = [];
22+
23+
/**
24+
* @param TypeResolverInterface[] $invoiceItemTypeResolvers
25+
*/
26+
public function __construct(array $invoiceItemTypeResolvers = [])
27+
{
28+
$this->invoiceItemTypeResolvers = $invoiceItemTypeResolvers;
29+
}
30+
31+
/**
32+
* Resolve item type of an invoice through composite resolvers
33+
*
34+
* @param array $data
35+
* @return string
36+
* @throws GraphQlInputException
37+
*/
38+
public function resolveType(array $data): string
39+
{
40+
$resolvedType = null;
41+
42+
foreach ($this->invoiceItemTypeResolvers as $invoiceItemTypeResolver) {
43+
if (!isset($data['product_type'])) {
44+
throw new GraphQlInputException(
45+
__('Missing key %1 in sales item data', ['product_type'])
46+
);
47+
}
48+
$resolvedType = $invoiceItemTypeResolver->resolveType($data);
49+
if (!empty($resolvedType)) {
50+
return $resolvedType;
51+
}
52+
}
53+
54+
throw new GraphQlInputException(
55+
__('Concrete type for %1 not implemented', ['InvoiceItemInterface'])
56+
);
57+
}
58+
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
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\SalesGraphQl\Model;
9+
10+
use Magento\Framework\GraphQl\Query\Resolver\TypeResolverInterface;
11+
12+
/**
13+
* Leaf for composite class to resolve invoice item type
14+
*/
15+
class InvoiceItemTypeResolver implements TypeResolverInterface
16+
{
17+
/**
18+
* @inheritDoc
19+
*/
20+
public function resolveType(array $data): string
21+
{
22+
if (isset($data['product_type'])) {
23+
if ($data['product_type'] == 'bundle') {
24+
return 'BundleInvoiceItem';
25+
}
26+
}
27+
return 'InvoiceItem';
28+
}
29+
}
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
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\SalesGraphQl\Model;
9+
10+
use Magento\Framework\GraphQl\Exception\GraphQlInputException;
11+
use Magento\Framework\GraphQl\Query\Resolver\TypeResolverInterface;
12+
13+
/**
14+
* Composite class to resolve order item type
15+
*/
16+
class OrderItemInterfaceTypeResolverComposite implements TypeResolverInterface
17+
{
18+
/**
19+
* TypeResolverInterface[]
20+
*/
21+
private $orderItemTypeResolvers = [];
22+
23+
/**
24+
* @param TypeResolverInterface[] $orderItemTypeResolvers
25+
*/
26+
public function __construct(array $orderItemTypeResolvers = [])
27+
{
28+
$this->orderItemTypeResolvers = $orderItemTypeResolvers;
29+
}
30+
31+
/**
32+
* Resolve item type of an order through composite resolvers
33+
*
34+
* @param array $data
35+
* @return string
36+
* @throws GraphQlInputException
37+
*/
38+
public function resolveType(array $data) : string
39+
{
40+
$resolvedType = null;
41+
42+
foreach ($this->orderItemTypeResolvers as $orderItemTypeResolver) {
43+
if (!isset($data['product_type'])) {
44+
throw new GraphQlInputException(
45+
__('Missing key %1 in sales item data', ['product_type'])
46+
);
47+
}
48+
$resolvedType = $orderItemTypeResolver->resolveType($data);
49+
if (!empty($resolvedType)) {
50+
return $resolvedType;
51+
}
52+
}
53+
54+
throw new GraphQlInputException(
55+
__('Concrete type for %1 not implemented', ['OrderItemInterface'])
56+
);
57+
}
58+
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
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\SalesGraphQl\Model;
9+
10+
use Magento\Framework\GraphQl\Query\Resolver\TypeResolverInterface;
11+
12+
/**
13+
* Leaf for composite class to resolve order item type
14+
*/
15+
class OrderItemTypeResolver implements TypeResolverInterface
16+
{
17+
/**
18+
* @inheritDoc
19+
*/
20+
public function resolveType(array $data): string
21+
{
22+
if (isset($data['product_type'])) {
23+
if ($data['product_type'] == 'bundle') {
24+
return 'BundleOrderItem';
25+
}
26+
}
27+
return 'OrderItem';
28+
}
29+
}
Lines changed: 145 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,145 @@
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\SalesGraphQl\Model\Resolver;
9+
10+
use Magento\Framework\Exception\LocalizedException;
11+
use Magento\Framework\GraphQl\Config\Element\Field;
12+
use Magento\Framework\GraphQl\Query\Resolver\ValueFactory;
13+
use Magento\Framework\GraphQl\Query\ResolverInterface;
14+
use Magento\Framework\GraphQl\Schema\Type\ResolveInfo;
15+
use Magento\Framework\Serialize\Serializer\Json;
16+
use Magento\Sales\Api\Data\InvoiceItemInterface;
17+
use Magento\Sales\Api\Data\OrderItemInterface;
18+
19+
/**
20+
* Resolve bundle options items for order item
21+
*/
22+
class BundleOptions implements ResolverInterface
23+
{
24+
/**
25+
* Serializer
26+
*
27+
* @var Json
28+
*/
29+
private $serializer;
30+
31+
/**
32+
* @var ValueFactory
33+
*/
34+
private $valueFactory;
35+
36+
/**
37+
* @param ValueFactory $valueFactory
38+
* @param Json $serializer
39+
*/
40+
public function __construct(
41+
ValueFactory $valueFactory,
42+
Json $serializer
43+
) {
44+
$this->valueFactory = $valueFactory;
45+
$this->serializer = $serializer;
46+
}
47+
48+
/**
49+
* @inheritDoc
50+
*/
51+
public function resolve(Field $field, $context, ResolveInfo $info, array $value = null, array $args = null)
52+
{
53+
return $this->valueFactory->create(function () use ($value) {
54+
if (!isset($value['model'])) {
55+
throw new LocalizedException(__('"model" value should be specified'));
56+
}
57+
if ($value['model'] instanceof OrderItemInterface) {
58+
/** @var OrderItemInterface $item */
59+
$item = $value['model'];
60+
return $this->getBundleOptions($item, $value);
61+
}
62+
if ($value['model'] instanceof InvoiceItemInterface) {
63+
/** @var InvoiceItemInterface $item */
64+
$item = $value['model'];
65+
// Have to pass down order and item to map to avoid refetching all data
66+
return $this->getBundleOptions($item->getOrderItem(), $value);
67+
}
68+
return null;
69+
});
70+
}
71+
72+
/**
73+
* Format bundle options and values from a parent bundle order item
74+
*
75+
* @param OrderItemInterface $item
76+
* @param array $formattedItem
77+
* @return array
78+
*/
79+
private function getBundleOptions(
80+
OrderItemInterface $item,
81+
array $formattedItem
82+
): array {
83+
$bundleOptions = [];
84+
if ($item->getProductType() === 'bundle') {
85+
$options = $item->getProductOptions();
86+
//loop through options
87+
foreach ($options['bundle_options'] ?? [] as $bundleOptionId => $bundleOption) {
88+
$bundleOptions[$bundleOptionId]['label'] = $bundleOption['label'] ?? '';
89+
$bundleOptions[$bundleOptionId]['id'] = isset($bundleOption['option_id']) ?
90+
base64_encode($bundleOption['option_id']) : null;
91+
if (isset($bundleOption['option_id'])) {
92+
$bundleOptions[$bundleOptionId]['values'] = $this->formatBundleOptionItems(
93+
$item,
94+
$formattedItem,
95+
$bundleOption['option_id']
96+
);
97+
} else {
98+
$bundleOptions[$bundleOptionId]['values'] = [];
99+
}
100+
}
101+
}
102+
return $bundleOptions;
103+
}
104+
105+
/**
106+
* Format Bundle items
107+
*
108+
* @param OrderItemInterface $item
109+
* @param array $formattedItem
110+
* @param string $bundleOptionId
111+
* @return array
112+
*/
113+
private function formatBundleOptionItems(
114+
OrderItemInterface $item,
115+
array $formattedItem,
116+
string $bundleOptionId
117+
) {
118+
$optionItems = [];
119+
// Find the item assign to the option
120+
/** @var OrderItemInterface $childrenOrderItem */
121+
foreach ($item->getChildrenItems() ?? [] as $childrenOrderItem) {
122+
$childOrderItemOptions = $childrenOrderItem->getProductOptions();
123+
$bundleChildAttributes = $this->serializer
124+
->unserialize($childOrderItemOptions['bundle_selection_attributes'] ?? '');
125+
// Value Id is missing from parent, so we have to match the child to parent option
126+
if (isset($bundleChildAttributes['option_id'])
127+
&& $bundleChildAttributes['option_id'] == $bundleOptionId) {
128+
$optionItems[$childrenOrderItem->getItemId()] = [
129+
'id' => base64_encode($childrenOrderItem->getItemId()),
130+
'product_name' => $childrenOrderItem->getName(),
131+
'product_sku' => $childrenOrderItem->getSku(),
132+
'quantity' => $bundleChildAttributes['qty'],
133+
'price' => [
134+
//use options price, not child price
135+
'value' => $bundleChildAttributes['price'],
136+
//use currency from order
137+
'currency' => $formattedItem['product_sale_price']['currency'] ?? null,
138+
]
139+
];
140+
}
141+
}
142+
143+
return $optionItems;
144+
}
145+
}

0 commit comments

Comments
 (0)