0

I am writing a module that uses a cli command get a csv file and use that to change the prices of a selection of products based on sku and new price retrieved from an CSV file.

I have the logic for the CLI command, for reading the csv and getting a collection of products based on the the sku's. But I would like to en mass change the prices for all the products.

How I now have it working now is that my module extends the command class and adds a cli command for this specific situation, bin/magento import:somename:pricingcsv path/to/file.csv. I use Magento\Framework\File\Csv class to read the csv get the sku's and prices, get a product collection, loop over every product in the collection set the new price and save them individually, but seeing as there are over 5000 products this method takes almost a second per product so over 1.5 hours in total.

$productCollection = $this->productCollectionFactory->create();
$productCollection->addFieldToSelect('*'); // only need sku, price, id,
$productCollection->addAttributeToFilter('sku', ['in' => array_keys($productsArray)]);

/** @var Product $product */
foreach($productCollection as $product) {
    /** @var Action */ // injected using the constructor
    $this->productAction->updateAttributes([$product->getId()], ['price' => $newPrice], 0);

Even though the price is the only property that is changing, saving the product object will go over all the product properties and update everyone even though only the price has changed.

I imagine that has to be a more streamlined way to do this. I have been looking through the

1 Answer 1

0

I did as below and working smothly

$product = $objectManager->create('\Magento\Catalog\Api\ProductRepositoryInterface')->getById($productid);
if($product->getId()) {
    $brandIds = $connection->fetchCol(" SELECT brand_id FROM ".$table_name." WHERE product_id = ".$productid);
    if(!empty($brandIds)){   
        echo $productid." \n ";         
        $objectManager->get('Magento\Catalog\Model\Product\Action')->updateAttributes(array($product->getId()),['product_brand' => implode($brandIds, ',')], 0);
    }                 
}
2
  • I don't think that is the right way to use the objectmanager, and you still are updating a single product. Sep 23, 2021 at 14:13
  • objectmanager is for just example. you can use proper way through constructor. and I am updating single product becuase all product has not same brand. you can assign multiple products through array. if same price for all products Sep 23, 2021 at 14:33

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.