Magento Observer Events - ordre des opérations


9

J'essaie d'injecter des fonctionnalités dans l' catalog_model_product_duplicateévénement. Une partie de ce module consistera à s'assurer que l'état du stock du produit dupliqué est également dupliqué; actuellement ce n'est pas le cas.

Je vois que CatalogInventoryobserve cet événement et met en place des informations boursières standard. Puis-je être assuré que les événements principaux sont résolus avant mes sections locales? Y a-t-il un ordre d'opérations sur lequel je peux compter?

Réponses:


11

L'ordre dans lequel les événements sont distribués dépend de l'ordre dans lequel les modules sont chargés. Puisque vous devez être sûr que les CatalogInventoryobservateurs du module tirent avant le vôtre, ce que vous devez faire est simplement de configurer votre module en fonction du Mage_CatalogInventorymodule. Vous pouvez le faire en ajoutant un nœud dépendant au code de votre app/etc/modules/My_Module.xmlfichier:

<config>
    <modules>
        <My_Module>
            <active>true</active>
            <codePool>local</codePool>
            <depends>
                <Mage_CatalogInventory />
            </depends>
        </My_Module>
    </modules>
</config>

Le dependsnœud dans le XML ci-dessus est l'élément de configuration crucial ici, car il force le module principal de Magento à se charger avant le vôtre.


7

L'ordre dans lequel les événements sont envoyés ne peut pas être facilement garanti. Ils dépendent de l'ordre dans lequel les modules sont chargés. En règle générale, tous les observateurs d'événements de base seront appelés avant les observateurs communautaires et locaux du pool de codes.

Il existe une méthode pour forcer les observateurs de magento à tirer après un personnalisé en "simulant" une dépendance d'un module principal à un module local ou communautaire. Jetez un œil à la réponse de Lee ici: faites un tir d'observateur personnalisé avant un observateur Magento existant .

/app/etc/modules/Groupname_Page.xml

<config>
    <modules>
        <Groupname_Page>
            <active>true</active>
            <codePool>local</codePool>
            <depends>
                <!-- Your dependencies go here -->
            </depends>
        </Groupname_Page>
        <Enterprise_PageCache>
            <depends>
                <Groupname_Page />
            </depends>
        </Enterprise_PageCache>
    </modules>
</config>

Personnellement, je n'aime pas cette approche car je ne sais pas quelles seraient les conséquences du forçage de cette dépendance.

Pour votre cas d'utilisation, il semble que vous devriez faire une sorte de détection de données / état pour savoir s'il a été déclenché ou non. Il serait préférable de vérifier les données / l'état d'un modèle plutôt que d'essayer de forcer un ordre d'événement.


Dans mon cas, cependant, je n'ai rien à faire si l'article en stock n'existe pas encore. Avez-vous des réflexions sur un événement ultérieur que j'ai pu flairer pour voir si c'était le résultat de la méthode en double?
philwinkle

5

Une réponse générale

Les observateurs sont exécutés d' abord par zone , puis par ordre de chargement des modules

Cela signifie que tous les observateurs enregistrés dans <global>sont exécutés avant tous les observateurs enregistrés dans <frontend>ou <adminhtml>.

Dans une zone, les observateurs sont exécutés dans l'ordre dans lequel ils apparaissent dans l'arborescence XML de configuration fusionnée, ce qui signifie techniquement dans l'ordre dans lequel les modules ont été chargés.

L'ordre de chargement des modules est déterminé comme suit:

  1. Un graphique de dépendance est construit à partir des <depends>définitions de app/etc/modules/*.xml. Si X dépend de Y, Y est chargé avant X.

  2. Après la commande par dépendance, les modules principaux ont priorité sur les modules communautaires et locaux

  3. Tout le reste est chargé par ordre alphabétique. Notez que le nom de fichier dans app/etc/modulesest utilisé pour la comparaison, pas le nom réel du module.

Vous avez donc deux options pour influencer l'ordre de chargement des modules:

  1. dépendre d'un autre module pour faire exécuter vos observateurs après lui (ou faire dépendre l'autre module du vôtre pour les faire exécuter avant)
  2. Renommez le fichier de définition du module. Vous n'avez pas besoin de renommer le module lui-même car le nom de fichier n'a pas d'importance pour autre chose que l'ordre de chargement.

("3. ajoutez votre module au pool de code principal" ne compte pas)

Voir également:


1

Juste une suggestion, observez les deux catalog_model_product_duplicateet catalog_model_product_save_afteravec un observateur singleton. En catalog_model_product_duplicatedéfinissant les données d'inventaire en tant que données d'observateur et en catalog_model_product_save_afterutilisant ces données pour remplir l'inventaire du produit dupliqué.


Vous proposez donc d'enregistrer une propriété dans l'objet qui m'a été donné dans le cas échéant, puis de la tester sur catalog_model_product_save_after... cela pourrait fonctionner. Le seul écueil serait la persistance de la propriété sans appeler save()... des pensées là-bas?
philwinkle

Vous économiserez le modèle d'inventaire, pas le produit, vous ne devriez donc pas être pris dans une boucle.
Petar Dzhambazov
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.