Adobe Commerce Developer Expert study materials
Adobe Commerce Developer Expert study resources

Adobe Commerce Developer Expert: Commerce Development: PHP, Modules, Dependency Injection, Plugins

Adobe Commerce Developer Expert · Work through your exam, one topic at a time.

All guide sections

Commerce Development: PHP, Modules, Dependency Injection, Plugins

Object manager and DI

Magento's object manager builds classes from di.xml. Understand constructor injection versus the discouraged ObjectManager::getInstance(). Know argument types: string, number, boolean, array, and object (with shared="false" for non-shared instances). Virtual types let you configure a named variant of a class without subclassing.

Plugins in depth

A plugin targets a public method of a class or interface. before methods receive original arguments and return modified arguments (or null to skip); around methods receive the callable $proceed and must return the result; after methods receive the result and can return a modified value. Plugins cannot intercept final classes/methods, static methods, or non-public methods. Order is controlled by sortOrder and the plugin list in di.xml; plugins on interfaces apply to implementations resolved through that interface.

Events, observers, and cron

Events are dispatched via the event manager; observers cannot change return values, making them suitable for side effects. Cron jobs are declared in crontab.xml with a group and schedule; know that cron group configuration lives in config.xml. Console commands are declared in di.xml under Magento\Framework\Console\CommandList.

Traps

  • A plugin on a method that is itself called internally (not via DI proxy) will not fire.
  • around plugins that forget to call $proceed break functionality.
  • Assuming after plugins can change arguments; they cannot.
  • Registering a plugin on a final method silently fails.

Worked example

To log every product save: create a plugin on ProductRepositoryInterface::save with a before method that logs $product->getSku(), declared in etc/di.xml with a type node for the interface. Because the repository is resolved through the interface, the plugin fires for all implementations.