web-dev-qa-db-fra.com

Magento supprime par programme les images de produits

Cela doit être une tâche de programmation tellement simple que je ne trouve absolument aucune information à ce sujet sur le net. Fondamentalement, j'essaie de SUPPRIMER les images de produits. Je souhaite supprimer toutes les images de la galerie multimédia d'un produit. Puis-je le faire sans parcourir un million de lignes de code pour une tâche aussi simple?

Veuillez noter que j'ai déjà essayé ceci:

$attributes = $product->getTypeInstance()->getSetAttributes();
if (isset($attributes['media_gallery'])) {
    $gallery = $attributes['media_gallery'];
    $galleryData = $product->getMediaGallery();//this returns NULL

    foreach($galleryData['images'] as $image){
        if ($gallery->getBackend()->getImage($product, $image['file'])) {
            $gallery->getBackend()->removeImage($product, $image['file']);
        }
    }
}

Cela ne fonctionne absolument pas. J'essaie de supprimer des images lors d'une importation afin de ne pas conserver de doublons. Toute aide serait grandement appréciée.

22
user439441

D'accord, c'est ainsi que j'ai finalement résolu mon problème.

if ($product->getId()){
    $mediaApi = Mage::getModel("catalog/product_attribute_media_api");
    $items = $mediaApi->items($product->getId());
    foreach($items as $item)
        $mediaApi->remove($product->getId(), $item['file']);
}

C'est le lien qui m'a finalement mis la tête droite: http://www.magentocommerce.com/wiki/doc/webservices-api/api/catalog_product_attribute_media

Dommage que ce ne soit pas aussi simple que $ product-> getImages (), hein?

46
user439441

Dans Magento 1.7.0.2 j'utilise ce code pour supprimer toutes les images d'une galerie de produits:

//deleting
Mage::app()->getStore()->setId(Mage_Core_Model_App::ADMIN_STORE_ID);
$mediaApi = Mage::getModel("catalog/product_attribute_media_api");
$items = $mediaApi->items($product->getId());
$attributes = $product->getTypeInstance()->getSetAttributes();
$gallery = $attributes['media_gallery'];
foreach($items as $item){
    if ($gallery->getBackend()->getImage($product, $item['file'])) {
        $gallery->getBackend()->removeImage($product, $item['file']);
    }
}
$product->save();

Avec le code de la réponse de Davids Tay, j'ai eu l'erreur: Erreur fatale: exception non interceptée ‘Mage_Eav_Model_Entity_Attribute_Exception’ avec le message ‘SQLSTATE [23000]: violation de contrainte d’intégrité: 1452 Impossible d’ajouter ou de mettre à jour une ligne enfant: une contrainte de clé étrangère échoue (base_xxx.catalog_product_entity_media_gallery_value, CONTRAINTE FK_CAT_PRD_ENTT_MDA_GLR_VAL_VAL_ID_CAT_PRD_ENTT_MDA_GLR_VAL_ID CLÉ ÉTRANGÈRE (value_id) RÉFÉRENCES `catalog_prod) '

9

Pour supprimer toutes les images d'une galerie de produits:

$product = Mage::getModel('catalog/product')->load($id);
$mediaGalleryAttribute = Mage::getModel('catalog/resource_eav_attribute')->loadByCode($entityTypeId, 'media_gallery');
$gallery = $product->getMediaGalleryImages();
foreach ($gallery as $image)
    $mediaGalleryAttribute->getBackend()->removeImage($product, $image->getFile());
$product->save();
8
Pihtt

Lors de la suppression d'images, j'ai trouvé une chose intéressante. Lorsque vous essayez ce code:

$galleryData = $product->getMediaGallery(); //this returns NULL

L'objet de galerie multimédia dépend de la façon dont votre produit a été créé, si:

$product = Mage::getModel('catalog/product')->loadByAttr('sku', $sku);

alors la galerie multimédia sera vide si:

$product = Mage::getModel('catalog/product')->load($id);

alors la galerie multimédia est un objet et vous pouvez utiliser cet objet pour supprimer des images de db. Pour supprimer des images du système de fichiers, vous devez ajouter un tel code:

@unlink(Mage::getBaseDir('media') . '\catalog\product\' . $image['file']);

mais si vous voulez changer l'image et la nommer comme image précédente (remplacer image1.png par image1.png) dans ce cas, vous aurez un problème de mise en cache du navigateur.

Vous pouvez également essayer de charger la galerie multimédia pour le produit:

$product->getResource()->getAttribute('media_gallery')->getBackend()->afterLoad($product);
5

C'est le code que j'ai finalement décidé d'utiliser pour cette tâche.

protected function _removeMediaGalleryImages(Mage_Catalog_Model_Product $product)
{
    $mediaGalleryData = $product->getMediaGallery();
    if (!isset($mediaGalleryData['images']) || !is_array($mediaGalleryData['images'])) {
        return;
    }

    $toDelete = array();
    foreach ($mediaGalleryData['images'] as $image) {
        $toDelete[] = $image['value_id'];
    }
    Mage::getResourceModel('catalog/product_attribute_backend_media')->deleteGallery($toDelete);
}
4
Colin Tickle

J'espère que cette réponse n'est pas malvenue, car ce n'est techniquement pas une solution obtenue via la programmation Magento comme vous le demandez, mais j'ai réussi à purger toutes les images de la galerie moi-même dans le même but simplement en tronquant les tableaux pertinents dans Magento 1.4.2.0 (je crois que c'est la même structure de table en 1.5 aussi).

TRUNCATE TABLE `catalog_product_entity_media_gallery`
TRUNCATE TABLE `catalog_product_entity_media_gallery_value`

Suivez ensuite en supprimant tous les fichiers image du répertoire / media/catalog/product.

J'ai cherché moi-même un moyen de le faire par programme, mais j'ai trouvé cela beaucoup plus efficace et je n'ai eu aucun effet secondaire négatif.

3
CVM
     Just use this code to create .php file and place it to root folder of magento.

    <?php 
    require_once 'app/Mage.php';

    Mage::app();
    Mage::app()->getStore()->setId(Mage_Core_Model_App::ADMIN_STORE_ID);

    $products = Mage::getModel('catalog/product')->getCollection();
      //->addAttributeToFilter('entity_id', array('gt' => 14000));

    $mediaApi = Mage::getModel("catalog/product_attribute_media_api");

    foreach($products as $product) {
        $prodID = $product->getId();
        $_product = Mage::getModel('catalog/product')->load($prodID);
        $items = $mediaApi->items($_product->getId());
        foreach($items as $item) {
            $mediaApi->remove($_product->getId(), $item['file']);
        }
    }
?>
3
Ramesh

Et ça

Mage::app()->getStore()->setId(Mage_Core_Model_App::ADMIN_STORE_ID);
    $mediaApi = Mage::getModel("catalog/product_attribute_media_api");
    $items = $mediaApi->items($product->getId());
    $attributes = $product->getTypeInstance()->getSetAttributes();
    $gallery = $attributes['media_gallery'];
    foreach($items as $item){
        if ($gallery->getBackend()->getImage($product, $item['file'])) {
            $gallery->getBackend()->removeImage($product, $item['file']);
        }
    }
    $product->save();
1
Vinay Sikarwar

Si vous souhaitez supprimer plus de produits comme 1000 ou 5000, utilisez celui du bas avec une requête directe.

Avant d'essayer celui-ci, faites une sauvegarde de votre base de données

<?php
require_once 'app/Mage.php';
umask(0);
Mage::app();
set_time_limit(0);
ini_set('display_error','1');


$resource = Mage::getSingleton('core/resource');
$connection = $resource->getConnection('core_write');

$id = 101;
$product = Mage::getModel('catalog/product')->load($id);

$q = "DELETE FROM `catalog_product_entity_media_gallery` where entity_id = '".$product->getId()."'"; 

$connection->query($q);

?>
1
Prashant Barot

Méthode la plus rapide pour supprimer l'image, puis suivez les étapes ci-dessous: supprimez tous les enregistrements de

  1. catalog_product_entity_media_gallery
  2. catalog_product_entity_media_gallery_value'

car Magento enregistre toutes les données d'image du produit dans ces tables.

Ensuite, indexez à partir de la gestion des index de l'administrateur pour définir le noir de l'image.

Ensuite, supprimez l'image from dir puis allez dans votre répertoire magento à media/catalog/product et de ce dossier supprimez tous les fichiers.

Un autre processus:

Andy Simpson, vous avez besoin d'un script qui is delete all product de votre système qui delete from DB and file system.

Étape1: Créer a php à root direct of magento system qui inclut Mage.php at first code.

require_once "YOURMAGENTODIR/app/Mage.php";
umask(0);

Step2: set current store is admin et définir le mode développeur

Mage::app('admin');
Mage::setIsDeveloperMode(true);

Étape3: Obtenez Product Collection et créer une boucle pour obtenir un produit un par un

$productCollection=Mage::getResourceModel('catalog/product_collection');

Step4: récupérer l'image du produit par un et supprimer l'image un en utilisant le code ci-dessous:

$remove=Mage::getModel('catalog/product_attribute_media_api')->remove($product->getId(),$eachImge['file']);

CODE COMPLET:

<?php
require_once "YOURMAGENTODIR/app/Mage.php";
umask(0);
Mage::app('admin');
Mage::setIsDeveloperMode(true);

$productCollection=Mage::getResourceModel('catalog/product_collection');
foreach($productCollection as $product){
echo $product->getId();
echo "<br/>";
         $MediaDir=Mage::getConfig()->getOptions()->getMediaDir();
        echo $MediaCatalogDir=$MediaDir .DS . 'catalog' . DS . 'product';
echo "<br/>";

$MediaGallery=Mage::getModel('catalog/product_attribute_media_api')->items($product->getId());
echo "<pre>";
print_r($MediaGallery);
echo "</pre>";

    foreach($MediaGallery as $eachImge){
        $MediaDir=Mage::getConfig()->getOptions()->getMediaDir();
        $MediaCatalogDir=$MediaDir .DS . 'catalog' . DS . 'product';
        $DirImagePath=str_replace("/",DS,$eachImge['file']);
        $DirImagePath=$DirImagePath;
        // remove file from Dir

        $io     = new Varien_Io_File();
         $io->rm($MediaCatalogDir.$DirImagePath);

        $remove=Mage::getModel('catalog/product_attribute_media_api')->remove($product->getId(),$eachImge['file']);
    }


}
1
Amit Bera

Placez le script ci-dessous dans la racine magento et exécutez

 <?php

  require_once("app/Mage.php");
  umask(0);
   Mage::app();
   $ob = new Clean();
   $ob->removemedia();

 Class Clean {

 function removemedia() {
$read = Mage::getSingleton('core/resource')->getConnection('core_read');
$select = $read->select()
        ->from('catalog_product_entity_media_gallery', '*')
        ->group(array('value_id'));

$flushImages = $read->fetchAll($select);
echo count($flushImages);
$array = array();
foreach ($flushImages as $item1) {
    $array[] = $item1['value'];
}

$valores = $array;

$pepe = 'media' . DS . 'catalog' . DS . 'product';

$leer = $this->listDirectories($pepe);

foreach ($leer as $item) {
    try {
        $item = strtr($item, '\\', '/');
        if (!in_array($item, $valores)) {
            $valdir[]['filename'] = $item;
            unlink('media/catalog/product' . $item);
        }
    } catch (Zend_Db_Exception $e) {

    } catch (Exception $e) {
        //Mage::log($e->getMessage());
    }
  }
 }

function listDirectories($path) {
    if (is_dir($path)) {
       if ($dir = opendir($path)) {
        while (($entry = readdir($dir)) !== false) {
            if (preg_match('/^\./', $entry) != 1) {
                if (is_dir($path . DS . $entry) && !in_array($entry, array('cache', 'watermark'))) {
                    $this->listDirectories($path . DS . $entry);
                } elseif (!in_array($entry, array('cache', 'watermark')) && (strpos($entry, '.') != 0)) {
                    $this->result[] = substr($path . DS . $entry, 21);
                }
            }
        }
        closedir($dir);
    }
 }
 return $this->result;
 }

  }
0
Bharani K

Accéder à la base de données pour de telles choses est une mauvaise idée. Vous pouvez supprimer des images (ou les réorganiser en modifiant la valeur de la "position") à l'aide de l'extrait de code suivant dans un module personnalisé (par souci de simplicité, j'utilise ObjectManager, mais vous devez placer ProductFactory et ProductRepositoryInterface dans le constructeur)

$objectManager = ObjectManager::getInstance();

//Get ProductFactory in order to instatiate the Product Object 
$productFactory = $objectManager->get('\Magento\Catalog\Model\ProductFactory');

//We have to use ProductRepositoryInterface in order to save the changes bellow to the product
$productRepository = $objectManager->get('\Magento\Catalog\Api\ProductRepositoryInterface');

//Load a Product by ID in this case 1
$product = $productFactory->create()->load(1);

//Gets an array containing arrays representing each image in the gallery
$mediaGalleryEntries = $product->getMediaGalleryEntries();

//Here we delete every image, you can use conditions in foreach
foreach ($mediaGalleryEntries as $key => $imageEntry) {
    unset($mediaGalleryEntries[$key]);
}

//Finally set the altered entries and save using productRepository
$product->setMediaGalleryEntries($mediaGalleryEntries);
$productRepository->save($product);

Le code ci-dessus testé dans Magento 2.3 et il supprime également les images du système de fichiers. Vous pouvez l'utiliser pour supprimer ou modifier une entrée (modifier la position, les rôles d'image, etc.)

Pour afficher chaque imageEntry, vous pouvez accéder à ses données en utilisant $ imageEntry-> getData ()

0
sarakinos
DELETE FROM catalog_product_entity_media_gallery WHERE value_id NOT IN (SELECT * FROM (SELECT MIN(value_id) FROM `catalog_product_entity_media_gallery` GROUP BY LEFT(value,17), entity_id  having count(*) > 1) x)

pourquoi 17?

L'exemple que vous avez dupliqué comme ceci:

/0/0/000116810609_1.jpg

/0/0/000116810609_2.jpg

/0/0/000116810609_3.jpg

/0/0/000116810609_4.jpg

LEFT(value,17)

/ 0/0/000116810609

/ 0/0/000116810609

/ 0/0/000116810609

/ 0/0/000116810609

Non ce sont des doublons;)

0
Andrei Balmus

J'ai dû faire quelque chose de similaire il n'y a pas si longtemps - je devais remplacer toutes les images de produit lors d'une importation.

Ce lien a beaucoup aidé: http://www.sharpdotinc.com/mdost/2010/03/02/magento-import-multiple-images-or-remove-images-durring-batch-import/ =

J'espère que cela vous donnera un coup de pouce dans la bonne direction.

0
monkey do