Sistema de módulos en CodeIgniter 4

Veamos cómo montar un sistema de módulos/plugins en una aplicación desarrollada con el FrameWork CodeIgniter 4.

Objetivo

Váis a desarrollar una aplicación con el FrameWork PHP CodeIgniter, y necesitáis ir ampliando vuestra aplicación con módulos. Por un lado, tener el core, y por otro, ir creando módulos para ir añadiéndolos sin tocar el core.

Vamos a ver cómo crear un sistema de módulos para ir ampliando tu aplicación en CodeIgniter 4.

Código

0. CodeIgniter

Si estáis leyendo este artículo, es que domináis CodeIgniter, o almenos lo conocéis. Pues bien, sabréis que el arbol del FrameWork es:

/App/
.../Config/
.../Controllers/
.../Models/
.../Views/
...etc
/public/
/system/
/writable/

1. Creamos carpeta Modulos

Pues nosotros, para nuestro sistema de módulos, vamos a crear dentro de App, la carpeta Modulos.

/App/
.../Config/
.../Controllers/
.../Models/
.../Modulos/
.../Views/
...etc
/public/
/system/
/writable/

2. Registramos la carpeta

Una vez creada la carpeta donde iremos almacenando nuestros módulos, vamos a registrar las carpetas para que todo funcione.

Deberemos modificar el fichero Autoload.php de la carpeta /App/Config.

Buscáis la asignación de la variable $psr4, y le añadís la linea donde almacenáis vuesto módulo.

// Fichero /App/Config/Autoload.php
public $psr4 = [
  APP_NAMESPACE => APPPATH, // For custom app namespace
  'Config'      => APPPATH . 'Config',
  'Modulos\Blog' => APPPATH. 'Modulos/Blog'
];

3. Modificamos Routes

Vamos complicando la cosa. Ahora toca modificar el fichero /App/Config/Routes.php

Al final del fichero, añadimos el siguiente código. Fijaos que lo que hace es leer todos los Routes de cada uno de los módulos que instalemos… Así, cada módulo, en su carpeta, tendrá su Routes.php particular.

// Fichro /App/Config/Routes.php

...
$modules_path = ROOTPATH . 'app/Modules/';
$modules = scandir($modules_path);

foreach ($modules as $module) {
	if ($module === '.' || $module === '..') {
		continue;
	}

	if (is_dir($modules_path) . '/' . $module) {
		$routes_path = $modules_path . $module . '/Config/Routes.php';
		if (file_exists($routes_path)) {
			require $routes_path;
		} else {
			continue;
		}
	}
}

Más adelante, lo veŕeis más claro cuando veáis la estructura de nuestros módulos.

4. Estructura Módulo

Veamos cómo estructuraremos cada uno de nuestros módulos creados.

/* Config */
/App/Modules/Blog/Config/Routes.php
/* Controllers */
/App/Modules/Blog/Controllers/BlogController.php
/* Models */
/App/Modules/Blog/Models/BlogModel.php
/* Views */
/App/Modules/Blog/Views/blogView.php

En definitiva, es crear la carpeta con nuestro Módulo, en el ejemplo Blog, y dentro las carpetas Config, Controllers, Models y Views.

5. Los ficheros necesarios para el módulo

Y ya está? No. Ahora viene lo complicado, los namespace. Os pongo un ejemplo muy sencillo de cada uno de los ficheros que os he comentado para que lo tengáis claro:

/App/Modules/Blog/Config/Routes.php

<?php
$routes->group("/{locale}/blog", ["namespace" => "\App\Modules\Blog\Controllers"], function ($routes) {
	$routes->get("/", "blogController::index");
	$routes->get("otro-metodo", "blogController::otroMetodo");
});
?>

/App/Modules/Blog/Controllers/blogController.php

<?php
namespace App\Modules\Blog\Controllers;

use App\Controllers\BaseController;
use App\Modules\Blog\Models\BlogModel;

class BlogController extends BaseController
{
  public function index()
  {
      $myblogModel = new BlogModel();

      $data["text"] = "Funciona";
      return view("\App\Modules\Blog\Views\blogView", $data);
  }
}

/App/Modules/Blog/Models/blogModel.php

<?php
namespace App\Modules\Blog\Models;

use CodeIgniter\Model;

class BlogModel extends Model
{
    public function __construct()
    {
        parent::__construct();
    }

    public function getEntrada($idioma, $id)
    {
        return "";
    }

/App/Modules/Blog/Views/blogView.php

<?php
echo "<p>Funciona: ". $text ."</p>";
?>

Lógicamente, es un simple ejemplo con todas las partes que puedes necesitar: config, controllers, models y views, pero que, el ejemplo en si, solo escribe un texto por pantalla.

Lo más importante de estos, es que os quedéis con la estructura del módulo, y sobretodo, en los namespace. Si no los declaráis correctamente, no os funcionará.

De esta manera sólo tenemos que ir creando nuestros módulos e irlos añadiendo a la carpeta /App/Modules

Espero que os sea de utilidad.

Más información