77
88namespace Magento \Bundle \Model \Product ;
99
10+ use Magento \Bundle \Api \Data \LinkInterface ;
11+ use Magento \Bundle \Api \Data \LinkInterfaceFactory ;
12+ use Magento \Bundle \Api \Data \OptionInterfaceFactory ;
1013use Magento \Catalog \Api \ProductRepositoryInterface ;
14+ use Magento \Framework \Exception \LocalizedException ;
15+ use Magento \Framework \Exception \NoSuchEntityException ;
16+ use Magento \Framework \ObjectManagerInterface ;
17+ use Magento \Store \Model \Store ;
18+ use Magento \TestFramework \Helper \Bootstrap ;
19+ use PHPUnit \Framework \TestCase ;
1120
1221/**
1322 * Test class for \Magento\Bundle\Model\Product\SaveHandler
1827 * @magentoDbIsolation disabled
1928 * @magentoAppIsolation enabled
2029 */
21- class SaveHandlerTest extends \ PHPUnit \ Framework \ TestCase
30+ class SaveHandlerTest extends TestCase
2231{
2332 /**
24- * @var \Magento\Framework\ ObjectManagerInterface
33+ * @var ObjectManagerInterface
2534 */
2635 private $ objectManager ;
2736
2837 /**
29- * @var \Magento\Store\Model\ Store
38+ * @var Store
3039 */
3140 private $ store ;
3241
@@ -40,21 +49,23 @@ class SaveHandlerTest extends \PHPUnit\Framework\TestCase
4049 */
4150 protected function setUp (): void
4251 {
43- $ this ->objectManager = \ Magento \ TestFramework \ Helper \ Bootstrap::getObjectManager ();
44- $ this ->store = $ this ->objectManager ->create (\ Magento \ Store \ Model \ Store::class);
52+ $ this ->objectManager = Bootstrap::getObjectManager ();
53+ $ this ->store = $ this ->objectManager ->create (Store::class);
4554 /** @var ProductRepositoryInterface $productRepository */
4655 $ this ->productRepository = $ this ->objectManager ->create (ProductRepositoryInterface::class);
4756 }
4857
4958 /**
59+ * Test option title on different stores
60+ *
5061 * @return void
62+ * @throws LocalizedException
63+ * @throws NoSuchEntityException
5164 */
5265 public function testOptionTitlesOnDifferentStores (): void
5366 {
54- /**
55- * @var \Magento\Bundle\Model\Product\OptionList $optionList
56- */
57- $ optionList = $ this ->objectManager ->create (\Magento \Bundle \Model \Product \OptionList::class);
67+ /** @var OptionList $optionList */
68+ $ optionList = $ this ->objectManager ->create (OptionList::class);
5869
5970 $ secondStoreId = $ this ->store ->load ('fixture_second_store ' )->getId ();
6071 $ thirdStoreId = $ this ->store ->load ('fixture_third_store ' )->getId ();
@@ -86,4 +97,150 @@ public function testOptionTitlesOnDifferentStores(): void
8697 $ options [0 ]->getTitle ()
8798 );
8899 }
100+
101+ /**
102+ * Test option link of the same product
103+ *
104+ * @return void
105+ * @throws LocalizedException
106+ * @throws NoSuchEntityException
107+ */
108+ public function testOptionLinksOfSameProduct (): void
109+ {
110+ /** @var OptionList $optionList */
111+ $ optionList = $ this ->objectManager ->create (OptionList::class);
112+ $ product = $ this ->productRepository ->get ('bundle-product ' , true );
113+
114+ //set the first option
115+ $ options = $ this ->setBundleProductOptionData ();
116+ $ extension = $ product ->getExtensionAttributes ();
117+ $ extension ->setBundleProductOptions ($ options );
118+ $ product ->setExtensionAttributes ($ extension );
119+ $ product ->save ();
120+
121+ $ product = $ this ->productRepository ->get ('bundle-product ' , true );
122+ $ options = $ optionList ->getItems ($ product );
123+ $ this ->assertCount (1 , $ options );
124+
125+ //set the second option with same product
126+ $ newOption = $ this ->setBundleProductOptionData ();
127+ array_push ($ options , current ($ newOption ));
128+ $ extension = $ product ->getExtensionAttributes ();
129+ $ extension ->setBundleProductOptions ($ options );
130+ $ product ->setExtensionAttributes ($ extension );
131+ $ product ->save ();
132+ $ this ->assertCount (2 , $ options );
133+
134+ //remove one option and verify the count
135+ array_pop ($ options );
136+ $ extension = $ product ->getExtensionAttributes ();
137+ $ extension ->setBundleProductOptions ($ options );
138+ $ product ->setExtensionAttributes ($ extension );
139+ $ product ->save ();
140+
141+ $ product = $ this ->productRepository ->get ('bundle-product ' , true );
142+ $ options = $ optionList ->getItems ($ product );
143+ $ this ->assertCount (1 , $ options );
144+ }
145+
146+ /**
147+ * Set product option link
148+ *
149+ * @param $bundleLinks
150+ * @param $option
151+ * @return array
152+ * @throws NoSuchEntityException
153+ */
154+ private function setProductLink ($ bundleLinks , $ option ): array
155+ {
156+ $ links = [];
157+ $ options = [];
158+ if (!empty ($ bundleLinks )) {
159+ foreach ($ bundleLinks as $ linkData ) {
160+ if (!(bool )$ linkData ['delete ' ]) {
161+ /** @var LinkInterface $link */
162+ $ link = $ this ->objectManager ->create (LinkInterfaceFactory::class)
163+ ->create (['data ' => $ linkData ]);
164+ $ linkProduct = $ this ->productRepository ->getById ($ linkData ['product_id ' ]);
165+ $ link ->setSku ($ linkProduct ->getSku ());
166+ $ link ->setQty ($ linkData ['selection_qty ' ]);
167+ $ link ->setPrice ($ linkData ['selection_price_value ' ]);
168+ if (isset ($ linkData ['selection_can_change_qty ' ])) {
169+ $ link ->setCanChangeQuantity ($ linkData ['selection_can_change_qty ' ]);
170+ }
171+ $ links [] = $ link ;
172+ }
173+ }
174+ $ option ->setProductLinks ($ links );
175+ $ options [] = $ option ;
176+ }
177+ return $ options ;
178+ }
179+
180+ /**
181+ * Set product option
182+ *
183+ * @return array
184+ * @throws NoSuchEntityException
185+ */
186+ private function setProductOption (): array
187+ {
188+ $ options = [];
189+ $ product = $ this ->productRepository ->get ('bundle-product ' , true );
190+ foreach ($ product ->getBundleOptionsData () as $ optionData ) {
191+ if (!(bool )$ optionData ['delete ' ]) {
192+ $ option = $ this ->objectManager ->create (OptionInterfaceFactory::class)
193+ ->create (['data ' => $ optionData ]);
194+ $ option ->setSku ($ product ->getSku ());
195+ $ option ->setOptionId (null );
196+
197+ $ bundleLinks = $ product ->getBundleSelectionsData ();
198+ if (!empty ($ bundleLinks )) {
199+ $ options = $ this ->setProductLink (current ($ bundleLinks ), $ option );
200+ }
201+ }
202+ }
203+ return $ options ;
204+ }
205+
206+ /**
207+ * Set bundle product option data
208+ *
209+ * @return array
210+ * @throws NoSuchEntityException
211+ */
212+ private function setBundleProductOptionData (): array
213+ {
214+ $ options = [];
215+ $ product = $ this ->productRepository ->get ('bundle-product ' , true );
216+ $ simpleProduct = $ this ->productRepository ->get ('simple ' );
217+ $ product ->setBundleOptionsData (
218+ [
219+ [
220+ 'title ' => 'Bundle Product Items ' ,
221+ 'default_title ' => 'Bundle Product Items ' ,
222+ 'type ' => 'select ' , 'required ' => 1 ,
223+ 'delete ' => '' ,
224+ ],
225+ ]
226+ );
227+ $ product ->setBundleSelectionsData (
228+ [
229+ [
230+ [
231+ 'product_id ' => $ simpleProduct ->getId (),
232+ 'selection_price_value ' => 10 ,
233+ 'selection_qty ' => 1 ,
234+ 'selection_can_change_qty ' => 1 ,
235+ 'delete ' => '' ,
236+
237+ ],
238+ ],
239+ ]
240+ );
241+ if ($ product ->getBundleOptionsData ()) {
242+ $ options = $ this ->setProductOption ();
243+ }
244+ return $ options ;
245+ }
89246}
0 commit comments