Skip to content
intermediate Phase 14 · Application Structure

Complete Request Lifecycle

Complete request lifecycle from HTTP request to response. Bootstrap → Area Code → Router → Controller → Action → Response

1h
0 problems
Topic Progress 0%

Request Lifecycle Overview

Complete Lifecycle

1. HTTP Request arrives
   ↓
2. pub/index.php (entry point)
   ↓
3. Bootstrap (autoload, ObjectManager, area code)
   ↓
4. Application::run()
   ↓
5. FrontController receives request
   ↓
6. Router matches URL to route
   ↓
7. Router generates action class name
   ↓
8. Action controller instantiated (via ObjectManager)
   ↓
9. Action::execute() runs
   ↓
10. Action returns Result (forward, redirect, or body)
   ↓
11. Response sent to browser

Detailed Steps

// Step 1-3: Bootstrap (we covered this)
$bootstrap = Bootstrap::create(BP, []);

// Step 4: Application runs
$bootstrap->run(new Http($objectManager));

// Step 5: FrontController receives request
// Magento\Framework\App\FrontController::dispatch()
$frontController = $objectManager->get(FrontController::class);
$response = $frontController->dispatch($request);

// Step 6: Router matches URL
// /catalog/product/view/id/1 →
// Module: Magento_Catalog
// Controller: Product
// Action: View

// Step 7: Router generates class name
// Magento\Catalog\Controller\Product\View

// Step 8-9: Controller instantiated and executed
$controller = $objectManager->create($controllerClass);
$result = $controller->execute();

// Step 10-11: Response returned
$response->sendResponse();

The entire lifecycle takes ~100-500ms depending on caching and complexity.

Routing in Detail

How Routing Works

1. Route Registration

<!-- app/code/Magento/Catalog/etc/frontend/routes.xml -->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
    <router id="standard">
        <module name="Magento_Catalog"/>
    </router>
</config>

2. URL to Route Matching

URL: /catalog/product/view/id/1

Breakdown:
  /catalog → FrontName (from route)
  /product → Controller name
  /view    → Action name
  /id/1    → Parameters

Route matching:
  'catalog' matches Magento_Catalog route
  → Controller: Product
  → Action: View
  → Full class: Magento\Catalog\Controller\Product\View

3. Router Chain

Magento has multiple routers in priority order:

Router Priority Purpose
Standard 1 Module routes
Cms 2 CMS pages
UrlRewrite 3 SEO URL rewrites
Default 99 Default route (404)
// Router chain in action:
1. StandardRouter: Try module routes
2. CmsRouter: Try CMS page match
3. UrlRewriteRouter: Try database rewrites
4. DefaultRouter: 404 if nothing matched

4. URL Rewrite System

// Database-driven URL rewrites
// catalog_product_view/id/1 → product-test.html

// URL rewrite table:
// request_path: product-test.html
// target_path: catalog/product/view/id/1
// redirect_type: 301 or 302

// When request comes in for product-test.html:
// UrlRewriteRouter rewrites to catalog/product/view/id/1
// StandardRouter then handles the rewritten URL

Route Configuration

// Routes are defined in routes.xml
// Each module can register one or more frontnames

<!-- admin routes -->
<router id="admin">
    <route id="admin" frontName="admin">
        <module name="Magento_Backend"/>
    </route>
</router>

<!-- The frontName 'admin' maps to:
     /admin/* URLs
     → Magento_Backend controllers -->

Controller Actions

Action Controller Structure

namespace Magento\Catalog\Controller\Product;

use Magento\Framework\App\Action\Action;
use Magento\Framework\App\Action\Context;

class View extends Action
{
    public function __construct(
        Context $context,
        private \Magento\Catalog\Helper\Output $outputHelper,
        private \Magento\Framework\Registry $registry
    ) {
        parent::__construct($context);
    }

    public function execute()
    {
        // 1. Get product ID from request
        $productId = (int) $this->getRequest()->getParam('id');

        // 2. Load product
        $product = $this->productRepository->getById($productId);

        if (!$product) {
            // 3a. Product not found → 404
            $this->messageManager->addErrorMessage(__('Product not found'));
            return $this->resultRedirectFactory->create()->setPath('/');
        }

        // 4. Check cache
        $cacheKey = 'product_view_' . $productId;
        if ($cached = $this->cache->load($cacheKey)) {
            return $this->resultFactory->create(
                ResultFactory::TYPE_PAGE
            )->setBody($cached);
        }

        // 5. Prepare page
        $page = $this->resultFactory->create(ResultFactory::TYPE_PAGE);
        $page->getLayout()->initMessages();

        // 6. Add blocks to layout
        $page->getLayout()->getBlock('product.info')
            ->setProduct($product);

        return $page;
    }
}

Result Types

// 1. Page result (renders layout)
return $this->resultFactory->create(ResultFactory::TYPE_PAGE);

// 2. Forward (internal redirect, same request)
return $this->resultForwardFactory->create()
    ->forward('view', ['id' => $productId]);

// 3. Redirect (external redirect, new request)
return $this->resultRedirectFactory->create()
    ->setPath('catalog/product/view', ['id' => $productId]);

// 4. JSON result (for AJAX/API)
return $this->resultFactory->create(ResultFactory::TYPE_JSON)
    ->setData(['success' => true, 'message' => 'Saved']);

// 5. Raw result (direct output)
return $this->resultFactory->create(ResultFactory::TYPE_RAW)
    ->setContents('Hello World');

Request Lifecycle Diagram

HTTP Request
  ↓
pub/index.php
  ↓
Bootstrap → ObjectManager → Area Code
  ↓
Application::run()
  ↓
FrontController::dispatch()
  ↓
Router::match()
  → StandardRouter (module routes)
  → CmsRouter (CMS pages)
  → UrlRewriteRouter (URL rewrites)
  ↓
Controller class name resolved
  ↓
ObjectManager::create(Controller\Class)
  ↓
Controller::execute()
  ↓
Result object returned
  ↓
Response sent
  ↓
HTTP Response to browser

Quiz

1. What is the first step after bootstrap in the request lifecycle?

Question 1 options

2. A URL like /catalog/product/view/id/1 maps to which class?

Question 2 options

3. Which router checks for URL rewrites in the database?

Question 3 options

Flashcards

Question

What is the request lifecycle order?

Answer

Request → Bootstrap → FrontController → Router → Controller → Action → Result → Response

Question

What does the Router do?

Answer

Matches URL to module, controller, and action class

Question

What are the result types?

Answer

Page, Forward, Redirect, JSON, Raw

Question

What is URL rewriting?

Answer

Database-driven mapping of friendly URLs to actual controller routes

Revision Notes

Key Takeaways

  • 1. Request lifecycle: Bootstrap → FrontController → Router → Controller → Action → Response
  • 2. Router matches URL: /catalog/product/view → Magento\Catalog\Controller\Product\View
  • 3. Multiple routers: Standard (modules), CMS, UrlRewrite, Default (404)
  • 4. Controller actions return result types: Page, Forward, Redirect, JSON, Raw
  • 5. URL rewrites map SEO-friendly URLs to actual routes via database

Interview Tips

  • Trace a complete request lifecycle step by step
  • Explain the router chain and priority order
  • Give examples of different result types and when to use each

Cheat Sheet

Lifecycle:
  1. HTTP Request
  2. pub/index.php → Bootstrap
  3. FrontController::dispatch()
  4. Router::match() → Controller class
  5. Controller::execute() → Result
  6. Response sent

Router Chain:
  Standard → Cms → UrlRewrite → Default (404)

URL: /catalog/product/view/id/1
  frontName: catalog (Magento_Catalog)
  controller: Product
  action: View
  class: Magento\Catalog\Controller\Product\View

Result Types:
  TYPE_PAGE    → renders layout
  TYPE_FORWARD → internal redirect
  TYPE_REDIRECT → external redirect
  TYPE_JSON    → JSON response
  TYPE_RAW     → direct output