Parametrizando nuestro sistema con symfony 1/2

Mucho se habla hoy en día de que un sistema parametrizado es mucho mejor que los famosos “códigos en duro” que los programadores solemos escribir dentro del fuente de los programas. Es muy normal ver gente que usa combos de selección múltiple que en realidad van cargados dentro del mismo HTML de la página. El problema ocurre realmente cuando hacemos esto con varias páginas y luego resulta muy engorroso el mantenimiento del sitio ya que hay que buscar todos los lugares en donde lo hicimos a la hora de agregar, quitar o modificar alguna de las opciones de nuestro combo.

Mucha gente acostumbra crear tablas paramétricas para por ejemplo “estados”, “paises”, “tipos”, etc. Considero, y es una opinión muy personal, que cuando estas tablas son creadas habría que analizar 2 puntos a fin de determinar si las mismas podrían ir dentro de la estructura que voy a proponer con este artículo.

  1. Cantidad de registros: Si la cantidad de registros es relativamente fija y no crecen tan variablemente como son las tablas transaccionales.
  2. Cantidad de columnas: Si éstas tablas tienen exactamente 2 columnas como generalmente serían id y nombre.

Cabe mencionar que creando tablas como las descriptas arriba vemos un crecimiento muy grande en el número de tablas de la base de datos y por supuesto un Diagrama Entidad Relación (DER – ER) muy complejo para graficar ya que la mayoría de las tablas suelen ser de este tipo.

Tomando en cuenta esto, propongo que trabajemos con una tabla a la cual denominaremos “parametro” y con la ayuda de Symfony y los artículos de la serie Personalizando el objeto sfUser de Symfony veremos como centralizar los datos paramétricos dentro de un solo lugar y los almacenaremos dentro de la sesión del usuario activo del sistema.

Tabla: parametro

Parametro:
  columns:
    dominio:                {type: string(50), notnull: true}
    abreviatura:            {type: string(10), notnull: true}
    descripcion:            {type: string(100), notnull: true}
    orden:                  {type: integer}
  indexes:
    parametro_unique:
      fields:               [dominio, abreviatura]
      type:                 unique
CREATE TABLE parametro (
    id BIGINT AUTO_INCREMENT,
    dominio VARCHAR(50) NOT NULL,
    abreviatura VARCHAR(10) NOT NULL,
    descripcion VARCHAR(100) NOT NULL,
    orden BIGINT,
    UNIQUE INDEX parametro_unique_idx (dominio, abreviatura),
    PRIMARY KEY(id)
);

Esta tabla tiene las siguientes columnas:

  • id: Primary Key de la tabla, autonumérica. Solo a fin de mantener la finalidad de la PK
  • dominio: Agrupador de registros
  • abreviatura: Código que será almacenado dentro de las tablas transacionales
  • descripcion: Texto que representa a cada dominio-abreviatura
  • orden: Un campo numérico para poder ordenar los parámetros

Pasemos a unos ejemplos menos abstractos.

Si queremos por ejemplo agregar países, escribiremos PAIS en el dominio de los registros, como abreviatura pondremos los códigos ISO de los países y en la descripción el nombre del país. El campo orden lo utilizaremos si queremos ordenar los países de alguna forma que no sea por orden alfabético.

Como otro ejemplo, supongamos que tenemos artículos del blog y que éstos deben tener un estado de acuerdo a la actividad que se esté realizando. Podríamos tener los estado “Borrador”, “En verificación”, “Publicado”, “Borrado”. Entonces simplemente tendríamos en el dominio ESTADO_ARTICULO, inventaríamos una abreviatura para cada uno que será el dato grabado en la tabla de artículos y la descripción de cada estado en el campo descripcion. Finalmente para poder mostrar los estados del artículo al momento de cargarlo podemos usar un combo y para que aparezcan ordenados por orden secuencial de acuerdo a lo presentado arriba utilizaremos el campo orden para poner 1 al Borrador y 4 al Borrado.

Veamos un ejemplo de como podrían quedar los datos.

Datos de la tabla parametro

Con esta estructura, cualquier parámetro del sistema puede estar en esta tabla, siempre y cuando cumpla con las condiciones que mencionamos al principio del artículo. Ahora nos queda nada más que ver como recuperaríamos estos datos, para lo cual se me ocurren dos escenarios:

El primero sería en el caso de que necesitemos elegir de una lista (combo box) uno específico, como por ejemplo al modificar un artículo y podamos cambiarle el estado. Para esto simplemente haríamos un select a la base de datos como el siguiente:

SELECT abreviatura, descripcion
FROM parametro
WHERE dominio = 'ESTADO_ARTICULO'
ORDER BY orden

Con este resultado simplemente crearíamos un combo como el siguiente, donde utilizaríamos la abreviatura como value y la descripcion como valor a mostrar

<select name="estado">
<option value="B">Borrador</option>
<option value="EV">En verificación</option>
<option value="PUB">Publicado</option>
<option value="X">Borrado</option>
</select>

El segundo escenario sería cuando queremos mostrar los datos de un registro específico. Una vez hecho el select para obtener el registro ya tendríamos la abreviatura ya que ésta se almacena en la tabla del artículo y obtendríamos la descripción con el siguiente select

SELECT descripcion
FROM parametro
WHERE dominio = 'ESTADO_ARTICULO'
  AND abreviatura ='X'

Es más, en el caso de que quisiéramos obtener una lista de artículos ya con sus descripciones propias podríamos simplemente hacer un JOIN

SELECT a.id, a.nombre, p.descripcion as estado
FROM articulo a
JOIN parametro p ON a.estado = p.abreviatura
  AND p.dominio = 'ESTADO_ARTICULO'
ORDER BY a.nombre

Dada la cantidad de parámetros que una aplicación puede llegar a tener me encontré con el problema de que se disparaban muchos selects a la base de datos para mostrar los parámetros y es aquí donde se puede implementar una manera de tenerlos siempre disponibles en la sesión del usuario cargados dentro de un array a fin de evitar enviar muchas peticiones a la base de datos.

Esto lo dejaremos para la segunda parte del artículo que prometo escribirlo pronto.

Espero sus comentarios al respecto.

Puedes ver el siguiente artículo sobre esta serie aquí.

Un comentario en “Parametrizando nuestro sistema con symfony 1/2”

  1. es muy bueno, acabo de hacer una cosa parecida justamente esta semana, sin haber visto el articulo, es parecido en la essencia, en mi caso el tema va de variables, osea las famosas variables de que se pueden escribir en yml y leerlas, modificarlas, lo que pasa que las del yml las dejo como por defecto, y en las base de datos para que el usuario las modifique, y claro como digiste esto consume mucho por las petisiones a bdd, y sigo para ahorrar en peticiones, genere un sistema que genera las variables en session apartir de la bdd o yml, sino existe en bdd, bajo seudonimo de misession_xxxx y valor.
    y va muy bien, ahora toca refactorizar hehehe.
    resumen hay veces que mas personas hacemos las mismas cosas en diferentes lugares, estaria bueno crear un sistema de las cosas que uno va hacer y mirar si alguien mas lo hara en ese tiempo asi crear un groupo de 2 o mas. y crear algo mucho mejor que uno crearia. un gran saludo.

Comenta este artículo