Tutorial Hacer Componentes Joomla

Descargar como docx, pdf o txt
Descargar como docx, pdf o txt
Está en la página 1de 21

Tutorial: Como crear componentes en Joomla – Patrón MVC

Patrón MVC
Concepto de Front-End y Back-End
Primer componente MVC simple con Joomla!
Segundo componente, Back-End y acceso a datos.
Crear el xml del componente de joomla y generar instalable.
Hacer Módulos para Joomla!
Hacer Plugins para Joomla!

El patrón de diseño MVC.

La nueva versión 1.5 de joomla! Incluye novedades en la elaboración de componentes, entre ellas la posibilidad de
incorporar un patrón de diseño MVC , que a la larga facilitará el mantenimiento de nuestro componente, y lo hará más
fácil de extender al mismo tiempo que resultará más fácil de leer por otras personas.
El patrón de diseño MVC se lleva utilizando mucho tiempo en el ámbito del desarrollo web en marcos de trabajo como
Jakarta struts de apache (java), Java Server Faces de Sun (java), Symphony (php), etc…
Lo primero que hay que tener claro es el funcionamiento del modelo MVC.
MVC son las siglas de Model View Controller, es decir, modelo vista controlador.
Una aplicación web basada en este patrón separa su código en tres partes diferenciadas:
El controlador: el controlador es el punto de entrada de la aplicación, se mantiene a la escucha de todas las peticiones,
ejecuta la lógica de la aplicación, y muestra la vista apropiada para cada caso.
El modelo : el modelo contiene todo el código relacionado con el acceso a datos. Es importante que sea un código lo más
genérico posible y se pueda reutilizar en otras situaciones y proyectos. Nunca incluiremos lógica en el modelo, solamente
consultas a la base de datos y validaciones de entrada de datos.
La vista : la vista contiene el código que representará lo que nosotros veremos por pantalla, en este caso se trata de
código html.
El objetivo de usar este patrón de diseño, es separar lo mas posible el código de nuestra aplicación, para que quede mas
ordenado.

Implementación del MVC de Joomla! 1.5

En el artículo anterior hablé sobre el patrón MVC . MVC es un patrón genérico, después cada marco de trabajo tiene una
forma de implementar este patrón.
El marco de trabajo de Joomla! proporciona una implementación sin archivos de configuración, al contrario de lo que
hacen otros marcos de trabajo como Struts o JSF. Esto puede ser una ventaja o una desventaja según como se mire.
Joomla no proporciona este archivo de configuración, sin embargo tiene otra forma de mapear las acciones del
controlador. Joomla le da vital importancia al nombre que le tienes que dar a cada fichero del componente, es
importantísimo que nombres bien el controlador, las vistas y los modelos de tu componente, de lo contrario Joomla no
sabrá encontrarlos .
De esto hablaremos más adelante.

Introducción al concepto de front-end y back-end


Nuestro componente tendrá dos partes diferenciadas: el front-end y el back-end.
Front-end: el front-end es la parte del componente que es visible para el usuario de nuestro sitio web. Se visualiza donde
hayamos incluido la etiqueta <jdoc:include type=”component” /> en el template. Su código fuente se encuentra en el
directorio components dentro del directorio principal de Joomla!.
Back-end : es la parte del componente que se mostrará cuando entremos al sitio como administradores. El componente
se mostrará donde lo hayamos especificado en el template del back-end. El template para la parte de back-end y la parte
de front-end es difrerente. Su codigo fuente se encuentra en el directorio components dentro del directorio administrator
dentro del directorio principal de Joomla!.
En el transcurso del desarrollo de nuestro componente podemos afrontar la parte de back-end y la de front-end
como dos desarrollos distintos.
En la parte de back-end realizaremos labores de mantenimiento y configuración para la aplicación. Después, en la
parte de front-end obtendremos los parámetros que previamente hemos configurado en la parte de back-end.
Por ejemplo, podemos crear un componente para gestionar recursos. En la parte de back-end del componente
podríamos crear un formulario para subir el recurso al servidor, y ponerle un nombre , una categoría, etc… y en la parte

1
de front-end simplemente generar una consulta a la base de datos y mostrar los recursos subidos al servidor. De esta
manera solo los usuarios con privilegios de administrador podrían subir recursos al servidor.
En los anteriores posts he hablado sobre el patrón MVC y sobre el concepto de front-end y back-end en Joomla!. Una
vez entendido se puede empezar a programar un componente MVC en condiciones.

Iniciación: Construir un componente simple en Joomla! 1.5 Usando el patrón MVC.

Siguiendo el patrón MVC, vamos a crear un componente simple para joomla 1.5 al que llamaremosprueba. El objetivo de
esta primera toma de contacto es entender la metodología de trabajo para crear el componente de joomla! 1.5.
Lo primero que haremos será ir a la carpeta principal de Joomla en nuestro servidor web. Dentro de esa carpeta localizar
el directorio components  .
Observa que dentro del directorio existen otros directorios que empiezan por com_xxxx . Esta es la primera norma que
pone Joomla!: los componentes se deben de ubicar en un directorio cuyo nombre empieze por com_ seguido del nombre
del componente, por ejemplo para el componente prueba seriacom_prueba (este aspecto es similar a la parte de
módulos que hemos visto anteriormente)
Por lo tanto creamos un directorio dentro del directorio components  y lo llamamos com_prueba.Cuando llamemos a
nuestro componente, lo primero que hace Joomla es buscar el archivo php que hay dentro con el mismo nombre que el
componente y ejecutarlo. Este es el punto de entrada del componente. Creamos el fichero  prueba.php  dentro del
directorio y de momento lo dejamos en blanco.Por ahora solo estamos creando la estructura del componente. Lo
siguiente es crear el archivocontroller.php, y de momento también lo dejaremos en blanco. Ahora necesitamos crear los
directorios en los que ubicaremos nuestro Modelo y nuestra Vista.
Crea un directorio con nombre models y otro con nombre views.
Dentro del directorio views, hay que crear un directorio por cada vista y el directorio tiene que tener el nombre de la vista;
crea el directorio prueba dentro del directorio views.
Dentro del directorio views/prueba crea el directorio tmpl  , aquí es donde se guardarán los layouts de la vista. El layout
es el fichero final que se mostrará por el navegador, más adelante explicaré esto.
Crea el fichero views/prueba/view.html.php  , este fichero también es necesario. Ahora crea el ficheroprueba.php dentro
de models.
Ya tienes la estructura básica del componente, aunque aún no hemos introducido código.

2
Como podrás imaginar el modelo del componente irá dentro de la carpeta models  , las vistas se ubicaran dentro del
directorio views, y el controlador en el archivo controller.php .
Joomla! 1.5 sabe qué componente tiene que cargar porque busca en la query string de la petición el parámetro “option”,
del cual obtiene el nombre del componente a cargar. Es decir, nosotros para llamar a nuestro componente prueba,
introduciremos en joomla la URL acabada con index.php?option=com_prueba.  Esto muestra la pagina principal de
nuestro componente, que por defecto carga la vista con el mismo nombre del componente, es decir, la vista con nombre
“prueba”.
Cuando se carga el componente, se ejecuta el punto de entrada a este, prueba.php, y en el punto de entrada será donde
nosotros crearemos una instancia de nuestro componente.
Introduce el siguiente código en el punto de entrada de tu componente:

defined( '_JEXEC' ) or die( 'Restricted access' );


require_once( JPATH_COMPONENT.DS.'controller.php' );
 
if($controller = JRequest::getWord('controller')) {
$path = JPATH_COMPONENT.DS.'controllers'.DS.$controller.'.php';
if (file_exists($path)) {
require_once $path;
} else {
$controller = '';
}
}
 
$classname = 'pruebaController'.$controller;
$controller = new $classname( );
 
$controller->execute( JRequest::getVar( 'task' ) );
 
$controller->redirect();

Vamos a comentar el siguiente codigo paso a paso:


La primera línea comprueba si esta definida la variable “_JEXEC”, y si no esta definida se muestra un mensaje de
error por pantalla mediante la función “die”. Esto es una medida de seguridad que incluye el marco de trabajo Joomla! y
que es recomendable usar en todos nuestros archivos .php que tengamos en el sitio, y que evitara que la gente acceda a
las paginas directamente sin hacer antes las comprobaciones de seguridad que lleva incluida Joomla!
Seguidamente se importa el fichero controller.php donde crearemos nuestra clase que contendrá el controlador.
JPATH_COMPONENT y DS son constantes que define el marco de trabajo de Joomla! y que contienen el path al
componente en el sistema y el separador de directorios adecuado para el sistema que se este utilizando, “\” para
Windows y “/” para sistemas Unix. Utilizar estas constantes nos facilitara el trabajo más adelante y hará nuestras
aplicaciones portables e independientes de la plataforma donde se estén utilizando.
Después de importar el controlador, se comprueba si existe el parámetro “controller” en la query string, y si existe
establece la variable path a JPATH_COMPONENT/controllers/$controller.php, para luego hacer un require_once de
path, e importar el controlador que se especifica en la petición y que se sitúa en la carpeta controllers .
Nosotros no hemos creado la carpeta controllers, por que de momento solo crearemos un controlador, pero también se
pueden crear varios controladores y se instanciará uno u otro según el parámetrocontroller  que se establezca en la query
string.
Después de importar el fichero correspondiente a nuestro controlador, lo instanciamos y ejecutamos el
método execute del controlador, y le pasamos como parámetro un string que contiene el valor del parámetro task que
hayamos establecido en la query string.
Después de esto se ejecuta el metodo redirect() del controlador, que redigirá el flujo del programa a la vista adecuada.
Parece complicado, pero no lo es tanto simplemente recuerda:
 Se comprueba si viene un parámetro en la query string que establezca un controlador, y si viene se importa el
fichero con el controlador.
 Se instancia el controlador.
 Se ejecuta el método execute del controlador.
 Se ejecuta el método redirect del controlador.
Después de esto, lógicamente, tendremos que incluir el código del controlador que acabamos de instanciar.
Vamos al fichero controller.php y copiamos el siguiente codigo:

defined( '_JEXEC' ) or die( 'Restricted access' );


3
jimport('joomla.application.component.controller');
 
class pruebaController extends JController
{
function display()
{
parent::display();
}
}

Esta vez lo único que hemos hecho es crear la clase que hará la función de controlador, y es  obligatorio que herede
de JController.Hemos sobrescrito el metodo display, pero lo único que hacemos es ejecutar el metodo display de la
clase padre, es decir, que básicamente no hacemos nada.
En un componente más complejo, antes de ejecutar parent::display(); incluiríamos lógica de negocio en la aplicación, con
acceso a datos , etc..
El controlador da paso a la vista correspondiente, que en este caso es la que se llame prueba.
Se le puede especificar la vista que se quiere ver pasándole a la petición un parámetro en la  query string , es decir, si en
vez de ver la vista por defecto quieres que el controlador redirija a una vista con nombre “noticias”, haremos una petición
como la siguiente : index.php?option=com_prueba&view=noticias.
Lo mismo se puede hacer con el parámetro controller,  pero en ese caso lo que haría sería instanciar el controlador con el
nombre especificado en lugar de el controlador por defecto que se instancia.
Después de crear nuestro controlador, vamos a crear nuestra vista.
Vamos al fichero view.html.php en el directorio views/prueba  y copiamos el siguiente código:

defined( '_JEXEC') or die( 'Restricted access');


jimport( 'joomla.application.component.view');
 
class pruebaViewprueba extends JView
{
function display($tpl = null)
{
$model =& $this->getModel();
$mensaje = $model->getMensaje();
$this->assignRef('mensaje',$mensaje);
 
parent::display($tpl);
}
 
}

Observa la definición de la clase. Como puedes observar tiene un nombre un poco peculiar, este nombre no se lo he
puesto así por que he querido, sino que he seguido una norma que establece el marco de trabajo Joomla!, y que consiste
en poner primero el nombre del componente que lo llama, seguido de view y seguido del nombre de la vista:
NombreComponenteViewNombreVista
Esta norma es la que se sigue también para el modelo.
Lo que vamos a hacer en este caso es sobrescribir el método display y utilizar assignRef para crear referencias que
utilizará el “layout”.
La primera línea del método display obtiene el modelo, Joomla busca un modelo con nombrePruebaModelPrueba debido
a que no se le pasa ningún parámetro a la función getModel() y lo instancia. Si le hubiéramos pasado el nombre de algún
modelo como parámetro, nos hubiera devuelto el modelo especificado.
Una vez tenemos el modelo ejecutamos el método getMensaje de este, que devuelve un string. El string se le pasa al
layout por referencia mediante assignRef.
Finalmente se ejecuta el método display de la clase padre, al cual se le puede pasar como parámetro el nombre del
layout que se quiere visualizar, en nuestro caso no le pasaremos ninguno y visualizará el layout con nombre default.php .
Crea el fichero views/prueba/tmpl/default.php . Este será el layout que se visualizara por defecto en nuestra vista. Añade
el siguiente código:
<h1> <?php echo $this->mensaje ?> </h1>
Observa que recogemos lareferencia que hemos asignado antes mediante asignRef() simplemente como si fuera una
variable local del script php. Yo he puesto este código muy simple, pero tu puedes poner todo el código html que se te
ocurra.
4
Solo nos queda preparar el modelo e implementar el método getMensaje() que hemos usado antes en la vista,
Ves a la carpeta modelsy en el fichero prueba.php escribe el siguiente codigo :
 
defined('_JEXEC') or die("Invalid access");
jimport('joomla.application.component.model');
 
class pruebaModelprueba extends JModel
{
 
function getMensaje(){
return "Hola, soy un valor devuelto por el modelo";
}
}
El código habla por si solo, ten en cuenta que yo he devuelto una cadena de texto por simplicidad, pero en una aplicación
más compleja nos se devolvería una cadena obtenida de una base de datos o unresultSet, p.e.
Ya está finalizada la creación del componente. Para llamarlo tendremos que pasarle en la url como argumento el nombre
del componente, y Joomla lo mostrará por pantalla. Como es lógico, Joomla sólo podrá mostrar un componente
simultáneamente por pantalla.
Así quedaría la estructura de directorios para la parte de front-end de los componentes de Joomla!:

En el caso del componente que acabo de diseñar, después de introducir en el navegador la dirección http://localhost/ sit
ioJoomla/index.php?option=com_prueba ,  debería mostrar, si todo ha ido bien : “Hola soy un valor que ha devuelto el
modelo”.

5
He explicado cómo hacer la parte de front-end de un componente de Joomla! La parte de back-end se desarrolla de una
forma similar, pero bajo la carpeta administrator/components del sistema de directorios de Joomla!, más adelante lo
explicaré, así como los metodos mas importantes de acceso a datos que trae el API de Joomla!, que nos ahorrarán
mucho tiempo y nos permitrán crear componentes mas seguros.

Segundo componente, Back-End y acceso a datos.

El tutorial anterior fue una introducción a la creación de componentes en Joomla 1.5, pero aun faltan muchas cosas.

Faltan cosas como el acceso a datos mediante el framework de Joomla, los tasks y más cosas que se me escapan he iré
completando más adelante.

Para la parte de back-end, el sistema es el mismo, lo único que deberemos de ubicar el componente en la carpeta
administrator/components . El acceso al componente es por la URL …tuSitio/administrator/index.php?
option=com_prueba .

El api de Joomla! nos provee de unos objetos específicos para operar con bases de datos.Siempre que se pueda es
recomendable usar estos objetos, en lugar de conectar directamente con las funciones de mysql que tiene php, ya que el
API de Joomla! hace mucho trabajo por debajo, como protección contra inyección Sql, optimización, etc… En ocasiones ,
necesitaremos un acceso a datos mas profundo, y no nos podremos conformar con lo que nos ofrece el api de Joomla!,
en estos casos no queda mas remedio que utilizar el acceso a datos de toda la vida. En este tutorial el componente se va
llamar prueba. Por lo tanto accederemos a el mediante la URL …/administrator/index?option=com_prueba. Nuestro
componente es muy simple: muestra una lista con los mensajes existentes y un formulario de introducción de datos en el
que se presenta un campo de texto y un botón para enviar el formulario. Al enviarse el formulario se introduce en una
tabla de la base de datos que hemos creado previamente el mensaje y nos lleva a la misma pagina que muestra todos
los mensajes insertados y te da la opción de seguir insertando mensajes.

Vamos a crear la base de datos, esta es la sentencia SQL que yo he usado:

CREATE TABLE 'jos_prueba' (


`id` INT NOT NULL AUTO_INCREMENT PRIMARY KEY ,
`mensaje` VARCHAR( 30 ) NOT NULL DEFAULT 'mensaje'
) ENGINE = innodb;
Como puedes observar son dos campos; una tabla muy simple. Vamos a crear la estructura principal de nuestro
componente como en el tutorial anterior, si tienes dudas, pégale un vistazo . La estructura principal del componente es
esta:

6
A continuación puedes observar el diagrama del componente que vamos a crear:

La vista Prueba Admin es la que se muestra por defecto en nuestro componente, en ella se hará un listado de todos los
mensajes creados en la base de datos, y al fina pondré un enlace que redirija a la vista IntroduceNuevo.

En la vista IntroduceNuevo, se presenta un formulario con una caja de texto y un botón de submit. Este boton de submit
redirige al task IntroduceMensaje, donde introduciremos el mensaje en la base de datos y redirigiremos a la vista
PruebaAdmin de nuevo para que se muestren todos los mensajes insertados y te da la opción de seguir insertando.

Lo primero que necesitamos es un modelo para nuestra vista PruebaAdmin, creamos la carpeta models, y dentro un
archivo con nombre pruebaAdmin.php , dentro de este archivo crearemos la clase que contiene el modelo.

El modelo tiene que recuperar todos los datos de la base de datos y devolverlos para que la vista pueda mostrarlos.

Dentro de la carpeta models crea el fichero pruebaAdmin.php . De momento vamos a agregar el código necesario para
recuperar los datos de la tabla. Este es el código que he usado:

defined('_JEXEC') or die();
jimport( 'joomla.application.component.model' );
class PruebaAdminModelPruebaAdmin extends JModel
{
var $datos;
function getData()
{
if (empty( $this->datos ))
{
$query = ' SELECT * '
. ' FROM #__prueba ';

$this->datos = $this->_getList( $query );


}

return $this->datos;
}
7
}

Como siempre la primera línea hace una comprobación para ver si se esta accediendo desde Joomla! o se esta haciendo
un acceso directo, esta medida de seguridad debe de estar siempre presente.

La segunda línea se utiliza la función jimport del api de Joomla!, esta función importa la clase abstracta para el modelo.

Observa que la nomenclatura sigue la norma descrita:

Nombre de la Vista– Model – Nombre del modelo

Al tener este nombre , el controaldor PruebaAdminController podra acceder directamente a los métodos de este modelo.

La función getData() comprueba si la variable $datos esta vacia, y si lo esta, entonces almacena en ella los datos de la
tabla jos_prueba en la variable.Para ello utiliza el metodo getList()

. Este método es heredado por la clase padre y lo que hace es devolver una lista de objetos con los resultados de la
consulta. Cada objeto de

la lista tendrá tantas propiedades como campos tenga la tabla consultada.Por lo tanto en la variable $datos se almacena

una lista de objetos con los resultados de la consulta.

Lo siguiente es mostrar estos datos en la vista PruebaAdmin.

Introduce el siguiente código en el fichero views/pruebaAdmin/view.html.php :

defined( '_JEXEC' ) or die( 'Restricted access' );


jimport( 'joomla.application.component.view');
class PruebaAdminViewPruebaadmin extends JView
{
function display($tpl = null)
{
$model =& $this->getModel();
$datos = $model->getData();
$this->assignRef( 'mensajes', $datos );
parent::display($tpl);
}
}
Las dos primeras líneas ya no necesitan explicación.

La nomenclatura de la Vista sigue el patrón descrito.

Se sobrescribe el método display() , lo primero es obtener el modelo, al seguir las nombras de nombrado no hace falta
especificar el nombre del modelo en el método getModel().

Almacenamos en la variable $datos la lista de objetos que devuelve el método que hemos creado anteriormente en el
modelo, y se la pasamos al layout mediante el método assignRef.

Código para el layout default.php de la vista :

<table class="adminlist">
<thead>
<tr>
<th width="5">ID </th>
<th>Mensaje </th>
</tr>
</thead>
<tbody>
8
<?php
$n =count( $this->mensajes );
for ($i=0; $i < $n; $i++)
{
$row =& $this->mensajes[$i];
?>

<tr>
<td> <?php echo $row->id; ?> </td>
<td><?php echo $row->mensaje; ?> </td>
</tr>

<?php

}
?>
<tr>
<td>&#160;</td>
<td><a href="<?php echo JURI::base();?> index.php?option=com_prueba&view=introduceNuevo">Nuevo Mensaje
</a></td>
</tr>
</tbody>
</table>
Recorremos la lista de objetos "mensajes" y creamos un elemento "tr" por cada mensaje, observa que estamos
accediendo a la propiedad id y mensaje de cada objeto de la lista, esto es por que como he explicado antes se crea
tantas propiedades como campos tenga el resultado de la consulta.

Al final de la tabla, he agregado un enlace que redirige a la vista que crearemos luego y que permitirá introducir un nuevo
mensaje. El método estático JURI::base() devuelve la url base del sitio, para realizar la petición correctamente.

Introduce algunos datos en tu tabla y comprueba que todo funciona correctamente.

Vamos a crear la vista introduceNuevo.

Crea el directorio introduceNuevo dentro de la carpeta views , crea el directorio tmpl y los archivos view.html.php y
tmpl/default.php correspondientes .

Introduce el siguiente código en view.html.php:

defined( '_JEXEC' ) or die( 'Restricted access' );


jimport( 'joomla.application.component.view');
class PruebaAdminViewIntroduceNuevo extends JView
{
function display($tpl = null)
{
parent::display($tpl);
}
}
No se realiza ningún acceso a datos , simplemente se ejecuta el método display() y se visualiza el layout por defecto
(“tmpl/default.php”) .La nomenclatura de la vista ha de seguir el patrón que ya se ha explicado anteriormente :

Nombre componente – View – Nombre de la vista .

Ahora vamos a ver el código del layout :

<form action="index.php" method="post">

<table border="0">
<tbody>

9
<tr>
<td>ID</td>
<td>Mensaje</td>
</tr>
<tr>
<td><input disabled size="3" name="id" /></td>
<td><input maxlength="30" size="30" name="mensaje" /></td>
</tr>
<tr>
<td>&#160;</td>
<td><input type="submit" value="Enviar" /></td>
</tr>
</tbody>
</table>
<input type="hidden" value="com_prueba" name="option" />
<input type="hidden" value="introduceMensaje" name="task" />

</form>
Como puedes observar, he creado un formulario que envía la información a index.php ,

y le he puesto una caja de texto para introducir el mensaje y otra para el id, la del id permanece bloqueada ya que se
trata de un campo autoincremental y se ira incrementando automáticamente en la base de datos.

Esta información la tiene que procesar el task introduceMensaje . La forma de indicar que la información ha de ser
procesada por este task es poniendo un input de tipo hidden con atributo name igual a task y un valor igual al nombre del
task que deseamos que procese el formulario. En el otro input de tipo hidden se se indica el option para indicar a Joomla!
que el task se encuentra dentro del componente com_prueba.

Los nombre de los campos input deben de coincidir con los nombres de los campos de la tabla en la que introduciremos
los datos.

Vamos a crear el task introduceMensaje :

En la clase controlador PruebaAdminController que debes haber creado anteriormente introduce el siguiente método:

function introduceMensaje(){

$option = JRequest::getCmd('option');
$modelo = $this->getModel('pruebaAdmin');
$res = $modelo->introduce(JRequest::get('post'));
if($res == 1){
$this->setMessage('Mensage introducido!');
$this->setRedirect('index.php?option=' . $option. '&view=pruebaAdmin');
}else{
$this->setMessage('Error al introducir!');
$this->setRedirect('index.php?option=' . $option. '&view=Error');
}
}
Al pulsar submit en el formulario anterior , los datos son enviados a index.php, el marco de trabajo Joomla! lee los
parámetros de entrada y detecta que hay un parámetro que indica el componente de destino , el componente
com_prueba recibe la petición y el controlador detecta que existe un parámetro task, este parámetro es un parámetro
especial que se usa en Joomla! para procesar acciones de formularios, Joomla! buscara en la clase controlador un
metodo que tenga el mismo nombre que el valor del parámetro task y le concedera el control. Es por eso que el nombre
del método ha de coincidir con el nombre del task que pusimos en el formulario. Se pueden mapear task’s a métodos
diferentes, pero esto queda pendiente para otro articulo.

En este task volvemos a utilizar el API de Joomla! para acceder a datos, pero en este caso vamos a usar el objeto
JTable, para introducir datos.

10
Podríamos utilizar funciones como mysql_query() para realizar consultas de tipo insert y update, sin embargo estas
funciones son mas difíciles de generar, requieren de conocimientos de lenguaje SQL y probablemente nos dejemos
huecos de seguridad que dan lugar a inyecciones SQL y otros fallos.

El API de Joomla! proporciona el objeto JTable para crear, leer , actualizar y borrar registros de una tabla.

Crea la carpeta tables, y dentro de esta carpeta crea el archivo Mensajes.php , El nombre del archivo a de ser igual que
el nombre de la clase JTable,

es decir si el archivo se llama Mensajes.php, la clase se llamara

TableMensajes. Si no se hace así, Joomla! tendra problemas para

encontrar el objeto JTable.

Introduce el siguiente código en el archivo:

defined( '_JEXEC' ) or die( 'Restricted access' );


class TableMensajes extends JTable
{
var $id = null;
var $mensaje = null;
function __construct(&$db)
{
parent::__construct( '#__prueba', 'id', $db );
}
}
Se declaran tantas propiedades como campos tenga la tabla sobre la que se quiere trabajar, el nombre de las
propiedades debe ser igual que el nombre de los campos.

En el constructor se le pasa como primer parámetro el nombre de la tabla, como segundo parámetro la clave primaria y
en el tercer parámetro la referencia al objeto base de datos del marco de trabajo Joomla!, el nombre de este tercer
parámetro es siempre igual.

Ya tenemos el objeto JTable necesario para utilizar desde el modelo pruebaAdmin, por lo tanto cuando ejecutemos el
task introduceMensaje, se instanciara el modelo pruebaAdmin y se ejecutara el método introduce de este. Es en el
método introduce del modelo pruebaAdmin donde se usa el objeto JTable que acabamos de crear.

Vamos a implementar el método introduce del modelo pruebaAdmin , introduce el siguiente método en el modelo:

function introduce($post){

$row =& JTable::getInstance('Mensajes', 'Table');


if (!$row->bind($post)) {
return JError::raiseWarning(500, $row->getError());
}
if (!$row->store()) {
return JError::raiseWarning(500, $row->getError());
}
return 1;
}
Observa que acepta como parámetro una variable a la que llama $post.

En esta variable almacenaremos la petición entera que previamente hemos obtenido en el controlador mediante la
instrucción : JRequest::get(’post’)

Esta instrucción recoge los parámetros de entrada de la petición, es como acceder al array $_POST de php, pero
mediante el API de Joomla!, lo que nos provee de protección contra inyección de código, etc…

11
Es importante saber que si se intenta pasar el valor de los parámetros post mediante el objeto JRequest desde otro sitio
que no sea el controlador, por ejemplo desde una vista, el objeto JTable no recibirá los parámetros correctamente y
generará un error al intentar obtener los valores de la petición.

En la primera línea del método se obtiene una instancia del objeto TableMensajes que hemos creado antes , si no pones
los nombre correctamente no se instanciará el objeto.

Después se ejecuta el método bin() del objeto TableMensajes que lo que hace es buscar en los parámetros post de
entrada parámetros con el mismo nombre que los campos de la tabla y enlazarlos, por eso es importante que en el
formulario hayamos escrito correctamente los nombres de los inputs.

Acto seguido se ejecuta el método store() , que almacena en la base de datos los datos provenientes del formulario.
Busca la clave primaria, y si ya existe un un registro con la misma clave primaria ejecuta una consulta update, si aun no
esta creada la clave primaria, ejecuta una consulta insert.

Si alguno de estos dos métodos no se ejecuta correctamente se lanza un error el método mediante el código : return
JError::raiseWarning(500, $row->getError()) .

De vuelta al task introduce mensaje, obtenemos la devolución del metodo introduce y la procesamos con este código :

if($res == 1){
$this->setMessage('Mensage introducido!');
$this->setRedirect('index.php?option=' . $option. '&view=pruebaAdmin');
}else{
$this->setMessage('Error al introducir!');
$this->setRedirect('index.php?option=' . $option. '&view=Error');
}
Este código ya lo hemos introducido antes en el task introduceMensaje.

Si todo ha funcionado correctamente , se redirección a la vista pruebaAdmin mediante el método de controlador


setRedirect(),en la cual se volverán a mostrar todos los mensajes insertados y un enlace para insertar mas mensajes. Si
no, se redirecciona a una vista con nombre error en la cual crearemos un mensaje de error a gusto de cada cual.

El método del controlador setMessage() establece el mensaje que aparecerá en la parte superior izquierda de la pantalla
por defecto, o donde este definido en el template de back-end, y hace que se muestre como en la foto :

12
Si has leido todo, enhorabuena.

Proximamente hablaré sobre como usar el editor wysiwyg de Joomla, sobre como usar AJAX en nuestros componentes y
también Google Maps.

También escribiré algo de módulos.

Crear el xml del componente de joomla y generar instalable.

Hasta ahora habíamos visto como hacer los componentes, tanto la parte de backend, como la de frontend, pero no
habíamos visto como crear un paquete instalable para poder compartirlo con todo el mundo que se pueda instalar desde
el instalador de extensiones de Joomla!.

Para ello simplemente hay que generar un fichero XML con nombre igual al del componente, en este caso prueba.xml y
con un formato específico y comprimirlo todo en un zip. Este zip será el instalable.

Vamos a ver un posible fichero XML para un componente de prueba.

<?xml version=”1.0″ encoding=”utf-8″?>


<!DOCTYPE install SYSTEM “http://dev.joomla.org/xml/1.5/component-install.dtd”>
<install type=”component” version=”1.5.0“>
<name>COM_PRUEBA</name>
<!– Los siguientes elementos son opcionales –>
<creationDate>2007 01 17</creationDate>
<author>David</author>
<authorEmail>[email protected]</authorEmail>
<authorUrl>http://www.nosolocodigo.com</authorUrl>
<copyright>Copyright Info</copyright>
<license>License Info</license>
<!– Esta cadena es almacenada en la base de datos –>
<version>Component Version String</version>
13
<!– La descripción es opcional, y por defecto es el nombre del componente –>
<description>Descripción del componente …</description>
<!– Script php personalizado que se ejecutará en la instalación –>
<installfile>install.php</installfile>
<!– Script php personalizado que se ejecutará en la desinstalación –>
<uninstallfile>uninstall.php</uninstallfile>
<!– Scripts SQL que se ejecutaran en la instalación –>
<install>
<sql>
<file driver=”mysql” charset=”utf8“>install.mysql.utf8.sql</file>
<file driver=”mysql“>install.mysql.nonutf8.sql</file>
</sql>
</install>
<!–Scripts SQL que se ejecutarán en la desinstalación–>
<uninstall>
<sql>
<file driver=”mysql” charset=”utf8“>uninstall.mysql.utf8.sql</file>
<file driver=”mysql“>uninstall.mysql.nonutf8.sql</file>
</sql>
</uninstall>

<!– Ficheros de la parte de front-end del componente, incluye aquí todos los ficheros del componente, incluidas las
vistas, controladores, etc… –>

<files>
<filename>index.html</filename>
<!—El punto de entrada al componente ha de tener el atributo component–>
<filename component=”prueba.php”>prueba.php</filename>
</files>

<!– Ficheros de leguanjes para el sitio –>

<languages>
<language tag=”en-GB“>en-GB.com_prueba.ini</language>
<language tag=”de-DE“>de-DE.com_prueba.ini</language>
<language tag=”nl-NL“>nl-NL.com_prueba.ini</language>
</languages>

<!– Ficheros multimedia para el sitio –>


<media destination=”com_test“>
<filename>image.png</filename>
<filename>flash.swf</filename>
</media>

<administration>
<!– Sección para el menu del Back-End –>
<menu img=”components/com_test/assets/test-16.png“>EventList
</menu>
<submenu>

<!– Date cuenta que todos los & estan escapados a &amp; para que el fichero XML valide correctamente y
pueda ser parseado por el instalador –>
<menu link=”option=com_helloworld&amp;task=hello&amp;who=world” >

Hello World! </menu>

<!– Puedes especificar el link como arriba o los atribitos de la URL individualmente como abajo –>
<menu img=”icon” task=”hello” controller=”z” view=”a” layout=”b” sub=”c“>Hello Again!</menu>
<menu view=”prueba” layout=”foo“>Testing Foo Layout</menu>
</submenu>
14
<!– Ficheros de la parte de Administración–>
<!–El atributo folder especifica la carpeta desde donde serán copiados los ficheros, por lo tanto index.html estará
ubicado dentro del componente en admin/index.html –>

<files folder=”admin“>
<filename>index.html</filename>
<!—El punto de entrada al componente ha de tener el atributo component–>
<filename component=”admin.prueba.php”> admin.prueba.php</filename>
</files>

<!– Ficheros de lenguaje de la parte de Administración –>


<languages folder=”admin“>
<language tag=”en-GB“>en-GB.com_prueba.ini</language>
<language tag=”de-DE“>de-DE.com_prueba.ini</language>
<language tag=”nl-NL“>nl-NL.com_prueba.ini</language>
</languages>

<!–Ficheros multimedia de la parte de Administración–>


<media folder=”admin” destination=”com_prueba“>
<filename>admin-image.png</filename>
<filename>admin-flash.swf</filename>
</media>

</administration>

</install>

Este fichero será leído por el instalador de Joomla! y de aquí sacara la información para proceder a instalar el
componente. Si el fichero no valida correctamente, no podrá ser parseado y fallará la instalación, así que estate al tanto
de que valide ya que XML es muy estricto y puede fallar por cualquier tontería, como dejarse espacios en blanco al inicio.
Con los comentarios incluidos dentro del fichero creo que se entiende todo, este fichero de ejemplo ha sido sacado de la
documentación oficial de Joomla y traducido al castellano para su mejor comprensión.

Hacer Módulos para Joomla!

Aunque con las extensiones existentes de Joomla tendremos suficiente en la mayoría de los casos, hay ocasiones en
que necesitamos algo concreto, como por ejemplo un módulo que muestre los usuarios registrados que cumplan años
hoy o uno que muestre los artículos publicados hace un año.

Y eso es precisamente lo que voy a hacer.

En el siguiente tutorial vamos a crear un modulo que consulte a la base de datos y muestre el titulo de los artículos con
un enlace al articulo completo.

Hacer un módulo es mucho más sencillo que un componente.

De hecho los módulos están pensados para mostrar datos concretos, como usuarios conectados, datos de contacto,
menús etc… que en muchos casos son una simple consulta a la base de datos.

Los módulos se encuentran situados en el directorio modules dentro del directorio de instalación de Joomla y por cada
módulo hay una carpeta con nombre mod_nombredelModulo .

Nuestro módulo se va a llamar anyo, por lo tanto la carpeta del módulo se llamará mod_anyo.

La estructura de un módulo es muy simple, tiene un fichero php con el mismo nombre que el módulo, el cual es el punto
de entrada, que tomará en control del módulo cuando este sea llamado.

15
Para separar la lógica de la presentación se ha creado la clase helper, en la cual escribiremos nuestras funciones y de
esta forma nuestro código quedará más ordenador y legible. La clase helper se encuentra en el fichero de nombre
helper.php en la raíz del directorio del módulo.

Desde mod_anyo.php ejecutaremos las funciones de la clase helper simplemente llamándolos como métodos estáticos ,
puedes encontrar una definición de la clase en el sitio oficial de Joomla

Por ultimo, tenemos el layout, o template, que se encuentra dentro de la carpeta tmpl de nuestro módulo , el cual puede
tener cualquier nombre que se te ocurra, pero le asignaremos default.php, que es el nombre por defecto que buscara
Joomla si no le indicamos lo contrario.

Para la parte de Back-End disponemos del fichero mod_anyo.xml , donde definiremos los parámetros del módulo y
mediante el cual podremos parametrizar el modulo para hacerlo mas configurable y reutilizable.

Vamos a ver el código de nuestro punto de entrada:

<?php

// no acceso directo
defined( '_JEXEC' ) or die( 'Restricted access' );

// incluir al helper que devolverá los datos, solo una vez


require_once( dirname(__FILE__).DS.'helper.php' );

$articulos = modAnyoHelper::getArticulos( $params );


require( JModuleHelper::getLayoutPath( 'mod_Anyo','default') );
?>
La primera línea, como siempre que hacemos una extensión para Joomla, es una línea de comprobación, que asegura
que no se este accediendo al modulo estar usando Joomla.

La segunda línea importa el fichero de la clase helper, donde almacenamos nuestras funciones.

En la tercera línea, ejecutamos la función getArticulos() de nuestro helper que devuelve una lista de objetos con los
resultados de la consulta SQL.

16
Por último, hacemos un require del layout, que en nuestro se llama default y lo hacemos usando el método
getLayoutPath de la clase JModuleHelper, que devuelve la ruta del layout pasándole como parámetro el nombre del
módulo y al nombre del layout.

En el helper almacenamos nuestras funciones, donde accedemos a datos para recuperar la lista de artículos que se
escribieron hoy hace un anyo. Vamos a ver el código:

<?php
class modAnyoHelper
{
function getArticulos( $params )
{
jimport('joomla.utilities.date');
$jnow = new JDate();
$now = $jnow->toMySQL();

$db = &JFactory::getDBO();
$consulta = "select title,id from #__content where datediff( #__content.created, '".$now."' ) = 365 limit
0,30";
$db->setQuery($consulta);
$categorias = $db->loadObjectList();
return $db->loadObjectList();
}
}
?>
La clase helper ha de llamarse con el nombre del modulo sin “_” seguido de helper, es decir, en nuestro caso seria
modanyoHelper.

Mediante jimport importamos el fichero necesario para instanciar una clase de tipo JDate.

Jimport admite como parámetro un string que apunte al “package” donde se encuentre la clase. Es un concepto similar al
import de java . Los paquetes se importan según la el árbol de clases que hay en la documentación oficial :

Después creamos el método getArticulos que será el que devuelva una lista de artículos que tengan un año de
antigüedad.

Utilizamos un objeto de tipo JDatabase para realizar la consulta y después simplemente obtenemos la lista de objetos
mediante el método loadObjectList .

El meollo de la cuestión esta en la consulta SQL, donde se utiliza la función datediff para consultar los artículos con una
antigüedad de 365 días

Finalmente , en el layout, sacamos por pantalla una lista HTML con enlaces a los artículos que se escribieron hace justo
365 días:

<?php
if($params->get('asignarCss')){
$css = $params->get('clase');
}

?>
<ul <?php if(isset($css )){ echo 'class="'.$css.'"';} ?> >
<?php
foreach ($articulos as $articulo) {
echo '
<li><a href="index.php?option=com_content&amp;id='.$articulo-">id.'>'. $articulo->title .'</a></li> ';
}
?>
</ul>

17
Fíjate que para acceder a los parámetros del fichero mod_anyo.xml se utiliza $params->get() .

Estos parámetros se definen previamente en el fichero xml que acompaña el modulo.

<?xml version="1.0" encoding="utf-8"?>


<install type="module" version="1.5.0">
<name>Hoy hace un año</name>
<author>David Noguera</author>
<version>1.5.0</version>
<creationDate>30.07.2006</creationDate>
<description>Modulo que carga los artículos de tal dia como hoy pero hace un año</description>
<authorEmail>[email protected]</authorEmail>
<files>
<filename module="mod_anyo">mod_anyo.php</filename>
<filename>helper.php</filename>
<filename>mod_anyo.xml</filename>
<filename>tmpl/default.php</filename>
<filename>tmpl/index.html</filename>
</files>
<params>
<param name="clase" type="text" default="mod_anyo"
label="Clase Css para el ul"
description="La clase que se aplicara al ul" />
<param name="asignarCss" type="radio" default="1"
label="Clase css" description="Determina si se debe asignar la clase css o no">
<option value="0">No</option>
<option value="1">Si</option>
</param>
</params>
</install>
Para finalizar solo queda meter todo esto en un zip y subirlo al instalador de Joomla!.

Hacer Plugins para Joomla!


Ya hemos visto como hacer componentes y como hacer módulos en Joomla! 1.5 y hemos visto que no es nada
complicado, y simplemente hay que entender la mecánica de trabajo .

Lo ultimo que nos queda son los plugins, con ellos podremos modificar el comportamiento estándar de Joomla!, pudiendo
interceptar ciertos eventos prefijados para ejecutar nuestro código antes o después del evento.

Los plugins pueden llegar a ser muy utiles y potentes.

Por ejemplo, se puede interceptar el evento de publicar un articulo y hacer que joomla imprima un mensaje personalizado
antes de cada articulo, o lo que a ti se te ocurra, simplemente tienes que tener a mano la lista de eventos (hooks)
definidos y tu imaginación para hacer con joomla! lo que quieras.

Existen varios tipos de plugins, por cada tipo de plugin existe un directorio dentro del directorio plugins, por lo tanto
tenemos el directorio plugins/content para los plugins de tipo content y así con todos los tipos.Existen varios tipos, mira
en tu carpeta plugins y comprueba los tipos.

Un plugin es un objeto que deriva de la clase JPlugin. Esta clase tiene unos métodos definidos que son ganchos
(hooks) , también se les podría llamar listeners , y que se ejecutaran cuando el evento asociado a cada clase se dispare,
por lo tanto tendremos que sobrescribir las funciones gancho que necesitemos y escribir nuestro código allí.

Por ejemplo, si sobrescribimos el método onLoginUser y escribimos una sencilla rutina que envié un email a nuestra
cuenta de correo, estaremos modificando el sistema para que cada vez que un usuario haga login, envié un email a
nuestra cuenta indicando quien se ha logueado y a que hora.

18
Esto es simplemente un ejemplo, ya que , lógicamente , seria inútil hacer una cosa así, además de llenar de correo
inservible nuestra bandeja de entrada.

Vamos a crear un plugin sencillo que se va a llamar HolaMundo y que va a imprimir por pantalla, antes de que se
visualice el contenido un mensaje, que previamente va a ser fijado en los parámetros del plugin.

Los parámetros del plugin se fijan como siempre en Joomla!, mediante el fichero xml de configuración.

Esta es la estrctura de nuestro plugin :

Primero vamos a ver el fichero xml de configuración, en el que definiremos nuestro parámetro.

<?xml version=”1.0″ encoding=”utf-8″ ?>


<install version=”1.5″ type=”plugin” group=”content”>
<name>Content – Hola Mundo</name>
<author>David Noguera</author>
<creationDate>15-02-2008</creationDate>
<authorEmail>[email protected]</authorEmail>
<authorUrl>www.nosolocodigo.com</authorUrl>
<version>1.0</version>
<description>Muestra un mensaje antes de mostrar el contenido
</description>
<files>
<filename plugin=”HolaMundo”>HolaMundo.php</filename>
<filename>HolaMundo.xml</filename>
</files>
<params>
<param name=”mensaje” type=”text” size=”50″ default=”Hola, me llamo David”
label=”Introduce el mensaje a ser mostrado aquí :” description=”Mensaje que se mostrará antes del contenido”/>
</params>
</install>

Como puedes observar, le estamos diciendo a Joomla que muestre en la seccion de parámetros del plugin , una caja de
texto de 50 de ancho, donde podremos especificar el mensaje que queremos que se muestre. Y le hemos dicho que el
fichero donde se encuentra el plugin es HolaMundo.php .

Vamos a crear nuestro plugin :

defined( '_JEXEC' ) or die( 'Acceso Restringido' );


jimport( 'joomla.plugin.plugin' );

class plgContentHolaMundo extends JPlugin {

function plgContentHolaMundo( &$subject ) {


parent::__construct( $subject );

19
}

function onBeforeDisplayContent(&$article, &$params, $limitstart=0) {

$plugin =& JPluginHelper::getPlugin('content', 'HolaMundo');


$pluginParams = new JParameter( $plugin->params );
$mensaje = "";

$mensaje = $pluginParams->get('mensaje', 'Hola Mundo');

$salidaPantalla = '
<h2>' . $mensaje . '</h2>

';

return $salidaPantalla;
}

}
?>
En Joomla 1.5 se ha introducido una nueva forma de hacer los plugins, más orientada a objetos.

Para que nuestro plgin funcione, en el fichero HolaMundo.php tendremos que crear la clase plgContentHolaMundo y
decirle que derive de JPlugin.

El nombre de la clase es muy importante, si no se pone bien no funcionará.

Después crearemos el constructor de la clase, el cual invoca el constructor de la clase padre.

El constructor ha de crearse con una función de igual nombre que la clase, ya que si lo hacemos con el método
__construct de php5 no será compatible con php4.

Esto se hace siempre igual en todos los plugins.

Después crearemos el metodo onBeforeDisplayContent , donde introduciremos el código que queremos que se ejecute
antes de mostrar el titulo.

Si te has fijado, el método admite como parámetro las variables $article, $params y $limitstart. Esta definición de
parámetros la tendremos que hacer siempre.

El contenido del articulo se almacena en $article->text, es decir, que si queremos modificar algo en el contenido del
articulo, deberemos modificar $article->text.

Vamos a ver el cuerpo de la función :

Con el metodo getPlugin de JPluginHelper, obtenemos el plugin pasandole como parámetro el tipo y el nombre, por este
orden.

Después en la variable $pluginParams almacenamos una instancia del objeto JParameter al que le tenemos que pasar
como parámetro la propiedad params del objeto plugin que previamente hemos obtenido.

Acto seguido almacenamos en la variable $mensaje el parámetro ‘mensaje’ que hemos definido en el fichero xml y que
podremos cambiar en la parte de Back-End de Joomla!.

Por último almacenamos en la variable $salidaPantalla lo que queremos que se muestre antes de mostrar el contenido , y
la devolvemos como valor de retorno.

Crea un zip con los dos ficheros, e instálalo con el instalador de extensiones de Joomla!, después ves al Plugin Manager
y actívalo, allí también podrás cambiar el mensaje que se imprime por pantalla.
20
Este es el resultado:

Puedes consultar los eventos disponibles en la documentación oficial de Joomla, que aunque sea oficial, es escasa, y
también puedes ver los eventos en los ficheros example.php que existen dentro de cada directorio de tipo de plugin, es
decir, en plugins/content , plugins/user … Este fichero te puede servir como plantilla a la hora de crear plugins.

21

También podría gustarte