Handling HTTP requests

Every application request in Magento is handled by front controller. (There is posibility to define multiple front controllers - for example admin panel uses dedicated front controller, but in common usecases this is not necessery) It will parse request URI and decide how it will be processed.

To simplify we can assume that every request URI has the same strucutre:

/route/controller/action

Based on those three variables front controller locates corresponding action class that wil handle that request.

Defining route

Routes definitions can be places in file 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="hello" frontName="hello">
            <module name="MMAcademy_Hello" />
        </route>
    </router>
</config>

In rotuer node we see reference to standard front controller. In node route we can see attribute frontName - value of this attribute will be matched against route variable in request URI. Within route node we can define multiple module nodes and their prority. For every module standard router will attempt to initialize class \{ModuleVendor}\{ModuleName}\Controller\{{ContollerVariable}\{ActionVariable}Action. Based on our module example for URI /hello/index/index front controller will attempt to load folowing action class: \MMAcademy\Hello\Controller\Index\IndexAction.

But not all URI in Magento are build from three words.

We can see standard controller routes that have less than three variables in URI. Every omitted variable defaults to value index. So action corresponding with URI /hello is identical with /hello/index/index. And on the same basis stores home page is special case of route /index/index/index.

But there can also be more three secrions in URI and it will still be valid standard controller route. Additional parameters can be added to URI as pair of key/value. This is practically identical to standard GET params but allow more readability. Common example is path to specified product page: /catalog/product/view/id/3231.

But we have seen that product URL can be "nice" Search Engine Optimized values. URL rewrite mechanisms allow to define pairs of "nice" URLs and internal URIs. Apart from standard controller or adminhtml controller there is rewrite controller. Every request attempts to mach with every controller defined in system in order they are defined. When request is processed by rewrite controller and it matches one of defined URL pair request is internally modified to point to corresponding internal address.

Finaly Hello world!

Now we know that we need to create class \MMAcademy\Hello\Controller\Index\IndexAction in order for StandardRouter to find it and execute.

Front action class must implement Magento\Framework\App\ActionInterface listed below, but usually we are extending from \Magento\Framework\App\Action\Action that implements few shortcuts and under-the-hood functionalities.

<?php
namespace Magento\Framework\App;

interface ActionInterface
{
    /**
     * Dispatch request
     *
     * @return \Magento\Framework\Controller\ResultInterface|ResponseInterface
     * @throws \Magento\Framework\Exception\NotFoundException
     */
    public function execute();
}

Here is simplest Action class implementation

<?php

namespace MMAcademy\Hello\Controller\Index;

use Magento\Framework\App\ResponseInterface;

class Index extends \Magento\Framework\App\Action\Action
{
    public function execute()
    {
        echo 'Hello world';
    }
}

But this is not a fulfilling result. Why? Beacuse it is not properly Object Oriented solution - we are using procedure in controller that echo's string instead of returning a result object that contains our response. However because we did use \Magento\Framework\App\Action\Action proper implementation is just few strokes away. We can use _resultFactory property to create new \Magento\Framework\Controller\Result\Raw object. That object will allow us to return just a plain text as a response to our HTTP query.

Be sure to take a longer look at \Magento\Framework\Controller\ResultFactory and other types of results we can create.

<?php

namespace MMAcademy\Hello\Controller\Index;

use Magento\Framework\App\ResponseInterface;

class Index extends \Magento\Framework\App\Action\Action
{

    /**
     * Dispatch request
     *
     * @return \Magento\Framework\Controller\ResultInterface|ResponseInterface
     * @throws \Magento\Framework\Exception\NotFoundException
     */
    public function execute()
    {
        /** @var \Magento\Framework\Controller\Result\Raw $result */
        $result = $this->resultFactory->create(\Magento\Framework\Controller\ResultFactory::TYPE_RAW);
        $result->setContents('Hello World!!!');
        return $result;
    }
}

Next Steps

results matching ""

    No results matching ""