POO vs POP


Programación Orientada a Objetos o Programación Orientada a Parches. 
Este es un dilema que se nos presenta a diario cuando se requiere extender la funcionalidad de una clase o modificar el diseño para agregar funcionalidad. Para muchos, el tiempo apremia y lo más evidente es resolver las cosas de una manera que, a priori, parece la más sencilla: un parche (*).
Pero cuidado, resulta muy fácil caer en una trampa que nos armamos nosotros mismos. Muchas veces, la solución más sencilla en tiempo, resulta una contra,  ya que la misma, no es escalable y el tiempo que no gastamos hoy haciendo un refactoring “complejo”, lo gastamos más adelante (multiplicado por N) debido a que esa lógica ya esta muy arraigada en la aplicación.
Un caso común, resulta del agregado de métodos o propiedades en clases a las que no les corresponde esa responsabilidad. Esto puede pasar por varios motivos:
  • Desconocimiento del framework propio: Se desconoce la existencia de otra clase que ya posee esa responsabilidad.
  • Falta de tiempo: Para no buscar en todo el framework si ya existe una clase a quién agregarle esta funcionalidad, se agrega en otra que podría soportarla.
  • Poco tiempo para refactorizar: agregarle la funcionalidad a una clase que no tengo al alcance en tiempo de ejecución, desemboca en la creación de un nuevo servicio para poder utilizarla. Pero como llevar mucho tiempo hacerlo, se descarta la idea.
  • Por simple inexperiencia de diseño: por falta de experiencia desarrollando objetos, no nos damos cuenta que lo que estamos haciendo, simplemente está “mal”. (Aquellos que venimos de programar estructurado, se nos complica un poco más pensar de manera abstracta en objetos y responsabilidades)
  • U otros casos más que ahora no se me ocurren.

Esto, multiplicado por la cantidad de personas programando en un equipo de esta misma manera, provoca que luego, introducir un simple cambio, lleve mucho más tiempo del esperado porque se rompen más funcionalidades de las que se arreglan.
Ahora, si este cambio es temporal, para salir del paso. Pues entonces debe tomarse como tal y arreglarlo (o cambiarlo) ni bien haya pasado la tormenta y evitar de esta manera que la deuda técnica crezca (que programando sólo de esta manera, podríamos empeñar hasta los anillos de la abuela).
Tengamos muy en cuenta que ésta deuda técnica va totalmente en contra nuestra, los desarrolladores, no solo de la empresa. ¿Quién prefiere romperse la cabeza durante una semana para introducir un cambio en lugar de poder hacerlo en un par de horas? Yo creo que nadie. Entonces, se debe trabajar en un diseño que permita introducir cambios fácilmente y para ahorrar, a nosotros mismos y a nuestros compañeros de equipo, el mal humor y los dolores de cabeza. Porque al fin y al cabo, el cerebro es nuestra herramienta de trabajo y de esta manera, lo maltratamos.
Se debe erradicar a los parches como una solución permanente y que sean solo eso, un parche provisorio, que va a quitarse a la brevedad.
Se debe priorizar la calidad del código por sobre la cantidad y rapidez

(*)Entiéndase en este caso por parche a aquella funcionalidad que se introduce al diseño para ahorrar tiempo.

Ejemplos:


  • Poner un IF para bifurcar la ejecución del código en lugar de crear dos objetos diferentes. 
  • Mezclar responsabilidades en una misma clase.
  • Repetir código en lugar de extraerlo de donde está y crear una nueva clase.

2 comentarios:

Carlos Ble dijo...

A veces se confunde el refactorizar un diseño con cambiar ficheros fuentes de sitio o de paquete por hacer lo que parece "mas limpio" cuando en realidad no aporta nada, es tiempo y por tanto dinero perdidos.
Hay que saber muy bien qué refactorizar y qué se va a ganar con ello.
Y siempre que haya ganancia, hacerlo.

Refactorizar para poder añadir buenos tests automaticos, es siempre una ganancia :-)

Juan Barrionuevo dijo...

Seguro Carlos.
El problema al que apunto es aquel que suma funcionalidad y complejidad al diseño.
Un ejemplo sencillo sería: "Hay que agregar una funcionalidad. Bueno, esta librería que esta aquí, si le ponemos un par de IFs dentro, sale funcionando en un periquete".
Al abusar de este tipo de casos, irremediablemente se cae en un "mal" diseño.

Para mí, se debería refactorizar esa librería para que no tenga más de una responsabilidad y permita fácilmente introducir más adelante un nuevo cambio.
E incluso, una mejor batería de tests enfocados a la nueva funcionalidad.

Publicar un comentario

Muchas gracias por leer el post y comentarlo.

 
Copyright 2009 Programación SOLIDa
BloggerTheme by BloggerThemes | Design by 9thsphere