Skip to content
intermediate Phase 20 · Module File Structure

Magento 2 Complete Module Architecture

All files in a module, their purposes, how they connect, and complete module directory tree.

1h
0 problems
Topic Progress 0%

Complete Module Directory Tree

A complete Magento 2 module contains many files, each serving a specific purpose.

app/code/Vendor/Module/
├── registration.php                    # Component registration
├── etc/
│   ├── module.xml                      # Module declaration
│   ├── di.xml                          # Global DI configuration
│   ├── events.xml                      # Global event observers
│   ├── routes.xml                      # Route definitions (deprecated)
│   ├── crontab.xml                     # Cron job definitions
│   ├── webapi.xml                      # REST API routes
│   ├── acl.xml                         # ACL permissions
│   ├── system.xml                      # System configuration
│   ├── config.xml                      # Default configuration values
│   ├── email_templates.xml             # Email template declarations
│   ├── indexers.xml                    # Indexer definitions
│   ├── queue_consumer.xml              # Message queue consumers
│   ├── queue_publisher.xml             # Message queue publishers
│   ├── queue_topology.xml              # Message queue topology
│   ├── communication.xml               # Message queue config
│   └── frontend/
│       ├── di.xml                      # Frontend DI config
│       ├── routes.xml                  # Frontend routes
│       ├── events.xml                  # Frontend observers
│       └── layout.xml                  # Layout file declarations
│   └── adminhtml/
│       ├── di.xml                      # Admin DI config
│       ├── routes.xml                  # Admin routes
│       ├── events.xml                  # Admin observers
│       ├── acl.xml                     # Admin ACL
│       └── menu.xml                    # Admin menu
│   └── webapi_rest/
│       └── di.xml                      # REST API config
│   └── webapi_graphql/
│       └── schema.graphql              # GraphQL schema
├── Api/
│   ├── Data/
│   │   └── ItemInterface.php           # Data transfer object interface
│   ├── ItemRepositoryInterface.php     # CRUD repository interface
│   └── ItemManagementInterface.php     # Business logic interface
├── Block/
│   ├── Item.php                        # Block class
│   └── Adminhtml/
│       └── Item.php                    # Admin block class
├── Controller/
│   ├── Index/
│   │   └── Index.php                   # Frontend controller
│   └── Adminhtml/
│       └── Item/
│           ├── Index.php               # Admin grid controller
│           ├── NewAction.php           # Admin form controller
│           ├── Save.php                # Admin save controller
│           └── Delete.php              # Admin delete controller
├── Cron/
│   └── Cleanup.php                     # Cron job class
├── Model/
│   ├── Item.php                        # Model class
│   ├── ItemFactory.php                 # (generated) Factory
│   ├── ResourceModel/
│   │   └── Item.php                    # Resource model (DB operations)
│   └── ResourceModel/
│       └── Item/
│           └── Collection.php         # Collection class
├── Observer/
│   └── ItemSave.php                    # Event observer
├── Plugin/
│   ├── ProductAfterSave.php            # After plugin
│   ├── ProductBeforeSave.php           # Before plugin
│   └── ProductAroundSave.php           # Around plugin
├── Service/
│   └── ItemService.php                 # Business service class
├── Setup/
│   ├── InstallSchema.php               # Schema installer
│   ├── UpgradeSchema.php               # Schema upgrader
│   ├── InstallData.php                 # Data installer
│   └── UpgradeData.php                 # Data upgrader
├── View/
│   ├── frontend/
│   │   ├── layout/
│   │   │   ├── default.xml             # Default layout
│   │   │   ├── catalog_product_view.xml # Product page layout
│   │   │   └── vendor_module_index_index.xml # Custom page layout
│   │   ├── templates/
│   │   │   └── item/
│   │   │       └── list.phtml          # Template file
│   │   ├── web/
│   │   │   ├── css/
│   │   │   │   └── source/
│   │   │   │       └── _module.less    # LESS source
│   │   │   ├── js/
│   │   │   │   └── custom.js           # JavaScript
│   │   │   └── images/
│   │   │       └── logo.png            # Image assets
│   │   └── requirejs-config.js         # RequireJS mapping
│   ├── adminhtml/
│   │   ├── layout/
│   │   │   └── vendor_module_item_index.xml
│   │   ├── templates/
│   │   └── ui_component/
│   │       └── item_listing.xml        # UI component grid
│   └── base/
│       └── web/
│           └── css/
│               └── _module.less        # Base styles
├── i18n/
│   ├── en_US.csv                       # English translations
│   └── fr_FR.csv                       # French translations
├── Test/
│   ├── Unit/
│   │   └── Model/
│   │       └── ItemTest.php            # Unit tests
│   └── Integration/
│       └── Model/
│           └── ItemRepositoryTest.php  # Integration tests
└── composer.json                       # Composer package definition

Total files: 50+ in a complete module.

Core Module Files Explained

Understanding each core file's purpose is essential for building complete modules.

registration.php:

<?php
use Magento\Framework\Component\ComponentRegistrar;

ComponentRegistrar::register(
    ComponentRegistrar::MODULE,
    'Vendor_Module',
    __DIR__
);

module.xml:

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:framework:Module/etc/module.xsd">
    <module name="Vendor_Module" setup_version="1.0.0">
        <sequence>
            <module name="Magento_Catalog"/>
        </sequence>
    </module>
</config>

di.xml:

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <type name="Vendor\Module\Service\ItemService">
        <arguments>
            <argument name="batchSize" xsi:type="number">100</argument>
        </arguments>
    </type>
    <type name="Magento\Catalog\Model\ProductRepository">
        <plugin name="vendor_product_after_save"
                type="Vendor\Module\Plugin\ProductAfterSave"
                sortOrder="10"/>
    </type>
</config>

Model class:

<?php
namespace Vendor\Module\Model;

use Magento\Framework\Model\AbstractModel;
use Vendor\Module\Api\Data\ItemInterface;

class Item extends AbstractModel implements ItemInterface
{
    const ENTITY_ID = 'entity_id';
    const NAME = 'name';
    const STATUS = 'status';
    
    protected function _construct()
    {
        $this->_init(\Vendor\Module\Model\ResourceModel\Item::class);
    }
    
    public function getEntityId(): ?int
    {
        return $this->getData(self::ENTITY_ID);
    }
    
    public function getName(): ?string
    {
        return $this->getData(self::NAME);
    }
}

Resource Model:

<?php
namespace Vendor\Module\Model\ResourceModel;

use Magento\Framework\Model\ResourceModel\Db\AbstractDb;

class Item extends AbstractDb
{
    protected function _construct()
    {
        $this->_init('vendor_module_items', 'entity_id');
    }
}

Module Configuration Files

Each configuration file in etc/ serves a specific purpose in the module lifecycle.

Routes (etc/frontend/routes.xml):

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
    <router id="standard">
        <route id="vendor_module" frontName="vendormodule">
            <module name="Vendor_Module"/>
        </route>
    </router>
</config>

Events (etc/events.xml):

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:framework:Event/etc/events.xsd">
    <event name="catalog_product_save_after">
        <observer name="vendor_product_after_save"
                  instance="Vendor\Module\Observer\ItemSave"/>
    </event>
</config>

Cron (etc/crontab.xml):

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Cron:etc/crontab.xsd">
    <group id="default">
        <job name="vendor_cleanup"
             instance="Vendor\Module\Cron\Cleanup"
             method="execute">
            <schedule>0 2 * * *</schedule>
        </job>
    </group>
</config>

REST API (etc/webapi.xml):

<?xml version="1.0"?>
<routes xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Webapi:etc/webapi.xsd">
    <route url="/V1/items/:itemId" method="GET">
        <service class="Vendor\Module\Api\ItemRepositoryInterface" method="getById"/>
        <resources><resource ref="anonymous"/></resources>
    </route>
</routes>

ACL (etc/acl.xml):

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:framework:Acl/etc/acl.xsd">
    <acl>
        <resources>
            <resource id="Magento_Backend::admin">
                <resource id="Vendor_Module::menu" title="Vendor Module">
                    <resource id="Vendor_Module::items" title="Manage Items"/>
                </resource>
            </resource>
        </resources>
    </acl>
</config>

Module Lifecycle and Best Practices

Building a complete module follows a lifecycle from creation to production deployment.

Development lifecycle:

# 1. Create module structure
mkdir -p app/code/Vendor/Module/{etc,Model,Block,Controller}

# 2. Create registration.php
# 3. Create module.xml
# 4. Create etc/di.xml
# 5. Develop module functionality
# 6. Run setup:upgrade
php bin/magento setup:upgrade

# 7. Compile DI
php bin/magento setup:di:compile

# 8. Deploy static content
php bin/magento setup:static-content:deploy

# 9. Clean cache
php bin/magento cache:clean

Production deployment checklist:

# Switch to production mode
php bin/magento deploy:mode:set production

# Compile DI
php bin/magento setup:di:compile

# Deploy static content
php bin/magento setup:static-content:deploy -f

# Clean and warm cache
php bin/magento cache:clean
php bin/magento cache:warmup

# Enable maintenance mode if needed
php bin/magento maintenance:enable
php bin/magento maintenance:disable

Module file summary:

File Purpose
registration.php Register component
module.xml Declare module
di.xml DI configuration
events.xml Observer registration
routes.xml URL routing
crontab.xml Scheduled tasks
webapi.xml REST API routes
acl.xml Permissions
system.xml Admin config
Setup/*.php DB schema/data

Best practices:

  • Keep modules focused on single responsibility
  • Use interfaces for all service contracts
  • Follow Magento coding standards
  • Write tests for business logic
  • Use plugins over events for method modification
  • Keep di.xml clean with virtual types
  • Version modules properly with setup_version

Quiz

1. What is the minimum set of files for a Magento 2 module?

Question 1 options

2. Which file defines REST API routes in a module?

Question 2 options

3. Where do database schema scripts go?

Question 3 options

Flashcards

Question

What are the 10+ XML files in a complete module's etc/ directory?

Answer

module.xml, di.xml, events.xml, routes.xml, crontab.xml, webapi.xml, acl.xml, system.xml, config.xml, email_templates.xml, and area-specific variants

Question

What does the Setup/ directory contain?

Answer

InstallSchema.php, UpgradeSchema.php, InstallData.php, UpgradeData.php

Question

Where do admin controllers go?

Answer

Controller/Adminhtml/{Entity}/{Action}.php

Question

What is the purpose of Api/ directory?

Answer

Service contract interfaces for external API exposure

Revision Notes

Key Takeaways

  • 1. Complete modules have 50+ files across multiple directories
  • 2. registration.php and module.xml are the minimum required files
  • 3. etc/ contains all XML configuration files
  • 4. Model/ handles business logic, Controller/ handles requests
  • 5. Setup/ manages database schema and data migrations
  • 6. Api/ defines service contracts for API exposure
  • 7. View/ contains templates, layouts, CSS, and JavaScript
  • 8. Follow Magento coding standards and best practices

Interview Tips

  • Draw a complete module directory tree from memory
  • Explain the purpose of each etc/ XML file
  • Describe the Model-ResourceModel-Collection pattern
  • Discuss service contracts and their importance
  • Know the development lifecycle from creation to deployment
  • Explain how to create a complete module from scratch

Cheat Sheet

Module Architecture Cheat Sheet

Core Files:

  • registration.php → Component registration
  • etc/module.xml → Module declaration
  • etc/di.xml → DI configuration

Model Pattern:

Model/Item.php → Business logic
Model/ResourceModel/Item.php → DB operations
Model/ResourceModel/Item/Collection.php → Query builder

etc/ Files:
module.xml, di.xml, events.xml, routes.xml, crontab.xml, webapi.xml, acl.xml, system.xml, config.xml

Setup/ Files:
InstallSchema.php, UpgradeSchema.php, InstallData.php, UpgradeData.php

View/ Structure:

view/{area}/layout/ → Layout XML
view/{area}/templates/ → PHP templates
view/{area}/web/css/ → Stylesheets
view/{area}/web/js/ → JavaScript