We will build a very simple module in Magento 2. When done, the module output will be
"Hello world!"
in a content block on a route customized in the frontend.
1. Prerequisite
Needless to say, you will need the latest Magento 2 version of 2.3. Before we start developing the Magento 2 module, there are two things people often forget and I recommend:
- Disable Magento cache :
Disabling the Magento cache during development will save you time because you have won the need to clear cache every time you change your code.
The easiest way to disbale the cache is to go to Admin → System → Cache Management → select all cache types and turn them off.
- Put Magento in developer mode :
You should put Magento in developer mode to make sure you see all the bugs that Magento is throwing at you.
To do this, open your terminal and go to root Magento 2. From there you run the following command:
1 2 | php bin/magento deploy:mode:set developer |
2. Create module files and directories.
Module Setup
In Magento 2, modules are grouped by namespace and placed directly in the app / code directory.
So our first step is to create the module directory and the files needed to register the module.
1. Create the following directories:
- app / code / Magento_Ex
- app / code / Magento_Ex / Helloworld
The Magento_Ex folder is the module namespace, and Helloworld is the module name.
Note: If you do not have the code
directory in your app
directory, create it manually.
2. Now that we have a module directory, we need to create a module file in the app / code / Magento_Ex / Helloworld / etc directory with the following code:
1 2 3 4 5 6 7 | <span class="token php language-php"><span class="token delimiter important"><?</span> xml version <span class="token operator">=</span> <span class="token double-quoted-string string">"1.0"</span> <span class="token delimiter important">?></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> config</span> <span class="token attr-name"><span class="token namespace">xmlns:</span> xsi</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> http://www.w3.org/2001/XMLSchema-instance <span class="token punctuation">"</span></span> <span class="token attr-name"><span class="token namespace">xsi:</span> noNamespaceSchemaLocation</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> urn:magento:framework:Module/etc/module.xsd <span class="token punctuation">"</span></span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> module</span> <span class="token attr-name">name</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> Magento_Ex_Helloworld <span class="token punctuation">"</span></span> <span class="token attr-name">setup_version</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> 1.0.0 <span class="token punctuation">"</span></span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"></</span> module</span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"></</span> config</span> <span class="token punctuation">></span></span> |
3. To register the module, create the register.php file in the app / code / Magento_Ex / Helloworld directory with the following code:
1 2 3 4 5 6 7 8 | <span class="token php language-php"><span class="token delimiter important"><?php</span> <span class="token package">Magento Framework Component ComponentRegistrar</span> <span class="token punctuation">:</span> <span class="token punctuation">:</span> <span class="token function">register</span> <span class="token punctuation">(</span> <span class="token package">Magento Framework Component ComponentRegistrar</span> <span class="token punctuation">:</span> <span class="token punctuation">:</span> <span class="token constant">MODULE</span> <span class="token punctuation">,</span> <span class="token single-quoted-string string">'Magento_Ex_Helloworld'</span> <span class="token punctuation">,</span> <span class="token constant">__DIR__</span> <span class="token punctuation">)</span> <span class="token punctuation">;</span> </span> |
4. Open your terminal and go to root Magento 2. Then run the following command
1 2 | php bin/magento setup:upgrade |
If you want to make sure the module is installed, you can go to Admin → Stores → Configuration → Advanced → Advanced and check if the module is in the list or you can open the /etc/config.php application and checks if an array exists for the keyword ‘Magento_Ex_Hellowworld’, and has the value set to 1.
Create a controller
1. First we need to define the route. To do this, create a route.xml file in the app / code / Magento_Ex / Helloworld / etc / frontend directory with the following code:
1 2 3 4 5 6 7 8 9 10 | <span class="token php language-php"><span class="token delimiter important"><?</span> xml version <span class="token operator">=</span> <span class="token double-quoted-string string">"1.0"</span> <span class="token delimiter important">?></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> config</span> <span class="token attr-name"><span class="token namespace">xmlns:</span> xsi</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> http://www.w3.org/2001/XMLSchema-instance <span class="token punctuation">"</span></span> <span class="token attr-name"><span class="token namespace">xsi:</span> noNamespaceSchemaLocation</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> urn:magento:framework:App/etc/routes.xsd <span class="token punctuation">"</span></span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> router</span> <span class="token attr-name">id</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> standard <span class="token punctuation">"</span></span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> route</span> <span class="token attr-name">id</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> helloworld <span class="token punctuation">"</span></span> <span class="token attr-name">frontName</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> helloworld <span class="token punctuation">"</span></span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> module</span> <span class="token attr-name">name</span> <span class="token attr-value"><span class="token punctuation">=</span> <span class="token punctuation">"</span> Magento_Ex_Helloworld <span class="token punctuation">"</span></span> <span class="token punctuation">/></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"></</span> route</span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"></</span> router</span> <span class="token punctuation">></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"></</span> config</span> <span class="token punctuation">></span></span> |
Here, we define a route and our route assigns an id of "helloworld"
.
The frontName
attribute will be the first part of our URL.
In Magento 2, URLs are built this way:
<frontName>/<controler_folder_name>/<control_group_name>
So in our example, the final URL would look like this:
hellowworld/index index
2. Now we create the index.php controller file in the app / code / Magento_Ex / Helloworld / Controller / Index directory with the following code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | <span class="token php language-php"><span class="token delimiter important"><?php</span> <span class="token keyword">namespace</span> <span class="token package">Magento_Ex Helloworld Controller Index</span> <span class="token punctuation">;</span> <span class="token keyword">use</span> <span class="token package">Magento Framework App Action Context</span> <span class="token punctuation">;</span> <span class="token keyword">class</span> <span class="token class-name">Index</span> <span class="token keyword">extends</span> <span class="token class-name"> Magento Framework App Action Action</span> <span class="token punctuation">{</span> <span class="token keyword">protected</span> <span class="token variable">$_resultPageFactory</span> <span class="token punctuation">;</span> <span class="token keyword">public</span> <span class="token keyword">function</span> <span class="token function">__construct</span> <span class="token punctuation">(</span> Context <span class="token variable">$context</span> <span class="token punctuation">,</span> <span class="token package">Magento Framework View Result PageFactory</span> <span class="token variable">$resultPageFactory</span> <span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token variable">$this</span> <span class="token operator">-</span> <span class="token operator">></span> <span class="token property">_resultPageFactory</span> <span class="token operator">=</span> <span class="token variable">$resultPageFactory</span> <span class="token punctuation">;</span> <span class="token keyword">parent</span> <span class="token punctuation">:</span> <span class="token punctuation">:</span> <span class="token function">__construct</span> <span class="token punctuation">(</span> <span class="token variable">$context</span> <span class="token punctuation">)</span> <span class="token punctuation">;</span> <span class="token punctuation">}</span> <span class="token keyword">public</span> <span class="token keyword">function</span> <span class="token function">execute</span> <span class="token punctuation">(</span> <span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token variable">$resultPage</span> <span class="token operator">=</span> <span class="token variable">$this</span> <span class="token operator">-</span> <span class="token operator">></span> <span class="token property">_resultPageFactory</span> <span class="token operator">-</span> <span class="token operator">></span> <span class="token function">create</span> <span class="token punctuation">(</span> <span class="token punctuation">)</span> <span class="token punctuation">;</span> <span class="token keyword">return</span> <span class="token variable">$resultPage</span> <span class="token punctuation">;</span> <span class="token punctuation">}</span> <span class="token punctuation">}</span> </span> |
In Magento 1, each controller can have many actions, but not in Magento 2. In Magento 2, every action has its own class that implements the execute()
.
Create a block
We will create a simple block class with the getHelloWorldTxt()
method that returns the string “Hello world”.
1. Create a Helloworld.php file in app / code / Magento_Ex / Helloworld / Block folder with the following code:
1 2 3 4 5 6 7 8 9 10 11 | <span class="token php language-php"><span class="token delimiter important"><?php</span> <span class="token keyword">namespace</span> <span class="token package">Magento_Ex Helloworld Block</span> <span class="token punctuation">;</span> <span class="token keyword">class</span> <span class="token class-name">Helloworld</span> <span class="token keyword">extends</span> <span class="token class-name"> Magento Framework View Element Template</span> <span class="token punctuation">{</span> <span class="token keyword">public</span> <span class="token keyword">function</span> <span class="token function">getHelloWorldTxt</span> <span class="token punctuation">(</span> <span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token keyword">return</span> <span class="token single-quoted-string string">'Hello world!'</span> <span class="token punctuation">;</span> <span class="token punctuation">}</span> <span class="token punctuation">}</span> </span> |
Create layout and template files
In Magento 2, layout
and template
files are placed in the view
directory within your module. In the view
directory, we can have three subdirectories: adminhtml
, base
and frontend
.
The adminhtml
directory is used for admin, the frontend
directory is used for frontend and the base directory is used for both, admin and frontend.
1. First, we will create a file helloworld_index_index.xml
in app / code / Magento_Ex / Helloworld / view / frontend / layout with the following code:
1 2 3 4 5 6 7 8 | <span class="token operator"><</span> page xmlns <span class="token punctuation">:</span> xsi <span class="token operator">=</span> <span class="token double-quoted-string string">"http://www.w3.org/2001/XMLSchema-instance"</span> xsi <span class="token punctuation">:</span> noNamespaceSchemaLocation <span class="token operator">=</span> <span class="token double-quoted-string string">"../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd"</span> layout <span class="token operator">=</span> <span class="token double-quoted-string string">"1column"</span> <span class="token operator">></span> <span class="token operator"><</span> body <span class="token operator">></span> <span class="token operator"><</span> referenceContainer name <span class="token operator">=</span> <span class="token double-quoted-string string">"content"</span> <span class="token operator">></span> <span class="token operator"><</span> block <span class="token keyword">class</span> <span class="token operator">=</span> <span class="token double-quoted-string string">"Magento_ExHelloworldBlockHelloworld"</span> name <span class="token operator">=</span> <span class="token double-quoted-string string">"helloworld"</span> template <span class="token operator">=</span> <span class="token double-quoted-string string">"helloworld.phtml"</span> <span class="token operator">/</span> <span class="token operator">></span> <span class="token operator"><</span> <span class="token operator">/</span> referenceContainer <span class="token operator">></span> <span class="token operator"><</span> <span class="token operator">/</span> body <span class="token operator">></span> <span class="token operator"><</span> <span class="token operator">/</span> page <span class="token operator">></span> |
Each page has a layout layout and for our controller action, the layout handling is helloworld_index_index.xml. You can create a layout configuration file for all layout handling.
In our layout file, we added a block to the content container and set our block’s template helloworld.phtml, which this template will create in the next step.
2. Create a helloworld.phtml file in app / code / Magento_Ex / Helloworld / view / frontend / templates with the following code:
1 2 | <span class="token tag"><span class="token tag"><span class="token punctuation"><</span> h1</span> <span class="token punctuation">></span></span> <span class="token php language-php"><span class="token delimiter important"><?php</span> <span class="token keyword">echo</span> <span class="token variable">$this</span> <span class="token operator">-</span> <span class="token operator">></span> <span class="token function">getHelloWorldTxt</span> <span class="token punctuation">(</span> <span class="token punctuation">)</span> <span class="token punctuation">;</span> <span class="token delimiter important">?></span></span> <span class="token tag"><span class="token tag"><span class="token punctuation"></</span> h1</span> <span class="token punctuation">></span></span> |
The $ this variable is pointing to our block class and is calling the getHelloWorldTxt () method, which returns a string “Hello world!”. Open the URL / helloworld / index / index in your browser and you will see a string “Helloworld!” appears on the screen.
Hopefully this article will help you understand more about the basic operations in Magento 2. Thank you for watching.