magento / magento2

Prior to making any Submission(s), you must sign an Adobe Contributor License Agreement, available here at: https://opensource.adobe.com/cla.html. All Submissions you make to Adobe Inc. and its affiliates, assigns and subsidiaries (collectively “Adobe”) are subject to the terms of the Adobe Contributor License Agreement.
http://www.magento.com
Open Software License 3.0
11.48k stars 9.29k forks source link

Custom option saved missing values when edit option same value #6747

Closed thaohientruong closed 6 years ago

thaohientruong commented 7 years ago

Preconditions

  1. Magento ver. 2.0.7
  2. PHP 7.0.9

I add a new module with same custom option. My module is add a questionnaire with multi option and choice values. I don't save value success. Magento same bug so. When product custom option are saved with same continuity value. The first value saved success, The continued value saved fail.

Steps to reproduce

  1. View detail product. Add some custom option. Save product
  2. View detail product. Before save: before_edit_option
  3. Edit values of custom option. Before save: before_save_edit_option
  4. Save product. After save, view custom option: after_save_edit_option

    Expected result

  1. Should handle edit the same value for same continuity value option and value of the custom option.

The option and value of the custom option run loop saved. After save always update Stored Data public function afterSave() { $this->cleanModelCache(); $this->_eventManager->dispatch('model_save_after', ['object' => $this]); $this->_eventManager->dispatch('clean_cache_by_tags', ['object' => $this]); $this->_eventManager->dispatch($this->_eventPrefix . '_save_after', $this->_getEventData()); $this->updateStoredData(); return $this; } private function updateStoredData() { if (isset($this->_data)) { $this->storedData = $this->_data; } else { $this->storedData = []; } return $this; } But set model for save of all custom option is one. (for both model saved option and values) `public function saveOptions() { foreach ($this->getOptions() as $option) { $this->_validatorBeforeSave = null; $this->setData( $option )->setData( 'product_id', $this->getProduct()->getId() )->setData( 'store_id', $this->getProduct()->getStoreId() ); /* Reset is delete flag from the previous iteration / $this->isDeleted(false);

        if ($this->getData('option_id') == '0') {
            $this->unsetData('option_id');
        } else {
            $this->setId($this->getData('option_id'));
        }
        $isEdit = (bool)$this->getId() ? true : false;

        if ($this->getData('is_delete') == '1') {
            if ($isEdit) {
                $this->getValueInstance()->deleteValue($this->getId());
                $this->deletePrices($this->getId());
                $this->deleteTitles($this->getId());
                $this->delete();
            }
        } else {
            if ($this->getData('previous_type') != '') {
                $previousType = $this->getData('previous_type');

                /**
                 * if previous option has different group from one is came now
                 * need to remove all data of previous group
                 */
                if ($this->getGroupByType($previousType) != $this->getGroupByType($this->getData('type'))) {
                    switch ($this->getGroupByType($previousType)) {
                        case self::OPTION_GROUP_SELECT:
                            $this->unsetData('values');
                            if ($isEdit) {
                                $this->getValueInstance()->deleteValue($this->getId());
                            }
                            break;
                        case self::OPTION_GROUP_FILE:
                            $this->setData('file_extension', '');
                            $this->setData('image_size_x', '0');
                            $this->setData('image_size_y', '0');
                            break;
                        case self::OPTION_GROUP_TEXT:
                            $this->setData('max_characters', '0');
                            break;
                        case self::OPTION_GROUP_DATE:
                            break;
                    }
                    if ($this->getGroupByType($this->getData('type')) == self::OPTION_GROUP_SELECT) {
                        $this->setData('sku', '');
                        $this->unsetData('price');
                        $this->unsetData('price_type');
                        if ($isEdit) {
                            $this->deletePrices($this->getId());
                        }
                    }
                }
            }
            $this->save();
        }
    }
    //eof foreach()
    return $this;
}`

Before check defirrent change between new value and store data. `protected function prepareDataForUpdate($object) { $data = $object->getData(); foreach ($object->getStoredData() as $key => $value) { if (array_key_exists($key, $data) && $data[$key] === $value) { unset($data[$key]); } } $dataObject = clone $object; $dataObject->setData($data); $data = $this->_prepareDataForTable($dataObject, $this->getMainTable()); unset($data[$this->getIdFieldName()]); unset($dataObject);

    return $data;
}

` I fixed set new model with each loop. But it's not good solution. Do you have any solution?

mrkhoa99 commented 7 years ago

@thaohientruong Magento 2.0.7 default version has the same issue?

thaohientruong commented 7 years ago

@mrkhoa99 yup. You can check again when edit value custom option of product (like image attach above )

magento-engcom-team commented 6 years ago

@thaohientruong, thank you for your report. Please try to reproduce this issue on fresh and clean installation without any third-party dependencies. Please, add the following information:

magento-engcom-team commented 6 years ago

@thaohientruong, we are closing this issue due to inactivity. If you'd like to update it, please reopen the issue.