Inicio > Cursos > PHP > Patrón MVC desde Cero
PHPPHP Enterprise y LaravelLección 14 de 15

Patrón MVC desde Cero

MVC (Model-View-Controller) separa tu aplicación en tres capas: el Modelo maneja los datos y la lógica de negocio, la Vista genera el HTML que ve el usuario, y el Controlador recibe las peticiones HTTP, coordina el Modelo y elige qué Vista mostrar. Esta separación permite que un diseñador trabaje en las vistas sin tocar la lógica, y un backend developer cambie la base de datos sin afectar la interfaz.

Construir un mini-framework MVC te enseña cómo funcionan Laravel, Symfony y CodeIgniter por dentro: un Router que mapea URLs a controladores, un Controller que procesa la petición y prepara datos, un Model que consulta la base de datos, y una View que renderiza el HTML con esos datos. Una vez entiendes este flujo, aprender cualquier framework PHP es cuestión de aprender su API, no sus conceptos.

<?php
// --- Router.php --- Mapea URLs a controladores
class Router {
    private array $rutas = [];

    public function get(string $path, array $handler): void {
        $this->rutas["GET"][$path] = $handler;
    }

    public function post(string $path, array $handler): void {
        $this->rutas["POST"][$path] = $handler;
    }

    public function resolver(): void {
        $method = $_SERVER["REQUEST_METHOD"];
        $path = parse_url($_SERVER["REQUEST_URI"], PHP_URL_PATH);
        $handler = $this->rutas[$method][$path] ?? null;
        if (!$handler) { http_response_code(404); echo "404"; return; }
        [$clase, $metodo] = $handler;
        (new $clase)->$metodo();
    }
}

// --- Model.php --- Acceso a datos
class TareaModel {
    private PDO $db;
    public function __construct() {
        $this->db = new PDO("sqlite:app.db");
    }
    public function todas(): array {
        return $this->db->query("SELECT * FROM tareas")->fetchAll(PDO::FETCH_ASSOC);
    }
    public function crear(string $titulo): void {
        $this->db->prepare("INSERT INTO tareas (titulo) VALUES (?)")
                 ->execute([$titulo]);
    }
}

// --- Controller.php --- Lógica de peticiones
class TareaController {
    public function index(): void {
        $model = new TareaModel();
        $tareas = $model->todas();
        include "views/tareas/index.php"; // Vista con $tareas
    }
    public function crear(): void {
        $titulo = htmlspecialchars($_POST["titulo"] ?? "");
        if ($titulo) (new TareaModel())->crear($titulo);
        header("Location: /tareas");
    }
}

// --- index.php --- Punto de entrada
$router = new Router();
$router->get("/tareas", [TareaController::class, "index"]);
$router->post("/tareas", [TareaController::class, "crear"]);
$router->resolver();

// --- views/tareas/index.php --- Vista HTML
// <h1>Tareas (<?= count($tareas) ?>)</h1>
// <?php foreach ($tareas as $t): ?>
//   <p><?= htmlspecialchars($t["titulo"]) ?></p>
// <?php endforeach; ?>
Consejo🔄 Flujo MVC: Request → Router → Controller → Model (datos) → View (HTML) → Response. Cada capa solo habla con la adyacente.
← Proyecto: API REST con PHPLaravel: Framework PHP Moderno →

Practica esta lección

Resuelve los ejercicios del curso de PHP en la app, gratis y con corrección automática.

Empezar a practicar