Magento 2 có cách nhanh hơn để thay đổi mục nhập thư viện phương tiện theo chương trình


8

Tôi cần thực hiện cập nhật lớn dữ liệu sản phẩm nhưng những gì tôi cần làm không thể đạt được khi nhập sản phẩm. Ví dụ, tôi cần cập nhật thư viện phương tiện và danh mục cho các sản phẩm nhất định, nhưng giải pháp tôi đưa ra mất quá nhiều thời gian.

Một tóm tắt nhỏ: Tôi đã thêm một lệnh vào Magento 2 CLI, với tệp cấu hình json, xóa, thêm, cập nhật hoặc sắp xếp các mục trong thư viện phương tiện cho một sản phẩm nhất định như thế này. Ở đây tôi dán một đoạn trích của mã:

/* $product is of type Magento\Catalog\Model\Product */

//get existing media gallery
$existingMediaGallery = $product->getMediaGallery();

/* 
   do stuff with media gallery (alter $existingMediaGallery)
   (add, remove, sort, ...)
*/

//set media gallery again
$product->setMediaGallery($existingMediaGallery);

//process media gallery
$mediaGalleryEntries = $product->getMediaGalleryEntries();
$this->getMediaGalleryProcessor()->clearMediaAttribute($product, array_keys($product->getMediaAttributes()));
if ($mediaGalleryEntries) {
  foreach ($mediaGalleryEntries as $k => $entry) {
    if (!isset($entry['removed']) && !empty($entry['types'])) {
      $this->getMediaGalleryProcessor()->setMediaAttribute($product, $entry['types'], $entry['file']);
    }
  }
}

//save product
$product->save();

Vì đây là một bản cập nhật lớn, dòng "$ sản phẩm-> save ()" được gọi nhiều lần và luôn mất từ ​​2 đến 4 giây. Vì tôi cần khởi chạy mã cho hàng ngàn sản phẩm, tôi cần một cách nhanh hơn để làm điều đó.

Tôi đã thử với

$product->getResource()->saveAttribute($product, 'media_gallery');

$product->addAttributeUpdate('media_gallery', $mediaGallery, $storeId);

nhưng điều đó không làm việc cho thư viện phương tiện (tôi chỉ làm việc cho eav).

Có cách nào để chỉ lưu thư viện phương tiện và duy trì những thay đổi này nhanh hơn không?

(Những gì tôi tìm kiếm là một cái gì đó giống như Magento\Catalog\Api\CategoryLinkManagementInterface::assignProductToCategoriesphương pháp lưu liên kết danh mục / sản phẩm nhanh hơn so với lưu toàn bộ sản phẩm)

Câu trả lời:


0

Tôi nghĩ rằng bạn đang đi đúng hướng: sản phẩm tiết kiệm đang mất nhiều thời gian và cần phải đi ..

Bây giờ, với cập nhật hình ảnh, điều đó có thể thực sự khó khăn. Nhưng tôi muốn nghĩ rằng nó có thể là một cách để phân tách vấn đề:

  • Tôi đoán là bạn cần dữ liệu đa phương tiện được lưu trữ trong cơ sở dữ liệu và điều đó có thể được thực hiện bằng cách sử dụng phương thức saveAttribution của bạn .. (rất nhanh). Tuy nhiên, bạn có thể muốn thêm một số thuộc tính trong tập lệnh cập nhật của mình: xem hình ảnh của thuộc tính, small_image, hình thu nhỏ '(xem trong cơ sở dữ liệu select * from eav_attribute where ((attribute_code like '%image%') or (attribute_code='thumbnail')) and entity_type_id=4))

  • bây giờ phức tạp hơn nhưng tôi có thể có một số ý tưởng, là để đối phó với hình ảnh nói về mặt vật lý và dữ liệu phương tiện bổ sung có thể (tiêu đề thẻ hình ảnh, vị trí, v.v.)

-> cho điểm thứ hai này: Tôi sẽ xem lớp Magento \ Catalog \ Model \ Product \ Gallery \ CreateHandler vì nó sẽ cho bạn thấy Magento giữ cho tất cả hoạt động liên quan đến dữ liệu truyền thông.


0

Theo tôi biết, không có cách nào để lưu các mục phương tiện mà không lưu sản phẩm. nhưng sản phẩm tiết kiệm không nên mất nhiều thời gian với sản phẩmRep repositoryInterface.

Tôi đã tạo một mô-đun tương tự và tôi không gặp vấn đề tương tự với lưu phương tiện.

Đây là giải pháp của tôi để lưu phương tiện:

 /**
     * Add Product media from folder.
     * @param $product
     * @param $productData
     * @return mixed
     */
    protected function setProductMedia($product, $productData)
    {
        $medias = [];
        $files = scandir(self::MEDIA_PATH);
        $mediaPath = '';
        foreach ($files as $file) {
            if ($file !== '.' && $file !== '..') {
                $path = realpath(self::MEDIA_PATH . $file);
                if ($path) {
                    if (basename($path, '.jpg') == trim($productData['productCode'])) {
                        $mediaPath = self::MEDIA_PATH . $file;
                        break;
                    }
                }
            }
        }

        if ((bool)$mediaPath) {
            $image = $this->_imageContent
               ->setBase64EncodedData(base64_encode(file_get_contents($mediaPath)))
               ->setType(image_type_to_mime_type(exif_imagetype($mediaPath)))
               ->setName(basename($mediaPath));

            $media = $this->_productAttributeMediaGalleryEntry
               ->setFile($mediaPath)
               ->setTypes(['thumbnail', 'small_image', 'image'])
               ->setLabel($productData['description'])
               ->setPosition(0)
               ->setMediaType('image')
               ->setContent($image)
               ->setDisabled(false)
               ->setPosition(0);

            $medias[] = $media;
            $product->setMediaGalleryEntries($medias);
       }

        return $product;
    }

Sau đó tôi lưu sản phẩm với sản phẩmRep repositoryInterface.

   try {
        $product = $this->_productRepository->get($productData['productCode']);
    } catch (NoSuchEntityException $e) {
        throw new NoSuchEntityException(__('Could Not Update Product Error: %1', $e->getMessage()));
    }

    $product = $this->setProductMedia($product, $productData);

    try {
       $this->_productRepository->save($product);
    } catch (InputException $exception) {
       $this->_logger->critical(__("Could not save product Error: %1", $exception->getMessage()));
    } catch (StateException $exception) {
       $this->_logger->critical(__("Could not save product, Error: %1",$exception->getMessage()));
    } catch (CouldNotSaveException $exception) {
       $this->_logger->critical(__('Could Not Save Product Error: %1' ,$exception->getMessage()));
    }

Nó tiết kiệm khá nhanh. Tôi có thể chạy 10.000 sản phẩm trong vòng vài phút. Điều đó bao gồm tìm kiếm phương tiện được đặt tên là {sku} .jpg và tất cả được nhồi trong một thư mục.


có thể chỉ đặt các vai trò hình ảnh tức là -> setTypes (['hình thu nhỏ', 'small_image', 'hình ảnh']) mà không thay thế toàn bộ hình ảnh?
ngủ
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.